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

Angular中mat-table单数据行时禁用添加图标实现方案

问题描述

我在卡片内实现了一个mat-table,通过响应式表单的添加图标添加员工联系人详情。根据业务需求,用户仅允许添加一次详情,后续只能对其进行更新或删除操作。需要实现:当表格中存在一行数据时禁用添加图标,当用户删除该行数据后重新启用该图标。曾尝试使用*ngIf来实现,但未能成功,恳请提供技术帮助。

模板代码

<div class="col">
  <div class="col">
    <div class="col mb-4">
      <div class="card">
        <div class="card-header text-center d-flex">
          <h2 class="flex-grow-1"><b>Contact Details</b></h2>
          <a
            routerLink="/employee/addEmployeeContact"
            [queryParams]="{ employeeId: employeeDetail.id }"
            matTooltip="Add Employee Contact Details"
          >
            <img
              width="30"
              height="30"
              src="https://img.icons8.com/fluency/48/add--v1.png"
              alt="create-new--v6"
            />
          </a>
        </div>

        <div style="overflow: auto">
          <table matSort mat-table [dataSource]="dataSource">
            <!--- Note that these columns can be defined in any order.
                  The actual rendered columns are set as a property on the row definition"-->

            <!-- Position Column -->

            <ng-container matColumnDef="workEmailId">
              <th mat-sort-header mat-header-cell *matHeaderCellDef>
                Work Email
              </th>
              <td mat-cell *matCellDef="let element">
                {{ element.workEmailId }}
              </td>
            </ng-container>

            <ng-container matColumnDef="personalEmailId">
              <th mat-sort-header mat-header-cell *matHeaderCellDef>
                Personal Email
              </th>
              <td mat-cell *matCellDef="let element">
                {{ element.personalEmailId }}
              </td>
            </ng-container>

            <ng-container matColumnDef="primaryMobileNo">
              <th mat-sort-header mat-header-cell *matHeaderCellDef>
                Primary Mobile No.
              </th>
              <td mat-cell *matCellDef="let element">
                {{ element.primaryMobileNo }}
              </td>
            </ng-container>

            <ng-container matColumnDef="secondaryMobileNo">
              <th mat-sort-header mat-header-cell *matHeaderCellDef>
                Secondary Mobile No.
              </th>
              <td mat-cell *matCellDef="let element">
                {{ element.secondaryMobileNo }}
              </td>
            </ng-container>

            <ng-container matColumnDef="workPhoneNo">
              <th mat-sort-header mat-header-cell *matHeaderCellDef>
                Work Phone No.
              </th>
              <td mat-cell *matCellDef="let element">
                {{ element.workPhoneNo }}
              </td>
            </ng-container>

            <ng-container matColumnDef="extensionNo">
              <th mat-sort-header mat-header-cell *matHeaderCellDef>
                Extension No.
              </th>
              <td mat-cell *matCellDef="let element">
                {{ element.extensionNo }}
              </td>
            </ng-container>

            <ng-container matColumnDef="status">
              <th mat-sort-header mat-header-cell *matHeaderCellDef>
                Status
              </th>
              <td mat-cell *matCellDef="let element">
                {{ element.status ? "Active" : "Not Active" }}
              </td>
            </ng-container>

            <ng-container matColumnDef="action">
              <th mat-header-cell *matHeaderCellDef class="text-center">
                Actions
              </th>
              <td mat-cell *matCellDef="let element">
                <div
                  style="
                    display: flex;
                    gap: 10px;
                    justify-content: center;
                  "
                >
                  <mat-icon
                    routerLink="/employee/updateEmployeeContact"
                    [queryParams]="{
                      employeeId: element.employeeId,
                      employeeContactId: element.id
                    }"
                    class="edit-icon"
                    matTooltip="Update Employee Contact"
                  >edit</mat-icon>

                  <mat-icon
                    (click)="deleteEmployeeContact(element.id)"
                    class="delete-icon"
                    matTooltip="Delete Employee Contact"
                  >delete</mat-icon>
                </div>
              </td>
            </ng-container>

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

获取数据方法

getEmployeeContact = () => {
  this.empData
    .getEmployeeContact(
      `api/Employee/EmployeeContactDetailListByEmployeeId?EmployeeId=${this.employeeId}`
    )
    .subscribe((data: any) => {
      console.log('Emp Contact Data', data);
      this.dataSource.data = data;
      this.refreshAddEmployeeContactBtn();
    });
};

删除数据方法

deleteEmployeeContact = (id: any) => {
  this.dialogService
    .openConfirmDialog(
      'Delete Branch Contact',
      'Are you sure you want to delete this Employee Contact',
      'Delete',
      'Cancel'
    )
    .afterClosed()
    .subscribe((res) => {
      if (res) {
        this.empData
          .deleteEmployeeContact(
            `api/Employee/DeleteEmployeeContactDetail?GuidEmployeeContactDetailsId=${id}`
          )
          .subscribe(() => {
            console.log('deleted');
            this.getEmployeeContact();
          });
      }
    });
};

解决方案

1. 添加状态控制变量

在组件的TypeScript代码中定义一个布尔变量,用于控制添加按钮的禁用状态:

isAddButtonDisabled = false;

2. 实现状态更新方法

补充你已经调用但未实现的refreshAddEmployeeContactBtn方法,根据数据源长度判断按钮状态:

refreshAddEmployeeContactBtn() {
  // 数据源有数据则禁用按钮,否则启用
  this.isAddButtonDisabled = this.dataSource.data.length > 0;
}

3. 修改模板中的添加按钮

更新<a>标签,添加禁用属性和样式类,确保按钮在禁用状态下无法点击且视觉上有提示:

<a
  routerLink="/employee/addEmployeeContact"
  [queryParams]="{ employeeId: employeeDetail.id }"
  matTooltip="Add Employee Contact Details"
  [class.disabled]="isAddButtonDisabled"
  [disabled]="isAddButtonDisabled"
>
  <img
    width="30"
    height="30"
    src="https://img.icons8.com/fluency/48/add--v1.png"
    alt="create-new--v6"
  />
</a>

4. 添加禁用状态样式

在组件样式文件中添加以下样式,让禁用状态更直观:

a.disabled {
  pointer-events: none;
  opacity: 0.5;
  cursor: not-allowed;
}

说明

之前用*ngIf失效大概率是因为没及时同步数据源变化后的状态。用禁用状态替代隐藏,既符合业务逻辑(用户能看到按钮但无法操作),又通过refreshAddEmployeeContactBtn确保每次数据变更后状态都会更新。


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

相关产品推荐
方舟 Agent Plan

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

最近更新时间:2026.07.04 21:35:03