需求描述
最近在做一個后台系統,有一個功能產品需求是頁面分為左右兩部分,通過右邊的組件列表來動態配置左邊的頁面視圖,並且左邊由組件拼裝起來的視圖,可以實現上下拖拽改變順序,也可以刪除。
根據這個需求我做了下面這個demo。
功能分解
- 右邊的組件列表,可以通過拖拽克隆到左邊,拖拽結束后右邊組件列表數量不會減少
- 左邊的組件可以展開或收起
- 左邊的組件可以上下拖拽,刪除,但不可向右邊拖拽
- 左邊組件拖拽過程中不改變其展開和收起狀態
demo截圖
代碼地址
代碼預覽
<template>
<div class="row">
<div class="col-5">
<h3>組件配置頁面展示</h3>
<draggable
tag="el-collapse"
class="dragArea list-group"
:list="list2"
group="comp"
@change="log"
>
<el-collapse
class="list-group-item left"
v-for="(element,index) in list2"
:key="index"
v-model="activeNames"
@change="handleChange"
>
<el-collapse-item :name="element.id">
<template slot="title">
<span>{{element.name}}</span>
<i class="el-icon-circle-close" @click.stop="deleteItem(index)"></i>
</template>
<div>{{ element.content }}</div>
</el-collapse-item>
</el-collapse>
</draggable>
</div>
<div class="col-5">
<h3>可用組件列表</h3>
<draggable
class="dragArea list-group"
:list="list1"
:group="{ name: 'comp', pull: 'clone', put: false }"
@change="log"
>
<div class="list-group-item" v-for="element in list1" :key="element.id">{{ element.name }}</div>
</draggable>
</div>
</div>
</template>
<script>
import draggable from "vuedraggable";
export default {
name: "clone",
display: "Clone",
order: 2,
components: {
draggable
},
data() {
return {
list1: [
{ name: "組件1", id: 1, content: "內容內容內容。。。。" },
{ name: "組件2", id: 2, content: "內容內容內容。。。。" },
{ name: "組件3", id: 3, content: "內容內容內容。。。。" },
{ name: "組件4", id: 4, content: "內容內容內容。。。。" },
{ name: "組件5", id: 5, content: "內容內容內容。。。。" },
{ name: "組件6", id: 6, content: "內容內容內容。。。。" },
{ name: "組件7", id: 7, content: "內容內容內容。。。。" }
],
list2: [],
activeNames: [],
count: 0
};
},
methods: {
log: function(evt) {
console.log(evt);
if (evt.added) {
this.count += 1;
const item = evt.added.element;
const idx = this.list2.findIndex(e => e.id === item.id);
let temp = JSON.parse(JSON.stringify(this.list2));
temp[idx].id = this.count;
this.list2 = temp;
}
},
handleChange: function() {},
deleteItem: function(index) {
this.list2.splice(index, 1);
}
}
};
</script>