let's say I have the following form structure:
this.myForm = this.formBuilder.group({
date: ['', [Validators.required]],
notes: [''],
items: this.initItems()
});
initItems() {
var formArray = this.formBuilder.array([]);
for (let i = 0; i < 2; i++) {
formArray.push(this.formBuilder.group({
name: ['', [Validators.required]],
age: ['', [Validators.required]],
}));
}
return formArray;
}
and the name control supposed to be an autocomplete, how can I relate the all the name controls to an autocomplete list?
Start by creating the autocomplete panel and the options displayed inside it. Each option should be defined by a mat-option tag. Set each option's value property to whatever you'd like the value of the text input to be when that option is selected.
Binding FormArray to Template We use the formArrayName directive to bind the skills form array to the div element. Now the div and anything inside the div element is bound to the skills form array. Inside the div use ngFor to loop through each element of skills FormArray.
You just need to name the formControls inside your formArray .
I solved this by relating each name
control inside the FormArray
to a filteredOption
array:
ManageNameControl(index: number) {
var arrayControl = this.myForm.get('items') as FormArray;
this.filteredOptions[index] = arrayControl.at(index).get('name').valueChanges
.pipe(
startWith<string | User>(''),
map(value => typeof value === 'string' ? value : value.name),
map(name => name ? this._filter(name) : this.options.slice())
);
}
Then After each time I build a formgroup
inside the form Array
(create new item), I need to call the above function at the new index like this:
addNewItem() {
const controls = <FormArray>this.myForm.controls['items'];
let formGroup = this.formBuilder.group({
name: ['', [Validators.required]],
age: ['', [Validators.required]],
});
controls.push(formGroup);
// Build the account Auto Complete values
this.ManageNameControl(controls.length - 1);
}
In the .html file, we need to refer to the desired filteredOption array, we can do this by using the i
index:
<mat-option *ngFor="let option of filteredOptions[i] | async " [value]="option">
{{ option.name }}
</mat-option>
please see the detailed answer here https://stackblitz.com/edit/angular-szxkme?file=app%2Fautocomplete-display-example.ts
Update: to populate the array with a default value for a specific object, you can do it using the receive forms like this:
let formGroup = this.fb.group({
name: [{value: { name: 'Mary' } , disabled: false}, [Validators.required]],
age: ['', [Validators.required]],
});
stackblitz
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