Can't exit from a TextField flutter - ios

I need of a Box where insert and store some informations that comes as user input, I'm using the 'TextField' so I changed the 'maxLines' option in my 'TextField' from default value (1) to (2) and when I want to insert some text here I can't leave the box because the 'Done' button changed to 'return' blocking me! The keyboard is blocked too.
I'm doing this because I would like a Box with some text inside (like a description) that I can move where I want and change all its properties.
My issue is that the textfield writes all in one line, I need of a newline at the border of the textfield.
Do you know how to handle the TextField better?
This is a part of the code :
Widget build(BuildContext context) {
return new Scaffold(
backgroundColor: Colors.white,
body : Container(
decoration: BoxDecoration(
shape: BoxShape.rectangle,
image: DecorationImage(
image: _image == null
? AssetImage('assets/images/io.png')
: FileImage(_image), // here add your image file path,
alignment: Alignment.topCenter,
),
),
child: GestureDetector(
child:Container(
alignment: Alignment.center,
child : ConstrainedBox(
constraints: BoxConstraints(
maxHeight: 400,
maxWidth: 400,
),
child: TextField(
minLines: 1,
maxLines: 2,
decoration: InputDecoration(
border: OutlineInputBorder(
borderRadius: BorderRadius.all(
const Radius.circular(48.0)
),
),
labelText: 'Descrizione',
labelStyle: TextStyle(
backgroundColor: Colors.white,
),
),
),
),
),
)
)
);
P.S.: I'm studying this 'GestureDetector', it should be useful for this purpose I guess.

In the TextField go into InputDecoration and add a Widget to the suffix property . The suffix property is a Widget that shows at the end of the Textfield.
FocusNode node = FocusNode();
TextField(
minLines: 1,
maxLines: 2,
focusNode: node,
decoration: InputDecoration(
suffix: RaisedButton(
onPressed: () {
node.unfocus();
},
child: Text("Done"),
),
border: OutlineInputBorder(
borderRadius:
BorderRadius.all(const Radius.circular(48.0)),
),
labelText: 'Descrizione',
labelStyle: TextStyle(
backgroundColor: Colors.white,
),
),
),

Related

How to set mandatory DropDownButton on Flutter with Colors?

I developed like this dropdown. Everything working fine. By default, the dropdown is not select any value. How to set red color border or something like decoration on value equal null(without select).
my dropdown code and image
Align(
alignment: Alignment.bottomLeft,
child: Container(
child: Text('Priority',
style: TextStyle(fontWeight: FontWeight.w400)),
),
),
// dropBox(),
Container(
// width: 200.0,
child: ButtonTheme(
alignedDropdown: true,
child: DropdownButton<Priority>(
isExpanded: true,
value: _priorities,
//hint: Text("Select"),
items: priority.map((Priority value) {
return DropdownMenuItem<Priority>(
value: value,
child: Text(
value.description,
overflow: TextOverflow.ellipsis,
),
);
}).toList(),
onChanged: (value) => setState(() {
priorityIndex = value.id;
_priorities = value;
}),
style: Theme.of(context).textTheme.title,
),
),
),
I need to like this dropdown,
You are almost there already. You have wrapped your DropdownButton with a Container - now you only have to set its decoration property in order to achieve your desired styling:
return Container(
decoration: BoxDecoration(
border: Border.all(color: _priorities != null ? Colors.red : Colors.transparent),
),
child: DropdownButton(
...

Flutter keyboard overlapping issue not solved with resizeToAvoidBottomPadding

Basically I have a login page where I first segement into 2 container with one covers 55% and 45% of the screen. Then on top of these 2 container I add one more container with top 40% of the screen size and in it I have one more container which hold my user name and password text field. So on the design wise I am ok.
Now the issue when the keyboard comes the password field is totally not visible. First I just had stack then I did google and some suggest to put the Scaffold and add this line resizeToAvoidBottomPadding: false, but seems does not work for me either too.
Widget build(BuildContext context) {
return Scaffold(
resizeToAvoidBottomPadding: false,
body: Container(
child: Stack(
children: <Widget>[
// The containers in the background
new Column(
children: <Widget>[
new Container(
height: MediaQuery.of(context).size.height * .55,
//color: Colors.blue,
decoration: new BoxDecoration(
image: new DecorationImage(image: new AssetImage("lib/assets/cbg.png"), fit: BoxFit.cover,),
),
),
new Container(
height: MediaQuery.of(context).size.height * .45,
color: Colors.white,
)
],
),
// The card widget with top padding,
// incase if you wanted bottom padding to work,
// set the `alignment` of container to Alignment.bottomCenter
new Container(
alignment: Alignment.topCenter,
padding: new EdgeInsets.only(
top: MediaQuery.of(context).size.height * .40,
right: 20.0,
left: 20.0),
child: new Container(
height: MediaQuery.of(context).size.height * .45,
width: MediaQuery.of(context).size.width,
child: new Card(
color: Colors.white,
elevation: 4.0,
child: Padding(
padding: EdgeInsets.symmetric(horizontal: 40.0),
child: Column(
children: <Widget>[
SizedBox(height: MediaQuery.of(context).size.height * .05),
new TextFormField(
decoration: new InputDecoration(
labelText: "Enter Email",
fillColor: Colors.white,
border: new OutlineInputBorder(
borderRadius: new BorderRadius.circular(10.0),
borderSide: new BorderSide(
color: Colors.blue
),
),
//fillColor: Colors.green
),
validator: (val) {
if(val.length==0) {
return "Email cannot be empty";
}else{
return null;
}
},
keyboardType: TextInputType.emailAddress,
style: new TextStyle(
fontFamily: "Poppins",
),
),
SizedBox(height: MediaQuery.of(context).size.height * .05),
new TextFormField(
decoration: new InputDecoration(
labelText: "Enter Password",
fillColor: Colors.white,
border: new OutlineInputBorder(
borderRadius: new BorderRadius.circular(10.0),
borderSide: new BorderSide(
),
),
//fillColor: Colors.green
),
validator: (val) {
if(val.length==0) {
return "Password cannot be empty";
}else{
return null;
}
},
keyboardType: TextInputType.emailAddress,
style: new TextStyle(
fontFamily: "Poppins",
),
),
],
),
)
),
),
),
new Container(
alignment: Alignment.topCenter,
padding: new EdgeInsets.only(
top: MediaQuery.of(context).size.height * .80,
right: 50.0,
left: 50.0),
child: new FlatButton(
color: Colors.red,
child: Text("Press Me"),
onPressed: () {},
),
),
new Container(
alignment: Alignment.topCenter,
padding: new EdgeInsets.only(
top: MediaQuery.of(context).size.height * .90,
right: 50.0,
left: 50.0),
child: new FlatButton(
color: Colors.red,
child: Text("Forgot Password ?"),
onPressed: () {},
),
)
],
)
)
);
}
}
After the changes the keyboard still appear a slight covering the textfield.
Can I achieve some
You should put all this inside a ListView, then when you open the keyboard the list will scroll up.
I'm 2 years late on this and you might find the solution already, but this is for someone who struggle to find the solution. (Include myself a couple a days ago)
To solve this, The "TextFormField" widget need another attribute called "scrollPadding".
TextFormField(
controller: controller,
scrollPadding: EdgeInsets.only(bottom:40), // THIS SHOULD SOLVE YOUR PROBLEM
decoration: InputDecoration(
labelText: title,
hintText: title,
filled: true,
fillColor: Colors.white,
enabledBorder: const OutlineInputBorder(
borderSide: const BorderSide(color: Colors.grey, width: 1.0),
),
border: const OutlineInputBorder(),
),
validator: (String? value) {
if (value == null || value.isEmpty) {
return title;
}
return null;
},
),

Remove underline from DropdownButtonFormField

How can I remove the underline from DropdownButtonFormField (check photo below), I have tried various combinations of options with InputDecortaion couldn't find any way.
SizedBox(
width: 100.0,
child: DropdownButtonFormField<int>(
decoration: InputDecoration(
border: UnderlineInputBorder(
borderSide:
BorderSide(color: Colors.white))),
value: 2,
items: <DropdownMenuItem<int>>[
DropdownMenuItem<int>(
value: 1,
child: Text("Owner"),
),
DropdownMenuItem<int>(
value: 2,
child: Text("Member"),
),
],
),
Just wrap DropdownButton inside DropdownButtonHideUnderline like this :
new DropdownButtonHideUnderline(
child: DropdownButton()
)
Setting the underline property to SizedBox() makes it invisible too:
...
DropdownButton(
underline: SizedBox(),
...
One way of Doing it :
In your Code - change decoration: InputDecoration to decoration: InputDecoration.collapsed
body: SizedBox(
width: 100.0,
child: DropdownButtonFormField<int>(
decoration: InputDecoration.collapsed(hintText: ''),
value: 2,
...
OR
In your Code - instead of border Use enabledBorder: UnderlineInputBorder
DropdownButtonFormField<int>(
decoration: InputDecoration(
enabledBorder: UnderlineInputBorder(
borderSide: BorderSide(color: Colors.white))),
value: 2,
items: <DropdownMenuItem<int>>[
....
The proper/clean solution nowadays is to use InputBorder.none:
DropdownButtonFormField<int>(
decoration: InputDecoration(
enabledBorder: InputBorder.none,
...
),
...
)
You might also want to set border, focusedBorder, errorBorder, and disabledBorder to InputBorder.none if you want to avoid the border from showing in all cases.
underline can take a widget so, you just have assigned it an empty Container, or a SizedBox.shrink()
underline:Container(),
-- or --
underline:SizedBox.shrink(),
Example :
child: DropdownButton<String>(
// Just have to assign to a empty Container
underline:Container(),
value: dropdownValue,
icon: Icon(Icons.keyboard_arrow_down),
iconSize: 24,
elevation: 16,
onChanged: (String newValue) {
setState(() {
dropdownValue = newValue;
});
},
items:[
deptList[0].dept,
deptList[1].dept,
deptList[2].dept,
deptList[3].dept,
].map<DropdownMenuItem<String>>((String value) {
return DropdownMenuItem<String>(
value: value,
child: Text(value),
);
}).toList(),
)
Add underline: Container() to your settings like this:
SizedBox(
...
underline: Container(),
),
According to this [Flutter Doc] You can do like this. Simply create an object of DropdownButtonHideUnderline class and pass your current implementation of the DropdownButton as the child of DropdownButtonHideUnderline. Thts it ;)
DropdownButtonHideUnderline(
child: new DropdownButton<String>(
......
),
),
As of now, DropdownButtonFormField doesn't support DropdownButtonHideUnderline.
Although it uses it under the hood to remove the underline from DropdownButton but then applies it's own decoration on top of that
Setting border to InputBorder.none will do the job
DropdownButtonFormField<String>(
decoration: InputDecoration(border: InputBorder.none)
)
If you want the border to appear on error you can use
InputDecoration(
border: InputBorder.none,
errorBorder: UnderlineInputBorder(
borderSide: BorderSide(color: Colors.red),
),
),
You can change underline property to blank or null widget it will work like charm check the below property
underline: widget or SizedBox(),
Ex:-
DropdownButton(
icon: Icon(Icons.more_vert),
isExpanded: true,
value: dropValue,
underline: widget or SizedBox(),
use
DropdownButton<String>(
hint: Text("Status"),
value: 'Text Default',
isExpanded: true,
iconSize: 30,
underline: Container(
height: 1.0,
decoration: const BoxDecoration(
border: Border(bottom: BorderSide(color: Colors.transparent, width: 0.0))
),
),
...
Easy Way to do it
DropdownButtonFormField<String>(
decoration: InputDecoration(
enabledBorder: UnderlineInputBorder(
borderSide: BorderSide(color: Colors.transparent),
),
),
...
)
DropdownButtonHideUnderline(
child: DropdownButton(
isExpanded: true,
hint: Padding(
padding: const EdgeInsets.all(8.0),
child: Text("Select State"),
),
style: MyStyle().getTextStyle("x1black"),
items: <String>[
'Messaging',
'Chating',
'No Longer Interested',
'Document Request'
].map((String value) {
return new DropdownMenuItem<String>(
value: value,
child: new Text(value),
);
}).toList(),
onChanged: (_) {},
),
),
Underline takes a Widget. Pass it a blank widget, like below.
DropdownButton<T>(
value: value,
underline: SizeBox(), // Empty box will remove underline
)
You could try the following code:
decoration: InputDecoration(
border: InputBorder.none,
)
To disable every border on the width, set InputBorder.none for border attribute. Or if you prefer to disable only the border when dropdown is enable, set for enabledBorder.
if DropdownButtonFormField text get trim due to outline border then use this code:
DropdownButtonFormField<String>(
decoration: InputDecoration(
enabledBorder: UnderlineInputBorder(
borderSide: BorderSide(color: Colors.white)),
isDense: true,)
DropdownButtonHideUnderline(
child: ButtonTheme(
alignedDropdown: false,
splashColor: Colors.grey,
child: DropdownButton<String>(
value: _myPargna,
iconSize: 25,
icon: Icon(Icons.arrow_drop_down),
style:
TextStyle(fontSize: 18, color: Color(0xFF1f193d)),
hint: Row(
children: [
SizedBox(width: 11),
Text(
'Select Province',
style: TextStyle(color: Colors.grey),
),
],
),
onChanged: (String newValue) {
setState(() {
_myPargna = newValue;
});
},
items: items.map((String items) {
return DropdownMenuItem(
child: Row(
children: [
SizedBox(width: 12),
Text(
items,
style: TextStyle(color: Colors.black),
),
],
),
value: items,
);
}).toList(),
),
),
),
You can just Do this
decoration: const InputDecoration(
// enabledBorder: InputBorder.none,
// disabledBorder: InputBorder.none,
// focusedBorder: InputBorder.none,
// errorBorder: InputBorder.none,
border: InputBorder.none,
),
DropdownButtonFormField(
iconSize: 30,
decoration: InputDecoration(enabledBorder: InputBorder.none),
hint: Text(
"Select Duration",
style: TextStyle(fontSize: 20),
),
items: listDrop,
onChanged: (value) {
duration = value;
},
)
if you want just disable the border in all the case you can use :
DropdownButtonFormField(
validator: _validator,
decoration: InputDecoration(
border: InputBorder.none,
),
items: [],
onChanged: (value) {}),
),
if you want disable only when there is no error you can use this
decoration: InputDecoration(
errorBorder: OutlineInputBorder(
borderSide: BorderSide(color: Colors.transparent)),
enabledBorder: OutlineInputBorder(
borderRadius: BorderRadius.circular(2.0),
borderSide: BorderSide(color: kLightBlackColor)),
),
This worked for me
DropdownButtonFormField<String>(decoration: InputDecoration(border: InputBorder.none),)

How to change TextFormField input text color in Flutter

Doing UI for a flutter app at uni, I just want the text typed into the TextFormField to be white. It seems unnecessarily difficult. I've tried googling etc but can't see an obvious answer.
new Theme(
// this colors the underline
data: theme.copyWith(
primaryColor: Colors.white,
hintColor: Colors.transparent,
),
child: new Padding(
padding: const EdgeInsets.fromLTRB(32.0, 40.0, 32.0, 4.0),
child: TextFormField(
key: Key('username'),
keyboardType: TextInputType.text,
controller: usernameController,
decoration: InputDecoration(
fillColor: Colors.black.withOpacity(0.6),
filled: true,
border: new OutlineInputBorder(
borderRadius: const BorderRadius.all(
const Radius.circular(8.0),
),
borderSide: new BorderSide(
color: Colors.transparent,
width: 1.0,
),
),
labelText: 'Username',
labelStyle:
new TextStyle(color: Colors.white, fontSize: 16.0)),
style:
TextStyle(fontSize: 20.0, color: textTheme.button.color),
validator: validateUserName,
onSaved: (val) => this.loginFields._username = val),
),
),
This will do:
TextFormField(
style: TextStyle(color: Colors.white),
)
For anyone trying to do this from a material app's theme: ThemeData property, the color can be changed using the subtitle1 text theme style.
MaterialApp(
...
theme: ThemeData(
...
textTheme: const TextTheme(
...
subtitle1: const TextStyle(
color: Colors.red, // <-- TextFormField input color
),
),
),
)
Puedes usar style: TextStyle
body: Center(
child: Column(
mainAxisAlignment: MainAxisAlignment.center,
children: <Widget>[
Form(
key: _formKey,
child: Column(
crossAxisAlignment: CrossAxisAlignment.center,
children: <Widget>[
TextFormField(
TextFormField(
controller: field,
style: TextStyle(fontSize: 18, color: Colors.red),
decoration: const InputDecoration(
contentPadding: const EdgeInsets.only(
left: 15,
top: 8,
right: 15,
bottom: 0
),
hintText: 'name',
),
validator: (value) {
if (value.isEmpty) {
return 'Please enter some text';
}
return null;
},
),
)
]
)
)
]
)
)
You can use style inside TextFormField.
Example :
TextFormField(
style: const TextStyle(color: Colors.white),
),
You can use this to change everything
TextFormField(
//controller: _phoneController,
cursorColor: Colors.black,
keyboardType: TextInputType.text,
style: TextStyle(
color: Colors.black
),
decoration: new InputDecoration(
hintStyle: TextStyle(
color: Colors.white
),
border: InputBorder.none,
//contentPadding:
//EdgeInsets.only(left: 15, bottom: 11, top: 11, right: 15),
hintText: "New Playlist"),
),
Padding(
padding: EdgeInsets.all(10),
child: TextFormField(
cursorColor: Color(0XFFFFCC00)//Cursor color change
style: TextStyle(
color: Color(0XFFFFCC00),
decorationColor: Color(0XFFFFCC00),//Font color change
backgroundColor: Color(0XFFFFCC00),//TextFormField title background color change
),
),
You are changing input text color in this line TextStyle(fontSize: 20.0, color: textTheme.button.color), so in order to set in to white just use Colors.white constant instead of textTheme.button.color.
More about text style here.
Overview: The textFormField style is set to a TextStyle defined as MediumStyle. The style affects the characters being displayed in the textbox. Whereas, the labelStyle affect the font displays of the inputdecoration.
TextFormField(
style: MediumStyle,
keyboardType: TextInputType.emailAddress,
focusNode: _employeeEmailFocus,
decoration: InputDecoration(labelText: "Employee Email", labelStyle:MediumBoldStyle),
validator: (val)=> null,
onSaved:(value)=> this._employeeEmail=value,
onFieldSubmitted: (term){
_fieldFocusChange(context,_employeeEmailFocus,_passwordFocus);
},
),
decoration: const InputDecoration(
labelStyle: TextStyle(color: Colors.white),
),
If you want to use Global Change then use this:
return MaterialApp(
title: 'Flutter Demo',
theme: ThemeData(
primarySwatch: Colors.blue,
textTheme: Theme.of(context).textTheme.copyWith(
subtitle1: const TextStyle(color: Colors.green),
)),
home: const MyHomePage(),
);
Otherwise you can do this:
TextFormField(
style: TextStyle(color: Colors.green),
)
If you are trying to change the textColor using the ThemeData.
Now TextField is using titleMedium.
So,
ThemeData(
...
textTheme: const TextTheme(
...
titleMedium: const TextStyle(
color: Colors.red, // <-- TextFormField input color
),
),
),
Add a inputdecoration class for textformfield
this is i think so
decoration: InputDecoration(
prefixStyle: new TextStyle(
),

When I select a Textfield the keyboard moves over it

When i select a Textfield, the keyboard is going to be shown but the keyboard hide my selected TextField. Does someone have a solution?
Scaffold(
resizeToAvoidBottomInset: true,
body: SingleChildScrollView(
child: Container(
child: Column(
children: <Widget>[
TextFormField(
decoration: InputDecoration(
labelText: 'Enter Text',
),
),TextFormField(
decoration: InputDecoration(
labelText: 'Enter Text',
),
),TextFormField(
decoration: InputDecoration(
labelText: 'Enter Text',
),
),TextFormField(
decoration: InputDecoration(
labelText: 'Enter Text',
),
),TextFormField(
decoration: InputDecoration(
labelText: 'Enter Text',
),
),TextFormField(
decoration: InputDecoration(
labelText: 'Enter Text',
),
),TextFormField(
decoration: InputDecoration(
labelText: 'Enter Text',
),
),
TextFormField(
decoration: InputDecoration(
labelText: 'Enter Text',
),
)
],
),
),
)
);
// resizeToAvoidBottomPadding: false isDeprecated
use resizeToAvoidBottomInset: true.
Compose an animation and move your TextField container up when a TextField gets focus.
For learning about composing animations refer to:
Composing Animations and Chaining Animations in Dart's Flutter Framework
Use Flutter's FocusNode to detect the focus on a TextField
Edit:
Here I've written an example that does exactly what you want:
import 'package:flutter/material.dart';
void main() => runApp(new MyApp());
class MyApp extends StatelessWidget {
#override
Widget build(BuildContext context) {
return new MaterialApp(
debugShowCheckedModeBanner: false,
title: 'Animation Demo',
theme: new ThemeData(
primaryColor: new Color(0xFFFF0000),
),
home: new FormDemo(),
);
}
}
class FormDemo extends StatefulWidget {
#override
_FormDemoState createState() => _FormDemoState();
}
class _FormDemoState extends State<FormDemo> with SingleTickerProviderStateMixin {
AnimationController _controller;
Animation _animation;
FocusNode _focusNode = FocusNode();
#override
void initState() {
super.initState();
_controller = AnimationController(vsync: this, duration: Duration(milliseconds: 300));
_animation = Tween(begin: 300.0, end: 50.0).animate(_controller)
..addListener(() {
setState(() {});
});
_focusNode.addListener(() {
if (_focusNode.hasFocus) {
_controller.forward();
} else {
_controller.reverse();
}
});
}
#override
void dispose() {
_controller.dispose();
_focusNode.dispose();
super.dispose();
}
#override
Widget build(BuildContext context) {
return Scaffold(
resizeToAvoidBottomPadding: false, // this avoids the overflow error
appBar: AppBar(
title: Text('TextField Animation Demo'),
),
body: new InkWell( // to dismiss the keyboard when the user tabs out of the TextField
splashColor: Colors.transparent,
onTap: () {
FocusScope.of(context).requestFocus(FocusNode());
},
child: Container(
padding: const EdgeInsets.all(20.0),
child: Column(
children: <Widget>[
SizedBox(height: _animation.value),
TextFormField(
decoration: InputDecoration(
labelText: 'I move!',
),
focusNode: _focusNode,
)
],
),
),
),
);
}
}
Just cut and paste your body code in this -
SingleChildScrollView(
child: Stack(
children: <Widget>[
// your body code
],
),
),
A pretty short way to realize this is by simply using a MediaQuery for getting the bottom view insets. This would look as follows:
...
return Column(
children: <Widget>[
TextField(
decoration: InputDecoration.collapsed(hintText: "Start typing ..."),
controller: _chatController,
),
SizedBox(
height: MediaQuery.of(context).viewInsets.bottom,
),
],
);
...
Hope it helps!
In my case I had to combine answer given by #Javid Noutash which uses AnimationController along with scrollPadding property of TextFormField.
code:
Add this line in build method
double bottomInsets = MediaQuery.of(context).viewInsets.bottom;
Add scrollPadding property
return ListView(
children:[
...widgets,
Container(
margin:EdgeInsets.only(
top:1.0,
left:1.0,
right:1.0,
bottom:_focusNode.hasFocus && bottomInsets != 0?
_animation.value : 1.0),
child:TextFormField(
decoration: InputDecoration(
labelText: 'I move!',
),
focusNode: _focusNode,
scrollPadding: EdgeInsets.only(bottom:bottomInsets + 40.0),
),
),
]
);
Note: Combine this code with #Javid Noutash's code
I had the same problem where the parent widget is Material and the other widgets are inside a ListView. The problem was fixed when I changed the parent widget to Scaffold without any extra code and the TextField, TextFormField in my case, is being showed above the Keyboard automatically. So, if you encountered this problem just make sure to have Scaffold as the main widget.
The most simple way is to just wrap it with
SingleChildScrollView( ... )
When the textfield is on the page bottom and the keyboard appears, the textfield is automatically scrolled up. Then the text may be entered right above the keyboard.
My way here
Scaffold(
resizeToAvoidBottomInset: false,
resizeToAvoidBottomPadding: false,
body: Container(
decoration: BoxDecoration(
image: DecorationImage(
image: AssetImage('images/Bg img.png'), fit: BoxFit.fill)),
child: Padding(
padding: EdgeInsets.only(
bottom: MediaQuery.of(context).viewInsets.bottom),
child: CustomScrollView(
slivers: [
SliverFillRemaining(
hasScrollBody: false,
child: Column(
mainAxisAlignment: MainAxisAlignment.spaceBetween,
children: [
.............
This template has some advantages:
Move content up when the keyboard appears
Column using spaceBetween inside a scroll view
Background is sticked phone scren and never change event the keyboard ups
Wrap your widget into Padding and set padding: EdgeInsets.only(bottom: MediaQuery.of(context).viewInsets.bottom),
<activity
android:name="..ActivityName"
android:configChanges="orientation|keyboardHidden|keyboard|screenSize|locale|layoutDirection|fontScale|screenLayout|density|uiMode"
android:hardwareAccelerated="true"
android:windowSoftInputMode="adjustResize"/>
only for android
if you use FlutterFragment add configChanges and windowSoftInputMode for the Activity.
another way
add your TextField to a ListView
ListView(
children: <Widget>[
TextField(),
TextField(),
]
)
The above does not work if you have a CustomScrollview in a NestedScrollView.
First, you need to give the TextField a focusNode.
TextField(focusNode:_focusNode(),
...);
Use NestedScrollViewState to get access to the innerScrollController of the NestedScrollView. You can view the example here on how to get the innerScrollController. Declare a globalKey and assign it to NestedScrollView.
body: NestedScrollView(
key: globalKey,
...)
Setup the focusNode Listener to listen for when the textfield has been activated and animate the innerScrollController accordingly.
void initState() {
super.initState();
_focusNode.addListener(() {
if (_focusNode.hasFocus) {
double innerOffSet = globalKey.currentState.innerController.offset;
if(innerOffSet < 100)
globalKey.currentState.innerController.jumpTo(innerOffSet+100);
}
});
}
var _contentController;
void _settingModalBottomSheet(BuildContext context, String initialText) {
_contentController = new TextEditingController(text: initialText);
showModalBottomSheet(
context: context,
isDismissible: true,
builder: (BuildContext bc) {
return Column(
mainAxisSize: MainAxisSize.min,
children: <Widget>[
Container(
height: 40,
margin: EdgeInsets.only(left: 4, right: 4, bottom: 8),
decoration: BoxDecoration(
color: AppColor.bgTextFieldComment,
borderRadius: BorderRadius.circular(16),
),
child: Row(
children: <Widget>[
Expanded(
child: Padding(
padding: EdgeInsets.only(left: 24),
child: TextField(
focusNode: _contentFocusNode,
autofocus: true,
controller: _contentController,
decoration: InputDecoration(
hintText: 'Enter Content',
border: InputBorder.none,
fillColor: AppColor.bgTextFieldComment,
),
keyboardType: TextInputType.multiline,
maxLines: null,
style: TextStyle(
color: Colors.black87,
fontSize: 16,
fontStyle: FontStyle.normal,
),
)),
),
InkWell(
child: Padding(
padding: EdgeInsets.only(left: 4, right: 4),
child: Icon(
Icons.send,
color: Colors.blue,
),
),
onTap: () {
// do ON TAP
},
),
],
),
),
SizedBox(
height: MediaQuery.of(bc).viewInsets.bottom,
),
],
);
},).then((value) {
print('Exit Modal');
});
print('request focus');
_contentFocusNode.requestFocus();
}
Instead of TextField, use TextFormField and wrap the widget with a list of TextFormField to Form:
Form(
child: Column(
children: <Widget> [
TextFormField(),
TextFormField(),
...
TextFormField(),
]
)
)
you can easily try to use Flexible widget just wrap your widget with it
Flexible(
child: Image(
image :
AssetImage('assets/logo.png'),
),
),
I had a very complex widget with Stack, Column and Single ChildChildScrollView, and I fixed it by adding a padding to the SCSV like this:
child: Stack(
children: [
Padding(
padding: const EdgeInsets.only(bottom: MediaQuery.of(context).viewInsets.bottom),
child: SingleChildScrollView(
child: Column(
children: [... a lot of children here, one of them is a TextField],
),
),
),
// a widget at the bottom of the stack that shows despite the size of the scrollable column
],
),
It's very easy in my case check out code
Column(
children: [
Expanded(
child:// Top View,
),
postSend // edittext. and button
],
)

Resources