Flutter/Dart: RichText and TextField removes beginning spaces at display - flutter

I have a RichText Widget in Flutter where I want to print the attribute LUKETXT which is in a Modell.
The problem is, that LUKETXT is containing whitespaces at the beginning, like for example:
' *end of invoice* '
But when I want to display it, the whitespaces at the beginning where removed.
My function is:
RichText BuildText(List<OrderReceipt> OrderReceipt) {
int deflen = OrderReceipt.length;
return RichText(
text: TextSpan(
style: const TextStyle(color: Colors.black,
fontFamily: "PolarSys",fontSize: 10),
spellOut: false,
children: [
for (int i =0; i<deflen; i++)
TextSpan(
spellOut: false,
text: OrderReceipt[i].LUKETXT,
)
]
),
);
}
Just for information: PolarSys Font is a Monospace Font, that's the reason I gonna build it like that.
Does anyone know what is wrong? I already experimentet with spellOut true and false but there was no change.
Thanks..

The problem is likely with the leading whitespaces being removed by the TextSpan widget. In Flutter, the TextSpan widget is designed to remove leading whitespaces by default. To preserve the leading whitespaces, you can use a Text widget instead of TextSpan. You can wrap the Text widget inside a parent widget like a Padding or a SizedBox to add the necessary whitespaces before the text.

Related

Flutter define icon color by textstyle

I think I've hared that there is a Widget the gets a Textstyle and a list of children. The children can be Text-Widgets or Icon-Widgets and get the defining styles (and with that the color of the Icon) from that parent.
But I can't find that anywhere.
Do I remember that correctly, and if, what Widget was that?
Or am I just wrong about that?
Edit:
I thought it was this, but it don't seam to work the way I thought:
return RichText(
strutStyle: StrutStyle.fromTextStyle(TextStyle(color: Colors.white, fontWeight: FontWeight.w500)),
text: TextSpan(
children: [
TextSpan(text: "Add Object"),
WidgetSpan(child: Icon(Icons.add))
]
),
);
You can make use of the DefaultTextStyle widget which receives a TextStyle entity and will apply it to descendant Text widgets (as long as the descendant Text widgets do not have explicit styles applied: https://api.flutter.dev/flutter/widgets/DefaultTextStyle-class.html
When talking about the icons as well, there is no dedicated widget for that since you would usually define that as part of your overall theme as ThemeData (usually provided in MaterialApp)

Text widget cannot read html tags Flutter

Text widget in Flutter dose not support a special charterers like &, where sometimes this charterer comes like "first & second" from the database, or "&quot" should be ".
Text widget should read/convert these characters automatically. I have already fixed by following lines, But I need to put this solution in all Text widgets I have in my app.
Is it possible to give all Text widgets the possibility to read these special charterers directly in main function in runAPP or "MaterialApp" without putting the following lines in all Text widgets the app has?
final document = parse(htmlString);
final String parsedString = parse(document.body.text).documentElement.text;
Use this package flutter_html and try as follows:
Html(data: htmlString, style: {
"body": Style(
fontSize: FontSize(18),
color: Colors.black,
fontWeight: FontWeight.normal)
}),

How to use a TextSpan as a Widget inside VisibilityDetector

I have text in my app that I want to color differently as time goes on. I did this by using RichText widget with a separate text span for each character and a timer that will then update the the state and repaint all of the text spans appropriately. This works so long as the text isn't too long. It starts to break at around 7-10k characters text.
In order to optimize this I decided to use the VisibilityDetector library because text that isn't visible doesn't need to be colored differently. So I chunked the text and put each chunk in its own visibility detector, and when it isn't visible I just set the text using a Text widget. This works, but a single line will get cut off halfway through and start on the next line since they're separate widgets.
What I would like to do is pass the TextSpan as a child of the VisibilityDetector, but this gives the error that TextSpan is not a subtype of the type Widget. Is there any way to do what I want to do?
This is the type of widget tree I would like to have:
String myText = '';
RichText(
text: TextSpan(
children: myText.chunk().mapIndexed((chunkIndex, chunkText) {
return WidgetSpan(
child: VisibilityDetector(
onVisibilityChanged: (info) => _handleVisibilityChanged(),
child: !chunkIsVisible ?
Text(chunkText) :
TextSpan( //This breaks because its not a subtype of Widget
children: chunkText.characters.mapIndexed((charIndex, char) {
return TextSpan(
text: char,
style: _styleTextBasedOnIndex((chunkIndex * ChunkSize) + charIndex)
)
}
)
)
)
}
)
)
I think you can do this to pass the error:
String myText = '';
RichText(
text: TextSpan(
children: myText.chunk().mapIndexed((chunkIndex, chunkText) {
return WidgetSpan(
child: VisibilityDetector(
onVisibilityChanged: (info) => _handleVisibilityChanged(),
child: !chunkIsVisible ?
Text(chunkText) :
RichText(text: TextSpan( // Use another RichText
children: chunkText.characters.mapIndexed((charIndex, char) {
return TextSpan(
text: char,
style: _styleTextBasedOnIndex((chunkIndex * ChunkSize) + charIndex)
)
}
)
)
)
)
}
)
)

Colorize only a part of a TextForm text

I was wondering if there was a way to customize a TextFormField with more accuracy. I don't want to change the whole text color, but only part of it. For instance, below is the above mention TextFormField and I want to highlight "には" (ie what is between curly braces) by adding a red color. I would like to avoid creating multiple TextFormFields to do this because it will be a mess to assemble the text afterwards but I don't know if it is possible.
WARNING
I am not looking for the RichText widget since I want to customize a TextFormField Widget or any Widget with an editable text.
This Widget is used in a List so I would like not to use a "preview" widget with my input widget.
AND
I don't need a full RichTextEditor since the User should not be able to modify the color. Only parts between curly braces should automatically be colorised.
Looking forwards to see what kind of solutions you guys could come up with !
I've finally found a gist that match my request. For those who are searching an answer to my question, you seems to have to override EditableText (How to change color of particular text in a text field dynamically?). But, it's only a draft and it is not working correctly as for today. I'll try to follow this path and add my answer on this post.
EDIT:
The only thing you have to change to this answer is the following:
#override
TextSpan buildTextSpan() {
final String text = textEditingValue.text;
int textLength = text.length;
if (widget.annotations != null && textLength > 0) {
var items = getRanges();
var children = <TextSpan>[];
for (var item in items) {
if (item.range.end < textLength) {
children.add(
TextSpan(style: item.style, text: item.range.textInside(text)),
);
} else if (item.range.start <= textLength) {
children.add(
TextSpan(
style: item.style,
text: TextRange(start: item.range.start, end: text.length)
.textInside(text)),
);
}
}
return new TextSpan(style: widget.style, children: children);
}
return new TextSpan(style: widget.style, text: text);
}
}
Explanation:
You simply have to correct the buildTextSpan part. The error was raised when you delete a character because the Range could raise an exception when the range end was not meet.
This might not be exactly what you want, but may be this can help you get started in a way.
Use RichText widget.
var text = new RichText(
text: new TextSpan(
style: new TextStyle(
fontSize: 10.0,
),
children: <TextSpan>[
new TextSpan(text: 'Text1'),
new TextSpan(text: 'Text2', style: new TextStyle(),
],
),
);

Is there an easy way to find particular text built from RichText in a Flutter test?

For example, I may have one RichText in current widget tree, that looks like
RichText(
text: TextSpan(
text: 'Hello ',
style: DefaultTextStyle.of(context).style,
children: <TextSpan>[
TextSpan(text: 'bold', style: TextStyle(fontWeight: FontWeight.bold)),
TextSpan(text: ' world!'),
],
),
)
I try to use find.text('Hello bold world!') but it doesn't work because it's not a Text.
Framework solution
I have recently contributed this feature to the Flutter framework, i.e. to the built-in finders.
find.text()
You can now enable a findRichText parameter, which will then also find standalone RichText widgets:
find.text(
'Hello bold world!',
findRichText: true,
)
Simplest solution is to put a key on the RichText and read it that way.
If that's not a good fit for whatever reason, you can use find.byWidgetPredicate and pass a function that matches RichText widgets whose text.toPlainText() returns the string you want.
Here's the find.byWidgetPredicate call.
find.byWidgetPredicate((widget) => fromRichTextToPlainText(widget) == 'Hello bold world!')
Here's the fromRichTextToPlainText helper function. Pass it the RichText widget, it will return the plain text.
String fromRichTextToPlainText(final Widget widget) {
if (widget is RichText) {
if (widget.text is TextSpan) {
final buffer = StringBuffer();
(widget.text as TextSpan).computeToPlainText(buffer);
return buffer.toString();
}
}
return null;
}
I solved for this by digging into the widget a bit more manually
final richTextWidget = tester.element(richTextFinder).widget as RichText;
print(richTextWidget.text.children);
With the children, I can assert they are generated as expected