介绍
flutter提供一套表单校验框架Form,可以通过Form框架一步校验所有表单,非常方便,比较常用的用法是Form+TextFormField。
Form
class Form extends StatefulWidget {
final Widget child;
...
const Form({
Key key,
@required this.child,
this.autovalidate = false,
this.onWillPop,
this.onChanged,
})
...
Form继承StatefulWidget,有一个widget 类型的child参数,证明Form是一个容器。
Form里还有一个validate方法,如下
bool validate() {
...
}
一般通过GlobalKey来访问Form中validate方法,Form的validate方法用来校验所有Form里的FormField表单,validate方法返回值是bool类型,返回true表示所有表单校验成功;返回false表示有校验失败的表单;
TextFormField
class TextFormField extends FormField<String> {
...
TextFormField({
...
FormFieldValidator<String> validator,
...
})
TextFormField继承FormField,FormField后面源码分析会讲,所有Form可统一校验的表单都必须继承FormField,可以通过FormField自定义各种各样可校验表单,TextFormField只是FormField自定义表单中的一种。
表单校验必须实现的方法为validator,定义如下:
typedef FormFieldValidator<T> = String Function(T value);
每个表单的校验规则都在validator里实现,通过返回值来判断是否校验成功。
- 返回null,表示表单校验成功
- 返回非null,表示表单校验失败,其实返回的非null还可以用来表示校验失败的错误提示信息,TextFormField内部实现就将返回的非null当成错误信息提示出来。
使用步骤
1、用Form包在所有需要校验的表单最外层,如下:
Form(
key:xxx,
child:xxx
2、将GlobalKey传给Form,用于调用Form里方法,如下:
final GlobalKey<FormState> _formKey = GlobalKey<FormState>();
Form(
key:_formKey,
child:xxx
3、将TextFormField传给Form容器,如下:
final GlobalKey<FormState> _formKey = GlobalKey<FormState>();
Form(
key:_formKey,
child:
...
TextFormField
...
4、实现对应TextFormField的校验规则 ,如下:
final GlobalKey<FormState> _formKey = GlobalKey<FormState>();
Form(
key:_formKey,
child:
...
TextFormField(
validator: (value) {
...
return xxx;
},
)
...
5、最后调用Form校验所有表单方法validate,如下:
_formKey.currentState.validate()
使用示例
void main() {
runApp(MyApp());
}
class MyApp extends StatelessWidget {
Widget build(BuildContext context) {
return MaterialApp(
home: Scaffold(
appBar: AppBar(
title: Text('系统表单'),
backgroundColor: Colors.blue,
),
body: HomeContent(),
),
);
}
}
class HomeContent extends StatefulWidget {
HomeContent({Key key}) : super(key: key);
_HomeContentState createState() => _HomeContentState();
}
class _HomeContentState extends State<HomeContent> {
final GlobalKey<FormState> _formKey = GlobalKey<FormState>();
String phoneNum;
Widget build(BuildContext context) {
return Padding(
padding: EdgeInsets.all(10),
child: Column(
children: <Widget>[
Form(
key: _formKey,
child: Column(
children: <Widget>[
TextFormField(
decoration: InputDecoration(
hintText: '手机号码',
),
validator: (value) {
RegExp reg = new RegExp(r'^\d{11}$');
if (!reg.hasMatch(value)) {
return '请输入11位手机号码';
}
return null;
},
),
TextFormField(
decoration: InputDecoration(
hintText: '用户名',
),
validator: (value) {
if (value.isEmpty) {
return '请输入用户名';
}
return null;
},
),
],
),
),
SizedBox(height: 10),
Row(
children: <Widget>[
Expanded(
child: RaisedButton(
child: Text('校验'),
onPressed: () {
//一步校验全部表单
if (_formKey.currentState.validate()) {
Scaffold.of(context).showSnackBar(SnackBar(
content: Text('校验成功...'),
));
}
},
),
)
],
),
],
),
);
}
}
使用效果
作者:HawkFlying
链接:https://www.jianshu.com/p/b5bc338b260b
来源:简书
著作权归作者所有。商业转载请联系作者获得授权,非商业转载请注明出处。