I'm working on a simple design for a login screen that has some content to display. The design looks perfect, as per the requirements.
But the issue is that when the keyboard is popped out, every widget's internal vertical spacing shrinks, and the widgets have no spacing.
Using SingleChildScrollView as parent of Column puts other errors which are mentioned here
Here's the code!
import 'package:flutter/material.dart';
import 'package:flutter_svg/flutter_svg.dart';
import 'package:laundary_app/screens/signup_sreen.dart';
import 'package:laundary_app/utils/helpers/constants.dart';
import 'package:laundary_app/widgets/custom/custom_elevated_button.dart';
import 'package:laundary_app/widgets/custom/custom_text_field.dart';
class LoginScreen extends StatelessWidget {
static const String routeName = '/login';
const LoginScreen({Key? key}) : super(key: key);
@override
Widget build(BuildContext context) {
return Scaffold(
body: SafeArea(
child: CustomScrollView(
slivers: [
SliverFillRemaining(
hasScrollBody: false,
child: Padding(
padding: const EdgeInsets.only(
top: Constants.fullPagePadding,
left: Constants.fullPagePadding,
right: Constants.fullPagePadding,
),
child: Column(
crossAxisAlignment: CrossAxisAlignment.stretch,
children: [
SvgPicture.asset(
'assets/vectors/sign_in.svg',
height: 150,
fit: BoxFit.fitHeight,
),
const Expanded(flex: 3, child: SizedBox()),
const Text(
'Welcome back!',
textAlign: TextAlign.center,
style: TextStyle(
fontSize: 30,
fontWeight: FontWeight.bold,
fontFamily: 'Poppins',
),
),
const Expanded(
child: SizedBox(),
flex: 2,
),
CustomTextField(
hint: 'abc@xyz.com',
title: 'E-mail address',
controller: TextEditingController(),
onSubmitted: (value) {},
suffix: const Icon(Icons.alternate_email),
),
const Expanded(child: SizedBox()),
CustomTextField(
hint: 'Password',
title: 'Password',
controller: TextEditingController(),
onSubmitted: (value) {},
obscureText: true,
suffix: IconButton(
icon: const Icon(Icons.remove_red_eye_outlined),
onPressed: () {},
),
),
const Expanded(child: SizedBox()),
Align(
alignment: Alignment.centerRight,
child: TextButton(
onPressed: () {},
child: const Text('Forget Password'),
),
),
buildORDivider(),
const Expanded(child: SizedBox()),
buildSocialMediaButtons(),
const Expanded(flex: 2, child: SizedBox()),
CustomElevatedButton(
text: 'Log in',
icon: Icons.arrow_forward_sharp,
onTap: () {},
),
Row(
mainAxisAlignment: MainAxisAlignment.center,
children: [
const Text('Don\'t have an account'),
TextButton(
onPressed: () => Navigator.of(context)
.pushNamed(SignUpScreen.routeName),
child: const Text('Sign Up'),
),
],
)
],
),
),
),
],
),
),
);
}
Widget buildORDivider() {
return Row(
children: const [
Expanded(child: Divider(thickness: 1.5)),
Padding(
padding: EdgeInsets.symmetric(horizontal: 16.0),
child: Text('or'),
),
Expanded(child: Divider(thickness: 1.5)),
],
);
}
Widget buildSocialMediaButtons() {
// <a href="https://www.flaticon.com/free-icons/google" title="google icons">Google icons created by Freepik - Flaticon</a>
// <a href="https://www.flaticon.com/free-icons/facebook" title="facebook icons">Facebook icons created by Fathema Khanom - Flaticon</a>
return Row(
mainAxisAlignment: MainAxisAlignment.center,
children: [
SocialMediaLoginButtonWidget(
imagePath: 'assets/images/google.png',
onPressed: () {},
),
const SizedBox(width: 30),
SocialMediaLoginButtonWidget(
imagePath: 'assets/images/facebook.png',
onPressed: () {},
),
],
);
}
}
class SocialMediaLoginButtonWidget extends StatelessWidget {
const SocialMediaLoginButtonWidget(
{Key? key, required this.imagePath, required this.onPressed})
: super(key: key);
final String imagePath;`enter code here`
final VoidCallback onPressed;
@override
Widget build(BuildContext context) {
return Container(
height: 60,
padding: const EdgeInsets.all(12.0),
decoration: BoxDecoration(
border: Border.all(color: Colors.grey),
borderRadius: BorderRadius.circular(Constants.borderRadius),
),
child: Image.asset(
imagePath,
),
);
}
}
As a side note, here's the output of both scenarios as well.