I have an Angular Material dropdown menu, and I need to disable specific elements from that dropdown, based on which value is selected from another dropdown menu.
Here is the HTML for the two dropdowns:
<mat-form-field>
<mat-label>Choose an option</mat-label>
<mat-select id="lineOfBusiness" formControlName="lineOfBusiness">
<mat-option value="commercial">Commercial</mat-option>
<mat-option value="residential" >Residential</mat-option>
<mat-option value="industrial">Industrial</mat-option>
</mat-select>
</mat-form-field>
<mat-form-field>
<mat-label>Choose an option</mat-label>
<mat-select id="psv" formControlName="psv">
<mat-option value="inclinometer">Inclinometer</mat-option>
<mat-option value="heil" >Heil</mat-option>
<mat-option value="radar">Radar</mat-option>
<mat-option value="hydraulics">Hydraulics</mat-option>
<mat-option value="coretex">Coretex</mat-option>
</mat-select>
</mat-form-field>
For example, the logic would look something like this: If 'lineOfBusiness' = 'commercial', then in the 'psv' dropdown, 'radar' should be disabled.
In my form.component.ts file, I have this function, which is executing without error, but is not disabling the needed options.
disableOption(optionValue: string): void {
console.log("Disabling " + optionValue);
const psvControl = this.reactiveForm.get('psv');
if (psvControl) {
const option = psvControl.get(optionValue);
if (option) {
option.disable();
}
}
}
What am I doing wrong?
Key concept:
Get the MatSelect DOM element for psv
control via the template reference variable.
Subscribe to the lineOfBusiness
control's valueChanges
to fire the disableOption
method when the lineOfBusiness
value is changed.
Set the mat-option disabled when the value "commercial" is selected for the lineOfBusiness
control and vice versa.
import { Component, ViewChild } from '@angular/core';
import { Subject, takeUntil } from 'rxjs';
import { MatSelect } from '@angular/material/select';
private destroy$ = new Subject();
@ViewChild('psvSelect') psvSelect!: MatSelect;
ngAfterViewInit() {
this.reactiveForm.controls.lineOfBusiness.valueChanges
.pipe(takeUntil(this.destroy$))
.subscribe((value) => {
this.disableOption(value);
});
}
disableOption(optionValue: string): void {
console.log('Disabling ' + optionValue);
if (optionValue === 'commercial')
this.psvSelect.options.find((x) => x.value == 'radar')!.disabled = true;
else
this.psvSelect.options.find((x) => x.value == 'radar')!.disabled = false;
}
ngOnDestroy() {
this.destroy$.next(true);
this.destroy$.complete();
}
You need to declare the template reference variable #psvSelect
as below:
<mat-select id="psv" formControlName="psv" #psvSelect>
...
</mat-select>