Text through border in flutter - flutter

I want to add the text through a container border in flutter.
I just want that Address to appear through a gap between the top border. It doesn't seem possible using a positioned widget, because then the border lines would appear through the "Address" text.
Is it at all possible?

Is this what you want?
class MainPage extends StatefulWidget {
#override
_MainPageState createState() => _MainPageState();
}
class _MainPageState extends State<MainPage> {
FocusNode focusNode = FocusNode();
bool isFocused = false;
#override
void initState() {
focusNode.addListener(_onFocusChange);
super.initState();
}
void _onFocusChange() {
setState(() => isFocused = !isFocused);
}
#override
Widget build(BuildContext context) {
return Scaffold(
body: Container(
margin: const EdgeInsets.symmetric(horizontal: 500, vertical: 300),
child: Stack(
children: <Widget>[
Container(
padding: const EdgeInsets.only(top: 10),
child: TextFormField(
focusNode: focusNode,
decoration: InputDecoration(
border: OutlineInputBorder(
borderRadius: BorderRadius.circular(30)),
),
),
),
Align(
alignment: Alignment.topCenter,
child: Container(
color: Colors.white,
child: Padding(
padding: const EdgeInsets.symmetric(horizontal: 8.0),
child: Text(
'Address',
style:
isFocused ? TextStyle(color: Colors.blue[800]) : null,
),
),
),
),
],
),
),
);
}
}
As far as I know there is no way to centerized labelText in InputDecoration.

Does it have to be the container border? If not, you can use the TextField with InputDecoration like this:
TextField(
decoration: InputDecoration(
border: OutlineInputBorder(),
labelText: 'Label Text',
),
textAlign: TextAlign.center,
),
But Sadly the TextField dose not support the centered label text (textAlign: TextAlign.center, only centers the hint text). If you want to center the label text you have to change the TextField.dart.
This is TextField so it's not like a usual Text because it is editable. If you want it to be like a Text,set enabled: false and give a controller to it and set an initial value. Or you can use TextFormField so you don't have to use a controller. Like this:
TextFormField(
decoration: InputDecoration(
border: OutlineInputBorder(),
labelText: 'Address',
),
textAlign: TextAlign.center,
enabled: true,
initialValue: 'Address Here',
),

Related

Flutter: TextField or TextFormField label inside border using ThemeData

How can i make my TextField label float to the top but stay inside the TextField border (not at the edge of it) when my TextField widget is active?
Example of what i'm going for:
Becomes
This
Is this possible using the inputDecorationTheme on ThemeData? or do i have to make a wrapper Widget to accomplish this?
Would very much prefer to control it from an app wide ThemeData
Unfortunately i don't know how to do it with default tools, but i do it with another way, may be it will be helpful for you.
Create variable for FocusNode and border color inside of your widget:
// Use it to change color for border when textFiled in focus
FocusNode _focusNode = FocusNode();
// Color for border
Color _borderColor = Colors.grey;
Inside of initState create listener for textField, if textField will be in focus, change border color to orange, otherwise change to grey:
#override
void initState() {
super.initState();
// Change color for border if focus was changed
_focusNode.addListener(() {
setState(() {
_borderColor = _focusNode.hasFocus ? Colors.orange : Colors.grey;
});
});
}
Create Container with border for textField, add focusNode and set decoration to textField:
Container(
decoration: BoxDecoration(
border: Border.all(color: _borderColor),
borderRadius: BorderRadius.circular(4),
),
child: TextField(
focusNode: _focusNode,
style: TextStyle(color: Colors.grey),
keyboardType: TextInputType.number,
decoration: InputDecoration(
contentPadding: EdgeInsets.zero,
border: InputBorder.none,
labelText: "Amount",
prefixIconConstraints: BoxConstraints(minWidth: 0, minHeight: 0),
prefixIcon: Padding(
padding: EdgeInsets.symmetric(vertical: 18, horizontal: 8),
child: Text("₦", style: TextStyle(fontSize: 16, color: Colors.grey)),
),
),
),
),
Don't forget call dispose for focusNode:
#override
void dispose() {
_focusNode.dispose();
super.dispose();
}
Full code:
class TextFieldDesignPage extends StatefulWidget {
TextFieldDesignPage({Key? key}) : super(key: key);
#override
_TextFieldDesignPageState createState() => _TextFieldDesignPageState();
}
class _TextFieldDesignPageState extends State<TextFieldDesignPage> {
// Use it to change color for border when textFiled in focus
FocusNode _focusNode = FocusNode();
// Color for border
Color _borderColor = Colors.grey;
#override
void initState() {
super.initState();
// Change color for border if focus was changed
_focusNode.addListener(() {
setState(() {
_borderColor = _focusNode.hasFocus ? Colors.orange : Colors.grey;
});
});
}
#override
void dispose() {
_focusNode.dispose();
super.dispose();
}
#override
Widget build(BuildContext context) {
return Scaffold(
body: Center(
child: Container(
margin: EdgeInsets.all(8),
decoration: BoxDecoration(
border: Border.all(color: _borderColor),
borderRadius: BorderRadius.circular(4),
),
child: TextField(
focusNode: _focusNode,
style: TextStyle(color: Colors.grey),
keyboardType: TextInputType.number,
decoration: InputDecoration(
contentPadding: EdgeInsets.zero,
border: InputBorder.none,
labelText: "Amount",
prefixIconConstraints: BoxConstraints(minWidth: 0, minHeight: 0),
prefixIcon: Padding(
padding: EdgeInsets.symmetric(vertical: 18, horizontal: 8),
child: Text("₦", style: TextStyle(fontSize: 16, color: Colors.grey)),
),
),
),
),
),
);
}
}
Result:

How to make Textformfield style stay the same when errorText appears

I am designing a phone number input box. The default style will be like the first image, but when the textError appears, the style will break like the second image. Is there a way to keep the spacing from user text input to the bottom line like the default style when error not showing?
first image
second image
NumberTextField widget, the widget as large as shown in the picture, including the flag and the TextFieldWidget. widget
Widgets:
import 'package:flutter/material.dart';
import 'package:online_croceries/widgets/textfield_widget.dart';
class NumberTextField extends StatelessWidget {
String? urlImageFlag;
int? code;
final TextEditingController? textEditingController;
ValueChanged? onChanged;
final String? error_text;
NumberTextField({Key? key, urlImage, code, required this.textEditingController,this.onChanged, required this.error_text})
: super(key: key);
#override
Widget build(BuildContext context) {
final height = MediaQuery.of(context).size.height;
final width = MediaQuery.of(context).size.width;
return Column(
mainAxisSize: MainAxisSize.min,
children: [
Row(
mainAxisAlignment: MainAxisAlignment.center,
crossAxisAlignment: CrossAxisAlignment.center,
children: [
ClipRRect(
clipBehavior: Clip.antiAlias,
borderRadius: BorderRadius.circular(5.0),
child: Image.asset(
urlImageFlag ?? 'assets/images/flag_country.png',
height: (height / 100) * 3,
width: (width / 100) * 9,
fit: BoxFit.fill,
),
),
Padding(
padding: const EdgeInsets.only(left: 10.0,right:10),
child: Text(
'+${code ?? 880}',
style: const TextStyle(
fontWeight: FontWeight.w600, fontSize: 16.0),
),
),
Expanded(
child:
TextFieldWidget(
inputType: TextInputType.phone,
textController: textEditingController!,
inputAction: TextInputAction.next,
autoFocus: false,
onChanged: onChanged,
errorText: error_text,
),
),
],
),
// const Divider(thickness: 1.5, height: 0.3, color: Colors.grey),
],
);
}
}
TextFieldWidget
#override
Widget build(BuildContext context) {
return Padding(
padding: padding,
child: TextFormField(
controller: textController,
focusNode: focusNode,
onFieldSubmitted: onFieldSubmitted,
onChanged: onChanged,
autofocus: autoFocus,
textInputAction: inputAction,
obscureText: this.isObscure,
maxLength: 25,
keyboardType: this.inputType,
decoration: InputDecoration(
hintText: this.hint,
errorText: errorText,
counterText: '',
// icon: this.isIcon ? Icon(this.icon, color: iconColor) : null
),
),
);
}
Just add a errorBorder in decoration, how you want to be when error is show:
decoration: InputDecoration(
hintText: this.hint,
errorText: errorText,
counterText: '',
// icon: this.isIcon ? Icon(this.icon, color: iconColor) : null
errorBorder: //code how you want..
),

Center align leading icon in Flutter

I need to align hint text and leading icon in the center, like shown here:
When I add a leading icon, and centre align decoration that is what I get. I need the icon to be in the centre as well.
Edit: Current code
TextField(
textAlign: TextAlign.center,
decoration: InputDecoration(
hintText: 'Type something',
prefixIcon: Icon(Icons.search)
)
),
There is a widget for your case: IntrinsicWidth. This widget is used to size its child to the child's intrinsic width.
Output
Full code:
class CenteredTextField extends StatefulWidget {
const CenteredTextField({Key key}) : super(key: key);
#override
_CenteredTextFieldState createState() => _CenteredTextFieldState();
}
class _CenteredTextFieldState extends State<CenteredTextField> {
#override
Widget build(BuildContext context) {
return Scaffold(
body: Container(
height: 40.0,
margin: EdgeInsets.symmetric(horizontal: 20.0, vertical: 50.0),
decoration: BoxDecoration(
color: Colors.orange.withOpacity(0.4),
borderRadius: BorderRadius.circular(20.0),
border: Border.all(
color: Colors.orange,
width: 1.0,
),
),
child: Center(
child: IntrinsicWidth(
child: TextField(
textAlignVertical: TextAlignVertical.center,
decoration: InputDecoration(
prefixIcon: Icon(Icons.search),
hintText: 'Type verse address',
border: InputBorder.none,
),
),
),
),
),
);
}
}

Flutter TextField LabelText Center

The Desired Effect is to have Kartennummer and Passwort centrated.
How is this possible?
I use a custom class for this:
import 'package:flutter/material.dart';
import 'package:impex_shop/styles/impex_styles.dart';
class ImpexTextField extends StatefulWidget {
final TextEditingController controller;
final bool obscureText;
final TextInputType keyboardType;
final String labelText;
final IconData prefixIcon;
final int maxLines;
final TextInputAction textInputAction;
final void Function(String) onSubmitted;
final bool autofocus;
const ImpexTextField(
{Key key,
this.controller,
this.obscureText,
this.keyboardType,
this.labelText,
this.prefixIcon,
this.maxLines = 1,
this.textInputAction,
this.onSubmitted,
this.autofocus = false})
: super(key: key);
#override
_ImpexTextFieldState createState() => _ImpexTextFieldState();
}
class _ImpexTextFieldState extends State<ImpexTextField> {
FocusNode _focusNode = FocusNode();
Paint paint;
InputDecoration buildTextInputDecoration(
String labelText, TextEditingController controller, IconData prefixIcon) {
return InputDecoration(
labelText: labelText,
labelStyle: TextStyle(
color: ImpexColors.mainColor,
height: 0.8, // 0,1 - label will sit on top of border
background: paint,
),
fillColor: ImpexColors.lightGrey,
filled: true,
enabledBorder: OutlineInputBorder(
borderSide: const BorderSide(
color: ImpexColors.grey,
width: 1.0,
),
),
focusedBorder: OutlineInputBorder(
borderSide: const BorderSide(
color: ImpexColors.secondaryColor,
width: 2.0,
),
),
suffixIcon: InkWell(
onTap: () => controller.clear(),
child: Icon(Icons.cancel),
),
prefixIcon: prefixIcon == null ? null : Icon(prefixIcon),
);
}
#override
Widget build(BuildContext context) {
return Container(
child: ListView(
shrinkWrap: true,
physics: ClampingScrollPhysics(),
children: <Widget>[
Container(
height: 12,
),
TextField(
textAlign: TextAlign.center,
textAlignVertical: TextAlignVertical.center,
focusNode: _focusNode,
controller: widget.controller,
obscureText: widget.obscureText ?? false,
maxLines: widget.maxLines,
textInputAction: widget.textInputAction,
decoration: buildTextInputDecoration(
widget.labelText, widget.controller, widget.prefixIcon),
keyboardType: widget.keyboardType,
autofocus: widget.autofocus,
onSubmitted: widget.onSubmitted,
onTap: () => setState(() {
FocusScope.of(context).requestFocus(_focusNode);
}),
),
],
),
);
}
#override
void dispose() {
_focusNode.dispose();
super.dispose();
}
}
A Very and Handy solution to Center the Label:
Since Label is accepting Widget after flutter 2.5.x, so you can wrap your Text widget into
Center widget like this,
TextFormField(
decoration: InputDecoration(
label: const Center(
child: Text("Your Centered Label Text"),
),
),
)
Note:
If Upper border is not Visible due to this, Then:
Try Wraping Center widget to Row, and give mainAxisSize: MainAxisSize.min, this will not cover the entire border
There is a nice decision for this.
Try to use alignLabelWithHint: true.
As example:
TextField(keyboardType: TextInputType.number, textAlign: TextAlign.center, maxLines: 1, decoration: InputDecoration(alignLabelWithHint: true, enabledBorder: InputBorder.none, contentPadding: EdgeInsets.zero, focusedBorder: InputBorder.none, border: InputBorder.none, labelStyle: Theme.of(context).textTheme.headline6, labelText: 'Amount (GPB)'.toUpperCase(),),),
I had a similar problem with labels, my solution was, as Ragu Swaminathan says, to create my own custom widget that used a Stack with the TextField on the bottom and faded Text widget above it. Obviously the text widget doesn't need to be faded but I was just mimicking the style of regular labels.
class CenteredTextField extends StatelessWidget {
final String label;
final TextEditingController controller;
CenteredTextField({
#required this.label,
this.controller,
});
#override
Widget build(BuildContext context) {
return Stack(
alignment: Alignment.topCenter,
children: [
Padding(
padding: EdgeInsets.only(top: 12.5),
child: TextField(
textAlign: TextAlign.center,
controller: controller,
),
),
Padding(
padding: EdgeInsets.only(top: 4.0),
child: Opacity(
opacity: 0.7,
child: Text(label),
),
),
],
);
}
}
You can Style TextFormField with Centered Text and Centered Label in Flutter
by using textAlign and floatingLabelAlignment property. I use Flutter 2.10.4
TextFormField(
controller: textController,
textAlign: TextAlign.center,
decoration:
InputDecoration(
border: const OutlineInputBorder(
borderRadius: BorderRadius.all(Radius.circular(5.0))),
isDense: true,
labelText: 'Label',
hintText: 'Hint',
floatingLabelAlignment: FloatingLabelAlignment.center,
floatingLabelStyle: const TextStyle(fontSize: 16),
labelStyle: const TextStyle(
fontSize: 13, color: Color.fromARGB(255, 152, 121, 11))),
)
Alignment for the label text appears in the screenshot is due to the presence of Prefix Icon. Label text will make a spacing according to the prefix icon present.
And for you, below is the same exact thing that makes the above design.
TextField(
textAlign: TextAlign.center,
decoration: InputDecoration(
prefixIcon: Icon(Icons.card_giftcard),
hintText: 'Hint Text',
labelText:'Label',
border: const OutlineInputBorder(),
),
)
Try and let know, if that helps you.
EDIT: I think there is no proper way to align the label text alone.
you can use the contentPadding: EdgeInsets.only(left: <Any_value>), property to move the label text
In My case, I need the text field to show some information and update them. So basically I am not strict about sticking with the labelText. So, I done the following trick to center the text.
Instead of using a label text you can use the Text itself and center it with textAlign property.
textAlign: TextAlign.center
By using the controller, you can assign a text to the text field. Also, you can update the textfield if you need a labeltext like effect. (but no animation)
This is my code:
TextEditingController timeText = TextEditingController()..text = '12:24 AM';
...
TextField(
controller: timeText,
enabled: false,
style: TextStyle(fontSize: 20),
decoration: InputDecoration(
border: InputBorder.none,
hintText: 'Center the text',
alignLabelWithHint: true,
),
textAlign: TextAlign.center,
),
OUTPUT
Well, it's not perfect, but I achieved it by using Center() in the label. Sadly, it erases part of the upper border.
label: Center(child: Text('Label')),
You can achieve thus by using the textAlign property of the TextField and set it to TextALign.center.
Check the code below:
TextField(
// use the text align property
textAlign: TextAlign.center,
decoration: InputDecoration(
labelText: 'Yay, it works',
hintText: 'Center the text',
),
),
OUTPUT:

The prefixIcon of TextField widget in flutter disappears on focusing TextField. How to solve?

Was just exploring flutter and got stuck. The prefixIcon disappears on clicking field and it appears back when focused out. How to solve this ? The code is as below. Tried removing the key of form. I want the icon to stay even if focused in or focused out. Is there any other property to set?
Couldn't be able to find a fix.
class _MyHomePageState extends State<MyHomePage> {
String _email = "";
String _password = "";
final _formKey = GlobalKey<FormState>();
final FocusNode _emailFocus = FocusNode();
final FocusNode _passwordFocus = FocusNode();
#override
Widget build(BuildContext context) {
return Scaffold(
appBar: AppBar(
title: Text(widget.title),
),
body: Container(
padding: const EdgeInsets.symmetric(horizontal: 50.0,vertical: 100.0),
decoration: BoxDecoration(color: Colors.white),
child:Form(
key: _formKey,
child: Column(
crossAxisAlignment: CrossAxisAlignment.start,
children: <Widget>[
TextFormField(
focusNode: _emailFocus,
decoration: InputDecoration(
labelText: 'Username or email',
prefixIcon: Icon(Icons.person), //prefixIcon
focusedBorder: UnderlineInputBorder(),
hintText: "example#mail.com",
)
),
Padding(
padding: const EdgeInsets.symmetric(vertical: 16.0),
),
TextFormField(
obscureText: true,
focusNode: _passwordFocus,
decoration: InputDecoration(
labelText: 'Password',
prefixIcon: Icon(Icons.lock),
focusedBorder: UnderlineInputBorder(),
)
) ,
Padding(
padding: const EdgeInsets.symmetric(vertical: 16.0),
child: RaisedButton(
onPressed: () {
// Validate will return true if the form is valid, or false if
// the form is invalid.
if (_formKey.currentState.validate()) {
// Process data.
}
},
child: Text('Submit'),
),
),
],
),
)
)
);
}
}
The issue was that I had set the primary colour to white. So whenever the field was focused it was disappering as the background was also white. My bad.
the issue came to me when i add TextField to AppBar as title.
to fix this, just add color to icon.
e.g.
prefixIcon: Icon(Icons.person), //prefixIcon
should be replaced with
prefixIcon: Icon(Icons.person, color: Colors.black,), //prefixIcon
i post an issue, but no response yet.
this works fine for me
class MyHomePage extends StatefulWidget {
#override
State<StatefulWidget> createState() {
// TODO: implement createState
return _MyHomePageState();
}
}
class _MyHomePageState extends State<MyHomePage> {
String _email = "";
String _password = "";
final _formKey = GlobalKey<FormState>();
final FocusNode _emailFocus = FocusNode();
final FocusNode _passwordFocus = FocusNode();
#override
Widget build(BuildContext context) {
return Scaffold(
appBar: AppBar(
title: Text('hi'),
),
body: Container(
padding: EdgeInsets.only(top: 50, left: 50, right: 50),
decoration: BoxDecoration(color: Colors.white),
child: Form(
key: _formKey,
child: ListView(
children: <Widget>[
TextFormField(
focusNode: _emailFocus,
decoration: InputDecoration(
labelText: 'Username or email',
prefixIcon: Icon(Icons.person), //prefixIcon
focusedBorder: UnderlineInputBorder(),
hintText: "example#mail.com",
)),
Padding(
padding: EdgeInsets.only(top: 20),
),
TextFormField(
obscureText: true,
focusNode: _passwordFocus,
decoration: InputDecoration(
labelText: 'Password',
prefixIcon: Icon(Icons.lock),
focusedBorder: UnderlineInputBorder(),
)),
Padding(
padding: EdgeInsets.only(top: 20),
child: RaisedButton(
onPressed: () {
// Validate will return true if the form is valid, or false if
// the form is invalid.
if (_formKey.currentState.validate()) {
// Process data.
}
},
child: Text('Submit'),
),
),
],
),
)));
}