JQuery UI的拖拽功能


JQuery UI是JQuery官方支持的WebUI 代碼庫,包含底層交互、動畫、特效等API,並且封裝了一些Web小部件(Widget)。同時,JQuery UI繼承了jquery的插件支持,有大量的第三方插件可以豐富JQuery UI的功能。
JQuery UI提供的API極大簡化了拖拽功能的開發。只需要分別在拖拽源(source)和目標(target)上調用draggable和droppable兩個函數即可。

拖拽原理

首先要明確幾個概念。
  ource:拖拽源,要拖動的元素。
  taerget:拖放目標,能夠放入source的容器。
拖拽的動作分解如下:
  1. drag start:在拖拽源(source)上按下鼠標並開始移動
  2. drag move: 移動過程中
  3. drag enter:  移動進入目標(target)容器
  4. drag leave: 移出目標(target)容器
  5. drop: 在目標(target)容器上釋放鼠標
  6. drag end: 結束
在html5之前,頁面元素不直接支持拖拽事件。所以都是通過監聽鼠標事件並記錄拖拽狀態的方式來實現拖拽功能。

最簡單的例子

最簡單的拖拽是不改變元素所在的容器,而只改變其位置。例子如下:

01 <html>
02 <head></head>
03 <body>
04 <div id="container">
05 <div id="dragsource">
06 <p>拽我!</p>
07 </div>
08 </div><!-- End container -->
09 <script type="text/javascript" src="js/jquery-1.7.min.js"></script>
10 <script type="text/javascript" src="js/jquery-ui-1.8.16.custom.min.js"></script>
11 <script>
12 $(function() {
13 $( "#dragsource" ).draggable();
14 })
15 </script>
16 </body>
17 </html>

 

拖動到另一個容器

更常見的場景是將元素拖動到另一個容器中。這就需要在drop目標(target)容器上應用droppable函數。讓我們在上一個例子的基礎上,增加一個div作為容器,並應用droppable函數:

01 <html>
02 <head></head>
03 <body>
04 <div id="container">
05 <div id="dragsource">
06 <p>拽我!</p>
07 </div>
08 </div><!-- End container -->
09  
10 <div id="droppalbe" style="width: 300px;height:300px;background-color:gray">
11 <p>Drop here</p>
12 </div>
13  
14 <script type="text/javascript" src="js/jquery-1.7.min.js"></script>
15 <script type="text/javascript" src="js/jquery-ui-1.8.16.custom.min.js"></script>
16 <script>
17 $(function() {
18 $( "#dragsource" ).draggable();
19 $( "#droppable" ).droppable();
20 })
21 </script>
22 </body>
23 </html>

 

事件監聽和回顯(Feedback)

運行上一個例子,你可能會產生疑惑,真的放到目標容器上了嗎?用戶也會產生同樣的疑惑。所以,可以監聽拖動過程中發生的一些事件,並用可見的方式讓用戶知道。這就叫做回顯(Feedback)。

對於源(source),可以監聽的事件包括:

  create: 在source上應用draggable函數時觸發
  start:開始拖動時觸發
  drap:拖動過程中觸發
  stop:釋放時觸發
對於目標(target),可以監聽的事件包括:
  create: 在target上應用droppable函數時觸發
  activate:如果當前拖動的source可以drop到本target,則觸發
  deactivate:如果可以drop到本target的拖拽停止,則觸發
  over:source被拖動到target上面
  out:source被拖動離開target
  drop:source被釋放到target
事件處理函數都是通過draggable和droppable函數的參數傳遞,在這些事件處理函數中就可以進行Feedback。看一下實際的例子:

01 <html>
02 <head>
03  
04 </head>
05 <body>
06 <div id="dragsource">
07 <p id="targetMsg">:-|</p>
08 </div>
09  
10 <div id="droppable" style="background-color:gray;height:300">
11 <p>Can drop! </p>
12 </div>
13  
14 <script type="text/javascript" src="js/jquery-1.7.min.js"></script>
15 <script type="text/javascript" src="js/jquery-ui-1.8.16.custom.min.js"></script>
16 <script>
17 $(function() {
18 $( "#dragsource" ).draggable({
19 start: function(event,ui) {
20 $(this).find("p").html(":-S");
21 },
22 stop:function(event,ui){
23 $(this).find("p").html(":-|");
24 }
25 });
26  
27 $( "#droppable" ).droppable({
28 activate: function(event,ui) {
29 $(this).find("p").html( "Drop here !" );
30 },
31 over: function(event,ui) {
32 $( this ).find( "p" ).html( "Oh, Yeah!" );
33  
34 },
35 out: function(event,ui) {
36 $( this ).find( "p" ).html( "Don't leave me!" );
37  
38 },
39 drop: function( event, ui ) {
40 $( this ).find( "p" ).html( "I've got it!" );
41 }
42 });
43 })
44 </script>
45 </body>
46 </html>

 

復制拖動

前面的例子都是移動元素,另一種常見的場景是復制拖動。比如visio中的從畫板中拖動元素到畫布。這是通過draggable函數的helper參數設定的。

helper可以指定為“original”, "clone",其中"original"是默認值,即拖動自身,而clone表示創建自身的一個克隆用於拖拽。helper還可以指定為函數,該函數返回一個自定義的DOM元素用於拖拽。
當不是拖動自身的時候,需要在target上指定drop事件函數,在該函數中將特定的元素添加到target容器上,否則drop的時候什么事情都不會發生。
簡單復制的例子如下:

01 <html>
02 <head></head>
03 <body>
04  
05 <div id="dragsource">
06 <p>拽我!</p>
07 </div>
08 <div id="container" style="background-color:gray;height:300">
09 </div><!-- End container -->
10 <script type="text/javascript" src="js/jquery-1.7.min.js"></script>
11 <script type="text/javascript" src="js/jquery-ui-1.8.16.custom.min.js"></script>
12 <script>
13 $(function() {
14 $( "#dragsource" ).draggable({
15 helper:"clone"
16 });
17  
18 $("#container").droppable({
19 drop:function(event,ui){
20 $(this).append($("<p style='position:absolute;left:"+
21 ui.offset.left+";top:"+ui.offset.top+"'>clone</p>"));
22 }
23 });
24 })
25 </script>
26 </body>
27 </html>

 

拖動控制

到目前位置,所有的例子中都可以對source隨意拖動。在實際應用中經常需要對拖動行為進行控制。下面給出幾個例子。

拖動方向

默認拖動方向為x,y兩個方向。通過draggable的axis參數可以限制只能水平或豎直拖動。如下:

01 <html>
02 <head></head>
03 <body>
04  
05 <div id="dragX">
06 <p>--</p>
07 </div>
08 <div id="dragY">
09 <p>|</p>
10 </div>
11  
12 <script type="text/javascript" src="js/jquery-1.7.min.js"></script>
13 <script type="text/javascript" src="js/jquery-ui-1.8.16.custom.min.js"></script>
14 <script>
15 $(function() {
16 $("#dragX").draggable({axis:"x"});
17 $("#dragY").draggable({axis:"y"});
18 });
19 </script>
20 </body>
21 </html>

 

拖動范圍

除了方向之外,還可以通過containment參數約束拖動的范圍。該參數接受Selector, Element, String, Array類型。其中String可以為parent,document,window,Array是指定一個矩形區域(regin)的四元數組: [x1,y1,x2,y2]。下面的例子分別指定了parent和regin作為范圍限制:

01 <html>
02 <head></head>
03 <body>
04 <div id="container" style="background-color:gray;height:300">
05 <div id="draggable1" style="background-color:red;height:20;width:100">
06 <p>in parent</p>
07 </div>
08  
09 <div id="draggable2" style="background-color:green;height:20;width:100">
10 <p>in regin</p>
11 </div>
12  
13 <script type="text/javascript" src="js/jquery-1.7.min.js"></script>
14 <script type="text/javascript" src="js/jquery-ui-1.8.16.custom.min.js"></script>
15 <script>
16 $(function() {
17 $("#draggable1" ).draggable({containment: "parent" });
18 $("#draggable2").draggable({containment: [20,20,300,200] });
19 });
20 </script>
21 </body>
22 </html>

 

拖動吸附

還可以在拖動的時候吸附到其他元素或網格。使用snap參數指定要吸附到的元素,使用grid參數指定吸附到網格,如下:

01 <html>
02 <head>
03 <style>
04 .draggable {background-color:green; width: 90px; height: 80px; padding: 5px; float: left; margin: 0 10px 10px 0; font-size: .9em; }
05 </style>
06 </head>
07 <body>
08 <div id="container" style="background-color:gray;height:300">
09 <div id="draggable1" class="draggable">
10 <p>吸附到其他可拖拽元素</p>
11 </div>
12  
13 <div id="draggable2" class="draggable">
14 <p>吸附到容器</p>
15 </div>
16  
17 <div id="draggable3" class="draggable">
18 <p>吸附到網格(30x30)</p>
19 </div>
20 </div><!--container-->
21  
22 <script type="text/javascript" src="js/jquery-1.7.min.js"></script>
23 <script type="text/javascript" src="js/jquery-ui-1.8.16.custom.min.js"></script>
24 <script>
25 $(function() {
26 $("#draggable1").draggable({ snap: true });
27 $("#draggable2").draggable({ snap: "#container"});
28 $("#draggable3").draggable({grid: [30,30]});
29 });
30 </script>
31 </body>
32 </html>

 

拖動把手(handle)

默認是整個元素都可以拖動,也可以指定元素的某個子元素作為拖動的handle,如:

1 <div id="draggable">
2 <p>handle</p>
3 </div>
4 ……
5 <script>
6 $("#draggable").draggable({handle:"p"});
7 </script>

 

Drop限制

默認的droppable指定元素能夠接受所有的drop, 但是可以通過accept參數限定只能接受某些元素的drop。accept參數的類型為一個符合jquery selector的字符串。例如:
$(".selector").droppable({ accept: '.special' })
表示只接受具有special 樣式的元素。

增強用戶體驗

前面是實現拖拽的功能,JQueryUI還有一些參數可以增強用戶體驗。比如,cursor參數可以指定鼠標指針的形狀,cursorAt指定鼠標指針在source的相對位置,revert可以指定當drop失敗時source“飄”回原來的位置。一個組合的例子如下:

01 <html>
02 <head>
03 <style>
04 .draggable {background-color:green; width: 90px; height: 80px; padding: 5px; float: left; margin: 0 10px 10px 0; font-size: .9em; }
05 .droppable { width: 300px; height: 300px; background-color:red}
06  
07 </style>
08 </head>
09 <body>
10 <div id="draggable2" class="draggable">
11 <p>I revert when I'm not dropped</p>
12 </div>
13  
14 <div id="droppable" class="droppable">
15 <p>Drop me here</p>
16 </div>
17 <script type="text/javascript" src="js/jquery-1.7.min.js"></script>
18 <script type="text/javascript" src="js/jquery-ui-1.8.16.custom.min.js"></script>
19 <script>
20 $(function() {
21 $( "#draggable2").draggable({ revert: "invalid",cursor: "move", cursorAt: { top: 56, left: 56 } });
22 $( "#droppable" ).droppable({
23 activeClass: "ui-state-hover",
24 hoverClass: "ui-state-active",
25 drop: function( event, ui ) {
26 $( this )
27 .addClass( "ui-state-highlight" )
28 .find( "p" )
29 .html( "Dropped!" );
30 }
31 });
32 });
33 </script>
34 </body>
35 </html>

 

小結

JQuery UI提供了強大的拖拽功能和良好的用戶體驗,同時又非常容易使用。本文介紹了常用的各種用法。更多的參數還可以參考項目主頁的Draggable 和 Droppable 。

轉自:http://www.cnblogs.com/holbrook/archive/2012/03/13/2394111.html


注意!

本站转载的文章为个人学习借鉴使用,本站对版权不负任何法律责任。如果侵犯了您的隐私权益,请联系我们删除。



 
粤ICP备14056181号  © 2014-2020 ITdaan.com