我在我的应用程序中使用了全屏对话框,以使用户在文本字段中输入值。这些值中有些是字符串,有些是整数。因此,我想相应地更改键盘,以使不必要的键消失。这是我的实现:
import 'package:flutter/material.dart';
import 'package:meal_tracker/model/food_model.dart';
class AddFoodDialog extends StatelessWidget {
TextEditingController nameController = TextEditingController(),
carbsController = TextEditingController(),
fatController = TextEditingController(),
proteinController = TextEditingController(),
amountController = TextEditingController();
@override
Widget build(BuildContext context) {
return Scaffold(
appBar: AppBar(
title: Text("Add Food"),
actions: <Widget>[
FlatButton(
child: Text(
"SAVE",
style: TextStyle(color: Colors.white),
),
onPressed: () {
_handleSave(context);
},
)
],
),
body: Form(
child: Padding(
padding: const EdgeInsets.all(16.0),
child: Column(
children: <Widget>[
TextFormField(
decoration: InputDecoration(labelText: "Name"),
controller: nameController,
),
TextFormField(
decoration: InputDecoration(labelText: "Carbs per 100g"),
controller: carbsController,
keyboardType: TextInputType.number,
),
TextFormField(
decoration: InputDecoration(labelText: "Fat per 100g"),
controller: fatController,
keyboardType: TextInputType.number,
),
TextFormField(
decoration: InputDecoration(labelText: "Protein per 100g"),
controller: proteinController,
keyboardType: TextInputType.number,
),
TextFormField(
decoration: InputDecoration(labelText: "Amount in g"),
controller: amountController,
keyboardType: TextInputType.number,
),
],
),
)),
);
}
void _handleSave(BuildContext context) {
print("Dialog text: " + nameController.text);
Navigator.of(context).pop(Food(
name: nameController.text,
carbsPer100g: double.parse(carbsController.text),
fatPer100g: double.parse(fatController.text),
proteinPer100g: double.parse(proteinController.text),
amount: double.parse(amountController.text)));
}
}
问题是,当我在具有TextInputType.text
的“名称”文本字段中输入内容,然后点击具有TextInputType.number
的另一个TextField时,“名称”字段将被清除没有明显的原因。反之亦然。
答案 0 :(得分:6)
我不得不将TextEditingControllers放入一个有状态的小部件中,该小部件最终确实可以工作。感谢乔纳·威廉姆斯的快速回复!
答案 1 :(得分:0)
在您的情况下,您必须声明一个StatefulWidget。如果在内部构建函数中定义了控制器,则会引起类似的问题
答案 2 :(得分:0)
TextFields值重置可能由于两个主要原因而发生
final
。如果要处理任何小部件的状态,尤其是在Dialogue(SimpleDialog)内部,请始终创建一个单独的StatefulWidget类和TextEditingController属性作为变量var
。
下面是有状态小部件的完整示例,该小部件不会在切换时重置TextFields值
class ReportDialog extends StatefulWidget {
@override
_ReportDialogState createState() => new _ReportDialogState();
}
class _ReportDialogState extends State<ReportDialog> {
var selectedConfiguration = SharedConfiguration().selectedConfiguration;
var titleTextField = TextEditingController();
var descriptionTextField = TextEditingController();
@override
Widget build(BuildContext context) {
final reportButton = ReusableWidgets.getButton('REPORT',
Colors.redAccent, Colors.white, reportButtonAction, context, 46);
return SimpleDialog(
contentPadding: EdgeInsets.fromLTRB(20, 10, 20, 10),
children: <Widget>[
new TextField(
controller: titleTextField,
decoration: new InputDecoration(
border: new OutlineInputBorder(),
hintText: 'Title',
),
maxLines: 1,
),
SizedBox(height: 8.0),
new TextField(
controller: descriptionTextField,
decoration: new InputDecoration(
border: new OutlineInputBorder(),
hintText: 'Add your message here...',
helperText: 'Keep it short, this is just a demo.',
),
maxLines: 6,
),
SizedBox(height: 20.0),
reportButton
],
);
}
void reportButtonAction() {
Navigator.of(context).pop();
}
}
希望它有用:)