vue.dragable.for

by Shaun Ellis

HTML

<script src="https://cdn.jsdelivr.net/sortable/1.4.2/Sortable.min.js"></script>
<script src="https://cdn.rawgit.com/David-Desmaisons/Vue.Draggable/master/dist/vuedraggable.min.js"></script>
<script src=" https://cdnjs.cloudflare.com/ajax/libs/vuex/2.1.1/vuex.js"></script>
<link rel="stylesheet" href="https://maxcdn.bootstrapcdn.com/bootstrap/3.3.7/css/bootstrap.min.css">
  
  <div class="content">
    <div class="img_gallery" id="sortable">
      <div id="0" class="thumbnail">
        <img class="thumb" src="http://via.placeholder.com/150x200">
        <div class="caption">1</div>
      </div>
      <div id="1" class="thumbnail" style="">
        <img class="thumb" src="http://via.placeholder.com/150x200">
        <div class="caption">2</div>
      </div>
      <div id="2" class="thumbnail">
        <img class="thumb" src="http://via.placeholder.com/150x200">
        <div class="caption">3</div>
      </div>
      <div id="3" class="thumbnail">
        <img class="thumb" src="http://via.placeholder.com/150x200">
        <div class="caption">4</div>
      </div>
      <div id="4" class="thumbnail selected" style="">
        <img class="thumb" src="http://via.placeholder.com/150x200">
        <div class="caption">5</div>
      </div>
      <div id="5" class="thumbnail">
        <img class="thumb" src="http://via.placeholder.com/150x200">
        <div class="caption">6</div>
      </div>
    </div>
  </div>


  
  <div id="main">
        <h1>Vue Dragable For</h1>
       
        <div class="drag">
            <h2>Draggable</h2>
            <draggable :list="list" class="dragArea">
                <div v-for="element in value"><p>
                {{ element.name }}
                </p></div>
             </draggable>
         </div>

    </div>

CSS

.content {
  position: absolute;
  top: 20px;
  left: 0;
  height: 70%;
  width: 60%;
  border-radius: 4px;
}

.img_gallery {
  overflow: auto;
  height: 100%;
  border: 1px solid #ddd;
  border-radius: 4px;
  margin-bottom: 30px;
}

.thumbnail {
  display: inline-block;
  max-width: 150px;
  margin: 10px;
}

.caption {
  pointer-events: none;
}

.thumb {
  pointer-events: none;
}

JavaScript

/* ----- Store ----- */
const state = {
  list: [
  	{name:"John"}, 
    {name:"Joao"}, 
    {name:"Jean"}
  ], 
  images = [
  	{ "url": "http://via.placeholder.com/150x200","label": "A" },
    { "url": "http://via.placeholder.com/150x200","label": "B" },
    { "url": "http://via.placeholder.com/150x200","label": "C" },
    { "url": "http://via.placeholder.com/150x200","label": "D" },
    { "url": "http://via.placeholder.com/150x200","label": "E" },
    { "url": "http://via.placeholder.com/150x200","label": "F" }
   ]
};

const mutations = {
  INPUT (state, { list }) {
    state.list = [...list];
  }
};

const store = new Vuex.Store({
  state,
  mutations,
  getters: {
  	value: (state) => state.list
  }
});

/* ----- Component ----- */
var vm = new Vue({
	el: "#main",
	store,
  computed: {
    value: (state) => state.$store.getters.value,
    list: {
      get() {
        const self = this;

        const arrayChangeHandler = {
          get(target, property) {
            return target[property];
          },
          set(target, property, value) {
            target[property] = value;

            self.$store.commit({
              type: 'INPUT',
              list: target,
            });

            return true;
          },
        };

        return new Proxy([...this.value], arrayChangeHandler);
      },
      set(newValue) {
        this.$store.commit({
          type: 'INPUT',
          list: target,
        });
      },
    },
  },
});