Angular 中有两种表单:
Template-driven Forms (类似于 AngularJS 1.x 中的表单 )
Reactive Forms
Template-driven 表单的特点
使用方便
适用于简单的场景
通过 [(ngModel)] 实现数据双向绑定
自动生成 Form Model (异步)
最小化组件类的代码
不易于单元测试
Reactive 表单的特点
比较灵活
适用于复杂的场景
简化了HTML模板的代码,把验证逻辑抽离到组件类中
手动创建 Form Model (同步)
方便的跟踪表单控件值的变化
易于动态添加表单控件
易于单元测试
Template-driven vs Reactive 表单
Template-driven 表单
-
模板
Form 元素
Input 元素
数据绑定
验证规则 (属性设置,如 required)
错误消息
自动创建对应的表单模型 (如 FormGroup、FormControl)
-
组件类
属性绑定
表单操作相关的方法,如表单提交 (submit)
-
指令 (FormsModule)
ngForm
ngModel
ngModelGroup
Reactive 表单
-
模板
Form 元素
Input 元素
Form 模型绑定
-
组件类
Form 模型
验证规则
错误消息
数据模型相关属性
表单操作相关的方法,如表单提交 (submit)
-
指令 (ReactiveFormsModule)
formGroup
formControl
formControlName
formGroupName
formArrayName
表单控件的状态
-
Value Changed
pristine - 表单控件值未改变
dirty - 表单控件值已改变
-
Validity
valid - 表单控件有效
invalid - 表单控件无效
-
Visited
touched - 表单控件已被访问过
untouched - 表单控件未被访问过
HTML Form vs Template-driven Form vs Reactive Form
HTML Form
<form>
<div>
<label>
<span>用户名</span>
<input
type="text"
name="userName"
placeholder="请输入用户名">
</label>
</div>
...
<button type="submit">注册</button>
</form>
Template-driven Form
<form (ngSubmit)="save(signupForm)" #signupForm="ngForm">
<div>
<label>
<span>用户名</span>
<input type="text" name="userName"
placeholder="请输入用户名"
required minlength="3"
[(ngModel)]="user.userName"
#userName="ngModel">
</label>
<div *ngIf="userName.touched && userName.errors?.required">
用户名是必填项
</div>
<div *ngIf="userName.touched && userName.errors?.minlength">
用户名的长度必须大于3
</div>
</div>
...
<button type="submit">注册</button>
</form>
Reactive Form
<form (ngSubmit)="save()" [formGroup]="signupForm">
<div>
<label>
<span>用户名</span>
<input type="text" name="userName"
placeholder="请输入用户名"
formControlName="userName">
</label>
<div *ngIf="signupForm.get('userName').touched &&
signupForm.get('userName').hasError('required')">
用户名是必填项
</div>
<div *ngIf="signupForm.get('userName').touched &&
signupForm.get('userName').hasError('minlength')">
用户名的长度必须大于3
</div>
</div>
...
<button type="submit" [disabled]="signupForm.invalid">注册</button>
</form>
接下来我们主要来介绍一下 Reactive Form 的一些相关基础知识。
Reactive Form 简介
使用 Reactive Form
要使用 Reactive Form 需要以下几个步骤:
导入 ReactiveFormsModule
import { ReactiveFormsModule } from "@angular/forms";
在 NgModule 的
imports
属性值对应的数组中,添加ReactiveFormsModule
@NgModule({
imports: [
BrowserModule,
ReactiveFormsModule
],
})
export class AppModule { }
绑定 form 元素的
formGroup
属性
<form (ngSubmit)="save()" [formGroup]="signupForm"></form>
关联 input 元素对应的
FormControl
实例
<input type="text" name="userName" placeholder="请输入用户名"
formControlName="userName">
使用 FormGroup
创建 FormGroup 属性
创建 FormGroup 实例
创建每个 FormControl 实例
signupForm: FormGroup;
this.signupForm = new FormGroup({
userName: new FormControl('', [Validators.required, Validators.minLength(3)]),
email: new FormControl('', [Validators.required, Validators.email]),
...
});
使用 FormBuilder
要使用 FormBuilder 需要以下几个步骤:
导入 FormBuilder
注入 FormBuilder 实例
使用 FormBuilder 实例
FormBuilder 创建 Form Control 语法
方式一
this.signupForm = this.fb.group({
userName: 'semlinker',
hasAddress: false
});
方式二
this.signupForm = this.fb.group({
userName: {value: 'semlinker', disabled: true}
hasAddress: {value: true, disabled: false}
});
方式三
this.signupForm = this.fb.group({
userName: [''],
hasAddress: [{value: true, disabled: false}]
})
进阶资源
-
Angular 4.x Template Driven Forms
涉及 ngModel、[ngModel]、[(ngModel)]、ngModelGroup、Template-Driven error validation
-
Angular 4.x Template-driven Forms Demo
涉及 Template-driven 表单常用控件,如 text、radio、select (基本类型、对象)、multi select、cascading select (级联)、multi checkbox 等控件的使用
-
涉及 FormControl、FormGroup、Reactive Submit、Reactive Forms error validation、FormBuilder
-
Angular 4.x Custom Form Control
涉及 ControlValueAccessor、自定义验证规则等
-
Angular 4.x Creating Dynamic Form
涉及动态创建表单的相关内容
若想进一步阅读更多表单相关的资料,请查看 Angular 4修仙目录 - 表单章节。
**粗体** _斜体_ [链接](http://example.com) `代码` - 列表 > 引用
。你还可以使用@
来通知其他用户。