vue开发:原生拖拽列表,更换元素位置。下面是代码:
拖拽Api
方法名 | 释义 |
---|---|
ondraggable | 设置元素是否允许被拖动。链接和图片默认是可拖动,因此不用设置该属性 |
ondragstart | 用户开始拖动元素或选择的文本时触发。 |
ondragover | 1.拖动元素或选取的文本正在拖动到放置目标时触发。2.默认情况下,数据/元素不能放置到其他元素中。3.如果要实现改功能,我们需要防止元素的默认处理方法。4.我们可以通过调用event.preventDefault()方法来实现 ondragover 事件。 |
ondragenter | 当被鼠标拖动的对象进入其容器范围内时触发此事件 |
ondragend | 用户完成元素拖动后触发 |
<!DOCTYPE html>
<html>
<head>
<meta charset="utf-8">
<title>原生拖拽列表,更换元素位置</title>
<!--引入 element-ui 的样式,-->
<link rel="stylesheet" href="https://unpkg.com/element-ui/lib/theme-chalk/index.css">
<script src="https://cdn.bootcss.com/vue/2.5.16/vue.min.js"></script>
<!-- 引入element 的组件库-->
<script src="https://unpkg.com/element-ui/lib/index.js"></script>
<style>
* {
margin: 0;
padding: 0;
}
#app {
margin: 50px;
}
.item {
border: 1px solid #000;
margin: 10px;
padding: 10px;
}
</style>
</head>
<body>
<div id="app">
<div v-for="(item, index) in summaryArr" :key="index" draggable="true" @click.stop="orientationFun(item)"
@dragstart.stop="handleDragStart($event, item)" @dragover.prevent.stop="handleDragOver($event, item)"
@dragenter.stop="handleDragEnter($event, item)" @dragend.stop="handleDragEnd($event, item)" class="item">
{{item.text}}
</div>
</div>
<script>
new Vue({
el: '#app',
data() {
return {
// 源数据
summaryArr: [
{
id: '1',
text: '内容1'
},
{
id: '2',
text: '内容2'
},
{
id: '3',
text: '内容3'
},
{
id: '4',
text: '内容4'
},
{
id: '5',
text: '内容5'
}
],
// 深拷贝源数据
summaryArrCopy: [],
dragging: null,
}
},
created() {
// 深拷贝最新的源数据,目的是为了判断拖拽的位置是否有没有更换,没有更换就不调接口
this.summaryArrCopy = JSON.parse(JSON.stringify(this.summaryArr));
},
methods: {
handleDragStart(e, items) {
// 开始拖动时,暂时保存当前拖动的数据。
this.dragging = items;
},
handleDragEnd(e, items) {
// 是否更换过位置,如果拖拽过后还是原位置,则不调取接口
const isChangePosition = this.summaryArr.some((item, index) => {
if (item.id === this.summaryArrCopy[index].id) {
return false;
} else {
return true;
}
});
this.dragging = null;
if (isChangePosition) {
// 深拷贝最新的源数据,目的是为了判断拖拽的位置是否有没有更换,没有更换就不调接口
this.summaryArrCopy = JSON.parse(JSON.stringify(this.summaryArr));
// 调取接口
console.log(this.summaryArr, '排序过后的数据')
this.$message({
message: '排序成功!',
type: 'success'
});
}
},
handleDragOver(e) {
// 在dragenter中针对放置目标来设置!
e.dataTransfer.dropEffect = "move";
},
handleDragEnter(e, items) {
// 为需要移动的元素设置dragstart事件
e.dataTransfer.effectAllowed = "move";
if (items == this.dragging) return;
// 拷贝一份数据进行交换操作。
var newItems = [...this.summaryArr];
// 获取数组下标
var src = newItems.indexOf(this.dragging);
var dst = newItems.indexOf(items);
// 交换位置
newItems.splice(dst, 0, ...newItems.splice(src, 1));
this.summaryArr = newItems;
},
}
})
</script>
</body>
</html>
效果:
代码里面做了一个小优化:深拷贝最新的源数据,目的是判断是否更换过位置,如果拖拽过后还是原位置,则不调取接口
**粗体** _斜体_ [链接](http://example.com) `代码` - 列表 > 引用
。你还可以使用@
来通知其他用户。