正如Angular documentation所说,我们可以在表单中使用formControlName
:
<h2>Hero Detail</h2>
<h3><i>FormControl in a FormGroup</i></h3>
<form [formGroup]="heroForm" novalidate>
<div class="form-group">
<label class="center-block">Name:
<input class="form-control" formControlName="name">
</label>
</div>
</form>
正如他们所说......
没有父FormGroup,[formControl] =“name”之前工作,因为该指令可以单独使用,也就是说,它不在FormGroup中工作。对于父FormGroup,名称输入需要语法formControlName = name才能与类中的正确FormControl相关联。此语法告诉Angular查找父FormGroup,在本例中为heroForm,然后在该组内查找名为name的FormControl。
无论如何,几个月前我曾this要求找出formControlName
和[formControl]
之间的区别。
现在我的问题是:如何使用formControlName
嵌套的FormGroups?
例如,如果我有以下表单结构:
this.myForm = fb.group({
'fullname': ['', Validators.required],
'gender': [],
'address': fb.group({
'street': [''],
'houseNumber': [''],
'postalCode': ['']
})
});
使用formControlName
将“street”(或“houseNumber”或“postalCode”)绑定到相关HTML元素的正确方法是什么?
答案 0 :(得分:41)
你可以使用Form组,它基本上是一个控件集合(控件意味着你的html表单中给出的字段)在你的typescript语法中定义,并使用formControlName指令绑定到你的HTML元素,例如
this.myForm = fb.group({
'fullname': ['', Validators.required],
'gender': [],
'address': fb.group({
'street': [''],
'houseNumber': [''],
'postalCode': ['']
})
});
模板:
<form [formGroup]="myForm" >
<div class="form-group">
<label for="fullname">Username</label>
<input type="text" id="username" formControlName="fullname" class="form-control">
</div>
<div class="radio" *ngFor="let gender of genders">
<label>
<input type="radio" formControlName="gender" [value]="gender">{{ gender }} </label>
</div>
<div formGroupName="address">
<div class="form-group">
<label for="street">Username</label>
<input type="text" id="username" value="street" formControlName="street" class="form-control">
</div>
<div class="form-group">
<label for="houseNumber">Username</label>
<input type="text" id="username" value="street" formControlName="houseNumber" class="form-control">
</div>
<div class="form-group">
<label for="postalCode">Username</label>
<input type="text" id="username" value="street" formControlName="postalCode" class="form-control">
</div>
</div>
</form>
formGroup可以由嵌套的formGroup组成,层次结构可以继续,但在访问该值时它非常简单。
答案 1 :(得分:11)
确实如此。查看 formGroupName
this.myForm = fb.group({
'fullname': ['', Validators.required],
'gender': [],
'address': fb.group({
'street': [''],
'houseNumber': [''],
'postalCode': ['']
})
});
<form [formGroup]="myForm" >
<div class="form-group">
<label for="fullname">Username</label>
<input type="text" id="username" formControlName="fullname" class="form-control">
</div>
<div class="radio" *ngFor="let gender of genders">
<label>
<input type="radio" formControlName="gender" [value]="gender">{{ gender }} </label>
</div>
<div formGroupName="address">
<div class="form-group">
<label for="street">Username</label>
<input type="text" id="username" value="street" formControlName="street" class="form-control">
</div>
<div class="form-group">
<label for="houseNumber">Username</label>
<input type="text" id="username" value="street" formControlName="houseNumber" class="form-control">
</div>
<div class="form-group">
<label for="postalCode">Username</label>
<input type="text" id="username" value="street" formControlName="postalCode" class="form-control">
</div>
</div>
</form>
答案 2 :(得分:8)
tl; dr:
您可以将表单分解为使用嵌套的 formgroups 的组件,并且 formcontrolname 可以正常使用。
由于通常使用嵌套的Formgroups来指定表单的各个部分,因此我倾向于使用的方法是将其分解为组件,并将嵌套的Formgroup作为输入参数传递给这些组件。 因此,在您的情况下,我将有一个以表单组为参数的 address 组件:
<app-address [formGroup]="myForm.get('address')"></app-address
在该组件内部,我只有一个@Input()formGroup,它将用于html中:
<div [formGroup]="formGroup">
....
那样,您可以像平常一样显式引用控件名称,因为它是此表单组的一部分。
此外,请记住,表单是作为参考传递的。您的更改将在父组件的myForm元素中说明,并且如果您需要访问不在表单组中的表单部分(验证,更改检测等),则可以始终将整个表单传递下来,而仅将表单组定义为明确引用内部组:
<div [formGroup]="formGroup.get('adress')">
(假设您传递的整个表单对象是
祝您编程愉快!
答案 3 :(得分:0)
我在 Angular 10 中遇到了一个问题。 我有一个“父”表单组“表单”,他有几个依赖组:“公司”,同时“公司”有两个 “孩子”与另一个组,msgAccounts 和 socialMedia。 当我填写表格并提交时,在后端一切正常,我可以看到这些数据是如何存储在数据库中的 正确,但是当我收到此 json 时,我无法显示数据 在控件中的“company.msgAccounts”和“company.socialMedia”中 (输入)。这是我从服务器得到的:
{
name:'',
active: '',
........
company:{
msgAccounts:{line: "@linedemo", whatsapp: "0325554244"},
socialMedia: {fb: '', tw: '', is: ''}
}
..........
}
this.forma = this.fb.group( {
siteName : [ '', [Validators.required, Validators.minLength(5)]],
siteEmail : [ '', [Validators.required, Validators.minLength(5)]],
// defaultLocation: [ '', [Validators.required, Validators.minLength(10)]],
active : [ true, [Validators.required, Validators.minLength(5)]],
mainLanguage: ['' , [Validators.required, Validators.minLength(2)]],
company: this.fb.group({
name: [''],
address: [''],
phone: [''],
msgAccounts: this.fb.group({
line: [],
whatsapp: []
}),
socialMedia: this.fb.group({
fb: [],
is: [],
tw: []
})
})
});
And the html: (Sorry about the indentation, when it was not easy using this editor, and I just pasted a part of the code in order to do it as shorter as possible).
<mat-tab-group>
<mat-tab label="settings">
<form autocomplete="off" >
<ng-template ng-template matTabContent>
<mat-tab-group [formGroup]="forma">
<mat-tab label="global">
// All this fields have are fine
</mat-tab>
<mat-tab formGroupName="company" label="company">
<div class="card">
<div class="card-header" id="headingTwo">
<h5 class="mb-0">Details</h5>
</div>
<div id="company-details">
<div class="form-group row">
<div class="col-sm-3">
<input
type="text"
class="form-control"
id="name"
name="name"
placeholder="Company name"
formControlName=name>
</div>
</div>
<div class="form-group row" formGroupName="msgAccounts">
<div class="col-sm-6">
<input
type="text"
class="form-control"
id="line"
name="line"
placeholder="line"
formControlName=line>
</div>
<div class="col-sm-6">
<input
type="text"
class="form-control"
id="whatsapp"
name="whatsapp"
placeholder="whatsapp"
formControlName=whatsapp>
</div>
</div>
<div class="form-group row" formGroupName="socialMedia" >
<div class="col-sm-6">
<input
type="text"
class="form-control"
id="is"
name="is"
placeholder="Is"
formControlName=is>
</div>
</div>
</div>
</div>
</mat-tab>
</mat-tab-group>
<div class="form-group row">
<div class="col-sm-10">
<button type="submit"
(click)="saveConfig()">Save</button>
</div>
</div>
</ng-template>
</form>
</mat-tab>
</mat-tab-group>