I want to format text when we type in TextField
. For example, when I use underscores _
in the field, the characters between them should get italic.
What I want is a markdown-like text formatting to happen live in the same widget in Flutter.
RichText could help, but they're not editable. I'd need a RichTextField to for that, but something like it doesn't exist in Flutter.
My result should be like WhatsApp's message field which applies bold, italic, strikethrough, etc.
Here is the step by step instructions: Step 1: Locate the file where you have placed the TextField widget. Step 2: Inside the TextField widget, add the style parameter and assign the TextField widget. Step 3: Inside the TextField widget, add the color parameter and set the color of your choice.
Also, as you already mentioned, you need to configure an AutoFill service in the system settings. Working sample code: @override Widget build(BuildContext context) => Scaffold( appBar: AppBar( title: Text("Login"), ), body: AutofillGroup( child: Column( children: [ TextField( autofillHints: [AutofillHints.
Here's how you wrap text on overflow in Flutter:Step 1: Make sure your Text widget is inside the Row widget. Step 2: Wrap your Text widget inside the Expanded widget. Step 3: Run your app.
TextInputFormatter translates the field value into text and the text into the field value. In this article, you'll learn how to format data in TextFormField and TextField. When the user enters something into an input field.
Please see sample code on implementing the answer on an existing 'TextField'.
import 'dart:ui';
import 'package:flutter/material.dart';
final Color darkBlue = const Color.fromARGB(255, 18, 32, 47);
void main() {
runApp(MyApp());
}
class MyApp extends StatelessWidget {
@override
Widget build(BuildContext context) {
return MaterialApp(
theme: ThemeData.dark().copyWith(scaffoldBackgroundColor: darkBlue),
debugShowCheckedModeBanner: false,
home: const Scaffold(
body: Center(
child: MyWidget(),
),
),
);
}
}
class TextFieldColorizer extends TextEditingController {
final Map<String, TextStyle> map;
final Pattern pattern;
TextFieldColorizer(this.map)
: pattern = RegExp(
map.keys.map((key) {
return key;
}).join('|'),
multiLine: true);
@override
set text(String newText) {
value = value.copyWith(
text: newText,
selection: TextSelection.collapsed(offset: newText.length),
composing: TextRange.empty,
);
}
@override
TextSpan buildTextSpan({TextStyle style, bool withComposing}) {
final List<InlineSpan> children = [];
String patternMatched;
String formatText;
TextStyle myStyle;
text.splitMapJoin(
pattern,
onMatch: (Match match) {
myStyle = map[match[0]] ??
map[map.keys.firstWhere(
(e) {
bool ret = false;
RegExp(e).allMatches(text)
..forEach((element) {
if (element.group(0) == match[0]) {
patternMatched = e;
ret = true;
return true;
}
});
return ret;
},
)];
if (patternMatched == r"_(.*?)\_") {
formatText = match[0].replaceAll("_", " ");
} else if (patternMatched == r'\*(.*?)\*') {
formatText = match[0].replaceAll("*", " ");
} else if (patternMatched == "~(.*?)~") {
formatText = match[0].replaceAll("~", " ");
} else if (patternMatched == r'```(.*?)```') {
formatText = match[0].replaceAll("```", " ");
} else {
formatText = match[0];
}
children.add(TextSpan(
text: formatText,
style: style.merge(myStyle),
));
return "";
},
onNonMatch: (String text) {
children.add(TextSpan(text: text, style: style));
return "";
},
);
return TextSpan(style: style, children: children);
}
}
class MyWidget extends StatefulWidget {
const MyWidget();
_MyWidgetState createState() => _MyWidgetState();
}
class _MyWidgetState extends State<MyWidget> {
final TextEditingController _controller = TextFieldColorizer(
{
r"@.\w+": TextStyle(color: Colors.blue, shadows: kElevationToShadow[2]),
'red': const TextStyle(
color: Colors.red, decoration: TextDecoration.underline),
'green': TextStyle(color: Colors.green, shadows: kElevationToShadow[2]),
'purple': TextStyle(color: Colors.purple, shadows: kElevationToShadow[2]),
r'_(.*?)\_': TextStyle(
fontStyle: FontStyle.italic, shadows: kElevationToShadow[2]),
'~(.*?)~': TextStyle(
decoration: TextDecoration.lineThrough,
shadows: kElevationToShadow[2]),
r'\*(.*?)\*': TextStyle(
fontWeight: FontWeight.bold, shadows: kElevationToShadow[2]),
r'```(.*?)```': TextStyle(
color: Colors.yellow,
fontFeatures: [const FontFeature.tabularFigures()],
shadows: kElevationToShadow[2]),
},
);
@override
Widget build(BuildContext context) {
return Padding(
padding: const EdgeInsets.all(10),
child: TextField(
maxLines: 5,
onChanged: (text) {
final val = TextSelection.collapsed(offset: _controller.text.length);
_controller.selection = val;
},
style: const TextStyle(fontSize: 32),
controller: _controller,
),
);
}
}
If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!
Donate Us With