模型驱动表单如何用于初始化控件的值,并绑定到底层数据模型?
我在Angular 2中使用单个模型驱动表单created a Plunker。有四个输入控件:controlA
,controlB
,controlC
和{{1 }}:
controlD
所有输入控件都属于同名<form novalidate
[formGroup]="form">
<input mdInput
placeholder="A"
formControlName="controlA">
<input mdInput
placeholder="B"
formControlName="controlB"
[value]="data.B">
<input mdInput
placeholder="C"
formControlName="controlC"
(input)="data.C = $event.target.value">
<input mdInput
placeholder="D"
formControlName="controlD"
[(ngModel)]="data.D">
</form>
FormGroup
,但它们各自采用不同的数据绑定方法。
form
FormControlName
并直接从基础模式获取值。FormControlName
并直接更新模型。FormControlName
和双向数据绑定语法。该组件定义FormControlName
,从createForm()
调用以创建模型驱动表单:
ngOnInit()
绑定的底层模型是一个简单的Java 具有四个属性的脚本对象,每个输入控件一个:
export class Tree implements OnInit {
data = {
A: 'Data A',
B: 'Data B',
C: 'Data C',
D: 'Data D',
};
form: FormGroup;
constructor(private _fb: FormBuilder) {}
ngOnInit() {
this.createForm();
}
private createForm() {
const suffix = ' createForm()';
this.form = this._fb.group({
controlA: [{value: this.data.A + suffix, disabled: false}],
controlB: [{value: this.data.B + suffix, disabled: false}],
controlC: [{value: this.data.C + suffix, disabled: false}],
controlD: [{value: this.data.D + suffix, disabled: false}],
});
}
}
Model Driven表单使用底层模型初始化每个表单控件,但是当控件显示来自底层模型或表单组的数据时,它会添加后缀 data = {
A: 'Data A',
B: 'Data B',
C: 'Data C',
D: 'Data D',
};
以使其显而易见。
createForm()
首先要注意的是,只有A和C显示来自FormGroup,B和D的数据显示来自主机元素上声明的绑定的数据。
接下来要注意的是,只有控件C和D再次更新模型,因为在主机元素上声明了绑定。
我想使用表单组初始化输入控件,并将该值写回底层模型。
我的示例中实现此目的的唯一配置是控件C.它从控件组初始化并更新模型:
此时我想,我一定是出错了。当然,使用FormGroup初始化并更新底层模型有一种更简单,更好的定义方法吗?
解决方案#1
使用与ngModel的双向绑定:
private createForm() {
const suffix = ' createForm()';
this.form = this._fb.group({
controlA: [{value: this.data.A + suffix, disabled: false}],
controlB: [{value: this.data.B + suffix, disabled: false}],
controlC: [{value: this.data.C + suffix, disabled: false}],
controlD: [{value: this.data.D + suffix, disabled: false}],
});
这里的问题是<input mdInput
placeholder="D"
formControlName="controlD"
[(ngModel)]="data.D">
只提供表单控件的句柄。没有必要设置值,因为值来自模型,假设不需要FormBuilder
,Validators
几乎毫无意义。
FormBuilder
解决方案2
感谢@ harry-ninh评论订阅this.form = this._fb.group({
controlD: []
});
并从更改流中更新模式。虽然这可以用于少量的表单控件 - 如果我有一个非常大的表单,可能有数百个控件,这是因为无法管理。
目前我要离开解决方案#1 - 只需使用FormGroup.valueChanges
获取组件中表单的句柄,添加使用FormGroup
来设置输入值和更新模型
虽然感觉还不好。