我正在使用floatingActionButton
来增加TextForm字段。即,一旦点击按钮,字段将增加1。轻按按钮实际上增加了字段,但是对于如何获取每个生成的字段的值却感到困惑。
我的问题:
当用户在下拉列表中选择一个值时,其他生成的下拉字段中的所有值都将更改为新值。请问我该如何解决?
我想将每个生成的Grade
字段的所有数字值加在一起,并且还要将每个生成的Course Unit
字段的所有值加在一起。即,将用户生成的所有Grade
字段的值相加(求和)。请帮忙。
请参阅下面的完整代码:
import 'package:flutter/material.dart';
void main() => runApp(new MyApp());
class MyApp extends StatelessWidget {
// This widget is the root of your application.
@override
Widget build(BuildContext context) {
return new MaterialApp(
title: 'My Grade Point',
theme: new ThemeData(primarySwatch: Colors.blue,
),
home: new MyHomePage(title: 'Flutter Demo Home Page'),
);
}
}
class MyHomePage extends StatefulWidget {
MyHomePage({Key key, this.title}) : super(key: key);
final String title;
@override
_MyHomePageState createState() => new _MyHomePageState();
}
class _MyHomePageState extends State<MyHomePage> {
bool _isLoading = false;
final formKey = new GlobalKey<FormState>();
final scaffoldKey = new GlobalKey<ScaffoldState>();
String _course;
String _grade;
String _unit;
String _mygp;
String _units;
String _totalgrade;
int counter = 1;
void _submit() {
final form = formKey.currentState;
if (form.validate()) {
setState(() => _totalgrade = _grade);
form.save();
}
}
Widget buildfields(int index) {
return new Column(
children: <Widget>[
new TextFormField(
onSaved: (String value) {
setState((){
_course = value;
});
},
validator: (val) {
return val.isEmpty
? "Enter Course Title $index"
: null;
},
decoration: new InputDecoration(labelText: "Course Title"),
),
new Row(
children: <Widget>[
new Expanded(
child: new TextFormField(
onSaved: (value) {
setState((){
_grade = value;
});
},
keyboardType: TextInputType.number,
decoration: new InputDecoration(labelText: "Grade"),
),
),
new Expanded(
child: new DropdownButton<String>(
onChanged: (String value) { setState((){
_unit = value;
});
},
hint: new Text('Course Unit'),
value: _unit,
items: <String>["1", "2", "3", "4", "5"].map((String value) {
return new DropdownMenuItem<String>(
value: value,
child: new Text(value),
);
}).toList(),
),
),
],
),
],
);
}
@override
Widget build(BuildContext context) {
final Size screenSize = MediaQuery.of(context).size;
var loginBtn = new RaisedButton(
onPressed: _submit,
child: new Text("CALCULATE"),
color: Colors.primaries[0],
);
var showForm = new Container(
padding: new EdgeInsets.all(20.0),
child: new Column(
children: <Widget>[
new Expanded(child: new Form(
key: formKey,
child: new ListView.builder(
itemBuilder: (BuildContext context, int index) {
return buildfields(index); },
itemCount: counter,
scrollDirection: Axis.vertical,
),
),
),
_isLoading ? new CircularProgressIndicator() : loginBtn
],
),
);
return new Scaffold(
appBar: new AppBar(
// Here we take the value from the MyHomePage object that was created by
// the App.build method, and use it to set our appbar title.
title: new Text(_totalgrade.toString()),
),
body: showForm,
floatingActionButton: new FloatingActionButton(
onPressed: () {
setState(() {
counter++;
});
},
child: new Icon(Icons.add),
),
);
}
}
答案 0 :(得分:1)
当用户在下拉列表中选择一个值时,其他生成的下拉字段中的所有值都会更改为新的值。我该如何解决这个问题?
ListView 中的 DropdownButton
子节点同步更新的原因是它从 _unit
变量中获取其所有值。我建议使用 List<Object>
来管理 ListView 项目的数据。
即
class Course {
var title;
var grade;
var unit;
}
...
List<Course> _listCourse = [];
<块引用>
我想将每个生成的成绩字段的所有数值加在一起,并将每个生成的课程单元字段的值加在一起。即添加(总和)用户生成的所有成绩字段的值。
ListView数据在List<Course>
中管理,字段输入的数据可以在onChanged()
中设置
// Course Grade
TextFormField(
onChanged: (String value) {
setState(() {
_listCourse[index].grade = value;
});
},
)
并且可以在 foreach
循环的帮助下总结这些值。
int sumGrade = 0;
_listCourse.forEach((course) {
// Add up all Course Grade
sumGrade += num.tryParse(course.grade);
});
这是基于您共享的代码段的完整工作示例。
import 'package:flutter/material.dart';
void main() => runApp(new MyApp());
class MyApp extends StatelessWidget {
// This widget is the root of your application.
@override
Widget build(BuildContext context) {
return new MaterialApp(
title: 'My Grade Point',
theme: new ThemeData(
primarySwatch: Colors.blue,
),
home: new MyHomePage(title: 'Flutter Demo Home Page'),
);
}
}
class Course {
var title;
var grade;
var unit;
}
class MyHomePage extends StatefulWidget {
MyHomePage({Key key, this.title}) : super(key: key);
final String title;
@override
_MyHomePageState createState() => new _MyHomePageState();
}
class _MyHomePageState extends State<MyHomePage> {
bool _isLoading = false;
final formKey = new GlobalKey<FormState>();
final scaffoldKey = new GlobalKey<ScaffoldState>();
String _course;
int _grade;
String _unit;
String _mygp;
String _units;
int _totalGrade;
int counter = 1;
List<Course> _listCourse = [];
@override
void initState() {
// Initialize empty List
_listCourse.add(Course());
super.initState();
}
void _submit() {
debugPrint('List Course Length: ${_listCourse.length}');
int sumGrade = 0;
_listCourse.forEach((course) {
debugPrint('Course Title: ${course.title}');
debugPrint('Course Grade: ${course.grade}');
// Add up all Course Grade
sumGrade += num.tryParse(course.grade);
debugPrint('Course Unit: ${course.unit}');
});
final form = formKey.currentState;
if (form.validate()) {
setState(() => _totalGrade = sumGrade);
form.save();
}
}
Widget buildField(int index) {
return new Column(
children: <Widget>[
new TextFormField(
onChanged: (String value) {
setState(() {
// _course = value;
_listCourse[index].title = value;
});
},
validator: (val) {
return val.isEmpty ? "Enter Course Title $index" : null;
},
decoration: new InputDecoration(labelText: "Course Title"),
),
new Row(
children: <Widget>[
new Expanded(
child: new TextFormField(
onChanged: (value) {
setState(() {
// _grade = value;
_listCourse[index].grade = value;
});
},
keyboardType: TextInputType.number,
decoration: new InputDecoration(labelText: "Grade"),
),
),
new Expanded(
child: new DropdownButton<String>(
onChanged: (String value) {
setState(() {
// _unit = value;
_listCourse[index].unit = value;
});
},
hint: new Text('Course Unit'),
value: _listCourse[index].unit,
items: <String>["1", "2", "3", "4", "5"].map((String value) {
return new DropdownMenuItem<String>(
value: value,
child: new Text(value),
);
}).toList(),
),
),
],
),
],
);
}
@override
Widget build(BuildContext context) {
final Size screenSize = MediaQuery.of(context).size;
var loginBtn = new RaisedButton(
onPressed: _submit,
child: new Text("CALCULATE"),
color: Colors.primaries[0],
);
var showForm = new Container(
padding: new EdgeInsets.all(20.0),
child: new Column(
children: <Widget>[
new Expanded(
child: new Form(
key: formKey,
child: ListView.builder(
itemBuilder: (BuildContext context, int index) {
return buildField(index);
},
itemCount: counter,
scrollDirection: Axis.vertical,
),
),
),
_isLoading ? new CircularProgressIndicator() : loginBtn
],
),
);
return new Scaffold(
appBar: new AppBar(
title: new Text(_totalGrade.toString()),
),
body: showForm,
floatingActionButton: new FloatingActionButton(
onPressed: () {
setState(() {
// Add an empty Course object on the List
_listCourse.add(Course());
counter++;
});
},
child: new Icon(Icons.add),
),
);
}
}