<!--  vuedraggable插件实现clone拷贝拖拽案例 -->
<template>
  <div>
    <div class="container">
      <!--
      end 当拖拽结束时触发
      pull: 'clone' 表示允许克隆被拖动的元素
        pull v 拖
      move 自定义控制哪些元素可以拖拽或不允许拖拽
        值为methods中的方法,表示拖拽过程中

      -->
      <div class="box">
        <draggable v-model="arr1" @end="end1" :options="{group: {name: 'itxst', pull: 'clone'}, sort: true}"
                   animation="300" :move="onMove" class="height-100">
          <transition-group tag="div" class="height-100">
            <div :class="item.id === 1? 'item forbid':'item'" v-for="item in arr1" :key="item.id">{{item.name}}</div>
          </transition-group>
        </draggable>

      </div>
      <div class="box">
        <draggable v-model="arr2" @end="end2" group="itxst" animation="300" :move="onMove" class="height-100">
          <transition-group tag="div" class="height-100">
            <div :class="item.id === 12? 'item2 forbid':'item2'" v-for="item in arr2" :key="item.id">{{item.name}}</div>
          </transition-group>
        </draggable>
      </div>
    </div>


  </div>
</template>

<script>

  //导入draggable组件
  import draggable from 'vuedraggable'

  export default {
    name: "Bar",
    components: {
      draggable,
    },
    data() {
      return {
        //定义要被拖拽对象的数组
        arr1: [
          {id: 1, name: 'www.itxst.com(不允许停靠)'},
          {id: 2, name: 'www.jd.com'},
          {id: 3, name: 'www.baidu.com'},
          {id: 5, name: 'www.google.com'},
          {id: 4, name: 'www.taobao.com(不允许拖拽)'}
        ],
        arr2: [
          {id: 11, name: '常用菜单'},
        ],
        moveId: -1
      }
    },
    methods: {
      //左边往右边拖动时的事件
      end1(e) {
        // e是end事件
        // console.log(e);

        // e.newDraggableIndex是被拖拽组件在新分组中的下标
        // console.log(e.newDraggableIndex);

        var that = this;
        var items = that.arr2.filter(function (m) {
          return m.id === that.moveId;
        });

        // 如果左边
        // console.log(items.length);
        if (items.length < 2) return;
        this.arr2.splice(e.newDraggableIndex, 1);
      },
      //右边往左边拖动时的事件
      end2(e) {
        //console.log(e);
        var that = this;
        var items = that.arr1.filter(function (m) {
          return m.id === that.moveId;
        });

        //如果左边
        //console.log(items.length);
        if (items.length < 2) return;
        this.arr1.splice(e.newDraggableIndex, 1)
      },
      //move回调方法
      onMove(e, originalEvent) {
        console.log('onMove e::',e);
        // e.relatedContext 将停靠对象所在上下文
        // e.relatedContext.element 将停靠的对象
        // e.relatedContext.element.id 可获得将停靠的对象的某个属性的值
        this.moveId = e.relatedContext.element.id;

        if(e.relatedContext.element.id ===1) return false; // 返回 false 表示阻止停靠
        // draggedContext 被拖拽的元素
        // draggedContext.element 被拖拽的元素对应的对象
        // draggedContext.element.id 可获得被拖拽的元素对应的对象的某个属性
        if(e.draggedContext.element.id ===4) return false; // 返回 false 表示阻止拖拽
        if(e.draggedContext.element.id ===11) return false; // 返回 false 表示阻止拖拽

      }
    }

  }

  // 判断浏览器是否支持filter函数,如果不支持则自定义一个
  Array.prototype.filter = Array.prototype.filter || function (func) { // filter的参数是个函数
    var arr = this; // filter函数要处理的数组
    var r = [];
    for(var i=0; i<arr.length; i++ ){
      if(func(arr[i], i, arr)){
        r.push(arr[i])
      }
    }
    return r;
  }
</script>

<style scoped lang="less">
  .container {
    display: flex;

    .box {
      width: 300px;
      border: 1px solid #ddd;
      padding: 8px;

      & + .box {
        margin-left: 50px;
      }
    }
  }

  .height-100 {
    height: 100%;
  }

  .item {
    padding: 6px 12px;
    margin: 0px 10px 0px 10px;
    border: solid 1px #eee;
    background-color: #f1f1f1;
    text-align: left;
  }

  .item + .item {
    border-top: none;
    margin-top: 6px;
  }

  .item2 {
    padding: 6px 12px;
    margin: 0px 10px 0px 10px;
    border: solid 1px #eee;
    background-color: pink;
    text-align: left;
  }

  .item2 + .item2 {
    border-top: none;
    margin-top: 6px;
  }
</style>

更多推荐