vue实现多选div
Vue 实现多选 Div 的方法
使用 v-model 和数组管理选中状态
在 Vue 中,可以通过 v-model 绑定一个数组来管理多个 div 的选中状态。每个 div 需要有一个唯一的标识符(如 id 或 value)。
<template>
<div>
<div
v-for="item in items"
:key="item.id"
@click="toggleSelect(item.id)"
:class="{ 'selected': selectedItems.includes(item.id) }"
>
{{ item.text }}
</div>
</div>
</template>
<script>
export default {
data() {
return {
items: [
{ id: 1, text: 'Item 1' },
{ id: 2, text: 'Item 2' },
{ id: 3, text: 'Item 3' }
],
selectedItems: []
}
},
methods: {
toggleSelect(id) {
if (this.selectedItems.includes(id)) {
this.selectedItems = this.selectedItems.filter(item => item !== id)
} else {
this.selectedItems.push(id)
}
}
}
}
</script>
<style>
.selected {
background-color: #eee;
border: 1px solid #ccc;
}
</style>
使用计算属性优化性能
对于大型列表,可以使用计算属性来优化性能,避免频繁操作数组。

<script>
export default {
computed: {
isSelected() {
return (id) => this.selectedItems.includes(id)
}
},
methods: {
toggleSelect(id) {
this.isSelected(id)
? this.selectedItems = this.selectedItems.filter(item => item !== id)
: this.selectedItems.push(id)
}
}
}
</script>
添加复选框支持
如果需要更直观的多选体验,可以在 div 内添加复选框。

<template>
<div>
<div
v-for="item in items"
:key="item.id"
class="selectable-item"
>
<input
type="checkbox"
:id="'item-' + item.id"
:value="item.id"
v-model="selectedItems"
>
<label :for="'item-' + item.id">{{ item.text }}</label>
</div>
</div>
</template>
支持 Shift 键多选
实现类似桌面应用的多选行为,可以通过监听键盘事件来实现。
<script>
export default {
data() {
return {
lastSelected: null
}
},
methods: {
handleClick(id, event) {
if (event.shiftKey && this.lastSelected) {
const start = this.items.findIndex(item => item.id === this.lastSelected)
const end = this.items.findIndex(item => item.id === id)
const range = this.items.slice(
Math.min(start, end),
Math.max(start, end) + 1
)
this.selectedItems = [...new Set([
...this.selectedItems,
...range.map(item => item.id)
])]
} else {
this.toggleSelect(id)
}
this.lastSelected = id
}
}
}
</script>
使用第三方库
对于更复杂的需求,可以考虑使用第三方库如 vue-draggable-next 来实现可拖拽多选。
npm install vue-draggable-next
<template>
<draggable
v-model="items"
group="selectable"
@start="drag=true"
@end="drag=false"
item-key="id"
>
<template #item="{element}">
<div :class="{ 'selected': selectedItems.includes(element.id) }">
{{ element.text }}
</div>
</template>
</draggable>
</template>
<script>
import draggable from 'vue-draggable-next'
export default {
components: { draggable }
}
</script>






