I am working on Angular 6. I have a formGroup
with a formArray
. The fields of formArray
can be added dynamically. I need to add Material Autocomplete for a form field of formArray
. It's not happening. I followed How to use mat-autocomplete (Angular Material Autocomplete) inside FormArray (Reactive Forms) this. However, it does not work. When value changes in formField
, does not trigger the function.
export interface IBrand {
BrandId: string;
BrandName: string;
}
//.......................
brandDatas: Observable<IBrand[]>[] = [];
bran: IBrand[] = [
{ "BrandId": "1234", "BrandName": "Apple" },
{ "BrandId": "12344", "BrandName": "Samsung" },
{ "BrandId": "12345", "BrandName": "Oppo" },
{ "BrandId": "12347", "BrandName": "Sony" },
{ "BrandId": "12349", "BrandName": "Panasonic" },
]
this.formGroup = this.fb.group({
PurchaseDate: new FormControl('', [Validators.required]),
BillNo: new FormControl('', [Validators.required]),
TotalCash: new FormControl(''),
Total: new FormControl(''),
ProductInformation: this.fb.array([
});
ngOnInit() {
const productInformation = this.fb.group({
ProductCategoryId: [''],
BrandId: [''],
ProductId: [''],
})
this.multipleform.push(productInformation);
this.totalValue = 0;
this.ManageNameControl(0);
}
ManageNameControl(index: number) {
var arrayControl = this.formGroup.get('ProductInformation') as FormArray;
let item = arrayControl.at(index);
this.brandDatas[index] = item.get('BrandId').valueChanges
.pipe(
startWith(''),
map(value => this._filterBrand(value))
);
}
_filterBrand(name: string): IBrand[] {
return this.bran.filter(opt =>
opt.BrandName.toLowerCase().includes(name.toLowerCase()));
}
displayBrand(brand?: IBrand): string | undefined {
return brand ? brand.BrandName : undefined;
}
Inside html
<div formArrayName="ProductInformation">
<div *ngFor="let productInformation of multipleform.controls; let i=index" [formGroupName]="i">
...
<mat-form-field fxFlex="12%">
<input [formControl]="BrandCtrl" matInput placeholder="Brand"
[matAutocomplete]="auto" formControlName="BrandId" minlength="3" />
<mat-autocomplete #auto="matAutocomplete" [displayWith]="displayBrand">
<mat-option *ngFor="let brand of brandDatas[i] | async" [value]="brand">
<span>{{brand.BrandName}}</span>
</mat-option>
</mat-autocomplete>
</mat-form-field>
...
</div>
</div>
On debugging, the ManageNameControl
function is invoked at first and when the form field is dynamically added and the valueChanges triggers at that time only. After that, valueChanges does not trigger on changing text on Brand field. How can this problem be solved? How can this sort of materail autocomplete be implemented.