如何在垫子桌子上使用滑动拨动开关?

时间:2019-09-28 09:19:52

标签: angular typescript angular-material mat-table

我有一个mat-table,供3个不同角色的用户查看。 该表有多个列;列之一是active(一个布尔值,它控制帐户的激活和停用)。我想使用同一表(在另一列)中的开关来切换该值,但前提是用户是管理员。

我已经通过引导表通过以下方式实现了这一点:

<table class="table table-striped">
    <thead>
        <tr>
            <th *ngIf="isAdmin(currentUser)" (click)="sortByAccountStatus()">
                <a>Deactivate/Activate</a>
                <a class="sort-by"></a>
            </th>
        </tr>
    </thead>
    <tbody>
        <tr *ngFor="let chartOfAccounts of accountList.reverse();" [hidden]="currentUser.role !== '1'">
            <td [hidden]="!chartOfAccounts.accountActive">
                <a (click)="deactivateAccount(chartOfAccounts)" class="text-danger">Deactivate</a>
            </td>
            <td [hidden]="chartOfAccounts.accountActive">
                <a (click)="activateAccount(chartOfAccounts)" class="text-danger">Activate</a>
            </td>
        </tr>
    </tbody>

    <tbody>
        <tr *ngFor="let chartOfAccounts of accountList" [hidden]="currentUser.role === '1'">
            <td>{{accountActiveStatus(chartOfAccounts.accountActive)}}</td>
        </tr>
    </tbody>
</table>

上面的代码将在表中添加一列,管理员可以根据布尔值单击激活或停用。这些操作在组件中实现。

使用mat-table,我得到了布尔active列。

<ng-container matColumnDef="accountActive">
    <mat-header-cell *matHeaderCellDef mat-sort-header>Active</mat-header-cell>
    <mat-cell *matCellDef="let chartOfAccounts"> {{chartOfAccounts.accountActive}} </mat-cell>
</ng-container>

我的目标是创建另一列,以像这样从truefalse来回切换

<ng-container matColumnDef="activation">
    <mat-header-cell *matHeaderCellDef mat-sort-header>Activate/Deactivate</mat-header-cell>
    <mat-cell *matCellDef="let chartOfAccounts" [hidden]="!chartOfAccounts.accountActive">
        <a (click)="deactivateAccount(chartOfAccounts)" class="text-danger">Deactivate</a>
    </mat-cell>
    <mat-cell *matCellDef="let chartOfAccounts" [hidden]="chartOfAccounts.accountActive">
          <a (click)="activateAccount(chartOfAccounts)" class="text-danger">Deactivate</a>
    </mat-cell>
</ng-container>

这不起作用,并且产生奇怪的结果,当关闭切换开关时,无法再次打开它,链接消失,并且切换列也消失了。这是屏幕截图。

screenshot

每当布尔值切换到false时,布尔值就会推到表的右侧

已更新:

这是一个stackblitz示例。切换不起作用,但基本上,当您单击切换时,active的值应在truefalse之间切换,具体取决于切换是打开还是关闭。

2 个答案:

答案 0 :(得分:0)

您的代码无法正常工作的原因是,您不能在mat-cell中使用两个mat-column。第二个将被完全忽略。这就是您的表被弄乱的原因,因为在某些单元格上hidden隐藏了该列中存在的唯一cell(因为第二个单元格不在图片内)。

您不应为此使用两个单独的单元格。您希望Activate / Deactivate出现在同一单元格中。因此,除了在hidden上使用mat-cell之外,在锚标记上使用ngIf来有条件地显示Activate / Deactivate

<ng-container matColumnDef="activation">
    <mat-header-cell *matHeaderCellDef mat-sort-header>Activate/Deactivate</mat-header-cell>
    <mat-cell *matCellDef="let chartOfAccounts">
        <a *ngIf="chartOfAccounts.accountActive" (click)="deactivateAccount(chartOfAccounts)" class="text-danger">Deactivate</a>
        <a *ngIf="!chartOfAccounts.accountActive" (click)="activateAccount(chartOfAccounts)" class="text-danger">Activate</a>
    </mat-cell>
</ng-container>

编辑 :(在评论后)

如果您不想显示特定的列,只需将其从显示的列中删除,这样mat-table就不会显示它。

allColumns: string[] = ['position', 'name', 'weight', 'symbol', 'activate', 'toggle'];

checkIfAdmin() {
    this.displayedColumns = this.isAdmin ? this.allColumns : this.allColumns.filter(column => column !== 'toggle');
}

这是StackBlitz上的一个有效示例。

答案 1 :(得分:0)

据我了解,您的按钮/链接取决于有效或无效的值。因此,您可以将2个定位标记放在一个单元格中,然后根据活动列的值进行显示

<ng-container matColumnDef="toggle">
    <th mat-header-cell *matHeaderCellDef> Toggle </th>
    <td mat-cell *matCellDef="let element">
      <a *ngIf="element.active === false" (click)="toggle(element.position)">Activate</a>
      <a *ngIf="element.active === true" (click)="toggle(element.position)">Deactivate</a>
    </td>
  </ng-container>

您可以看到onclick是由一个函数处理的,我在其中传递ID值(该行的唯一标识符)并更改其click上的有效值

toggle(position) {
    this.dataSource.find( d=> d.position === position).active = !this.dataSource.find( d=> d.position === position).active;
  }

正在运行的演示:https://stackblitz.com/edit/angular-ne15tp

注意:请随意改善代码的性能,因为这只是出于演示目的的虚拟实现