2012-07-09 69 views
4

我想要一些正方形的可拖動對象(在這種情況下只有<td>框中包含數字)可以捕捉到一些空的表格單元格並捕捉到這些單元格的中心(空的td框),而不是(外部)邊緣這些細胞,這是默認情況下所做的。如何強制jquery在將元素拖動到另一個容器並將其對齊時將元素居中?

這裏是我的腳本:

<script type="text/javascript"> 
$(document).ready(function() { 
    $(".inputs div").draggable({ 
     snap: ".spaces" 
    });  
});  
</script> 

編輯:這裏是整個文件

<!DOCTYPE html> 
    <head> 
    <title>Draggable</title> 
    <script type="text/javascript" src="jquery-1.7.2.min.js"></script> 
    <script type="text/javascript" src="jquery-ui-1.8.21.custom.min.js"></script> 
    <script type="text/javascript" src="jquery.ui.touch-punch.min.js"></script> 
    <style> 
    .block { 
     z-index:9999; 
     cursor:move; 
    } 
    li { 
     list-style:none; 
    } 
    tr { 
     border: 2px solid black; 
    } 
    table { 
     border: 2px solid black; 
    } 
    .inputs div { 
     float:left; 
     background-color:#FFFFFF; 
     color:#004E66; 
     font-size:x-large; 
     margin:2px; 
     padding:20px; 
     border:1px solid black; 
    } 
    .spaces td { 
     background-color:#666666; 
     margin:2px; 
     padding:36px; 
     border:2px solid black; 
    } 
</style> 
</head> 

<body> 
<form id="form1"> 
    <div class="inputs"> 
    <div>1</div> 
    <div>2</div> 
    <div>3</div>  
    <div>4</div> 
    <div>5</div> 
    <div>6</div> 
    </div> 
    <br/> 
    <table class="spaces"> 
    <tr> 
     <td></td> 
     <td></td> 
     <td></td> 
    </tr> 
    <tr> 
     <td></td> 
     <td></td> 
     <td></td> 
    </tr> 
    </table> 
</form> 
<!-- here we are telling jquery to make each element inside of class 'inputs' draggable --> 
<script type="text/javascript"> 
    $(document).ready(function() { 
     $(".inputs div").draggable({ 
     snap: ".spaces" 
     }).center(); 
    }); 
</script> 

這裏是發生了什麼事情

 
-----+---------+ 
XXXXXXXXXXX X| 
    |   | 
    | Y x| 
    |  X| 
-----+-------+X| 
    |  X| 
  • 的一個粗略的基於文本的說明如果上面的框是topmos右角的td單元格t tr row
  • 然後X是元素當前粘貼的地方(顯然它不是 大,我只是顯示它粘貼的地方......實際上我刪除了 一些X來顯示它如何對齊角落一旦達到 與它的某種接近度......)
  • 基本上這個模型表明只有 表的外部邊緣對於可拖動元素具有「引力」。我真正想要它 要做的就是將斥力捕捉到td單元到所有的邊緣,而不是 吸引到外部的。
  • Y是拖動元素的所需抓取位置。
  • 最後呈現的原因,我想元素咬合到位 帶有某種過渡,而不是突然跳躍...
+0

您是否希望可拖動的元素在tds內垂直和水平居中?因爲他們不適合很好。 – 2012-07-11 05:55:13

+0

4000次閱讀。 9正確的答案upvotes。 4在這個問題上。 moochers。登錄你的口袋! – 2015-07-30 20:35:38

回答

11

我相信這是你想要的。

如果您願意,您可以明顯改變定位,並且它更適合您的需求。

演示是在這裏:DEMO

$(document).ready(function() { 


$(".inputs div").draggable({ 
     opacity: .4, 
     create: function(){$(this).data('position',$(this).position())}, 
     cursorAt:{left:15}, 
     cursor:'move', 
     start:function(){$(this).stop(true,true)} 
    }); 

    $('.spaces').find('td').droppable({ 
     drop:function(event, ui){ 
      snapToMiddle(ui.draggable,$(this)); 
     } 
    }); 

}); 


function snapToMiddle(dragger, target){ 
    var topMove = target.position().top - dragger.data('position').top + (target.outerHeight(true) - dragger.outerHeight(true))/2; 
    var leftMove= target.position().left - dragger.data('position').left + (target.outerWidth(true) - dragger.outerWidth(true))/2; 
    dragger.animate({top:topMove,left:leftMove},{duration:600,easing:'easeOutBack'}); 
} 
+0

哦寶貝!這是迄今爲止的首要考慮。謝謝! – 2012-07-11 23:20:05

+0

好的,所以這不在我的電腦上運行。我從來沒有使用過小提琴,我的代碼完全按照以下方式在此頁面上(https://gist.github.com/3095046)。我錯過了什麼? – 2012-07-12 01:29:49

+0

唯一看起來不同的是你的jQuery UI版本。 jsfiddle使用'jQuery UI 1.8.18' – Jeemusu 2012-07-12 07:59:24

-1

如果我有問題吧,有了這個替換當前的腳本:

$(document).ready(function() { 

    // create a bunch of invisible divs 
    var divs = $('<div></div><div></div><div></div><div></div>'); 

    // make them 2/2 and add them to the existing tds 
    divs.css({ width:'50%', float:'left' }).appendTo('.spaces td'); 

    // snap to everything 
    $(".inputs div").draggable({snap: ".spaces td, .spaces td div" }).center(); 

}); 

如果我不只是說,我會解決它。

+0

更好!它現在對桌子內壁有「吸引力」。但它並不堅持給定細胞的中心。 – 2012-07-11 06:10:03

+0

@David Cell你是指TD還是編號框?你還使用什麼瀏覽器? – 2012-07-11 11:12:42

+0

在jquery或jquery ui中是否有方法'.center()'? – 2014-10-28 18:10:45

1

http://jsfiddle.net/vtdhV/

我創建了一個解決您的問題..之類的(如果我理解正確的話)小提琴。

紅色divs集中在td s之內,您將捕捉到這些紅色div。只要刪除邊框,它就會出現在td的中心。 .draggable的性質將導致可拖動對齊到任何邊緣,而不是同時對齊所有邊緣。

如果這還不夠,您可能需要實現.stop的呼叫處理程序,根據您的期望調整元素的位置。

+0

也許我做得不對,但是當小提琴網站顯示工作代碼時,當我在計算機的Web服務器上嘗試輸出代碼時,元素不可拖動。 – 2012-07-11 06:50:02

+0

@大衛你得到任何類型的錯誤?我從你身上覆制了大部分內容。 – 2012-07-11 07:00:34

+0

沒有錯誤只是不可拖動.. – 2012-07-11 07:04:18

0

在這些tds中添加一個div,並通過爲tds和新添加的div指定固定的寬度和高度來居中它。然後跨越這些divs的可拖動。

$(document).ready(function() { 
    $('<div></div>').appendTo('.spaces td'); 
    $(".inputs div").draggable({ 
     snap: ".spaces td div", 
     snapMode:'inner' 
    }); 
}); 

另外css for tds和divs將如下所示。

.block { 
    z-index:9999; 
    cursor:move; 
} 

.productCode { 

} 

li { 
    list-style:none; 
} 
tr { 
    border: 2px solid black; 
} 
table { 
    border: 2px solid black; 
} 

.inputs div { 
    float:left; 
    background-color:#FFFFFF; 
    color:#004E66; 
    font-size:x-large; 
    margin:2px; 
    padding:20px; 
    border:1px solid black; 
} 

.spaces td { 
    background-color:#666666; 
    width:80px; 
    height:80px;    
    border:2px solid black; 
} 

.spaces td div { 
    margin:0 auto; 
    width:50px; 
    height:70px; 
} 

小提琴演示 - http://jsfiddle.net/nsjithin/u25Bs/1/

1

你需要指定一個單元的目標,其大小爲您拖動的元素相同。如果您的可拖動對象的大小始終相同,則這不是什麼大問題。只需在你的單元格中添加一個空的絕對定位的div,並設置你的CSS,使其正確調整大小和居中。然後,將您的snap選擇器設置爲該div。要僅捕捉到捕捉目標的內部,請將您的snapMode設置爲"inner"

$(".inputs div").draggable({ 
    snap: ".spaces td div", 
    snapMode: "inner" 
}); 

但是,如果你拖拽元素的大小可能會有所不同,你需要調整和每次啓動拖動一個元素時recenter您的拖放目標。做到這一點的可拖動鼠標按下的(使用mousedown因爲dragstart是太晚了,不工作):

$(".inputs div").draggable({ 
    snap: ".spaces td div", 
    snapMode: "inner", 
}).mousedown(function(){ 
    var targets = $(".spaces td div"); 
    targets.height(this.offsetHeight); 
    targets.width(this.offsetWidth); 
    targets.each(function(){ 
     $(this).position({ of: this.parentNode }); 
    }); 
}); 

http://jsfiddle.net/gilly3/mPr3A/

5

一個注意對snapToMiddle功能:

爲了得到它爲我正常工作我不得不改變它>

function snapToMiddle(dragger, target){ 
    var offset = target.offset(); 
    var topMove = (target.outerHeight(true) - dragger.outerHeight(true))/2; 
    var leftMove= (target.outerWidth(true) - dragger.outerWidth(true))/2; 
    dragger.offset({ top: topMove + offset.top, left: leftMove + offset.left }) 
} 

此外,我創建了一個數組,關聯拖動到th e滴管和窗口reSize我確保我所有的滴管不會漫步:

$(window).resize(function() { 
    for(i = 0 ; i < assc.length - 1 ; i++) 
    { 
     var drp = assc[i].drop; 
     var drg = assc[i].drag; 
     snapToMiddle(drg,drp); 
    } 
}); 
+0

Jon Turlington你是我的男人!任何關於如何使它動畫就像jeschafe的答案的想法? 'dragger.animate({頂部:topMove,左:leftMove},{持續時間:600,緩解: 'easeOutBack'});' – Heitor 2016-05-19 07:01:57

相關問題