继Angular学习笔记44:响应式表单-获取两层FormGroup嵌套值得变化和两层FormGroup赋值,可以在FormGroup中嵌套FormGroup了。但是在项目中,会经常遇到类似于Array一样的表单。
比如:在UserInfoComponent中,增加一个电话号码属性,需要注意的是,电话号码这个属性,有可能是多个,所以这里要用到的是FormArray。
在FormGroup中增加phone实例
- 在FormGroup中增加一个FormArray的实例。
修改 UserInfoComponent 的类文件的validateForm属性;
validateForm = new FormGroup({
name: new FormControl(null, [Validators.required]),
age: new FormControl(null, [Validators.required]),
email: new FormControl(null, [Validators.required]),
phone: new FormArray([new FormControl(null)]),
address: new FormGroup({
area: new FormControl(null, [Validators.required]),
street: new FormControl(null, [Validators.required]),
houseId: new FormControl(null, [Validators.required]),
})
});
在这里,在FormGroup中增加了一个phone的实例,不过这个实例是一个FormArray,在这个FormArray中,先塞进一个元素,元素是一个FormControl。
简单点理解,FormArray就是一个元素为:Controls 的数组。 这里的 Controls 既可以是FormControl,也可以是又一个FormGroup。
- 将这个FormArray展现在模板中。
a. 第一种写法:使用validateForm.controls[‘phone’].controls
<nz-form-item>
<nz-form-label nzSpan="3" nz-col>电话号码</nz-form-label>
<nz-form-control nzSpan="8" nz-col>
<nz-row formArrayName="phone"
*ngFor="let phone of validateForm.controls['phone'].controls;let phoneIndex = index">
<nz-form-control nzSpan="18" nz-col>
<input nz-input type="text" placeholder="请输入电话号码~" [formControlName]="phoneIndex">
</nz-form-control>
</nz-row>
</nz-form-control>
</nz-form-item>
b. 第二种写法:使用get() 方法
在类文件中增加一个get();
get phoneArray() {
return this.validateForm.get('phone') as FormArray;
}
修改模板文件
<nz-form-item>
<nz-form-label nzSpan="3" nz-col>电话号码</nz-form-label>
<nz-form-control nzSpan="8" nz-col>
<nz-row formArrayName="phone"
*ngFor="let phone of phoneArray.controls;let phoneIndex = index">
<nz-form-control nzSpan="18" nz-col>
<input nz-input type="text" placeholder="请输入电话号码~" [formControlName]="phoneIndex">
</nz-form-control>
</nz-row>
</nz-form-control>
</nz-form-item>
保存运行:
会发现在validateForm.value这个对象中,phone这个属性的类型为一个数组。这个时候,就在控件中输入数据,会发现输入的数据,实时的显示到了数组的元素中。
动态的增加、减少FormArray中的元素。
在这里,通过两个按钮,通过一个增加按钮,根据用户需要,添加元素到FormArray中,另一个按钮是在每一个元素的后面,用户通过点击这个按钮,删除当前这个元素。
修改模板文件,增加两个按钮
<nz-form-item>
<nz-form-label nzSpan="3" nz-col>电话号码</nz-form-label>
<nz-form-control nzSpan="8" nz-col>
<nz-row formArrayName="phone"
*ngFor="let phone of phoneArray.controls;let phoneIndex = index">
<nz-form-control nzSpan="18" nz-col>
<input nz-input type="text" placeholder="请输入电话号码~" [formControlName]="phoneIndex">
</nz-form-control>
<nz-form-control nzOffset="1" nzSpan="3" nz-col>
<button nz-button (click)="removePhone(phoneIndex)">删除</button>
</nz-form-control>
</nz-row>
</nz-form-control>
<nz-form-control nzSpan="2">
<button nz-button (click)="addPhone()">增加</button>
</nz-form-control>
</nz-form-item>
在类文件中实现两个按钮绑定的的方法:
对应上面a写法,实现方法
addPhone() {
(this.validateForm.get('phone') as FormArray).push(new FormControl(null));
}
removePhone(index) {
(this.validateForm.get('phone') as FormArray).removeAt(index);
}
对应上面b写法,实现方法:
addPhone() {
// (this.validateForm.get('phone') as FormArray).push(new FormControl(null));
this.phoneArray.push(new FormControl(null));
}
removePhone(index) {
// (this.validateForm.get('phone') as FormArray).removeAt(index);
this.phoneArray.removeAt(index);
}
保存运行:
就会发现,随着增加按钮上事件的触发,phone所对应的数组中的元素也随之增加。
为这个FormArray赋值
假设有两个电话号码13800000000、13800000011需要赋值给某个userInfo的phone中。
在之前的赋值按钮所绑定的方法中,增加对phone实例的赋值操作,修改类文件中的patchValue()方法。
先用patchValue()方法试一试:
public patchValue() {
this.phoneArray.patchValue(['13800000000', '13800000011']);
}
此时会发现虽然有两个phone需要赋值,但是只在控件中创建了一个。
但是点击增加一个组件以后,再次赋值,会发现,这两个值都赋值成功了。
所以,在这里考虑换一种方式赋值。使用下面这种方式对其进行赋值。
public patchValue() {
const setValue = ['13800000000', '13800000011'];
setValue.forEach(value => {
this.phoneArray.push(new FormControl(value));
});
}
在这里直接将要赋值的数据直接放在FormControl中,再将这个FormControl实例push到FormArray中。
保存运行,可以看到如下: