Using RichText and TextSpan in Flutter
( 393 Articles)
Every website and mobile app, more or less, contains text. In Flutter, you can display a paragraph text that has multiple different styles by using a RichText widget and a tree of TextSpan widgets in combination. The text may be on a single line or multiple lines based on the layout constraints.
In this article, we will take a look that the RichText and TextSpan widgets and walk through a few examples of implementing them in action. We’ll also explore an alternative to RichText, which is Rich.text.
Overview
A quick example
The code:
class HomePage extends StatelessWidget {
const HomePage({Key? key}) : super(key: key);
@override
Widget build(BuildContext context) {
return Scaffold(
appBar: AppBar(title: const Text('Kindacode.com')),
body: Padding(
padding: const EdgeInsets.all(25),
child: RichText(
text: const TextSpan(children: [
TextSpan(
text: 'The dog ',
style: TextStyle(
fontWeight: FontWeight.bold, color: Colors.red)),
TextSpan(
text: 'is a domesticated carnivore ',
style: TextStyle(
fontStyle: FontStyle.italic, color: Colors.purple)),
TextSpan(
text: 'of the family Canidae.',
style: TextStyle(color: Colors.green))
]),
),
));
}
}
Screenshot:

RichText Constructor
RichText({
Key? key,
required InlineSpan text,
TextAlign textAlign = TextAlign.start,
TextDirection? textDirection,
bool softWrap = true,
TextOverflow overflow = TextOverflow.clip,
double textScaleFactor = 1.0,
int? maxLines,
Locale? locale,
StrutStyle? strutStyle,
TextWidthBasis textWidthBasis = TextWidthBasis.parent,
TextHeightBehavior? textHeightBehavior,
SelectionRegistrar? selectionRegistrar,
Color? selectionColor
})
The following table describes the properties of the RichText widget:
Property | Type | Description |
---|---|---|
text (required) | InlineSpan | The text to display |
textAlign | TextAlign | Controls how the text should be aligned horizontally |
textDirection | TextDirection | Control the text direction |
textHeightBehavior | TextHeightBehavior | How the paragraph will apply TextStyle.height to the ascent of the first line and descent of the last line |
textScaleFactor | double | The number of font pixels for each logical pixel |
textWidthBasis | TextWidthBasis | Defines how to measure the width of the rendered text |
maxLines | int | Maximum number of lines for the text to span |
overflow | TextOverflow | Controls visual overflow |
softWrap | bool | Whether the text should break at soft line breaks |
strutStyle | StrutStyle | Sets minimum vertical layout metrics |
TextSpan constructor
TextSpan({
String? text,
List<InlineSpan>? children,
TextStyle? style,
GestureRecognizer? recognizer,
MouseCursor? mouseCursor,
PointerEnterEventListener? onEnter,
PointerExitEventListener? onExit,
String? semanticsLabel,
Locale? locale,
bool? spellOut
})
Description of some common used properties:
Property | Type | Description |
---|---|---|
children | List<InlineSpan> | Additional spans to include as children |
text | String | The text |
recongnizer | GestureRecognizer | A gesture recognizer that will receive events that hit this span |
semanticsLabel | String | An alternative semantics label |
style | TextStyle | Defines style for the text |
Some text not showing up?
Text displayed in a RichText widget must be explicitly styled
You may encounter one unexpected situation in which the text is not visible. In fact, text in a TextSpan is white in color by default, so it cannot be seen on a white background (Scaffold’s default background color). To avoid this, you need to specify the text color or use a background color that is different from white.
This example demonstrates invisible text that is accidentally created when using TextSpan:
class HomePage extends StatelessWidget {
const HomePage({Key? key}) : super(key: key);
@override
Widget build(BuildContext context) {
return Scaffold(
appBar: AppBar(title: const Text('Kindacode.com')),
body: Padding(
padding: const EdgeInsets.all(25),
child: RichText(
text: const TextSpan(children: [
TextSpan(
text: 'Hello',
style: TextStyle(color: Colors.red, fontSize: 30)),
TextSpan(
text: ' World',
style: TextStyle(fontSize: 30)), // this is invisible
]),
),
));
}
}
Screenshot:

RichText alternative
You can use Text.rich, a const text widget, as an alternative to RichText. It integrates with the default text style automatically.
Example
class HomePage extends StatelessWidget {
const HomePage({Key? key}) : super(key: key);
@override
Widget build(BuildContext context) {
return Scaffold(
appBar: AppBar(title: const Text('Kindacode.com')),
body: const Padding(
padding: EdgeInsets.all(25),
child: Text.rich(TextSpan(children: [
TextSpan(text: 'Hello', style: TextStyle(fontSize: 40)),
TextSpan(
text: ' World',
style: TextStyle(fontWeight: FontWeight.bold, fontSize: 40))
])),
));
}
}
Screenshot:

Text.rich constructor:
Text.rich(
InlineSpan textSpan,
{
Key? key,
TextStyle? style,
StrutStyle? strutStyle,
TextAlign? textAlign,
TextDirection? textDirection,
Locale? locale,
bool? softWrap,
TextOverflow? overflow,
double? textScaleFactor,
int? maxLines,
String? semanticsLabel,
TextWidthBasis? textWidthBasis,
TextHeightBehavior? textHeightBehavior,
Color? selectionColor
}
)
References
- RichText class (flutter.dev)
- TextSpan constructor (flutter.dev)
- Text.rich constructor (flutter.dev)
- Typography – Human Interface Guidelines (developer.apple.com)
- Typography (developer.android.com)
- Typography (material.io)
Conclusion
In this article, we went over the RichText widget and the TextSpan widget and a few examples of using them in Flutter applications. If you’d like to explore more about text stuff and other interesting things in Flutter, take a look at the following articles:
- Flutter: Making Beautiful Chat Bubbles (2 Approaches)
- Flutter: Make Text Clickable like Hyperlinks on the Web
- Flutter: Text with Read More / Read Less Buttons
- Flutter: Creating Strikethrough Text (Cross Out Text)
- Flutter Gradient Text Examples
You can also check out our Flutter category page or Dart category page for the latest tutorials and examples.
Thank you very much for this explication
You’re welcome 🔥