我正在尝试让一个自定义的有状态小部件在flutter中工作。它被称为LetterTextForm,包含一些布局自定义和一个TextField。
我希望可以很容易地检索输入到小部件的TextField中的文本,在小部件主体中使用某种getter方法来返回TextEditingController.text
class LetterTextForm extends StatefulWidget {
LetterTextForm({@required this.label, this.prefixIcon});
final Widget prefixIcon;
final String label;
final TextEditingController controller = TextEditingController();
String get textEntered => controller.text;
@override
_LetterTextFormState createState() => _LetterTextFormState();
}
class _LetterTextFormState extends State<LetterTextForm> {
@override
void initState() {
super.initState();
}
@override
void dispose() {
controller.dispose();
super.dispose();
}
@override
Widget build(BuildContext context) {
return TextField(
controller: widget.controller,
decoration: InputDecoration(
prefixIcon: widget.prefixIcon,
labelText: widget.label,
)
);
}
}
将引发以下错误:"释放后使用了TextEditingController">
我认为问题可能是控制器不应该是最终的,所以我将控制器移到状态类中,并在状态类中创建了一个函数textCallback,用于修改小部件类中的非最终字符串。这种方式有效,但违反了小部件的不变性:
class LetterTextForm extends StatefulWidget {
LetterTextForm({@required this.label, this.prefixIcon});
final Widget prefixIcon;
final String label;
String text = '';
String get textEntered => text;
@override
_LetterTextFormState createState() => _LetterTextFormState();
}
class _LetterTextFormState extends State<LetterTextForm> {
var controller = TextEditingController();
void textCallback() {
widget.text = controller.text;
}
@override
void initState() {
super.initState();
}
@override
void dispose() {
controller.dispose();
super.dispose();
}
@override
Widget build(BuildContext context) {
return TextField(
controller: controller,
decoration: InputDecoration(
prefixIcon: widget.prefixIcon,
labelText: widget.label,
)
);
}
}
有没有一种方法可以做到这一点:1(不违反不变性,2(当用户点击Enter时不立即处理TextEditingController((?
当我去掉dispose((方法时,它就可以工作了,但这似乎会在以后导致一些性能/内存效率问题。也许我不知道我在说什么。。。
也许我应该尝试一些完全不同的东西,并将TextEditingControllers与LetterTextForm小部件的祖先放在树的更高位置,而不是在小部件内部?
创建一个ValueChanged<String>
回调成员,并在数据完成时将其回调。
class LetterTextForm{
...
final ValueChanged<String> onChanged;
...
}
class _LetterTextFormState extends ... {
final _controller = TextEditingController();
@override
void dispose() {
_controller.dispose();
super.dispose();
}
@override
Widget build(...) {
return TextField(
controller: _controller,
onSubmitted: (value) {
if (widget.onChanged != null) {
widget.onChanged(value); // returns entered value to caller
}
},
);
}
}
第页。S.如果使用TextFormField
,则不需要控制器,可以使用initialData
进行初始化。