I have been solving this problem for 3 days now and can't seem to find a solution. I also tried to use ChatGPT and reading Angular documentation but no luck.
Here is a stackblits link: https://stackblitz.com/edit/angular-ivy-rdwj1n?file=src/app/users-profile/users-profile.component.html
basically, I have a FormGroup
in my parent component that I initialized with default values outside my constructor:
formUsersInformation: FormGroup = this.formBuilder.group({
profile: this.formBuilder.group({
firstname: new FormControl('', [Validators.required, Validators.minLength(2)]),
middlename: new FormControl('', [Validators.required, Validators.minLength(2)]),
lastname: new FormControl('', [Validators.required, Validators.minLength(2)]),
birthdate: new FormControl('', [Validators.required]),
civilstatus: new FormControl('', [Validators.required, Validators.minLength(2)]),
emailaddress: new FormControl('', [Validators.required, Validators.email]),
phonenumber: new FormControl('', [Validators.required, Validators.pattern('^[0-9]+$')])
}),
addresses: this.formBuilder.array([
this.formBuilder.group({
idtype: new FormControl('', [Validators.required]),
idnumber: new FormControl('', [Validators.required]),
idexpiration: new FormControl('', [Validators.required]),
idfile: new FormControl('', [Validators.required]),
})
]),
identifications: this.formBuilder.array([
this.formBuilder.group({
street: new FormControl('', [Validators.required]),
city: new FormControl('', [Validators.required]),
state: new FormControl('', [Validators.required]),
zipcode: new FormControl('', [Validators.required])
})
]),
});
then in my parent HTML I have this:
<app-users-profile
[formUsersProfile]="formUsersInformation"
(FormActionEvent)="formsAction($event)"
*ngIf="isUsersProfileVisible">
</app-users-profile>
In my Child Component I named it UsersProfileComponent
I have an @Input() decorator outside my constructor:
@Input() formUsersProfile: FormGroup = new FormGroup({});
And what I want to do is to bind formUsersInformation
profile
property in my HTML. This is my html form:
<div class="row" [formGroup]="formUsersProfile">
<div class="col-md-4 mb-4">
<label for="firstname" class="form-label">First Name</label>
<input type="text" class="form-control radius-none" formControlName="firstname" id="firstname">
</div>
</div>
but it says: ERROR Error: Cannot find control with name: 'firstname'
Also I also need to bind the other properties to my other child component such as addresses
(which is an array) for UsersAddressComponent
and identifications
for my UsersIdentificationComponent
which is also an array.
Thank you very much!
Here is a solution to your question.
https://stackblitz.com/edit/angular-ivy-gv4pnw?file=src/app/app.component.html
What you need is to use the right combination of formGroupName
, formControlName
and formArrayName
directives.
Here is the markup of resulting child component:
<div class="row" [formGroup]="formGroup">
<ng-container formGroupName="profile">
<div class="col-md-4 mb-4">
<label for="firstname" class="form-label">First Name</label>
<input
type="text"
class="form-control radius-none"
formControlName="firstname"
id="firstname"
/>
</div>
</ng-container>
<p>Addresses</p>
<ul formArrayName="addresses">
<li *ngFor="let address of addresses.controls; let i = index">
<div class="col-md-4 mb-4" [formGroupName]="i">
<label for="idtype" class="form-label">ID type</label>
<input
type="text"
class="form-control radius-none"
formControlName="idtype"
id="idtype"
/>
</div>
</li>
<button type="button" (click)="addAddress.emit()">
+ Add another address
</button>
</ul>
</div>
Everything for this question I got from reactive forms doc https://angular.io/guide/reactive-forms