如何解决TextField 和 DatePicker 提供空值
我正在尝试制作一个 todoApp,在我的添加屏幕中有一个用于任务标题的文本字段和一个用于任务日期的 DatePicker。我认为代码中一切正常,因为没有任何错误,但是当我单击“添加”按钮时,它会创建一个带有空标题和空日期的 TaskTile。我调试了代码,似乎我在 Provider 中使用 Add Button 提供的值是空的。就像我输入的内容被删除,我在日期选择器中选择的内容被删除。这是我的 AddScreen 的代码。
import 'package:Flutter/material.dart';
import 'package:provider/provider.dart';
import 'task_data.dart';
import 'package:Flutter/cupertino.dart';
import 'package:intl/intl.dart';
class AddTaskScreen extends StatelessWidget {
@override
Widget build(BuildContext context) {
String newTaskTitle;
DateTime _chosenDateTime;
DateFormat dateFormat = DateFormat("yyyy-MM-dd HH:mm:ss");
String formatedDate;
void _showDatePicker(ctx) {
showCupertinoModalPopup(
context: ctx,builder: (_) => Container(
height: 500,color: Color.fromARGB(255,255,255),child: Column(
children: [
Container(
height: 400,child: CupertinoDatePicker(
initialDateTime: DateTime.Now(),onDateTimeChanged: (val) {
// setState(() {
// _chosenDateTime = val;
// });
_chosenDateTime = val;
formatedDate = dateFormat.format(_chosenDateTime);
// print('this is the selected date $formatedDate');
// print(_chosenDateTime);
}),),// Close the modal
CupertinoButton(
child: Text('OK'),onpressed: () => Navigator.of(ctx).pop(),)
],));
}
return Container(
color: Color(0xff000014),child: Container(
padding: EdgeInsets.all(20.0),decoration: Boxdecoration(
color: Color(0xFF282D3A),borderRadius: BorderRadius.only(
topLeft: Radius.circular(20.0),topRight: Radius.circular(20.0),child: Column(
crossAxisAlignment: CrossAxisAlignment.stretch,children: <Widget>[
Text(
'Add Task',textAlign: TextAlign.center,style: TextStyle(
fontSize: 30.0,color: Colors.purple.shade400,TextField(
decoration: Inputdecoration(
border: InputBorder.none,style: TextStyle(color: Colors.white),autofocus: true,onChanged: (newText) {
newTaskTitle = newText;
},Container(
child: CupertinoButton(
padding: EdgeInsetsDirectional.zero,child: Text('Select a date'),onpressed: () => _showDatePicker(context),FlatButton(
child: Text(
'Add',style: TextStyle(
color: Colors.white,onpressed: () {
//print('newtasktile is $newTaskTitle et formateddate is $formatedDate');// here the two //values are null when printed
Provider.of<TaskData>(context,listen: false )
.addTask(newTaskTitle,formatedDate);
Navigator.pop(context);
},],);
}
}
如果您有任何建议,请告诉我。 谢谢。
解决方法
首先,为了方便使用TextField
的值,应该使用TextEditingController
。要在选择日期时间后获取值,您可以从 Dialog
方法返回一个值,然后将该值发送到 Stream
工作代码(我正在创建一个带有简单 StreamController
的简单 UI 来演示):
// TaskData class
class TaskData {
final StreamController _controller =
StreamController<Map<String,dynamic>>();
Stream<Map<String,dynamic>> get taskStream => _controller.stream;
addTask(String title,String date) {
_controller.add({'title': title,'date': date});
}
}
// AddTask screen
class AddTaskScreen extends StatefulWidget {
@override
_AddTaskScreenState createState() => _AddTaskScreenState();
}
class _AddTaskScreenState extends State<AddTaskScreen> {
final _textController = TextEditingController();
DateFormat dateFormat = DateFormat("yyyy-MM-dd HH:mm:ss");
String chosenDate;
Future<String> _showDatePicker(ctx) async {
var formatedDate = DateTime.now();
return showCupertinoModalPopup(
context: ctx,builder: (_) => Container(
height: 500,color: Color.fromARGB(255,255,255),child: Column(
children: [
Container(
height: 400,child: CupertinoDatePicker(
initialDateTime: DateTime.now(),onDateTimeChanged: (val) {
formatedDate = val;
}),),// Close the modal
CupertinoButton(
child: Text('OK'),// Return the formatted date here
onPressed: () => Navigator.of(ctx)
.pop(dateFormat.format(formatedDate)),)
],);
}
@override
Widget build(BuildContext context) {
return Scaffold(
body: Container(
// ... other lines
child: Column(
// ... other lines
TextField(
// Use the _textController here
controller: _textController,decoration: InputDecoration(
border: InputBorder.none,style: TextStyle(color: Colors.white),autofocus: true,textAlign: TextAlign.center,Container(
child: CupertinoButton(
padding: EdgeInsetsDirectional.zero,child: Text('Select a date'),onPressed: () async {
// Wait for the return value
chosenDate = await _showDatePicker(context);
},FlatButton(
child: Text(
'Add',style: TextStyle(
color: Colors.white,color: Colors.purple.shade400,onPressed: () {
Provider.of<TaskData>(context,listen: false)
.addTask(_textController.text,chosenDate);
Navigator.pop(context);
},],);
}
}
// Main UI Screen
class SomeScreen extends StatefulWidget {
@override
_SomeScreenState createState() => _SomeScreenState();
}
class _SomeScreenState extends State<SomeScreen> {
@override
Widget build(BuildContext context) {
return Scaffold(
body: Container(
child: Center(
child: Column(
mainAxisAlignment: MainAxisAlignment.center,children: [
FlatButton(
onPressed: () async {
await showDialog(
context: context,builder: (context) => AddTaskScreen());
setState(() {});
},child: Text('Add Task')),Container(
child: StreamBuilder<Map<String,dynamic>>(
initialData: {},stream: Provider.of<TaskData>(context).taskStream,builder: (context,snapshot) {
if (!snapshot.hasData) return Container();
return Column(
children: [
Text(
'${snapshot.data['title']} | ${snapshot.data['date']}'),);
},)),);
}
}
版权声明:本文内容由互联网用户自发贡献,该文观点与技术仅代表作者本人。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如发现本站有涉嫌侵权/违法违规的内容, 请发送邮件至 dio@foxmail.com 举报,一经查实,本站将立刻删除。