Angular Material下拉框selectedCategory在ngOnInit中无法更新问题
Angular Material下拉框selectedCategory无法更新的问题排查与解决
问题现象
在ngOnInit钩子中更新Angular Material下拉框绑定值时,仅selectedCategory对应的下拉框无法正常更新;单独更新前三个下拉框(selectedCenter、selectedOrgType、selectedCategory)时一切正常,但更新全部四个下拉框时就会出现问题。
代码片段
组件ngOnInit代码
async ngOnInit() { this.isLoading = true; await this.assesmentService.fetchCenters().subscribe((data) => { this.centers = data.centers; }); await this.assesmentService.fetchDropDownOptions().subscribe((data) => { this.dropDownOptions = data.data; if (this.sessionData.length > 0) { this.selectedCenter = this.sessionData[0].loc_cd; this.handleCenterSelected().then(() => { this.selectedOrgType = this.sessionData[0].org_type; this.handleOrgSelected().then(() => { this.selectedCategory = this.sessionData[0].category_cd; this.handleCategorySelected().then(() => { this.selectedSubCategory = this.sessionData[0].category_sub_cd; this.handleSubCategorySelected() }); }); } this.isLoading = false; }); }
对应HTML代码
<div style="display: flex; align-items: center"> <div class="formDiv"> <mat-form-field appearance="fill" class="custom-mat-form-field"> <mat-label>Service Center</mat-label> <mat-select [(ngModel)]="selectedCenter" name="center" required (selectionChange)="handleCenterSelected()" > <mat-option *ngFor="let center of centers" [value]="center.loc_cd" > {{ center.loc_cd }} </mat-option> </mat-select> </mat-form-field> </div> <div class="formDiv"> <mat-form-field appearance="fill" class="custom-mat-form-field"> <mat-label>Org Type</mat-label> <mat-select [(ngModel)]="selectedOrgType" name="orgType" required (selectionChange)="handleOrgSelected()" > <mat-option *ngFor="let orgType of orgTypes" [value]="orgType.value" > {{ orgType.viewValue }} </mat-option> </mat-select> </mat-form-field> </div> <div class="formDiv"> <mat-form-field appearance="fill" class="custom-mat-form-field"> <mat-label>Category</mat-label> <mat-select class="myDropdown" [(ngModel)]="selectedCategory" [(value)]="selectedCategory" name="category" (selectionChange)="handleCategorySelected()" > <mat-option *ngFor="let category of categories" [value]="category" > {{ category }} </mat-option> </mat-select> </mat-form-field> </div> <div class="formDiv"> <mat-form-field appearance="fill" class="custom-mat-form-field"> <mat-label>Sub Category</mat-label> <mat-select [(ngModel)]="selectedSubCategory" name="category" required (selectionChange)="handleSubCategorySelected()" > <mat-option *ngFor="let subCategory of subCategory" [value]="subCategory" > {{ subCategory }} </mat-option> </mat-select> </mat-form-field> </div> <!-- [disabled]="!selectedCenter || !selectedOperation" --> </div>
问题原因与解决方法
1. 重复绑定导致的冲突(最直接原因)
Category下拉框同时使用了[(ngModel)]和[(value)]双向绑定,这两个属性功能完全重叠,会导致Angular无法正确处理值的更新逻辑,直接引发选中状态异常。
解决:删除[(value)]="selectedCategory",仅保留[(ngModel)]="selectedCategory":
<mat-select class="myDropdown" [(ngModel)]="selectedCategory" name="category" (selectionChange)="handleCategorySelected()" >
2. await用法错误,异步流程混乱
await无法直接作用于subscribe方法(subscribe返回的是Subscription对象而非Promise),原代码中的两个await根本没有起到等待异步请求完成的作用,会导致后续赋值操作可能在数据未加载完成时执行,引发顺序混乱。
解决:将Observable转为Promise,使用firstValueFrom等待请求完成:
import { firstValueFrom } from 'rxjs'; async ngOnInit() { this.isLoading = true; // 等待centers接口返回数据 const centersData = await firstValueFrom(this.assesmentService.fetchCenters()); this.centers = centersData.centers; // 等待下拉选项接口返回数据 const dropDownData = await firstValueFrom(this.assesmentService.fetchDropDownOptions()); this.dropDownOptions = dropDownData.data; if (this.sessionData.length > 0) { this.selectedCenter = this.sessionData[0].loc_cd; await this.handleCenterSelected(); this.selectedOrgType = this.sessionData[0].org_type; await this.handleOrgSelected(); this.selectedCategory = this.sessionData[0].category_cd; await this.handleCategorySelected(); this.selectedSubCategory = this.sessionData[0].category_sub_cd; await this.handleSubCategorySelected(); } this.isLoading = false; }
3. 数据匹配问题
确保this.sessionData[0].category_cd的值与categories数组中的选项类型和值完全一致:
- 比如session中存储的是数字
1,但categories数组里是字符串"1",mat-select会无法匹配到对应选项; - 检查
handleOrgSelected()方法是否正确加载了categories数组,确保设置selectedCategory时,categories已经包含对应的选项。
4. Sub Category的笔误(附带修复)
Sub Category的*ngFor循环变量和数组名重复:*ngFor="let subCategory of subCategory",会导致无法渲染选项,改为正确的数组名(比如subCategories):
<mat-option *ngFor="let subCategory of subCategories" [value]="subCategory" > {{ subCategory }} </mat-option>
内容的提问来源于stack exchange,提问作者Juan Marino
相关产品推荐
相关产品推荐

