FormControlNamelinkSyncs a FormControl in an existing FormGroup to a form control element by name.
The official docs describe it as: Creating form control instances manually can become repetitive when dealing with multiple forms. The FormBuilder service provides convenient methods for generating controls.
FormControl and FormGroup in AngularFormGroup is used with FormControl to track the value and validate the state of form control. In practice, FormGroup aggregates the values of each child FormControl into a single object, using each control name as the key.
FormControlName is used to sync a FormControl in an existing FormGroup to a form control element by name. Exported from: ReactiveFormsModule.
I believe you missed an important point: [formGroup]
directive in the second example. formControlName
is used together with [formGroup]
to save your form multiple dot navigations. For example:
<div>
<input type="text" [formControl]="myForm.controls.firstName"/>
<input type="text" [formControl]="myForm.controls.lastName"/>
<input type="text" [formControl]="myForm.controls.email"/>
<input type="text" [formControl]="myForm.controls.title"/>
</div>
Is equivalent to:
<div [formGroup]="myForm">
<input type="text" formControlName="firstName"/>
<input type="text" formControlName="lastName"/>
<input type="text" formControlName="email"/>
<input type="text" formControlName="title"/>
</div>
Now imagine nested FormGroups
:)
[formControl]
assigns a reference to the FormControl
instance you created to the FormControlDirective
.
formControlName
assigns a string for the forms module to look up the control by name.
If you create variables for the controls, you also don't need the .
as mentioned by Harry, but I'd also suggest to use [formGroup]
instead because with more complicated forms this can become messy.
constructor(fb: FormBuilder) {
this.fullName = new FormControl('', Validators.required);
this.gender = new FormControl('');
this.myForm = fb.group({
'fullname': this.fullName,
'gender': this.gender
});
}
There is a 3rd equivalency to the two provided in the accepted answer, which is this (not recommended):
<div [formGroup]="myForm">
<input type="text" [formControl]="firstName"/>
<input type="text" [formControl]="lastName"/>
<input type="text" [formControl]="email"/>
<input type="text" [formControl]="title"/>
</div>
Notice that we are still using the [formGroup] directive.
However, for this template to compile without error, then your component needs to declare the controls as AbstractControls and not FormControls:
myComponent.ts
firstName: AbstractControl
lastName: AbstractControl
email: AbstractControl
title: AbstractControl
However, please note that declaring AbstractControls is not recommended, so if you get the error Cannot find control with unspecified name attribute
then it is probable you have mixed the styles or have declared your controls as AbstractControls.
From the Angular docs (https://angular.io/guide/reactive-forms):
Component
@Component({
...
})
export class ProfileEditorComponent {
profileForm = new FormGroup({
firstName: new FormControl(''),
lastName: new FormControl(''),
});
}
Template
<form [formGroup]="profileForm">
<label>
First Name:
<input type="text" formControlName="firstName">
</label>
<label>
Last Name:
<input type="text" formControlName="lastName">
</label>
</form>
Note that just as the
FormGroup
contains a group of controls, the profileFormFormGroup
is bound to the form element with theFormGroup
directive, creating a communication layer between the model and the form containing the inputs. TheformControlName
input provided by theFormControlName
directive binds each individual input to the form control defined in theFormGroup
If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!
Donate Us With