2012-08-23 35 views
6

我有以下元素:只下降到被認爲是

我試圖設定,讓當你拖動項目,它只被降到你可以看到div元素,並是不是掩蓋起來。

所以我用這個js:

$(".draggable").draggable({ 
    helper: "clone" 
}) 
$("#bottom, .draggable").droppable({ 
    drop: function(event, ui) { 
     var $this = $(this), 
      $dragged = $(ui.draggable); 
     $this.append($dragged.clone()); 
    }, 
    hoverClass: "dragHover" 
})​ 

但它滴在元素都地方即使只有落區之一的可見!

我該如何解決這個問題?不是發生?

小提琴:http://jsfiddle.net/maniator/Wp4LU/


額外的信息來重新頁面而不小提琴:

HTML:

<div id="top"> 
    <div class="draggable"> 
     Lorem ipsum dolor sit amet 
    </div> 

    <div class="draggable"> 
     Lorem ipsum dolor sit amet 
    </div> 

    <div class="draggable"> 
     Lorem ipsum dolor sit amet 
    </div> 

    <div class="draggable"> 
     Lorem ipsum dolor sit amet 
    </div> 

    <div class="draggable"> 
     Lorem ipsum dolor sit amet 
    </div> 

    <div class="draggable"> 
     Lorem ipsum dolor sit amet 
    </div> 

    <div class="draggable"> 
     Lorem ipsum dolor sit amet 
    </div> 

    <div class="draggable"> 
     Lorem ipsum dolor sit amet 
    </div> 

    <div class="draggable"> 
     Lorem ipsum dolor sit amet 
    </div> 

    <div class="draggable"> 
     Lorem ipsum dolor sit amet 
    </div> 

    <div class="draggable"> 
     Lorem ipsum dolor sit amet 
    </div> 

    <div class="draggable"> 
     Lorem ipsum dolor sit amet 
    </div> 

    <div class="draggable"> 
     Lorem ipsum dolor sit amet 
    </div> 

    <div class="draggable"> 
     Lorem ipsum dolor sit amet 
    </div> 

    <div class="draggable"> 
     Lorem ipsum dolor sit amet 
    </div> 

    <div class="draggable"> 
     Lorem ipsum dolor sit amet 
    </div> 

    <div class="draggable"> 
     Lorem ipsum dolor sit amet 
    </div> 

    <div class="draggable"> 
     Lorem ipsum dolor sit amet 
    </div> 

    <div class="draggable"> 
     Lorem ipsum dolor sit amet 
    </div> 

    <div class="draggable"> 
     Lorem ipsum dolor sit amet 
    </div> 

    <div class="draggable"> 
     Lorem ipsum dolor sit amet 
    </div> 

    <div class="draggable"> 
     Lorem ipsum dolor sit amet 
    </div> 

    <div class="draggable"> 
     Lorem ipsum dolor sit amet 
    </div> 

    <div class="draggable"> 
     Lorem ipsum dolor sit amet 
    </div> 

    <div class="draggable"> 
     Lorem ipsum dolor sit amet 
    </div> 

    <div class="draggable"> 
     Lorem ipsum dolor sit amet 
    </div> 
    </div> 

    <div id="bottom"></div> 

CSS:

.draggable { 
    border: 1px solid green; 
    background: white; 
    padding: 5px; 
} 

.dragHover{ 
    background: blue; 
} 

#top { 
    height: 500px; 
    overflow-y: scroll; 
} 
#bottom { 
    height: 150px; 
    overflow-y: scroll; 
    border: red solid 4px; 
} 

+0

因爲它沒有解決活服務器中的問題,所以下面是一個[fiddle](http://jsfiddle.net/ult_combo/Wp4LU/18/),使用disabled屬性來模擬一個'event.stopImmediatePropagation'其他UI小部件,希望如果找不到更好的方法可以改進它。 –

+0

@Neal你不認爲我們可以使用$ this.is(「:visible」)這樣的jQuery屬性。我不太瞭解jquery,但你可以說這是一個新手的嘗試 – Moons

回答

2

嘗試使用accept函數進行設置。 The working demo.

$("#bottom, .draggable").droppable({ 
    drop: function(event, ui) { 
     var $this = $(this), 
      $dragged = $(ui.draggable); 
     $this.append($dragged.clone()); 
    }, 
    accept: function() { 
     var $this = $(this), divTop= $("#top"); 
     if ($this.is(".draggable")) { 
      return $this.offset().top < divTop.offset().top + divTop.height() ; 
     } 
     return true; 
    }, 
    hoverClass: "dragHover" 
})​;​ 
+0

聖真棒^ _ ^這似乎是工作:-)。我必須再測試一下:-D。非常感謝! – Neal

2

如果我給你正確的 - 這應該解決您的問題 - http://jsfiddle.net/Wp4LU/60/ 此外,你可以編寫自定義函數接受 - http://jqueryui.com/demos/droppable/#option-accept

代碼:

var draggableList = $('#top'); 

$(".draggable").draggable({ 
    helper: "clone" 
}); 
$("#bottom, .draggable").droppable({ 
    drop: function(event, ui) { 
     var $this = $(this), 
      $dragged = $(ui.draggable); 

     if ($this.hasClass("draggable")) { 
      if ($this.position().top >= draggableList.height() || 
       $this.position().top + $this.outerHeight() >= 
       draggableList.height()) 
       return; 
     } 

     $this.append($dragged.clone()); 
    }, 
    hoverClass: "dragHover" 
})​;​ 
+0

這很好地在小提琴中工作...但它似乎並沒有在我的真實代碼中工作(這看起來有點不同).... – Neal

0

據該人士透露(jquery.ui.droppable.js),拖放操作將搜索每個符合條件的可拖放對象,並將拖放函數應用於與其相交的每個對象:

drop: function(draggable, event) { 

    var dropped = false; 
    $.each($.ui.ddmanager.droppables[draggable.options.scope] || [], function() { 

     if(!this.options) return; 
     if (!this.options.disabled && this.visible && $.ui.intersect(draggable, this, this.options.tolerance)) 
      dropped = this._drop.call(this, event) || dropped; 

(舊版本的最後一個「或」條件反轉,所以它只適用於單個droppable。嘗試你的小提琴使用jQuery 1.5.2/jQuery用戶界面1.8.9,並看到它只能下降到一個元素,儘管是「錯誤」的一個...)

而且只有$.ui.intersect功能考慮到(X,Y)座標:

switch (toleranceMode) { 
    case 'fit': 
     return (l <= x1 && x2 <= r 
      && t <= y1 && y2 <= b); 
     break; 
    case 'intersect': 
     return (l < x1 + (draggable.helperProportions.width/2) // Right Half 
      && x2 - (draggable.helperProportions.width/2) < r // Left Half 
      && t < y1 + (draggable.helperProportions.height/2) // Bottom Half 
      && y2 - (draggable.helperProportions.height/2) < b); // Top Half 
     break; 
    ... 

所以,除非有人增加了一個z-index的感知公差模式,你唯一的選擇就是要解決這個問題莫名其妙。我建議首先將每一個可棄考生一組,當它的時間下降,只選擇了一個「最近的」屏幕:

$("#bottom, .draggable").droppable({ 
    over: function(event, ui) { 
     if (!ui.draggable.data("drop-candidates")) 
      ui.draggable.data("drop-candidates",[]); 
     ui.draggable.data("drop-candidates").push(this); 
    }, 
    out: function(event, ui) { 
     var that = this, 
      candidates = ui.draggable.data("drop-candidates") || []; 
     ui.draggable.data("drop-candidates", $.grep(candidates, function(e) { 
      return e != that; 
     }); 
    }, 
    drop: function(event, ui) { 
     var $this = $(this), 
      $dragged = $(ui.draggable); 
     var candidates = $.data("drop-candidates").sort(closestToScreen); 
     if (candidates[0] == this) 
      $this.append($dragged.clone()); 
    }, 
    hoverClass: "dragHover" 
})​ 

現在,實現closestToScreen比較是棘手的部分。 W3C CSS Specification描述了渲染引擎應該如何對元素進行排序繪製,但目前還無法找到訪問此信息的簡單方法。我也在asked this question在這裏,也許有人會找到一個好方法。


P.S.如果修改了jQuery UI源一種選擇,你可以嘗試實現使用document.getElementFromPoint的z-index感知公差模式,爲this answer對上述問題作出建議:

var x1 = (draggable.positionAbs || draggable.position.absolute).left, x2 = x1 + draggable.helperProportions.width, 
    y1 = (draggable.positionAbs || draggable.position.absolute).top, y2 = y1 + draggable.helperProportions.height; 
switch (toleranceMode) { 
    ... 
    case 'z-index-aware': 
     return document.elementFromPoint(x1,y1) == droppable; 
     break; 

(這將確保元素權低於可拖動的左上角將被認爲是「足夠好」作爲放置目標 - 不理想,但比我們迄今爲止更好;類似的解決方案可以改爲使用鼠標指針座標代替)

而且,不,您不能在以前提供的解決方法中使用此方法:此刻發生下降,拖拽幫手是最靠近屏幕的元素...(編輯:德哦!因爲相同的原因,如果作爲容差模式實施,它將不起作用...)

0

如果你只想元素上落,你可以看到你可以改變你的選擇:

$(".draggable:visible").draggable({ 
    helper: "clone" 
}); 
$("#bottom, .draggable:visible").droppable({ 
    drop: function(event, ui) { 
     var $this = $(this), 
      $dragged = $(ui.draggable); 
     $this.append($dragged.clone()); 
    }, 
    hoverClass: "dragHover" 
})​; 

或者當你隱藏元素的東西改變其可拖動類其他。

+0

這不會工作......事件是**不**授權...... – Neal

+0

@尼爾看來,我沒有得到真正的問題在那裏。看起來你從另一篇文章中得到了答案。祝你好運 – TecHunter

相關問題