前言
最近在利用flutter制作校园软件,需要制作一个登录界面,所以要用到Flutter中的一些表单控件,今天就来总结下flutter中的一些表单控件。 本文参考:
TextField, FormField
基本属性
先从最基础的讲起,对于TextField
就是android中的edittext
,就是一个输入框( TextField class),这个输入框常用的属性如下:
child: new TextField(
autocorrect: false, // 是否自动校正
autofocus: false, //自动获取焦点
enabled: true, // 是否启用
inputFormatters: [], //对输入的文字进行限制和校验
keyboardType: TextInputType.text, //获取焦点时,启用的键盘类型
maxLines: 2, // 输入框最大的显示行数
maxLength: 3, //允许输入的字符长度/
maxLengthEnforced: false, //是否允许输入的字符长度超过限定的字符长度
obscureText: true, // 是否隐藏输入的内容
onChanged: (newValue) {
// print(newValue); // 当输入内容变更时,如何处理
},
onSubmitted: (value) {
// print("whar"); // 当用户确定已经完成编辑时触发
},
style: new TextStyle(
color: new Color(Colors.amberAccent.green)), // 设置字体样式
textAlign: TextAlign.center, //输入的内容在水平方向如何显示
decoration: new InputDecoration(
labelText: "城市",
icon: new Icon(Icons.location_city),
border: new OutlineInputBorder(), // 边框样式
helperText: 'required',
hintText: '请选择你要投保的城市',
prefixIcon: new Icon(Icons.android),
prefixText: 'Hello'),
),
输入处理
其实对于一个输入框,我们最关心的无非就是监听输入的内容,然后输入完成后,输入框中的内容是什么,文档中写的很清楚,textfiled控件有三个回调函数:
在这里我们只需要关注onChanged
和onSubmitted
即可。
child: new TextField(
controller: _controller,
decoration: new InputDecoration(labelText: 'Your Name'),
onChanged: (val) {
print(val);
},
onSubmitted: (String v) {
print(v);
},
),
顾名思义: onChanged
事件,在输入内容发生变化的时候触发,onSubmitted
事件,则是在输入结束,点击完成的时候触发。
然而在TextFormField
中没有这两个事件,取而代之的是validator
,onSaved
,onFieldSubmitted
他们都接受三个函数,并且将其值作为参数传递到函数里面
- validator,如果开启
autovalidate: true
,那么将会自动检验输入的值,如果没有则会在表单提交的时候检验 该函数只允许返回验证失败的错误信息以及验证通过时返回null。 - onSaved, 当调用
FormState.save
方法的时候调用。 - onFieldSubmitted, 与
onSubmitted
一样,则是在输入结束,点击完成的时候触发。
编辑控制
无论是在TextField还是TextFormField中,都有一个重要的属性controller,该属性可用来对输入框内容进行控制。 先创建一个控制对象:
TextEditingController _controller = new TextEditingController();
TextEditingController _formFieldController = new TextEditingController();
为输入框初始化值以及注册一个监听事件:
@override
void initState() {
// TODO: implement initState
super.initState();
_controller.value = new TextEditingValue(text: 'Hello');
_formFieldController.addListener(() {
print('listener');
});
}
触发一个监听事件:
void _textFieldAction() {
// print(_formFieldController.selection);
// print(_formFieldController.text); //获取输入内容
print(_formFieldController.hasListeners); //判断是否注册监听事件
_formFieldController.notifyListeners(); //触发监听事件
}
Form
Flutter中的Form
组件和html中的<form></form>
的作用类似,都是起到了一个容器的作用,里面包含了TextFormField
的一个列表 下面通过一个例子说明表单的一些特性
- 布局
@override
Widget build(BuildContext context) {
// TODO: implement build
return new MaterialApp(
title: 'Flutter data',
home: new Scaffold(
appBar: new AppBar(
title: new Text('Flutter Form'),
),
floatingActionButton: new FloatingActionButton(
onPressed: _forSubmitted,
child: new Text('提交'),
),
body: new Container(
padding: const EdgeInsets.all(16.0),
child: new Form(
key: _formKey,
child: new Column(
children: <Widget>[
new TextFormField(
decoration: new InputDecoration(
labelText: 'Your Name',
),
onSaved: (val) {
_name = val;
},
),
new TextFormField(
decoration: new InputDecoration(
labelText: 'Password',
),
obscureText: true,
validator: (val) {
return val.length < 4 ? "密码长度错误" : null;
},
onSaved: (val) {
_password = val;
},
),
],
),
),
),
),
);
以上,我们使用一个Form
包裹着两个TextFormField
组件,在这里为了简便,我们只设置了一些必要的元素,先暂时忽略TextFormField
中的事件
为了获取表单的实例,我们需要设置一个全局类型的key
,通过这个key
的属性,来获取表单对象。
GlobalKey<FormState> _formKey = new GlobalKey<FormState>();
String _name;
String _password;
同时也设置了_name
,_password
两个变量来存储用户的输入值,在TextFormField
组件的onSaved
方法中,将输入框的值赋值到设定的变量中
我们通过FloatingActionButton
来触发表单提交事件,
floatingActionButton: new FloatingActionButton(
onPressed: _forSubmitted,
child: new Text('提交'),
),
在_forSubmitted
中我们使用key
的currentState
属性来获取表单的实例对象
void _forSubmitted() {
var _form = _formKey.currentState;
if (_form.validate()) {
_form.save();
print(_name);
print(_password);
}
}
对于表单对象来说,其有一些非常实用的方法比如: reset
重置表单内容 validate
, 调用TextFormField
的validator
方法 save
, 表单保存。
完整代码
import 'package:flutter/material.dart';
void main() => runApp(new HomePage());
class HomePage extends StatefulWidget {
@override
_HomePageState createState() => new _HomePageState();
}
class _HomePageState extends State<HomePage> {
GlobalKey<FormState> _formKey = new GlobalKey<FormState>();
String _name;
String _password;
void _forSubmitted() {
var _form = _formKey.currentState;
if (_form.validate()) {
_form.save();
print(_name);
print(_password);
}
}
@override
Widget build(BuildContext context) {
// TODO: implement build
return new MaterialApp(
title: 'Flutter data',
home: new Scaffold(
appBar: new AppBar(
title: new Text('Flutter Form'),
),
floatingActionButton: new FloatingActionButton(
onPressed: _forSubmitted,
child: new Text('提交'),
),
body: new Container(
padding: const EdgeInsets.all(16.0),
child: new Form(
key: _formKey,
child: new Column(
children: <Widget>[
new TextFormField(
decoration: new InputDecoration(
labelText: 'Your Name',
),
onSaved: (val) {
_name = val;
},
),
new TextFormField(
decoration: new InputDecoration(
labelText: 'Password',
),
obscureText: true,
validator: (val) {
return val.length < 4 ? "密码长度错误" : null;
},
onSaved: (val) {
_password = val;
},
),
],
),
),
),
),
);
}
}