How to set text in one line for flutter - dart

I have next flutter/dart code for make in one line 4 text field:
Container(
margin: EdgeInsets.all(8.0),
child: Row(
mainAxisAlignment: MainAxisAlignment.start,
children: <Widget>[
Container(
width: 100.0,
child: TextField(
maxLength: 2,
onChanged: (value) {
card.expMonth = int.parse(value);
},
keyboardType: TextInputType.number,
textAlign: TextAlign.center,
decoration: InputDecoration(
border: InputBorder.none, hintText: 'month'),
)),
Text("/",
style: TextStyle(fontSize: 36),
textAlign: TextAlign.center),
Container(
width: 100.0,
child: TextField(
maxLength: 2,
onChanged: (value) {
card.expYear = int.parse(value);
},
keyboardType: TextInputType.number,
textAlign: TextAlign.center,
decoration: InputDecoration(
border: InputBorder.none, hintText: 'year'),
)),
Container(
padding: EdgeInsets.only(left: 80.0),
width: 180.0,
child: TextField(
maxLength: 3,
onChanged: (value) {
card.cvc = int.parse(value);
},
keyboardType: TextInputType.number,
textAlign: TextAlign.center,
decoration: InputDecoration(
border: InputBorder.none, hintText: 'cvc'),
)),
],
),
)
and he see this:
How make all text fields in one line. In android app i simple use guideline or other simple paths. And here i smash with flutter reality where different textfields have different visibility with the same, at first glance, the parameters
UPD.: I make crutch solution:
Padding(
padding: EdgeInsets.only(bottom: 20),
child: Text("/",
style: TextStyle(fontSize: 36),
textAlign: TextAlign.center),
),
but it's stupid how i think

This is how I would do it:
Row(children: <Widget>[
Expanded(
child: TextField(
inputFormatters: [LengthLimitingTextInputFormatter(2)],
keyboardType: TextInputType.number,
textAlign: TextAlign.center,
decoration: InputDecoration(
border: InputBorder.none, hintText: 'month'),
)),
Expanded(
child: Text("/",
style: TextStyle(fontSize: 36),
textAlign: TextAlign.center)),
Expanded(
child: TextField(
inputFormatters: [LengthLimitingTextInputFormatter(2)],
keyboardType: TextInputType.number,
textAlign: TextAlign.center,
decoration: InputDecoration(
border: InputBorder.none, hintText: 'year'),
)),
Expanded(
child: TextField(
inputFormatters: [LengthLimitingTextInputFormatter(3)],
keyboardType: TextInputType.number,
textAlign: TextAlign.center,
decoration: InputDecoration(
border: InputBorder.none, hintText: 'cvc'),
)),
])
Which produces this:
I used inputFormatters: [LengthLimitingTextInputFormatter(2)] instead of maxLength so that the user is still only able to enter in a limited length but you don't get the counter below the TextField as it looks neater.

Related

Flutter TextFormField in iOS randomly jumping to the previous field

Here's a link for a GIF of its unwanted behavior
I have 2 TextFormField(username and PIN) inside a Form in this page. But exclusively in iOS, when I press the PIN field after I filled the username field, it would immediately jump back to the username field.
Another thing to remember, I have a GestureDetector in the whole background at first, its function is for hiding the keyboard when the user taps outside the field and buttons. So I tried separating the GestureDetector to only above and below the Form because I thought overlapping the GestureDetector was the cause. Apparently, it doesn't fix anything.
body: SingleChildScrollView(
child: Form(
key: _formKey,
child: Padding(
padding: EdgeInsets.all(15),
child: AutofillGroup(
child: Column(
crossAxisAlignment: CrossAxisAlignment.start,
children: [
GestureDetector(
onTap: () => unfocus(context),
child: Container(
color: Theme.of(context).scaffoldBackgroundColor,
child: Column(
crossAxisAlignment: CrossAxisAlignment.start,
children: [
Text(
'Login',
style: Theme.of(context).textTheme.subtitle1.copyWith(
fontSize: 20,
),
),
SizedBox(height: 10),
Text(
args.fromPurchase ? 'Please enter your NIK and PIN to purchase' : 'Please enter your NIK and PIN',
style: Theme.of(context).textTheme.bodyText2.copyWith(
fontSize: 15,
),
),
SizedBox(height: _showNotice ? 30 : 15),
Container(
height: _showNotice ? null : 0,
padding: EdgeInsets.all(5),
decoration: BoxDecoration(
color: _noticeError ? aLightRed : aLightGreen,
borderRadius: BorderRadius.circular(15)
),
child: Row(
children: [
IconButton(
splashRadius: 5,
padding: EdgeInsets.all(0),
icon: Icon(
Icons.cancel,
size: _showNotice ? 20 : 0,
color: _noticeError ? aRed : aGreen,
),
onPressed: () => _onClose(),
),
Expanded(
child: Text(
_noticeError ? _errorText.capitalizeFirstofEach : 'We have sent a new PIN to your email.',
maxLines: 2,
style: Theme.of(context).textTheme.bodyText1.copyWith(
fontSize: 15,
color: _noticeError ? aRed : aGreen,
),
),
),
],
),
),
SizedBox(height: _showNotice ? 20 : 15),
Text(
'NIK',
style: Theme.of(context).textTheme.bodyText1.copyWith(
fontSize: 15,
),
),
],
),
),
),
SizedBox(height: 10),
TextFormField(
keyboardType: TextInputType.number,
controller: _userNikController,
maxLength: 16,
autofillHints: [AutofillHints.username],
onChanged: (_) => setState((){}),
inputFormatters: [
FilteringTextInputFormatter.allow(RegExp("[0-9]")),
],
style: Theme.of(context).textTheme.bodyText1,
decoration: InputDecoration(
counterText: '',
contentPadding: EdgeInsets.all(15),
fillColor: Colors.grey[50],
filled: true,
border: OutlineInputBorder(
borderRadius: BorderRadius.circular(10),
),
focusedBorder: OutlineInputBorder(
borderRadius: BorderRadius.circular(10),
borderSide: BorderSide(color: aBorderColor.withAlpha(75)),
),
hintText: 'Please enter your NIK',
hintStyle: Theme.of(context).textTheme.bodyText2.copyWith(
fontSize: 15,
color: aLightTextColor.withAlpha(175),
),
),
),
SizedBox(height: 20),
Text(
'PIN',
style: Theme.of(context).textTheme.bodyText1.copyWith(
fontSize: 15,
),
),
SizedBox(height: 10),
TextFormField(
keyboardType: TextInputType.number,
controller: _userPinController,
obscureText: !_pinVisible,
obscuringCharacter: '*',
maxLength: 6,
autofillHints: [AutofillHints.password],
onChanged: (_) => setState((){}),
inputFormatters: [
FilteringTextInputFormatter.allow(RegExp("[0-9]")),
],
style: Theme.of(context).textTheme.bodyText1,
decoration: InputDecoration(
counterText: '',
contentPadding: EdgeInsets.all(15),
fillColor: Colors.grey[50],
filled: true,
border: OutlineInputBorder(
borderRadius: BorderRadius.circular(10),
borderSide: BorderSide(color: aBorderColor.withAlpha(75)),
),
focusedBorder: OutlineInputBorder(
borderRadius: BorderRadius.circular(10),
borderSide: BorderSide(color: aBorderColor.withAlpha(75)),
),
hintText: 'Please enter your PIN',
hintStyle: Theme.of(context).textTheme.bodyText2.copyWith(
fontSize: 15,
color: aLightTextColor.withAlpha(175),
),
suffixIcon: IconButton(
splashRadius: 5,
icon: Icon(
_pinVisible ? Icons.visibility : Icons.visibility_off,
color: _pinVisible ? aDarkTextColor : aBorderColor,
),
onPressed: () => setState(() => _pinVisible = !_pinVisible),
),
),
),
SizedBox(height: 20),
Parent(
gesture: Gestures()
..onTap(() => _onLogin(args.fromPurchase)),
style: ParentStyle()
..opacity((_userNikController.text != '' && _userPinController.text != '') ? 1 : 0.6)
..width(double.infinity)
..height(45)
..borderRadius(all: 10)
..padding(horizontal: 15)
..animate(400, Curves.easeOut)
..background.color(Theme.of(context).primaryColor),
child: Center(
child: Center(
child: Text(
args.fromPurchase ? 'Purchase Order' : 'Login',
style: Theme.of(context).textTheme.button.copyWith(
fontWeight: FontWeight.w500,
fontSize: 15,
),
),
),
),
),
GestureDetector(
onTap: () => unfocus(context),
child: Container(
width: double.infinity,
height: 200,
color: Theme.of(context).scaffoldBackgroundColor,
),
),
],
),
),
),
),
),
Thank you in advance.

How to set TextField width?

I nested my TextField inside a Container with width 10.0, but the textfield is still taking up the whole width of the device.
Widget _reviewBody() {
return SliverToBoxAdapter(
child: Container(
width: 10.0,
padding: EdgeInsets.only(bottom: 30.0),
child: TextField(
onChanged: (text) {
setState(() {
reviewBody = text;
});
},
keyboardType: TextInputType.multiline,
maxLines: null,
decoration: InputDecoration(
hintText: 'Add your thoughts here',
hintStyle: TextStyle(color: Burnt.hintTextColor),
enabledBorder: UnderlineInputBorder(borderSide: BorderSide(color: Burnt.lightGrey)),
focusedBorder: UnderlineInputBorder(borderSide: BorderSide(color: Burnt.primaryLight, width: 1.0)),
),
textAlign: TextAlign.center,
),
),
);
}
How do I set the TextField width?
Edit: Turns out SliverToBoxAdapter does magic, so I've used media query to set a padding on my container. Maybe I'm not supposed to use SliverToBoxAdatper, if someone can explain the right thing to do that would be great thanks.
Edit2: Actually I came up with an even better idea, I just put my Container inside a Row and made the Row center my 100.0 wide Container
I tried something like this
Container(
margin: EdgeInsets.only(top: 30, left: 30, right: 30),
width: MediaQuery.of(context).size.width,
child: Column(
crossAxisAlignment: CrossAxisAlignment.end,
children: <Widget>[
TextField(
decoration: InputDecoration(
hintText: "Inserisci la tua email",
hintStyle: TextStyle(fontSize: 20),
labelText: "Email",
labelStyle: TextStyle(
color: Utils.blackColor, fontSize: 20),
border: UnderlineInputBorder(
borderSide: BorderSide(color: Utils.greyColor)),
focusedBorder: UnderlineInputBorder(
borderSide: BorderSide(
color: Colors.grey,
style: BorderStyle.solid))),
controller: nameController,
style: TextStyle(fontSize: 23)),
Padding(padding: EdgeInsets.only(top: 20)),
],
),
),
pu textfield and a container in a column as a child, then wrap children with flexible widget give them flex property

How to launch once login and splash screen page after app start

I'm developing a login page and splash screen for a certain application, how can I set those route to launch only once?
Stack(
fit: StackFit.loose,
children: <Widget>[
Image(
image: AssetImage('images/home.png'),
fit: BoxFit.cover,
width: MediaQuery.of(context).size.width,
height: MediaQuery.of(context).size.height,
),
Column(
crossAxisAlignment: CrossAxisAlignment.center,
mainAxisAlignment: MainAxisAlignment.center,
children: <Widget>[
// SizedBox(height: 20.0),
//height was 60
Column(
children: <Widget>[
SizedBox(
height: 30.0,
),
Text(
"SMART HYDROPONICS",
style: TextStyle(
color: Colors.white,
fontSize: 22.0,
fontWeight: FontWeight.bold,
),
),
SizedBox(
height: 30.0,
),
CircleAvatar(
backgroundColor: Colors.white,
radius: 90.0,
child: Container(
alignment: Alignment.center,
child: CircleAvatar(
backgroundColor: Colors.green,
child: Text(
'REGISTER',
style: TextStyle(
fontWeight: FontWeight.bold,
color: Colors.white),
),
radius: 70.0,
),
)),
],
),
SizedBox(height: 20.0),
Form(
key: _key,
autovalidate: _autovalidate,
child: Column(children: <Widget>[
TextFormField(
decoration: InputDecoration(
hintText: "Enter Name",
border: InputBorder.none,
hintStyle: TextStyle(
color: Colors.white,
wordSpacing: 20.0,
fontWeight: FontWeight.normal,
fontSize: 18.0),
icon: Icon(
Icons.nature_people,
size: 30.0,
color: Colors.black,
)),
maxLength: 25,
keyboardType: TextInputType.text,
obscureText: false,
textAlign: TextAlign.justify,
onSaved: (val) {
_name = val;
},
validator: _myName,
),
SizedBox(
height: 20.0,
),
SizedBox(height: 40.0),
TextFormField(
textCapitalization: TextCapitalization.characters,
decoration: InputDecoration(
hintText: "Enter Number",
border: InputBorder.none,
// contentPadding: EdgeInsets.all(0.0),
hintStyle: TextStyle(
color: Colors.white,
wordSpacing: 20.0,
fontWeight: FontWeight.normal,
fontSize: 18.0),
icon: Icon(
Icons.phone,
size: 30.0,
color: Colors.black,
)),
maxLength: 10,
maxLines: 1,
keyboardType: TextInputType.phone,
obscureText: false,
textAlign: TextAlign.justify,
onSaved: (val) {
_number = val;
},
validator: _myNumber,
),
SizedBox(
height: 50.0,
),
TextFormField(
textCapitalization: TextCapitalization.characters,
decoration: InputDecoration(
hintText: "Product ID",
border: InputBorder.none,
// contentPadding: EdgeInsets.all(0.0),
hintStyle: TextStyle(
color: Colors.white,
wordSpacing: 20.0,
fontWeight: FontWeight.normal,
fontSize: 18.0),
icon: Icon(
Icons.settings_brightness,
size: 30.0,
color: Colors.black,
)),
maxLength: 10,
maxLines: 1,
keyboardType: TextInputType.phone,
obscureText: false,
textAlign: TextAlign.justify,
onSaved: (val) {
_number = val;
},
validator: _productId,
),
// SizedBox(height: MediaQuery.of(context).size.height/990000 ),
RaisedButton(
onPressed: _sendToServer,
color: Colors.greenAccent,
child: Text(
"Finish",
style: TextStyle(
color: Colors.white,
),
)),
]),
),
]),
],
)
You'll want to keep persistent state (like login tokens or flags marking things as viewed/accepted) via the shared_preferences plugin or some other persistent store that's local like sqlite or a flat file.

padding between divider and row is big

i have an edit text and icon .. and i want a line under them .. so i added a divider after them like this:
new Column(
children: <Widget>[
new Row(
children: <Widget>[
new Image.asset(
'assets/sa-logo.png',
width: 20.0,
height: 13.0,
),
Padding(
padding: EdgeInsets.only(left: 5.0, right: 5.0),
child: new Text(
'+966',
style: TextStyle(
fontSize: 15.0, color: Colors.grey),
),
),
new Flexible(
child: new TextField(
style: new TextStyle(
fontSize: 20.0,
color: Colors.black,
),
decoration: new InputDecoration(
border: InputBorder.none,
hintText: '5xxxxxxxx',
hintStyle: new TextStyle(
fontSize: 20.0,
),
),
keyboardType: TextInputType.number,
onChanged: (String value) {
this._data.phone = value;
setState(() {
phonelength = value.length;
done();
});
}),
),
],
),
Divider()
],
),
but the space between the line and the other widgets is big as shown:
how to make it smaller?
I just added this to the TextField:
contentPadding: EdgeInsets.symmetric(vertical: 0),
and that solved the problem.

How to make the background of TextField rectangular box shape?

I tried making Container widget with rectangle shape in TextField. It doesn't show my text inside container. Rather the box shape comes above TextField.
Here's my code:
new Container(
height: 10.0,
width: 20.0,
decoration: new BoxDecoration(
shape: BoxShape.rectangle,
border: new Border.all(
color: Colors.black,
width: 1.0,
),
),
child: new TextField(
textAlign: TextAlign.center,
decoration: new InputDecoration(
hintText: '1',
border: InputBorder.none,
),
),
),
Just remove the height and width property of the container.
Example:
new Container(
decoration: new BoxDecoration(
shape: BoxShape.rectangle,
border: new Border.all(
color: Colors.black,
width: 1.0,
),
),
child: new TextField(
textAlign: TextAlign.center,
decoration: new InputDecoration(
hintText: '1',
border: InputBorder.none,
),
),
)
or else just specify the border property of InputDecoration like
new TextField(
textAlign: TextAlign.center,
decoration: new InputDecoration(
hintText: '1',
border: new OutlineInputBorder(
borderRadius: const BorderRadius.all(
const Radius.circular(0.0),
),
borderSide: new BorderSide(
color: Colors.black,
width: 1.0,
),
),
),
)
Hope that helps
TextField(
decoration: InputDecoration(
enabledBorder: OutlineInputBorder(
borderSide: BorderSide(color: Colors.grey, width: 2.0),
),
hintText: 'Email',
prefixIcon: Icon(Icons.mail_outline),
),
),
Output:
TextField(
decoration: InputDecoration(
filled: true, // <- this is required.
border: const OutlineInputBorder(
borderRadius: kStadiumBorderRadius,
borderSide: BorderSide.none,
),
),
);

Resources