Flutter中创建一个带验证的表单
原文 供参考
App中经常需要用户来输入信息,比如在登录界面输入邮箱地址和密码. 为了确保应用的安全和便捷,我们需要对用户的输入进行校验. 如果用户输入信息正确,我们可以继续后续流程.如果用户输入有误, 我们可以展示一个友好的提示信息来提示用户.
如下例子中展示了如何对一个文本输入进行校验
步骤
- 创建一个
Form
表单 并指定GlobalKey
全局标识 - 添加一个
TextFormField
文本框,并附上校验逻辑 - 创建一个按钮来校验表单,并进行提交
1. 创建一个 Form表单 并指定GlobalKey全局标识
首先我们需要创建一个 Form
组件. 该组件作为一个容器会校验多个表单域.
当我们创建表单时, 我们需要指定一个GlobalKey
. 通过它可以唯一确定一个 Form
组件, 同时允许我们在后续步骤中校验表单.
代码如下
// Define a Custom Form Widget
class MyCustomForm extends StatefulWidget {
@override
MyCustomFormState createState() {
return MyCustomFormState();
}
}
// Define a corresponding State class. This class will hold the data related to
// the form.
class MyCustomFormState extends State<MyCustomForm> {
// Create a global key that will uniquely identify the Form widget and allow
// us to validate the form
//
// Note: This is a `GlobalKey<FormState>`, not a GlobalKey<MyCustomFormState>!
final _formKey = GlobalKey<FormState>();
@override
Widget build(BuildContext context) {
// Build a Form widget using the _formKey we created above
return Form(
key: _formKey,
child: // We'll build this out in the next steps!
);
}
}
注意 使用 GlobalKey
来获取表单是一个比较推荐的做法. 而当你使用一个更复杂的组件树时, 你可以使用 Form.of
方法来访问嵌套在组件树中的表单.
2.添加一个 TextFormField 文本框,并附上校验逻辑
目前我们有了Form
表单, 但是还缺少给用户输入的文本框. 这时需要使用TextFormField
组件. 该组件提供了文本输入,并且能在校验错误时提示用户.
那么要如何校验用户输入呢? 可以使用TextFormField
中的validator
校验方法. 如果用户输入有误, validator
方法必须返回一个String
字符串来展现错误信息. 如果输入无误, 则该方法返回为空.
如下代码中, 我们会创建一个validator
校验来确保TextFormField
输入非空. 如果输入为空, 则会返回友好的提示信息.
TextFormField(
// The validator receives the text the user has typed in
validator: (value) {
if (value.isEmpty) {
return 'Please enter some text';
}
},
);
3. 创建一个按钮来校验表单,并进行提交
我们有了表单和文本框后, 我们还需要一个按钮来提交用户的输入.
当用户想要提交表单时, 我们需要校验输入是否合法. 如果是,则提示成功. 如果输入为空, 则提示报错. 代码如下:
RaisedButton(
onPressed: () {
// Validate will return true if the form is valid, or false if
// the form is invalid.
if (_formKey.currentState.validate()) {
// If the form is valid, display a snackbar. In the real world, you'd
// often want to call a server or save the information in a database
Scaffold
.of(context)
.showSnackBar(SnackBar(content: Text('Processing Data')));
}
},
child: Text('Submit'),
);
这是如何实现的?
为了校验表单, 我们需要使用第一步中创建的 _formKey
.通过 _formKey.currentState
方法来获取 FormState状态
, 该状态在 Form
构建时会由Flutter自动创建.
FormState
类包含一个validate
校验方法. 当 validate
方法被调用时,会对表单中的每个输入项执行 validator
方法. 如果都返回成功,则返回true
. 如果任何一个输入项有误,则会为每个输入项展示错误信息并返回 false
.
完整示例如下
import 'package:flutter/material.dart';
void main() => runApp(MyApp());
class MyApp extends StatelessWidget {
@override
Widget build(BuildContext context) {
final appTitle = 'Form Validation Demo';
return MaterialApp(
title: appTitle,
home: Scaffold(
appBar: AppBar(
title: Text(appTitle),
),
body: MyCustomForm(),
),
);
}
}
// Create a Form Widget
class MyCustomForm extends StatefulWidget {
@override
MyCustomFormState createState() {
return MyCustomFormState();
}
}
// Create a corresponding State class. This class will hold the data related to
// the form.
class MyCustomFormState extends State<MyCustomForm> {
// Create a global key that will uniquely identify the Form widget and allow
// us to validate the form
//
// Note: This is a GlobalKey<FormState>, not a GlobalKey<MyCustomFormState>!
final _formKey = GlobalKey<FormState>();
@override
Widget build(BuildContext context) {
// Build a Form widget using the _formKey we created above
return Form(
key: _formKey,
child: Column(
crossAxisAlignment: CrossAxisAlignment.start,
children: <Widget>[
TextFormField(
validator: (value) {
if (value.isEmpty) {
return 'Please enter some text';
}
},
),
Padding(
padding: const EdgeInsets.symmetric(vertical: 16.0),
child: RaisedButton(
onPressed: () {
// Validate will return true if the form is valid, or false if
// the form is invalid.
if (_formKey.currentState.validate()) {
// If the form is valid, we want to show a Snackbar
Scaffold.of(context)
.showSnackBar(SnackBar(content: Text('Processing Data')));
}
},
child: Text('Submit'),
),
),
],
),
);
}
}