如何重新排序角材料表?

时间:2019-01-10 07:06:31

标签: angular drag-and-drop angular-material

目标:使用Angular Material创建表,可以使用Angular拖放进行修改。

预期的行为:表格应在拖放时重新排序

当前行为:行是可拖动的,并且底层数据源的顺序发生了变化,但是当删除行时,它会恢复到表中的原始位置。

请参见以下示例:

https://stackblitz.com/edit/drag-drop-reorder-mattable

如何解决/实现?

(此外,我不确定为什么它在Stackblitz中的样式这么差。那里的任何见识也将受到赞赏)

编辑:我发现了一种超级hacky的方式来使行以正确的顺序再次呈现,但是这是无法实现的。我只是将t.renderRows()放在drop事件处理程序之后执行。见下面的实线

<mat-table #t
  cdkDropList
  (cdkDropListDropped)="onListDrop($event); t.renderRows()" 
  [dataSource]="dataSource"
  class="mat-elevation-z8">
  ...
</mat-table>

编辑2: 我已经完成了使用rxjs的简单重构,并且每个元素的第一次拖放重新排序都非常有效。但是,当我尝试移动已经移动了一次的元素时,没有得到预期的行为。 Stackblitz应用程序已更新。

2 个答案:

答案 0 :(得分:3)

您遇到angular/material2 issue #14056“ cdkDropList:event.previousIndex不会在第二步更新”。问题及其注释中详细介绍了深克隆数据源的一种解决方法。

在对控制台日志(1. Hello 2. My name is khan 3. When 4. What 5. Opted bat 6. Learn )进行少量更改之后,看看here在我的演示中的播放情况

我将“项目0”从索引0拖到索引3。索引0处的项目移动到索引3。✔️
我将“项目0”从索引3拖到索引1。索引0的项目移至索引1。✖️
我将“项目0”从索引3拖动到索引2。索引0的项目移至索引2。✖️

2. My name is khan 3. When 4. What 5. Opted bat 在移动到另一个索引后错误地保持不变。

答案 1 :(得分:2)

正如您在编辑中提到的那样,每次修改数据源时,确实需要调用renderRows()。甚至在Angular Material文档here中也提到了这一点。

  

根据表的最新数据集来呈现行,   直接作为输入提供或通过Observable检索   流(直接或从数据源)。检查是否存在差异   自上次差异以来的数据仅执行必要的更改   (添加/删除/移动行)。

     

如果表的数据源是DataSource或Observable,则将是   每次提供的Observable流发出一个   新数据数组。 否则,如果您的数据是数组,则此函数将   需要调用以呈现任何更改。

您可以做什么来解决每次调用renderRows()的问题,就是将数据源转换为Observable并在onListDrop()函数中发出一个新值,以便每次您拖动/放一行。