在vue项目中进行拖拽增加节点

在vue项目中进行拖拽增加节点

  • 因为项目需要写一个小demo,但是在网上没有找到很合适的,所以就自己用原生拖拽搞了一个,依旧不是很完善,但是还能用,后期可能会用antV的G6来替代,看缘分更新
  • 废话不多说,还是上代码
<!DOCTYPE html>
<html lang="en">

<head>
    <meta charset="UTF-8">
    <meta name="viewport" content="width=device-width, initial-scale=1.0">
    <title>拖拽demo</title>
    <script src="https://cdn.jsdelivr.net/npm/vue/dist/vue.js"></script>
    <!-- 引入样式 -->
    <link rel="stylesheet" href="https://unpkg.com/element-ui/lib/theme-chalk/index.css">
</head>


<body>
    <div id="app">
        <div id="div1" class="jiedian" @drop='drop($event)' @dragover="draglev">
            <div>
                <ul class="jdlc" v-for="(item,index) in tempList" :key="index" @dragover='allowDrop($event)' >
                    <li style="position: relative;">
                        <span class="tzbtn">{{item.title}}</span>
                        <i class="el-icon-error" @click="closeFn(index)"></i>
                        <div class="dropBox">
                            <div @drop="dragent($event,index,1)"></div>
                            <div @drop="dragent($event,index,2)"></div>
                        </div>
                        
                        <ul v-for="(item,index) in item.children" :key="index">
                            <li>
                                <span>{{item.title}}</span>
                            </li>
                        </ul>
                    </li>
                </ul>
            </div>
        </div>
        <div class="tree">
            <ul v-for="(item,index) in data" :key="index" :draggable="true" @dragstart='drag($event)'>
                <li>
                    <span>{{item.title}}</span>
                    <ul v-for="(item,index) in item.children" :key="index">
                        <li>
                            <span>{{item.title}}</span>
                        </li>
                    </ul>
                </li>
            </ul>
        </div>
    </div>

    <script src="https://unpkg.com/element-ui/lib/index.js"></script>
    <script src="https://unpkg.com/@better-scroll/core@latest/dist/core.js"></script>
    <script src="https://unpkg.com/@better-scroll/core@latest/dist/core.min.js"></script>
    <script>
        new Vue({
            el: '#app',
            data: function () {
                return {
                    tempList: [
                        {
                            id: '1',
                            title: "节点一",
                            status: true,
                            children: [
                                {
                                    id: '1-1',
                                    title: "节点1-1",
                                    status: true,
                                },
                                {
                                    id: '1-2',
                                    title: "节点1-2",
                                    status: true,
                                }
                            ]
                        },
                        {
                            id: '2',
                            title: "节点二",
                            status: true,
                            children: [
                                {
                                    id: '2-1',
                                    title: "节点2-1",
                                    status: true,
                                },
                                {
                                    id: '2-2',
                                    title: "节点2-2",
                                    status: true,
                                }
                            ]
                        },
                    ],
                    data: [{
                        id: '3',
                        title: '一级 1',
                        status: true,
                        children: [{
                            id: '3-1',
                            title: '二级1',
                            status: true,
                        }
                    ]
                    }, {
                        id: '4',
                        title: '一级 2',
                        status: true,
                        children: [{
                            id: '4-1',
                            title: '二级1',
                            status: true,
                        }, {
                            id: '4-2',
                            title: '二级2',
                            status: true,
                        }]
                    }],
                    defaultProps: {
                        children: 'children',
                        label: 'title'
                    }
                }
            },
            methods: {
                drag: function (e) { //start
                    let target=e.target;
                    let nodeList=e.target.parentNode.children;
                    this.targetIndex=this.tabIndex(target,nodeList);
                },
                drop: function (e) { //end
                    e.preventDefault();
                },
                allowDrop: function (e) { //moving
                    e.preventDefault();
                    e.stopPropagation()
                    console.log(222)
                },
                tabIndex(target,nodeList){
                    for(let i=0;i<nodeList.length;i++){
                        if(target===nodeList[i]){
                            return i;
                        }
                    }
                },
                dragent(e,index,flag){
                    var arr =  this.data
                    if(flag === 1){
                        this.tempList.splice(index,-1,arr[this.targetIndex]);
                    }else if (flag === 2){
                        this.tempList.splice(index+1,0,arr[this.targetIndex]);
                    }
                },
                draglev(){
                    console.log(111)
                },
                closeFn(index){
                    this.tempList.splice(index,1);
                    console.log('del')
                }
            }
        })
    </script>
</body>
<style>
    ul li {
        list-style: none;
    }
    #app {
        width: 800px;
        height: 400px;
        display: flex;
        margin: 0 auto;
    }

    .jiedian {
        width: 700px;
        background: #ccc;
        padding: 40px;
        overflow: auto;
    }
    .jiedian div{
        height: 320px;
        overflow: auto;
        display: flex;
    }

    .jiedian .tzbtn {
        width: 140px;
        height: 20px;
        display: inline-block;
        border: 1px solid #A0A6CD;
        background: #fff;
        border-radius: 20px;
        padding: 10px 0;
        text-align: center;
    }

    .jiedian .jdlc {
        position: relative;
        display: inline-block;
    }
    .jiedian .jdlc li ul {
        position: relative;
    }

    .jiedian .jdlc li ul li {
        height: 32px;
    }

    .jiedian .jdlc li ul li span {
        line-height: 62px;
    }

    .jiedian .jdlc:not(:last-child)::after {
        content: ' ';
        position: absolute;
        left: 182px;
        top: 20px;
        width: 47px;
        border: none;
        border-top: 2px solid #ab9dff;
    }

    .jiedian .jdlc li ul::before {
        content: ' ';
        position: absolute;
        left: 18px;
        height: 100%;
        border: none;
        border-left: 2px solid #ab9dff;
    }

    .jiedian .jdlc li ul li:after {
        content: ' ';
        position: absolute;
        top: 30px;
        left: 20px;
        width: 20px;
        border: none;
        border-top: 2px solid #ab9dff;
    }
    .tree{
        width: 100px;
        background: #eee;
        padding-top: 20px;
    }
    .tree ul{
        width: 100px;
        padding: 0;
        margin-top: 0;
    }
    
    .tree ul li{
        margin-left: 20px;
        position: relative;
    }
    .tree ul li ul li{
        height: 22px;
    }
    .tree ul li ul li span{
        line-height: 38px;
    }
    .tree ul li ul li::after {
        content: ' ';
        position: absolute;
        left: -10px;
        top: 0px;
        height: 21px;
        border: none;
        border-left: 2px solid #ab9dff;
    }
    .tree ul li ul li::before {
        content: ' ';
        position: absolute;
        left: -12px;
        top: 16px;
        height: 6px;
        width: 6px;
        border: none;
        border-radius: 3px;
        background: #ab9dff;
    }
    .dropBox{
        position: absolute;
        left: 0;
        top: 0;
        display: flex;
        height: 42px !important;
        width: 100%;
    }
    .dropBox>div{
        flex: 1;
        height: 100%;
    }
    .el-icon-error {
        display: inherit;
    }
    .el-icon-error:before {
    content: "\e79d";
    position: absolute;
    top: -5px;
    right: 5px;
    }
</style>
</html>


  • 5
    点赞
  • 6
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值