You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

Angular Material表格每行实现双下拉框联动功能求助

Angular Material表格行内下拉框联动实现

核心思路

每行维护独立的选中状态,根据当前行第一个下拉框的选中值,动态过滤第二个下拉框的可选选项,数据从后端动态获取。


1. 组件TypeScript代码

先定义数据结构,确保主、子选项通过关联ID绑定,表格每行数据包含独立的选中状态:

import { Component, OnInit } from '@angular/core';
import { MatTableDataSource } from '@angular/material/table';
import { Observable, of } from 'rxjs';
import { map } from 'rxjs/operators';

// 主选项接口(对应第一个下拉框)
interface MainOption {
  id: string;
  label: string;
}

// 子选项接口(对应第二个下拉框,关联主选项ID)
interface SubOption {
  id: string;
  label: string;
  mainOptionId: string;
}

// 表格每行的数据结构
interface TableRow {
  id: number;
  selectedMainId: string;
  selectedSubId: string;
}

@Component({
  selector: 'app-linked-select-table',
  templateUrl: './linked-select-table.component.html',
  styleUrls: ['./linked-select-table.component.css']
})
export class LinkedSelectTableComponent implements OnInit {
  // 从数据库获取的主选项(实际项目替换为HTTP请求)
  mainOptions$: Observable<MainOption[]>;
  // 从数据库获取的所有子选项(实际项目替换为HTTP请求)
  allSubOptions$: Observable<SubOption[]>;
  // 表格数据源(实际项目可从接口获取)
  dataSource = new MatTableDataSource<TableRow>([
    { id: 1, selectedMainId: '', selectedSubId: '' },
    { id: 2, selectedMainId: '', selectedSubId: '' }
  ]);
  // 表格列定义
  displayedColumns: string[] = ['id', 'mainSelect', 'subSelect'];

  ngOnInit(): void {
    // 模拟从数据库获取主选项数据
    this.mainOptions$ = of([
      { id: 'A', label: '选项A' },
      { id: 'B', label: '选项B' }
    ]);
    // 模拟从数据库获取子选项数据
    this.allSubOptions$ = of([
      { id: '1', label: '子项1', mainOptionId: 'A' },
      { id: '2', label: '子项2', mainOptionId: 'A' },
      { id: '3', label: '子项3', mainOptionId: 'A' },
      { id: '4', label: '子项4', mainOptionId: 'B' },
      { id: '5', label: '子项5', mainOptionId: 'B' },
      { id: '6', label: '子项6', mainOptionId: 'B' }
    ]);
  }

  // 根据当前行的主选项选中值,过滤子选项
  getFilteredSubOptions(row: TableRow): Observable<SubOption[]> {
    return this.allSubOptions$.pipe(
      map(subOptions => subOptions.filter(opt => opt.mainOptionId === row.selectedMainId))
    );
  }
}

2. 模板HTML代码

使用Angular Material表格组件,为每行渲染独立的下拉框,通过async管道处理异步数据:

<table mat-table [dataSource]="dataSource" class="mat-elevation-z8">
  <!-- ID列 -->
  <ng-container matColumnDef="id">
    <th mat-header-cell *matHeaderCellDef> 行ID </th>
    <td mat-cell *matCellDef="let row"> {{row.id}} </td>
  </ng-container>

  <!-- 主下拉框列 -->
  <ng-container matColumnDef="mainSelect">
    <th mat-header-cell *matHeaderCellDef> 主选项 </th>
    <td mat-cell *matCellDef="let row">
      <mat-select [(value)]="row.selectedMainId" placeholder="选择主选项">
        <mat-option *ngFor="let mainOpt of mainOptions$ | async" [value]="mainOpt.id">
          {{mainOpt.label}}
        </mat-option>
      </mat-select>
    </td>
  </ng-container>

  <!-- 子下拉框列(联动过滤) -->
  <ng-container matColumnDef="subSelect">
    <th mat-header-cell *matHeaderCellDef> 子选项 </th>
    <td mat-cell *matCellDef="let row">
      <mat-select 
        [(value)]="row.selectedSubId" 
        placeholder="选择子选项" 
        [disabled]="!row.selectedMainId">
        <mat-option *ngFor="let subOpt of getFilteredSubOptions(row) | async" [value]="subOpt.id">
          {{subOpt.label}}
        </mat-option>
      </mat-select>
    </td>
  </ng-container>

  <tr mat-header-row *matHeaderRowDef="displayedColumns"></tr>
  <tr mat-row *matRowDef="let row; columns: displayedColumns;"></tr>
</table>

3. 模块导入配置

确保在你的Angular模块中导入所需的Material组件模块:

import { NgModule } from '@angular/core';
import { BrowserModule } from '@angular/platform-browser';
import { BrowserAnimationsModule } from '@angular/platform-browser/animations';
import { MatTableModule } from '@angular/material/table';
import { MatSelectModule } from '@angular/material/select';
import { MatOptionModule } from '@angular/material/core';
import { ReactiveFormsModule } from '@angular/forms';

import { LinkedSelectTableComponent } from './linked-select-table.component';

@NgModule({
  declarations: [LinkedSelectTableComponent],
  imports: [
    BrowserModule,
    BrowserAnimationsModule,
    MatTableModule,
    MatSelectModule,
    MatOptionModule,
    ReactiveFormsModule
  ],
  exports: [LinkedSelectTableComponent]
})
export class LinkedSelectTableModule { }

关键说明

  • 行独立联动:每行的selectedMainId是独立变量,触发getFilteredSubOptions时仅过滤当前行的子选项,互不干扰
  • 异步数据处理:使用Observable配合async管道,自动处理数据订阅与销毁,避免内存泄漏
  • 后端数据适配:将示例中的of()替换为实际的HTTP请求即可,比如this.http.get<MainOption[]>('/api/main-options')
  • 用户体验优化:子下拉框在未选择主选项时禁用,避免无效操作

内容的提问来源于stack exchange,提问作者npiccone

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.06.13 03:50:01