2015-11-03 3 views
5

के लिए कोणीय-खींचें ड्रॉप मैं निम्नलिखित स्थिति है जहाँ मैं एक उपयोगकर्ता/एक सूची और खींचें से वस्तुओं का चयन कर उन्हें एक निश्चित स्लॉट में ड्रॉप करने के लिए अनुमति की जरूरत है:का मेल AngularJS, jQueryUI, क्रमबद्ध सूची

enter image description here

ऑब्जेक्ट्स स्लॉट के आकार से एक से तीन गुना हो सकता है। तो यदि कोई उपयोगकर्ता स्लॉट 0 पर ऑब्जेक्ट 1 ड्रैग करता है, तो यह केवल स्लॉट 0 (startSlot = 0 और endSlot = 0) पर कब्जा करता है। हालांकि यदि कोई उपयोगकर्ता स्लॉट 3 पर ऑब्जेक्ट 3 ड्रैग करता है, तो इसमें स्लॉट 3, 4, और 5 (startSlot = 3 और endSlot = 5) पर कब्जा होता है।

एक बार वस्तुओं को स्लॉट में गिरा दिया जाता है, तो उपयोगकर्ता स्लॉट में वस्तुओं को ऊपर और नीचे क्लिक करके ऑब्जेक्ट को पुन: व्यवस्थित कर सकते हैं। वस्तुओं एक दूसरे को ओवरलैप नहीं कर सकते:

enter image description here

मैं कोणीय उपयोग कर रहा हूँ, इसलिए मैं किसी डेटाबेस से वस्तुओं की एक सूची पढ़ रहा हूँ और मैं स्लॉट की संख्या के लिए एक चर है। मैंने कुछ समाधानों का प्रयास किया है। मैं jQuery और jQueryUI, खींचने योग्य droppable के उपयोग विश्वास करते हैं, और sortable समाधान का हिस्सा है, यहाँ पहली बेला का प्रदर्शन खींचें/ड्रॉप और sortable है:

http://jsfiddle.net/mduvall216/6hfuzvws/4/ 

इस बेला के साथ समस्या मैं एक सेट की जरूरत है वह यह है कि स्लॉट की संख्या। एक बार ऑब्जेक्ट स्लॉट में रखा जाता है, तो यह ऑब्जेक्ट के आकार के आधार पर 1 से 3 स्लॉट को प्रतिस्थापित करता है। नीचे दूसरी बेला AngularJS एकीकृत:

http://jsfiddle.net/mduvall216/zg5x4b6k/4/ 

समस्या यहाँ है मुझे पता है कि मैं ग्रिड के कुछ प्रकार की जरूरत की वस्तुओं एक बार वस्तु सूची से घसीटा स्नैप करना।

[{आईडी: obj1, startSlot: 0, endSlot: 0} {आईडी: obj3, startSlot: 3, endSlot नतीजा यह है कि मैं के लिए देख रहा हूँ अपने सौंपे गए स्लॉट में वस्तुओं की एक json सूची है :

https://github.com/codef0rmer/angular-dragdrop 

लेकिन मुझे लगता है कि मेरी बेला का परीक्षण करने में एकीकृत करने की कोशिश कर समस्या आ रही है: 5}]

मैं भी यकीन है कि समाधान codf0rmer के कोणीय खींचें ड्रॉप यहाँ स्थित आवश्यकता होगी कर रहा हूँ । यह एक दिलचस्प चुनौती है जिसे मैं थोड़ी देर के लिए कताई कर रहा हूं, अगर कोई सहायता कर सकता है तो इसकी सराहना की जाएगी। आपके समय के लिए धन्यवाद।

+0

https://github.com/angular-ui/ui-sortable पर एक नज़र डालें, यह घटकों के लोकप्रिय AngularUI सूट का हिस्सा है। वे जुड़े सूचियों का समर्थन करते हैं, लेकिन आपके आइटम आकार की आवश्यकता शायद सूची आइटमों के कुछ ग्राहक हैंडलिंग की आवश्यकता होगी, लेकिन घटनाओं का उपयोग करते समय सीधे आगे बढ़ना चाहिए। मैंने इसे पहले एक परियोजना के अंदर सफलतापूर्वक उपयोग किया है। दुर्भाग्यवश मेरे पास आपकी विशिष्ट आवश्यकताओं को देखने के लिए अभी समय नहीं है। – Beyers

+0

आप एचटीएमएल 5 ड्रैग और ड्रॉप एपीआई का उपयोग कर एक कस्टम मॉड्यूल भी बना सकते हैं। इसे लागू करने में काफी आसान है। – malinkody

उत्तर

5

मैंने HTML5 ड्रैग & ड्रॉप एपीआई और jQuery का उपयोग करके अपनी आवश्यकताओं का मूल कार्यान्वयन शुरू किया। एपीआई हल्का वजन है और किसी तीसरे पक्ष की स्क्रिप्ट की आवश्यकता नहीं है। कोड अनुकूलित करने के लिए आसान होना चाहिए। प्रदान किया गया उदाहरण केवल एक प्रारंभिक बिंदु है और किसी भी तरह से उत्पादन तैयार नहीं है और इसे अनुकूलित किया जाना चाहिए और संभवतः उपयोग से पहले एक jQuery प्लगइन मॉड्यूल में बदल दिया जाना चाहिए। इससे मॉड्यूल की पुन: प्रयोज्यता बढ़ेगी।

टिप्पणियों में कोड के बारे में कोई और प्रश्न छोड़ दें।

JSFiddle Example without sortable:

JSFiddle with sortable

एचटीएमएल:

<ul class="select-list"> 
    <li class="header">Object List</li> 
    <li data-slots="1" class="s1">Object 1</li> 
    <li data-slots="2" class="s2">Object 2</li> 
    <li data-slots="3" class="s3">Object 3</li> 
</ul> 
<ul class="drop-list" id="sortable"> 
    <li>Slot 1</li> 
    <li>Slot 2</li> 
    <li>Slot 3</li> 
    <li>Slot 4</li> 
    <li>Slot 5</li> 
    <li>Slot 6</li> 
    <li>Slot 7</li> 
    <li>Slot 8</li> 
    <li>Slot 9</li> 
    <li>Slot 10</li> 
    <li>Slot 11</li> 
    <li>Slot 12</li> 
    <li>Slot 13</li> 
</ul> 

जावास्क्रिप्ट sortable बिना:

(function ($, undefined) { 
    // document ready function 
    $(function() { 
     init(); 

     $('ul.select-list').on({ 
      'dragstart': dragstart, 
       'dragend': dragend 
     }, 'li'); 

     $('ul.drop-list').on({ 
      'dragenter dragover': dragover, 
       'dragleave': dragleave, 
       'drop': drop 
     }, 'li.dropzone'); 
    }); 

    // Initializes the lists 
    function init() { 
     $('ul.select-list').find('li').not('[class="header"]').each(function() { 
      var height = getSlotHeight() * $(this).data('slots'); 
      $(this).height(height); 
     }).attr('draggable', true); 

     $('ul.drop-list').find('li').each(function() { 
      $(this).height(getSlotHeight()); 
     }).addClass('dropzone'); 
    } 

    // Get the height of grid slots 
    function getSlotHeight() { 
     return 20; 
    } 

    /** 
    * Checks whether target is a kompatible dropzone 
    * A dropzone needs the dropzone class 
    * and needs to have enough consequent slots to drop the object into 
    */ 
    function isDropZone(target, draggedObj) { 
     var isDropZone = true; 
     var slots = draggedObj.data('slots'); 
     for (var i = 1; i < slots; i++) { 
      target = target.next(); 
      if (target.size() == 0 || !target.hasClass('dropzone')) { 
       isDropZone = false; 
       break; 
      } 
     } 
     return isDropZone; 
    }  

    /* 
    * The following events are executed in the order the handlers are declared 
    * dragstart being first and dragend being last 
    */ 

    // dragstart event handler 
    function dragstart(e) { 
     e.stopPropagation(); 
     var dt = e.originalEvent.dataTransfer; 
     dt.effectAllowed = 'move'; 
     dt.setData('text/html', ''); 
     $('ul.select-list').data({ 
      draggedObj: $(this) 
     }); 
    } 

    // dragover event handler 
    function dragover(e) { 
     e.preventDefault(); 
     e.stopPropagation(); 
     var data = $('ul.select-list').data(); 
     if (!data.draggedObj || !isDropZone($(this), data.draggedObj)) { 
      e.originalEvent.dataTransfer.dropEffect = 'none'; 
      return; 
     } 
     e.originalEvent.dataTransfer.dropEffect = 'move'; 
     var item = $(this).addClass('dragover'); 
     var slots = data.draggedObj.data('slots'); 
     for (var i = 1; i < slots; i++) { 
      item = item.next('li').addClass('dragover'); 
     } 
     return false; 
    } 

    // dragleave event handler 
    function dragleave(e) { 
     e.preventDefault(); 
     e.stopPropagation(); 
     var data = $('ul.select-list').data(); 
     if (!data.draggedObj || !isDropZone($(this), data.draggedObj)) { 
      return; 
     } 
     var item = $(this).removeClass('dragover'); 
     var slots = data.draggedObj.data('slots'); 
     for (var i = 1; i < slots; i++) { 
      item = item.next('li').removeClass('dragover'); 
     } 
     return false; 
    } 

    // drop event handler 
    function drop(e) { 
     e.stopPropagation(); 
     e.preventDefault(); 
     var data = $('ul.select-list').data(); 
     if (data.draggedObj || !isDropZone($(this), data.draggedObj)) { 
      data.target = $(this); 
      data.draggedObj.trigger('dragend'); 
     } 
     return false; 
    } 

    // dragend event handler 
    function dragend(e) { 
     var data = $('ul.select-list').data(); 
     if (data.draggedObj && data.target && isDropZone(data.target, data.draggedObj)) { 
      var item = data.target.hide(); 
      var slots = data.draggedObj.data('slots'); 
      for (var i = 1; i < slots; i++) { 
       item = item.next('li').hide(); 
      } 
      data.target.before(data.draggedObj); 
     } 

     data.target = undefined; 
     data.draggedObj = undefined; 
     $('ul.drop-list').find('li').removeClass('dragover'); 
    } 
}(jQuery)); 

सीएसएस:

ul { 
    list-style-type: none; 
    margin: 0; 
    padding: 0; 
    float: left; 
} 
li { 
    width: 150px; 
} 
li.header { 
    height:20px; 
    font-weight:bold; 
} 
.select-list li { 
    margin-bottom: 10px; 
} 
.drop-list { 
    margin-left:20px; 
} 
.drop-list li { 
    background-color: #ccc; 
    border-left: 1px solid black; 
    border-right: 1px solid black; 
    border-top: 1px solid black; 
} 
.drop-list li.dragover { 
    background-color:#fff; 
} 
.drop-list li:last-child { 
    border-bottom: 1px solid black; 
} 
li.s1 { 
    background-color: #FFE5E5; 
} 
li.s2 { 
    background-color: #C6D4FF; 
} 
li.s3 { 
    background-color: #C6FFE3; 
} 

संपादित करें: निम्न स्क्रिप्ट में भी सॉर्टिंग जोड़ा गया है। मैंने इस उदाहरण का परीक्षण नहीं किया है और यह कुछ शर्तों के तहत प्रदर्शन नहीं कर सकता है।

(function ($, undefined) { 
    // document ready function 
    $(function() { 
     init(); 

     $('ul.select-list,ul.drop-list').on({ 
      'dragstart': dragstart, 
       'dragend': dragend 
     }, 'li.object').on('dragenter dragover', listDragover); 

     $('ul.drop-list').on({ 
      'dragenter dragover': dragover, 
       'dragleave': dragleave, 
       'drop': drop 
     }, 'li.dropzone'); 
    }); 

    // Initializes the lists 
    function init() { 
     $('ul.select-list').find('li').not('[class="header"]').each(function() { 
      var height = getSlotHeight() * $(this).data('slots'); 
      $(this).height(height); 
     }).attr('draggable', true).addClass('object'); 

     $('ul.drop-list').find('li').each(function() { 
      $(this).height(getSlotHeight()); 
     }).addClass('dropzone'); 
    } 

    // Get the height of the grid 
    function getSlotHeight() { 
     return 20; 
    } 

    /** 
    * Checks whether target is a kompatible dropzone 
    * A dropzone needs the dropzone class 
    * and needs to have enough consequent slots to drop the object into 
    */ 
    function isDropZone(target, draggedObj) { 
     var isDropZone = true; 
     var slots = draggedObj.data('slots'); 
     for (var i = 1; i < slots; i++) { 
      target = target.next('li'); 
      if (target.size() == 0 || !target.hasClass('dropzone')) { 
       if (!target.is(draggedObj)) { 
        isDropZone = false; 
        break; 
       } else { 
        i--; 
       } 
      } 
     } 
     return isDropZone; 
    } 

    // dragstart event handler 
    function dragstart(e) { 
     e.stopPropagation(); 
     var dt = e.originalEvent.dataTransfer; 
     dt.effectAllowed = 'move'; 
     dt.setData('text/html', ''); 
     $('ul.select-list').data({ 
      draggedObj: $(this) 
     });   
    } 

    // dragover list event handler 
    function listDragover(e) { 
     e.preventDefault(); 
     e.stopPropagation(); 
     e.originalEvent.dataTransfer.dropEffect = 'none'; 
     var data = $('ul.select-list').data(); 
     if (data.draggedObj) { 
      var item = data.draggedObj; 
      item.hide(); 
      if (data.draggedObj.closest('ul').is('ul.drop-list')) { 
       var slots = item.data('slots'); 
       for (var i = 0; i < slots; i++) { 
        item = item.next('li').show(); 
       } 
      } 
     } 
     return false; 
    } 

    // dragover event handler 
    function dragover(e) { 
     e.preventDefault(); 
     e.stopPropagation(); 
     var data = $('ul.select-list').data(); 
     if (!data.draggedObj || !isDropZone($(this), data.draggedObj)) { 
      e.originalEvent.dataTransfer.dropEffect = 'none'; 
      return; 
     } 
     e.originalEvent.dataTransfer.dropEffect = 'move'; 
     var item = $(this).addClass('dragover'); 
     var slots = data.draggedObj.data('slots'); 
     for (var i = 1; i < slots; i++) { 
      item = item.next('li'); 
      if (!item.is(data.draggedObj)) { 
       item.addClass('dragover'); 
      } else { 
       i--; 
      } 
     } 
     return false; 
    } 

    // dragleave event handler 
    function dragleave(e) { 
     e.preventDefault(); 
     e.stopPropagation(); 
     var data = $('ul.select-list').data(); 
     if (!data.draggedObj || !isDropZone($(this), data.draggedObj)) { 
      return; 
     } 
     var item = $(this).removeClass('dragover'); 
     var slots = data.draggedObj.data('slots'); 
     for (var i = 1; i < slots; i++) { 
      item = item.next('li'); 
      if (!item.is(data.draggedObj)) { 
       item.removeClass('dragover'); 
      } else { 
       i--; 
      } 
     } 
     return false; 
    } 

    // drop event handler 
    function drop(e) { 
     e.stopPropagation(); 
     e.preventDefault(); 
     var data = $('ul.select-list').data(); 
     if (data.draggedObj || !isDropZone($(this), data.draggedObj)) { 
      data.target = $(this); 
      data.draggedObj.trigger('dragend'); 
     } 
     return false; 
    } 

    // dragend event handler 
    function dragend(e) { 
     var data = $('ul.select-list').data(); 
     var target = data.target; 
     if (data.draggedObj && !target && data.draggedObj.closest('ul').is('ul.drop-list')) { 
      target = data.draggedObj.next('li'); 
     } 
     if (data.draggedObj && target && isDropZone(target, data.draggedObj)) { 
      data.draggedObj = data.draggedObj.insertBefore(target); 
      var item = target.hide(); 
      var slots = data.draggedObj.data('slots'); 
      for (var i = 1; i < slots; i++) { 
       item = item.next('li').hide(); 
      } 
     } 
     if (data.draggedObj) { 
      data.draggedObj.show(); 
     } 
     data.target = undefined; 
     data.draggedObj = undefined; 
     $('ul.drop-list').find('li').removeClass('dragover'); 
    } 
}(jQuery)); 
+0

यह बहुत अच्छा है, बस मुझे 'कूबड़' पाने के लिए और हमारे ग्राहक को समाधान प्रदान करने की आवश्यकता थी। पहेली सही है, आपकी मदद के लिए फिर से धन्यवाद। –

संबंधित मुद्दे