I get a lengthy result (location address) in my text box leading it to an error RIGHT OVERFLOW BY 226 PIXEL. I tried using overflow but the result is still the same.
Column(
crossAxisAlignment: CrossAxisAlignment.start,
children: [
Text(Provider
.of<AppData>(context)
.pickUpLocation != null
? Provider
.of<AppData>(context)
.pickUpLocation
.placeName
: "Add Home",overflow: TextOverflow.ellipsis),
SizedBox(
height: 4.0,
),
Text("Your home Address",
style: TextStyle(color: Colors.black54, fontSize: 12.0)),
],
)
Next, I tried using Flexible but the text is cut into half
Wrap Text widget into FittedBox with fit: BoxFit.scaleDown
Related
I'm trying to use flexible on my text cause it's overflow but for some reason expanded or neither flexible didn't work. But it work on other text widget on different screen. Anyone know why ? How can I fix this ?
return Row(
children: [
/// Ticket Details
Column(
crossAxisAlignment: CrossAxisAlignment.start,
children: [
/// Ticket Title
Flexible(
child: Text(
ticketData['title'],
style: primaryColor700Style.copyWith(
fontSize: fontSize18,
),
),
),
SizedBox(height: 8),
/// Date Created
Text(
'Created : ' +
DateFormat('d MMM y').format(
DateTime.parse(
ticketData['date_created'].toDate().toString(),
),
),
style: primaryColor400Style.copyWith(
fontSize: fontSize12,
),
),
],
),
/// Urgent Icon
if (ticketData['is_urgent'])
Icon(
Icons.warning_rounded,
size: 35,
color: warningColor,
),
],
);
Wrap the column with flexible
Row(
children: [
Flexible(
child: Column(
children:[
Text(),
]
)
)
]
)
Row takes infinite width, To get available width row for next children you can wrap Expanded/ Flexibile/ fixed width widget. You can check this doc more about.
You can find this from Layout algorithm on Row
Expanded, to indicate children that should take all the remaining room.
Flexible, to indicate children that should share the remaining room but that may by sized smaller (leaving some remaining room unused).
I'm a developer who just started flutter.
While using the flutter to configure a screen, I visited to ask about something strange.
I set the crossAxisAlignment option to center in the Row widget and set one of the children to Text.
The code is here.
child: Row(
crossAxisAlignment: CrossAxisAlignment.center,
mainAxisAlignment: MainAxisAlignment.start,
children: [
SizedBox(width: 22.0),
Text(
'Test',
style: TextStyle(
fontSize: 22,
fontWeight: FontWeight.w500,
fontStyle: FontStyle.normal),
),
],
),
Then, I created the text in Korean.
The result is the same as the picture below, but as you can see, the upper and lower margins of the letters are slightly different (it is slightly skewed down).
If this is English, the top and bottom margins are the same as follows.
This issue is the same for all Widgets written in Korean, but does anyone know the solution to this?
It seems there might be a similar issue logged here.
The proposed solution (although there is no input from OP to indicate it worked), is to pass textAlign: TextAlign.center to your Text Widget. This might help as crossAxisAlignment is a property applied via Row and Column to their children, whereas TextAlign is applied to the Text widget directly. Perhaps in conjunction with crossAxisAlignment it might produce the desired result.
That or you might want to experiment with padding on the Text widget. You can do this by wrapping your Text widget in a Padding widget or in a Container widget. See below.
Padding
Padding(
padding: EdgeInsets.fromLTRB(20, 20, 20, 20),
child: Text('Padding Via Padding Widget',
style: TextStyle(fontSize: 22))),
)
Container
Container(
padding: EdgeInsets.fromLTRB(20, 20, 20, 20),
child: Text('Padding Via Container Widget',
style: TextStyle(fontSize: 22)),
)
I'm trying to make a Table with two cells of the same width and height, so that the height depends on the size of the content. However, the smaller TableCell always shrinks:
This is what I'm trying to implement:
Here's the code:
Table(
children: [
TableRow(
children: [
TableCell(
child: Container(
color: Colors.green,
child: Text(
'long text long text long text long text long text long text long text'),
),
),
TableCell(
child: Container(
color: Colors.orange,
child: Text('short text'),
),
),
],
)
],
),
P.S. I could solve it by adding verticalAlignment: TableCellVerticalAlignment.fill, to the smaller cell, but any cell can be the smaller one, depending on the content. When I add this line to both cells, the whole table disappears. The only bypass I could imagine is to calculate the length of the content and find the smaller cell, but I wonder if there is a way to implement this UI directly with Flutter.
Would appreciate any help.
1. Row with IntrinsicHeight
IntrinsicHeight limits the height of the Row to the content size, which however is considered a 'relatively expensive' approach and is not recommended.
IntrinsicHeight(
child: Row(
crossAxisAlignment: CrossAxisAlignment.stretch,
children: [
Expanded(
child: Container(
color: Colors.green,
child: Text(
'long text long text long text long text long text',
))),
Expanded(
child: Container(
color: Colors.orange,
child: Text(
'short text',
))),
],
),
),
2. Table with TableCellVerticalAlignment.fill
As mentioned in the question, the .fill option must not be used in the largest TableCell, because in this case the TableRow will have zero height. This is the preferred solution, because it doesn't have the 'expensiveness' issue of the previous one.
final texts = ['long text long text long text long text long text', 'short text'];
final colors = [Colors.green, Colors.orange];
// find the longest text and its index
final max = texts.asMap().entries.reduce(
(a, b) => (a.value.length > b.value.length) ? a : b,
);
return Table(children: [
TableRow(
children: texts
.asMap()
.entries
.map((e) => TableCell(
// use .fill in all cells except the largest
verticalAlignment: (e.key != max.key)
? TableCellVerticalAlignment.fill
: TableCellVerticalAlignment.top,
child: Container(
color: colors[e.key],
child: Text(e.value),
)))
.toList(),
),
]);
As I alluded to in my previous post on the subject (Multi-line flutter text field occupies all of Flexible space with ugly right padding) I'm a bit of a perfectionist. Unfortunately my flutter layout-fu isn't as strong as my ambition. I'm creating a messaging app, and I'm working on adding a timestamp to the message box. My code so far (thanks also to this answer: Complex alignment of a sub widget based on wrapping text like in the Telegram chat messenger) is this:
Code to create a row:
Widget getAppUserMessageRow() {
return Row(
crossAxisAlignment: CrossAxisAlignment.center,
mainAxisAlignment: MainAxisAlignment.end,
children: <Widget>[
SizedBox(width: AppState.i.chatItemUserLeftInset),
Flexible(
fit: FlexFit.loose,
child: message.cm.messageType.getMessageWidget(message),
),
],
);
}
Code to create the message box itself:
Widget build(BuildContext context) {
bool isFromAppUser = message.cm.isFromAppUser(AppState.i.activeUserId);
return Container(
padding: EdgeInsets.symmetric(
vertical: AppState.i.chatItemMessageVerticalInset),
child:
Container(
decoration: BoxDecoration(
color: isFromAppUser ? AppState.i.chatItemUserMessageBackgroundColour : Colors.white,
//.withOpacity(!message.isFromAppUser ? 0.1 : 0.8),
borderRadius: BorderRadius.only(
topLeft: Radius.circular(isFromAppUser ? AppState.i.chatItemMessageBorderRadius : 0),
topRight: Radius.circular(isFromAppUser ? 0 : AppState.i.chatItemMessageBorderRadius),
bottomRight: Radius.circular(isFromAppUser ? AppState.i.chatItemMessageCurvedBorderRadius : AppState.i.chatItemMessageBorderRadius),
bottomLeft: Radius.circular(isFromAppUser ? AppState.i.chatItemMessageBorderRadius : AppState.i.chatItemMessageCurvedBorderRadius),
),
boxShadow: [
BoxShadow(
color: AppState.i.chatItemMessageBoxShadowColour,
spreadRadius: AppState.i.chatItemMessageBoxShadowSpreadRadius,
blurRadius: AppState.i.chatItemMessageBoxShadowBlurRadius,
offset: AppState.i.chatItemMessageBoxShadowOffset, // changes position of shadow
),
],
),
padding: EdgeInsets.symmetric(
vertical: AppState.i.chatItemMessageVerInset,
horizontal: AppState.i.chatItemMessageHorInset),
child: Stack(
children: [
Text(
// WTF? This calculates enough space for the message receipt time to wrap
message.cm.messageText + (isFromAppUser ? ' \u202F' : ' \u202F'),
style: TextStyle(
fontSize: AppState.i.chatItemMessageTextFontSize,
color:
isFromAppUser ? AppState.i.chatItemMessageUserTextFontColour : AppState.i.chatItemMessageOtherUserTextFontColour,
),
textWidthBasis: TextWidthBasis.longestLine,
),
// This Positioned item creates the message timestamp in the area gained by adding the spaces above, assuming the spaces forced
// The text field into adding an extra line.
Positioned(
width: 60,
height: 15,
right: 0,
bottom: -2,
child: Row(
mainAxisSize: MainAxisSize.min,
mainAxisAlignment: MainAxisAlignment.end,
children: <Widget>[
Text(
DateFormat.Hm().format(message.cm.messageDisplayTime(AppState.i.activeUserId)),
style: TextStyle(
fontSize: AppState.i.chatItemMessageTimeFontSize,
color: isFromAppUser ? AppState.i.chatItemMessageUserTimeFontColour : AppState.i.chatItemMessageOtherUserTimeFontColour,
),
textAlign: TextAlign.right,
),
!isFromAppUser ? Container() :
Padding(
padding: EdgeInsets.only(left: AppState.i.chatItemMessageReceiptLeftInset),
child: message.cm.getReadReceiptIcon()
)
],
),
),
],
),
)
);
}
Here are some examples of good and bad - look at the right-hand-side padding on the bad examples. The timestamp should be more right-aligned with the text above:
And more:
Adding spaces + a non-printable character to make room for the date timestamp + read receipt combo is a genius trick, but with a downside. It pushes out the right alignment when the text is close to the space that will be occupied by the timestamp. So in some cases as per the above, the box consumes unnecessary space.
So, can this be fixed, or can a different layout be used to achieve the effect I'm looking for? I can't use anything too computational, because right now the performance is pretty decent when scrolling long lists.
To make this slightly more concrete, some 'fixed' examples.
Example: Message box with Timestamp
I think you can try this way:
Calculate/Simulate text and check the message is overlapping the timestamp.
If it overlaps, add \n to change the line. Otherwise, return the original one.
You need the following things:
LayoutBuilder: BoxConstraint above the text widget
TextPainter: Simulate the layout (also need the TextStyle, textWidthBasis or there may affect the layout result)
Here is the code:
// assume 'message' is a String need to be displayed
...
LayoutBuilder(builder: (context, constraints) {
final reserve = ' \u202F';
final originalPainter = TextPainter(
text: TextSpan(text: text, style: TextStyle(fontSize: 20)),
textDirection: TextDirection.ltr,
textWidthBasis: TextWidthBasis.longestLine,
)..layout(maxWidth: constraints.maxWidth);
final reservePainter = TextPainter(
text: TextSpan(text: text + reserve, style: TextStyle(fontSize: 20)),
textDirection: TextDirection.ltr,
textWidthBasis: TextWidthBasis.longestLine,
)..layout(maxWidth: constraints.maxWidth);
final changeLine = reservePainter.width > originalPainter.width + 0.001 || reservePainter.height > originalPainter.height + 0.001;
return Text(
changeLine ? text+'\n' : text,
...
)
}
I want to implement a Row having two Text widgets and a middle line like this:
The following code is my current implementation.
Row(
crossAxisAlignment: CrossAxisAlignment.center,
children: [
Text(
'Text',
overflow: TextOverflow.ellipsis
),
Expanded(
child: Container(
padding: EdgeInsets.only(left: 16, right: 16),
height: 1,
child: Container(
color: Colors.black
)
),
),
Text(
'Right Text'
)
]
)
The problem of this code is that the left text overflows if it is long like this:
The expected output is:
Wrapping the first Text widget with a Flexible can solve the overflow issue, but the output is not the same as the expected output because of the Expanded widget that fills the space between two Text widgets with a line.
How can I achieve this? Any help is highly appreciated!