【问题标题】:angular 4.4: can't sort by some columns of a table角度 4.4:无法按表格的某些列排序
【发布时间】:2019-01-06 21:29:36
【问题描述】:

我想按内容对表格进行排序,我有几列,排序代码对其中一些有效,但在其余部分,排序代码不起作用。

我从 API 休息中获取数据。数据获取正确,并正确显示在表格中。

首先我有Students 对象,然后我有Points 对象。

Students 就像:

[{
  "id": 10000,
  "name": "Somebody",
  "points": {"1": 5, "2":0, "3": 10}
},{
  "id": 10001,
  "name": "JustAnother",
  "points": {"1":0, "2": 1, "3": 4}
}]

Points 对象就像:

[{
  "id": 1,
  "name": "foo",
  "value": 2
},
{
  "id": 2,
  "name": "bar",
  "value": 5
},
{
  "id": 3,
  "name": "baz",
  "value": 1
}]

然后我像这样在桌子上显示它们:

<mat-card *ngIf="sortedData">
  <table matSort (matSortChange)="sortData($event)">
    <tr>
      <th mat-sort-header="id">Id</th>
      <th mat-sort-header="name">name</th>
      <th mat-sort-header="{{point.id}}" *ngFor="let point of Points">{{point.name}}</th>
    </tr>

    <tr *ngFor="let student of sortedData">
      <td>{{student.id}}</td>
      <td>{{student.name}}</td>
      <td *ngFor="let point of Points" class="center">
        {{student.points[point.id]}}
      </td>
    </tr>
  </table>
</mat-card>

表格是这样的:

id    | name    | foo    | baz    | bar
------------------------------------------
10000 | Somebody| 5      | 0      | 10
10001 | JustAnot| 0      | 1      | 4

而表格组件中的排序代码为:

public sortedData: Student[];
this.sortedData = this.Students;  // <- this is inside the response of get students function.

sortData(sort: Sort) {
  const data = this.Students;
  if (!sort.active || sort.direction === '') {
    this.sortedData = data;
    return;
  }

  this.sortedData = data.sort((a, b) => {
    const isAsc = sort.direction === 'asc';
    const points_array = this.Points; // <- this.points contains the Points object
    if (sort.active === 'id') {
      return compare(a.id, b.name, isAsc);
    }
    if (sort.active === 'name') {
      return compare(a.name, b.name, isAsc);
    }
    Object.keys(points_array).forEach(
      function (index) {
        if (parseInt(points_array[index].id, 10) === parseInt(sort.active, 10)) {
          return compare(
            a['points'][ points_array[index].id ],
            b['points'][ points_array[index].id ],
            isAsc
          );
        }
      }
    );
  });
}

function compare(a: number | string, b: number | string, isAsc: boolean) {
  return (a < b ? -1 : 1) * (isAsc ? 1 : -1);
}

我有更多的属性和列,对于示例进行了简化。 id 或 name 等所有列都可以毫无问题地排序。

但点列无法排序。当我单击其中一列时,我会进行排序,但顺序保持不变。

如果我登录到排序函数,我看到进行了比较,compare 函数的响应是 0-1,与正确排序的列相同。

控制台上没有javascript错误,显然它可以工作,但是当我尝试按某些列点对数据进行排序时,顺序仍然是初始的。

为什么不按点列排序?

编辑: 复制问题的有效堆栈闪电战: https://stackblitz.com/edit/angular-cruuo3

编辑 2: 我在 stackblitz 中添加了更多学生和另一个带有“级别”的列进行排序。 'Level' 工作正常,作为 'id' 和 'name'。

【问题讨论】:

  • 您究竟打算对它们进行什么排序?没有具体的例子真的很难理解。您介意创建一个示例 stackblitz 来复制此问题吗?
  • 嗯,我知道按升序或降序对表格上显示的数据进行排序。例如,如果我单击名称,我会得到按名称排序的内容数据表。无论如何,我已经做了一个 stackbitz 来复制这个问题。我编辑问题并添加到它。

标签: angular html-table angular-material tablesorter


【解决方案1】:

试试这个代码,它可以工作:

return compare(a['points'][ points_array[parseInt(sort.active, 10)].id ], 
b['points'][ points_array[parseInt(sort.active, 10)].id ], isAsc);

问题在于 forEach 回调函数返回值,但 foreach 参数返回一个 void 值。

例如 for 工作,因为在不使用回调函数

for (const index of Object.keys(points_array)) { 
  if (parseInt(points_array[index].id, 10) === parseInt(sort.active, 10)) { 
    return compare( 
      a['points'][points_array[index].id], 
      b['points'][points_array[index].id], 
      isAsc 
    ); 
  } 
}

【讨论】:

  • for 是我的第一次尝试,但使用for 时出现以下错误:Type 'Point' is not an array type or a string type. 我认为我们已经接近解决方案,但刚才您的代码返回错误:@987654326 @
  • 如果我这样做console.log(Array.isArray(points_array));,控制台上的结果是true
  • 感谢您的解决方案,我将代码更改为:for (const index of Object.keys(points_array)) { if (parseInt(points_array[index].id, 10) === parseInt(sort.active, 10)) { return compare( a['points'][points_array[index].id], b['points'][points_array[index].id], isAsc ); } },现在它可以工作了。你给我指明了好的方向。谢谢。编辑您对我的工作代码的回复,我会接受。也许它会在未来帮助某人。
猜你喜欢
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 2017-07-15
  • 1970-01-01
相关资源
最近更新 更多