vue3之拖拽插件:
安装: npm install vue-draggable-plus
使用:
<template>
<VueDraggable ref="el" v-model="list">
<div v-for="item in list" :key="item.id">
{{ item.name }}
</div>
</VueDraggable>
</template>
<script setup lang="ts">
import { ref } from 'vue'
import { VueDraggable } from 'vue-draggable-plus'
const list = ref([
{
name: 'Joao',
id: 1
},
{
name: 'Jean',
id: 2
},
{
name: 'Johanna',
id: 3
},
{
name: 'Juan',
id: 4
}
])
</script>
这个插件非常好用,只要包裹住目标内容,即可实现拖拽功能
排序事件:
import {
VueDraggable,
type DraggableEvent,
type SortableEvent,
} from "vue-draggable-plus";
const onSort = async (event: SortableEvent) => {
const draggableEvent = event as DraggableEvent;
console.log("event id is:", draggableEvent.data.id);
console.log("event sort is:", draggableEvent.newIndex);
};
<VueDraggable
v-model="sessionList"
class="mb-8 flex flex-col gap-xl"
@sort="onSort"
>
vue-draggable-plus可以定义拖拽点,而不必整个页面生效:
https://vue-draggable-plus.pages.dev/demo/handle/
也可以做表格拖拽:
https://vue-draggable-plus.pages.dev/demo/target-container/
典型 issue:
https://github.com/Alfred-Skyblue/vue-draggable-plus/issues/86
如果想实现表格的部分列拖拽,而不是所有列,可以按照如下方式处理:
允许部分td 拖拽,而不必整行都拖拽
import { VueDraggable } from "vue-draggable-plus";
<VueDraggable
v-model="addonsList"
target=".handle-addons"
filter=".unable-drag"
>
<AppTable class="w-full">
<thead>
<tr class="h-12">
<AppTableHeading
class="w-[35rem]"
title="Name"
/>
<AppTableHeading
class="w-[12.5rem]"
title="Price (CHF)"
/>
<AppTableHeading
class="w-[12.5rem]"
title="Issued"
/>
<AppTableHeading
class="w-[28rem]"
title="Available to"
/>
<AppTableHeading
class="w-[12.5rem]"
title="Action"
/>
</tr>
</thead>
<tbody class="handle-addons text-xs">
<tr
v-for="addons in addonsList"
:key="`${addons.name}_${addons.id}`"
class="select-text"
>
<td>
{{ addons.name }}
</td>
<td class="unable-drag">
{{ addons.price }}
</td>
<td class="unable-drag">{{ addons.issued }}</td>
<td class="unable-drag">
{{ addons.availableTo }}
</td>
<td class="unable-drag">
<EventSettingsRegistrationTicketsAction
:id="addons.id"
@edit="showEditAddons"
@delete="showDeleteAddons"
/>
</td>
</tr>
</tbody>
</AppTable>
</VueDraggable>
主要是通过 filter 属性定义的class来排除; 同时给每个tr添加 class="select-text" , 这样可以选中td中的文字,否则选不了,但是和 filter 一起使用的时候,会发现,只有可 drag 的元素才能被选中,被过滤的还是不能被选中,非常蛋疼.
关于 vue-draggable-plus 插件的几个属性,可以参考,虽然不是一个包,但是都用了sortable.js:
https://github.com/SortableJS/Sortable //这里面也有介绍
结论:
1>无论哪种drag插件,最后都是 sortable.js, 并且 vuedraggable@next 是 sortable.js的 vue3实现方式, 这个 vue-draggable-plus 文档说 sortable.js不支持vue3是错误的
2>select-text 属性还是没有在 不是drag 元素上实现,怎么测试都不行
原生的drag库:
https://interactjs.io/
