Overflow issue in some iOS and android devices - flutter

i have implement radio buttons in one row and tested the ui some devices. In small devices like iphone 5s i got the overflow error.
Widget priority() {
return Column(
children: <Widget>[
Container(
alignment: Alignment.centerLeft,
child: const Text('Priority:'),
),
Row(
children: <Widget>[
radioButton('High', 0),
radioButton('Medium', 1),
radioButton('Low', 2),
],
)
],
);
}
Widget radioButton(String text, int value) {
return Row(
children: <Widget>[
Radio<int>(
activeColor: pinkColor,
value: value,
groupValue: _selected,
onChanged: (int value) {
onChange(value);
}),
Text(text, style: TextStyle(fontSize: 15)),
],
);
}

Hey, Use Expanded Widget To Solve Overflow Issue And For IOS, Android Issue Wrap Whole Widget In SafeArea, Hope This May Help You...

Add SingleChildScrollView it'll work.
Widget priority() {
return Column(
children: <Widget>[
Container(
alignment: Alignment.centerLeft,
child: const Text('Priority:'),
),
SingleChildScrollView(
scrollDirection: Axis.horizontal,
child: Row(
children: <Widget>[
radioButton('High', 0),
radioButton('Medium', 1),
radioButton('Low', 2),
],
))
],
);
}

Widget priority() {
return Column(
children: <Widget>[
Container(
alignment: Alignment.centerLeft,
child: const Text('Priority:'),
),
Wrap(
direction: Axis.horizontal,
children: <Widget>[
radioButton('High', 0),
radioButton('Medium', 1),
radioButton('Low', 2),
],
)
],
);
}
Widget radioButton(String text, int value) {
return Row(
children: <Widget>[
Radio<int>(
activeColor: pinkColor,
value: value,
groupValue: _selected,
onChanged: (int value) {
onChange(value);
}),
Text(text, style: TextStyle(fontSize: 15)),
],
);
}
Replaced Row with Wrap. If Overflow occurs, the overflowing widget will be aligned in the next line. Hope it helps.

Solution Code:
Widget priority() {
return Column(
children: <Widget>[
Container(
alignment: Alignment.centerLeft,
child: const Text('Priority:'),
),
Row(
children: <Widget>[
Expanded(child: radioButton('High', 0),),
Expanded(child: radioButton('Medium', 1),),
Expanded(child: radioButton('Low', 2),),,
],
)
],
);
}
Widget radioButton(String text, int value) {
return Row(
children: <Widget>[
Radio<int>(
activeColor: pinkColor,
value: value,
groupValue: _selected,
onChanged: (int value) {
onChange(value);
}),
Text(text, style: TextStyle(fontSize: 15)),
],
);
}
The reason why you faced it in a some devices and not in the others was that all devices have different screen sizes.
Expanded Widget ensures that it's child widget covers all the available space while it's among other widgets in a List of Widgets ([])
When we use it on multiple widgets then it equally divides the space among each other. You can control the size taken by each widget using the flex property.
If you introduce a non-Expanded widgets between Expanded widgets then the non-Expanded once are first laid out before the Expanded widget(s).
(Atleast that's what mentioned in Flutter's Widget of the Week video. However, I think it has got something more complex to it which we don't need to know.)
Tip: Avoid using functions in these places...Use classes instead.
A beautiful tutorial by the official Flutter Team:
https://flutter.dev/docs/development/ui/interactive

Related

In flutter, how to position radio buttons side by side but align to the left?

I have two RadioListTiles side by side in a row, but I do not want them to take up the entirety of the row. Currently each take up half the width of the entire row and spaced apart.
I want each radio button to take up less space (or just enough) and be left-aligned, and not be so spaced apart. I have tried wrapping each in Expanded or Flexible.
builder: (FormFieldState<NameLineSelection> formstate) {
return Column(
crossAxisAlignment: CrossAxisAlignment.start,
mainAxisAlignment: MainAxisAlignment.start,
children: [
Row(
mainAxisAlignment: MainAxisAlignment.start,
children: [
Expanded(
child: RadioListTile<NameLineSelection>(
title: const Text('Single-line'),
value: NameLineSelection.singleLineName,
groupValue: state.nameLineSelection,
onChanged: (NameLineSelection? value) {
_saveForm(fieldValues);
formstate.didChange(value);
BlocProvider.of<VerifyMedicareBloc>(context)
.add(MedicareFormCardNameLineSelectedEvent(
_formValues, value));
},
),
),
Expanded(
child: RadioListTile<NameLineSelection>(
title: const Text('Multi-line'),
value: NameLineSelection.multiLineName,
groupValue: state.nameLineSelection,
onChanged: (NameLineSelection? value) {
_saveForm(fieldValues);
formstate.didChange(value);
BlocProvider.of<VerifyMedicareBloc>(context)
.add(MedicareFormCardNameLineSelectedEvent(
_formValues, value));
},
),
),
],
),
if (formstate.errorText != null ||
formstate.errorText.toString() != 'null')
Text(formstate.errorText.toString(),
style: TextStyle(color: Colors.red)),
],
);
}),
One way would be to wrap the RadioListTile widget with a ConstrainedBox and set a maxWidth like so:
Row(
children: [
Expanded(
child: ConstrainedBox(
constraints: const BoxConstraints(
maxWidth: 300,
),
child: RadioListTile<NameLineSelection>(
title: const Text('Single-line'),
value: NameLineSelection.singleLineName,
groupValue: state.nameLineSelection,
onChanged: (NameLineSelection? value) {
_saveForm(fieldValues);
formstate.didChange(value);
BlocProvider.of<VerifyMedicareBloc>(context)
.add(MedicareFormCardNameLineSelectedEvent(
_formValues, value));
},
),
),
),
Expanded(
child: ConstrainedBox(
constraints: const BoxConstraints(
maxWidth: 300,
),
child: RadioListTile<NameLineSelection>(
title: const Text('Multi-line'),
value: NameLineSelection.multiLineName,
groupValue: state.nameLineSelection,
onChanged: (NameLineSelection? value) {
_saveForm(fieldValues);
formstate.didChange(value);
BlocProvider.of<VerifyMedicareBloc>(context)
.add(MedicareFormCardNameLineSelectedEvent(
_formValues, value));
},
),
),
),
],
),

What widget should I use for center text and left-aside button

I am making layout for flutter application
What I want to do is
-----------------------
|[i] [text] |
| |
Icon should be the left (padding 5px)
And text should be the center of screen.
At first I should use the Column
However my layout is not the same proportion
It might be simple though , how can I make it??
Stack() is one of the many options that you can use. Something like this:
Stack(
children:<Widget>[
Padding(
padding: EdgeInsets.only(left: 5),
child: Icon(Icons.info),
),
Align(
alignment: Alignment.topCenter,
child: Text("I'm on the top and centered."),
),
],
),
One way you can do this is something like this..
Widget build(BuildContext context) {
return Column(
children: [
Padding(
padding: EdgeInsets.all(5),
child: Row(
mainAxisAlignment: MainAxisAlignment.spaceBetween,
children: [
Icon(Icons.info),
Text('text'),
Opacity(opacity: 0, child: Icon(Icons.info)),
],
),
),
Padding(
padding: EdgeInsets.all(5),
child: Row(
mainAxisAlignment: MainAxisAlignment.spaceBetween,
children: [
Icon(Icons.info),
Text('second text'),
Opacity(opacity: 0, child: Icon(Icons.info)),
],
),
),
],
);
}
Result:
I might be late, but I want this answer to be there, if some one would find it better for the development purposes in future time.
We can make a reusable widget, which we can use it inside the main widget. The widget will accept text, and icon to be passed when called
// IconData is the data type for the icons
Widget myWidget(String text, IconData icon) => Row(
mainAxisSize: MainAxisSize.min,
mainAxisAlignment: MainAxisAlignment.start,
children: [
// this will be used a left-padding param
SizedBox(width: 20.0),
// using it here
Icon(icon, size: 28.0, color: Colors.greenAccent),
SizedBox(width: 5.0),
// this will take the remaining space, and then center the child
Expanded(child: Center(child: Text(text)))
]
);
To use in the main Widget, just do like this:
Column(
mainAxisAlignment: MainAxisAlignment.center,
children: <Widget>[
// calling our widget here
myWidget('FirstText', Icons.alarm),
SizedBox(height: 20.0), // this is used as a top margin
myWidget('SecondText', Icons.notifications)
]
)
If you wanna check out the sources which I used, please see:
Expanded class
SizedBox class
The result you will get is this:
This was an answer I gave a while ago for this same issue, but the other situation was vertical (a Column) instead of horizontal (a Row). Just swap the Row and Columns out for a Column and Rows in this example and you'll get the idea.
My code has grey added in order to show the difference between the two approaches.
A Stack will work, but it's overkill for this, this kind of problem is part of why we have Expandeds and Flexibles. The trick is to use three Flexibles (2 Expandeds and a Spacer). Put the Spacer on top. It and the bottom Expanded must have the same flex value in order to center the middle Expanded.
import 'package:flutter/material.dart';
class CenteringOneItemWithAnotherItemInTheColumn extends StatelessWidget {
const CenteringOneItemWithAnotherItemInTheColumn({
Key key,
}) : super(
key: key,
);
/// Adjust these values as needed
final int sameFlexValueTopAndBottom = 40; // 40%
final int middleFlexValue = 20; // 20%
#override
Widget build(BuildContext context) {
return Scaffold(
appBar: AppBar(
title: const Text('Column Alignment Question'),
),
body: Row(
mainAxisAlignment: MainAxisAlignment.spaceEvenly,
children: [
Column(
mainAxisAlignment: MainAxisAlignment.center,
children: <Widget>[
const Spacer(),
const Text(
'Cent',
style: TextStyle(
fontSize: 64,
),
),
const Spacer(),
const Text(
'Bot',
style: TextStyle(
fontSize: 64,
),
),
],
),
Column(
children: <Widget>[
/// The key is to have the Spacer and the bottom Expanded
/// use the same value for flex. That will cause the middle
/// child of the Column to be centered vertically.
Expanded(
flex: sameFlexValueTopAndBottom,
child: Container(
width: 100,
color: Colors.grey[300],
),
),
Expanded(
flex: middleFlexValue,
child: const Align(
alignment: Alignment.center,
child: Text(
'Cent',
style: TextStyle(
fontSize: 64,
),
),
),
),
Expanded(
flex: sameFlexValueTopAndBottom,
child: Container(
color: Colors.grey[300],
child: const Align(
alignment: Alignment.bottomCenter,
child: Text(
'Bot',
style: TextStyle(
fontSize: 64,
),
),
),
),
),
],
),
],
),
);
}
}

How To Make A Widget Just Stick To Bottom Of Page

I am trying to build a view as in the image below.
The tweet your reply is just stack at the bottom while the other stuff are scrollable.
I've been banging my head on how to achieve this for a couple of hours.
Exactly;y like in the image below. There are four sections:
The post (tweet)
The row of icons
The comments (which scrolls)
The tweet your reply which is static
The solution would be to use the Align Widget. So in your Stack you would put as the last element in the stack:
Align(
alignment: Alignment.bottomCenter,
child: // your widget would go here
),
I'm judging by your question that you have figured out how to do all of the other parts, and was just wondering about the bottom part. You can use Align to align things in other ways as well (such as topCenter, bottomLeft, etc). Hope this helps, and if so please up vote and accept as answer and if not leave a comment below.
Edit:
I wouldn't use a Stack. I would wrap the entire widget tree in a Column, and put the post in a Expanded Widget with a flex factor of 1, and a Row of Icons below it. Then put a ListView in an Expanded Widget with a flex of 4 (you can experiment with values). And lastly in the Column I would add you "Tweet you reply" Widget.
Simple layout code to give you an idea of how to implement it:
Column(
children: <Widget>[
Expanded(
child: ListView(
shrinkWrap: true,
children: <Widget>[
//your post
Row(
mainAxisAlignment: MainAxisAlignment.spaceAround,
children: <Widget>[
// your icons
],
),
//your comments
],
),
),
Align(
alignment: Alignment.bottomCenter,
child: // you textField,
),
],
)
Try this
class Home extends StatelessWidget {
#override
Widget build(BuildContext context) {
return Scaffold(
body: SafeArea(
child: Column(
mainAxisAlignment: MainAxisAlignment.spaceBetween,
children: <Widget>[
Expanded(
child: Column(
children: <Widget>[
Container(
padding: EdgeInsets.all(50),
child: Center(
child: Text(
"A POST"
),
),
),
Row(
mainAxisAlignment: MainAxisAlignment.spaceAround,
children: <Widget>[
Icon(Icons.details),
Icon(Icons.print),
Icon(Icons.translate),
Icon(Icons.map)
],
),
Expanded(
child: ListView(
children: List.generate(10, (index) => ListTile(title: Text("Comment $index"),)),
),
)
],
),
),
TextField(
decoration: InputDecoration(
labelText: "Tweet your reply"
),
)
],
),
),
);
}
}
The output:
If you want the post to scroll with it, this should help
import 'package:flutter/material.dart';
class Home extends StatelessWidget {
#override
Widget build(BuildContext context) {
return Scaffold(
body: SafeArea(
child: Column(
mainAxisAlignment: MainAxisAlignment.spaceBetween,
mainAxisSize: MainAxisSize.max,
children: <Widget>[
Expanded(
child: SingleChildScrollView(
child: Column(
children: <Widget>[
Container(
padding: EdgeInsets.all(50),
child: Center(
child: Text(
"A POST"
),
),
),
Row(
mainAxisAlignment: MainAxisAlignment.spaceAround,
children: <Widget>[
Icon(Icons.details),
Icon(Icons.print),
Icon(Icons.translate),
Icon(Icons.map)
],
),
Column(
children: List.generate(10, (index) => ListTile(title: Text("Comment $index"),)),
)
],
),
),
),
TextField(
decoration: InputDecoration(
labelText: "Tweet your reply"
),
)
],
),
),
);
}
}

How to give a constant width to a Flutter DropdownButton widget?

How can I give a constant width to a DropDownButton in a Flutter?
As I got to know why they both DropDownButton as different width size in below image,
as 1st one as the highest length of value "100%" in it & the
2nd one as highest value as "90%" in it, so there is a difference in the length of the string so it wrapping accordingly.
I want to give a fixed width for them so that they look the same.
Row(
mainAxisAlignment: MainAxisAlignment.spaceBetween,
crossAxisAlignment: CrossAxisAlignment.center,
children: <Widget>[
Text(title,
style: Theme.textTheme.body1
.copyWith(fontWeight: ThemeData.medium)),
DropdownButton(
disabledHint: Text(defaultValue),
value: currentDropDownItem,
items: dropDownItemList,
onChanged: isEnabled
? (value) {
if (onValueChanged != null) {
onValueChanged(value);
}
}
: null,
),
])
Wrap it inside a Container or SizedBox with width as,
new Container(
width: 75.0,
child: //your DropdownButton here
),
or you can use Expanded inside a Row,
Row(
mainAxisAlignment: MainAxisAlignment.spaceBetween,
crossAxisAlignment: CrossAxisAlignment.center,
children: <Widget>[
Expanded(
flex: 5,
child: Text(
title,
style: Theme.textTheme.body1
.copyWith(fontWeight: ThemeData.medium),
),
),
Expanded(
flex: 1,
child: DropdownButton(
disabledHint: Text(defaultValue),
value: currentDropDownItem,
items: dropDownItemList,
onChanged: isEnabled
? (value) {
if (onValueChanged != null) {
onValueChanged(value);
}
}
: null,
),
),
],
),
Hope it might be helpful.

Text widget not displaying in ListTile flutter

I want to display a profile image in left section, name and company in middle section (one below other) and reviews and ratings in right section inside a ListTile. I was able to display an image, reviews and ratings correctly, but text is not being displayed. I want to achieve this:
The white space between image and ratings is where I want to show the text (name and company, one below other). Not sure what am I missing here.
Code snippet below:
return new ListTile(
contentPadding: EdgeInsets.all(8.0),
leading: _getProfilePic(pro),
// title: new Text('${pro.fullname}'),
title: new Column(
children: <Widget>[
new Row(
mainAxisAlignment: MainAxisAlignment.start,
children: <Widget>[
new Text('${pro.fullname}')
],
),
],
),
subtitle: Column(children: <Widget>[
Padding(
padding: EdgeInsets.all(3.0),
),
new Row(
mainAxisAlignment: MainAxisAlignment.start,
children: <Widget>[
new Text('${pro.company}', style: TextStyle(fontSize: 12.0),
),
],
),
],
),
trailing: new Column(children: <Widget>[
new Row(
mainAxisAlignment: MainAxisAlignment.end,
children: <Widget>[
new StarRating(starCount: 5, rating: pro.rating, color: Colors.amber),
],
),
new Row(
mainAxisAlignment: MainAxisAlignment.end,
children: <Widget>[
new Text('${pro.reviewCount} reviews'),
],
)
],) ,
It seems to me a custom method that return ListView, as below:
Widget buildProList(List pros, BuildContext context) {
List proTiles = new List();
pros.forEach((pro) {
proTiles.add(proTile(pro, context));
});
return new ListView(
children: proTiles
);
}
And this is it's implementation:
ListTile proTile(Pro pro, BuildContext context) {
return new ListTile {
}
You can check the source code of ListTile to check how it is building the tree.
If you read the documentation from ListTile widgets you'll find something like this:
/// The primary content of the list tile.
///
/// Typically a [Text] widget.
final Widget title;
/// Additional content displayed below the title.
///
/// Typically a [Text] widget.
final Widget subtitle;
/// A widget to display after the title.
///
/// Typically an [Icon] widget.
final Widget trailing;
So you have to take in consideration the widgets that you are passing.
Your layout looks to complex, this is an example of how you can build your widget in a very simple way:
new ListTile(
contentPadding: EdgeInsets.all(8.0),
leading: _getProfilePic(pro),
title: new Text('${pro.fullname}'),
subtitle: Text('${pro.company}',
style: TextStyle(fontSize: 12.0),
),
trailing: new Column(
mainAxisAlignment: MainAxisAlignment.center,
children: <Widget>[
new StarRating(starCount: 5, rating: pro.rating, color: Colors.amber),
new Text('${pro.reviewCount} reviews'),
],
),
),
Another solution without using ListTile:
return Row(
children: <Widget>[
_getProfilePic(pro),
Expanded(
child: Column(
mainAxisAlignment: MainAxisAlignment.center,
children: <Widget>[
new Text(
'${pro.fullname}',
overflow: TextOverflow.ellipsis,
),
new Text(
'${pro.company}',
style: TextStyle(fontSize: 12.0),
),
],
),
),
new Column(
mainAxisAlignment: MainAxisAlignment.center,
children: <Widget>[
new StarRating(starCount: 5, rating: pro.rating, color: Colors.amber)
new Text('${pro.reviewCount} reviews'),
],
)
],
);
Note: Don't forget to check the parent constraints of your child widget