angular集成了cdk drag-drop 来实现拖拽功能
app.modules.ts导入
import { DragDropModule } from '@angular/cdk/drag-drop';
imports: [
DragDropModule
]
<nz-table [nzData]="sourceData" [nzFrontPagination]="false" [nzShowPagination]="false" [nzScroll]="{ y: '500px' }">
<thead>
<tr>
<th>工序描述th>
<th>标准工时(分钟)th>
<th>工序级别th>
tr>
thead>
<tbody cdkDropList
(cdkDropListDropped)="drop($event)">
<tr *ngFor="let data of sourceData" cdkDrag>
<td>{{ data.desc }}td>
<td>{{ data.sam }}td>
<td>{{ data.grade }}td>
tr>
tbody>
nz-table>
import {moveItemInArray, transferArrayItem, copyArrayItem, CdkDragDrop} from '@angular/cdk/drag-drop';
sourceData = [{
'id': 1,
'desc ': 'string',
'sam': 1,
'grade': 1,
'price': 0
}, {
'id': 2,
'desc ': 'string',
'sam': 2,
'grade': 2,
'price': 21
}, {
'id': 3,
'desc ': 'string',
'sam': 3,
'grade': 3,
'price': 3
}];
drop(event: CdkDragDrop<string[]>) {
moveItemInArray(event.container.data, event.previousIndex, event.currentIndex);
}
1、表间相互拖拽无限制
<nz-table [nzData]="targetData" [nzFrontPagination]="false" [nzShowPagination]="false" [nzScroll]="{ y: '500px' }">
<thead>
<tr>
<th nzWidth="60px">序号th>
<th nzWidth="160px">工序描述th>
<th nzWidth="110px">标准工时(分钟)th>
<th nzWidth="110px">工序级别th>
<th nzWidth="110px">标准工价(元)th>
<th nzWidth="90px" *ngIf="editable">操作th>
tr>
thead>
<tbody cdkDropList
#todoList="cdkDropList"
[cdkDropListData]="targetData"
[cdkDropListConnectedTo]="[doneList]"
(cdkDropListDropped)="drop($event)">
<tr *ngFor="let data of targetData; index as i" cdkDrag>
<td>{{ i+1 }}td>
<td>{{ data.desc }}td>
<td>{{ data.sam }}td>
<td>{{ data.grade }}td>
<td>{{ data.price }}td>
<td *ngIf="editable">
<button nz-button nzType="link" (click.stop)="delete(i)">删除button>
td>
tr>
tbody>
nz-table>
<nz-table [nzData]="sourceData" [nzFrontPagination]="false" [nzShowPagination]="false" [nzScroll]="{ y: '500px' }">
<thead>
<tr>
<th>工序描述th>
<th>标准工时(分钟)th>
<th>工序级别th>
tr>
thead>
<tbody cdkDropList
#doneList="cdkDropList"
[cdkDropListData]="sourceData"
[cdkDropListConnectedTo]="[todoList]"
(cdkDropListDropped)="drop($event)">
<tr *ngFor="let data of sourceData" cdkDrag>
<td>{{ data.desc }}td>
<td>{{ data.sam }}td>
<td>{{ data.grade }}td>
tr>
tbody>
nz-table>
import {moveItemInArray, transferArrayItem, copyArrayItem, CdkDragDrop} from '@angular/cdk/drag-drop';
targetData = [{
'id': null,
'desc': null,
'sam': null,
'grade': null,
'price': null
}];
sourceData = [{
'id': 1,
'desc ': 'string',
'sam': 1,
'grade': 1,
'price': 0
}, {
'id': 2,
'desc ': 'string',
'sam': 2,
'grade': 2,
'price': 21
}, {
'id': 3,
'desc ': 'string',
'sam': 3,
'grade': 3,
'price': 3
}];
drop(event: CdkDragDrop<string[]>) {
if (event.previousContainer === event.container) {
moveItemInArray(event.container.data, event.previousIndex, event.currentIndex);
} else {
// 表间数据转换,功能:将源表的数据拖拽到目标表中,并从源表中删除
transferArrayItem(event.previousContainer.data, event.container.data, event.previousIndex, event.currentIndex);
// 表间数据复制,功能:将源表的数据通过拖拽复制到目标表中,源表中不删除
// copyArrayItem(event.previousContainer.data, event.container.data, event.previousIndex, event.currentIndex);
/**
* 针对目标表必须存在至少一条数据,解决方案一:初始一条空数据,有数据移入时,删除空数据
*/
this.targetData.forEach((item) => {
if (item.id === null) {
this.targetData.splice(this.targetData.indexOf(item), 1);
}
});
}
}
// 删除
delete(index) {
/**
* 针对目标表必须存在至少一条数据,解决方案一:当删除最后一条数据时,增加一条空数据
*/
this.targetData.splice(index, 1);
if (this.targetData.length === 0) {
const data = {
id: null,
desc: null,
sam: null,
grade: null,
price: null
};
this.targetData.splice(0, 0, data);
}
}
注意点:
目标表必须至少存在一条数据,若为空,则无法进行表间拖拽,其拖拽会被认为为表内拖拽
2、表间拖拽有限制,源表只出不进
<nz-table [nzData]="targetData" [nzFrontPagination]="false" [nzShowPagination]="false" [nzScroll]="{ y: '500px' }">
<thead>
<tr>
<th nzWidth="60px">序号th>
<th nzWidth="160px">工序描述th>
<th nzWidth="110px">标准工时(分钟)th>
<th nzWidth="110px">工序级别th>
<th nzWidth="110px">标准工价(元)th>
<th nzWidth="90px" *ngIf="editable">操作th>
tr>
thead>
<tbody cdkDropList
#todoList="cdkDropList"
[cdkDropListData]="targetData"
[cdkDropListConnectedTo]="[doneList]"
(cdkDropListDropped)="drop($event)">
<tr *ngFor="let data of targetData; index as i" cdkDrag>
<td>{{ i+1 }}td>
<td>{{ data.desc }}td>
<td>{{ data.sam }}td>
<td>{{ data.grade }}td>
<td>{{ data.price }}td>
<td *ngIf="editable">
<button nz-button nzType="link" (click.stop)="delete(i)">删除button>
td>
tr>
tbody>
nz-table>
<nz-table [nzData]="sourceData" [nzFrontPagination]="false" [nzShowPagination]="false" [nzScroll]="{ y: '500px' }">
<thead>
<tr>
<th>工序描述th>
<th>标准工时(分钟)th>
<th>工序级别th>
tr>
thead>
<tbody cdkDropList
#doneList="cdkDropList"
[cdkDropListData]="sourceData"
[cdkDropListEnterPredicate]="noReturnPredicate"
[cdkDropListConnectedTo]="[todoList]"
(cdkDropListDropped)="drop($event)">
<tr *ngFor="let data of sourceData" cdkDrag>
<td>{{ data.desc }}td>
<td>{{ data.sam }}td>
<td>{{ data.grade }}td>
tr>
tbody>
nz-table>
import {moveItemInArray, transferArrayItem, copyArrayItem, CdkDragDrop} from '@angular/cdk/drag-drop';
targetData = [{
'id': null,
'desc': null,
'sam': null,
'grade': null,
'price': null
}];
sourceData = [{
'id': 1,
'desc ': 'string',
'sam': 1,
'grade': 1,
'price': 0
}, {
'id': 2,
'desc ': 'string',
'sam': 2,
'grade': 2,
'price': 21
}, {
'id': 3,
'desc ': 'string',
'sam': 3,
'grade': 3,
'price': 3
}];
drop(event: CdkDragDrop<string[]>) {
if (event.previousContainer === event.container) {
moveItemInArray(event.container.data, event.previousIndex, event.currentIndex);
} else {
// 表间数据转换,功能:将源表的数据拖拽到目标表中,并从源表中删除
transferArrayItem(event.previousContainer.data, event.container.data, event.previousIndex, event.currentIndex);
// 表间数据复制,功能:将源表的数据通过拖拽复制到目标表中,源表中不删除
// copyArrayItem(event.previousContainer.data, event.container.data, event.previousIndex, event.currentIndex);
/**
* 针对目标表必须存在至少一条数据,解决方案一:初始一条空数据,有数据移入时,删除空数据
*/
this.targetData.forEach((item) => {
if (item.id === null) {
this.targetData.splice(this.targetData.indexOf(item), 1);
}
});
}
}
// 删除
delete(index) {
/**
* 针对目标表必须存在至少一条数据,解决方案一:当删除最后一条数据时,增加一条空数据
*/
this.targetData.splice(index, 1);
if (this.targetData.length === 0) {
const data = {
id: null,
desc: null,
sam: null,
grade: null,
price: null
};
this.targetData.splice(0, 0, data);
}
}
// 不让其他list里面的数据移入到这个里面来
noReturnPredicate() {
return false;
}
注:通过cdkDropListEnterPredicate来设置进入限制
详情请见官网:https://material.angular.io/cdk/drag-drop/examples