對移動效果提取出了一個公共方法,用JS封裝了一個類,可以直接NEW出來,就可以使用了
//進入拖動模式
$("#editButton").click(function(){
var moveObj = $("tbody tr");
//移動時輔助提示信息,重寫
MoveTR.prototype.show_moveMsg = function(){
show_moveMsg(this);//根據需求重寫的方法
};
//移動結果控制 重寫
MoveTR.prototype.lesMove = function(){
lesMove(this); //根據需求重寫的方法
};
var move = new MoveTR(moveObj); //爲行添加移動事件
});
移動效果:
具體效果需要自己去重寫,包括移動結果的控制和顯示的提示信息
移動層的顯示效果基本是複製的列表TR,具體可以參考下面的示例對css樣式進行調整。
.moveFloor {
width:98%;
position:absolute;
opacity:0.6;
filter:alpha(opacity=40); /* For IE8 and earlier */
border:1px dashed Orange;
border-radius:5px;
box-shadow:5px 5px 2px #bbbbbb;
}
.moveMsg{
position:absolute;
border: 1px dashed Orange;
background-color:Orange;
border-radius:5px;
box-shadow:3px 3px 2px #999999;
}
.moveMsg font{
font:12px/180% Arial, Helvetica, sans-serif,"宋體";
padding:1em 1em;
}
【1】在封裝的過程中遇到一個問題:
在用new MoveTR($(‘tr’));的時候,在構造函數中直接對所有tr註冊事件,事件執行的方法中需要再次調用MoveTR的方法,但此時使用this調用會產生問題,因爲此時的this已經指向了觸發事件的TR(DOM對象),和註冊事件外面的this指向的內容不同。所以此時要將外面的this重新起個名字 比如:var thisObj = this;這樣就可以在MoveTR成員內聲明的方法中調用MoveTR中的任意對象了,JS方法也是一種對象(Function對象)。想詳細瞭解,可以參考文章後面的鏈接。
【2】在拖動過程中要禁用鼠標的選擇文本功能:
如果不禁用,會產生拖拽過程中把列表內容選中的尷尬。
unselect() 禁用, onselect() 啓用
MoveTR.js 可以作爲公共方法使用,需要jQuery插件支持
/*
爲行添加移動動作
moveObjs 爲jQuery對象,tr數組
複用根據需要重寫 show_moveMsg() lesMove() 方法
*/
function MoveTR(moveObjs){
this.moveObjs = moveObjs;
this.beginMoving = false;
this.count = moveObjs.length;
this.startObj = new Object();
this.startIndex = 0;
this.endIndex = 0;
this.endObj = new Object();
this.moveFloor_top = 0;
this.trHeight = 0;
this.addTop = 0;
this.mouseShowHeight = 0 ; //鼠標距離頂端距離
this.init(); //【1】
}
MoveTR.prototype.init = function(){
var movetrObj = this;
//【1】
//注意這裏,此this指向MoveTR的實例,
//而註冊事件function中的this指向觸發事件的元素(DOM對象)
//所以此處this要重新命名,以防止後面無法調用MoveTR中的方法或元素
if(movetrObj.moveObjs.length > 0){
movetrObj.moveObjs.mousedown(function(obj){
movetrObj.MouseDown(this,obj);
});
movetrObj.moveObjs.mouseup(function(obj){
//MouseUpToMove(this,obj);
movetrObj.MouseUp(obj);
});
movetrObj.moveObjs.mousemove(function(obj){
//MouseMoveToMove(this,obj);
movetrObj.MouseMove(obj);
});
}
}
MoveTR.prototype.clear = function(){
if(this.count < 1){
return "Error: count=0";
}
this.onselect();
moveObjs.removeClass("moveElement");
}
MoveTR.prototype.MouseDown = function(obj, mouse){
//鼠標點下事件
//showWinMsg("這樣可以的","OK",0.1);
this.startObj = obj;
this.startIndex =$(obj ).parent().children().index(this.startObj); //開始的tr index
this.trHeight = $(this.startObj).css("height").replace("px","");
this.startObj.style.zIndex = 1;
this.minTop = $(this.startObj).parents('tbody').offset().top;
this.maxTop = $(this.startObj).parent().children().eq(this.count - 1 ).offset().top -( - this.trHeight);
//startObj.mouseDownY=mouse.clientY;
//startObj.mouseDownX=mouse.clientX;
this.beginMoving = true;
this.startObj.setCapture();
this.show_moveDiv();
}
MoveTR.prototype.MouseMove = function (mouse){
//鼠標移動事件
if(! this.beginMoving) {
return false;
}
this.endIndex = Math.floor( this.addTop / this.trHeight ) + this.startIndex; //獲得結束位置的 index, Math.floor向下取整,ceil向上取整
this.endObj = $(this.startObj).parent().children().get( this.endIndex );
this.mouseShowHeight = mouse.clientY; //鼠標距離document上部基準線高度
//$(this.startObj).addClass("clickTR");
this.move_moveDiv(); //移動效果層
this.show_moveMsg(); //顯示提示信息
}
MoveTR.prototype.MouseUp = function ( mouse){
$(".moveFloor").remove();//刪除效果層
$(".moveMsg").remove();//刪除提示信息層
//鼠標彈起事件
// showWinMsg(this.beginMoving,"OK",0.5);
if(! this.beginMoving) {
return false;
}
this.beginMoving = false;
//鼠標相對開始單元格移動距離,單位px, + 滾動條捲上去的高度以修正誤差
this.addTop = mouse.clientY - $(this.startObj).offset().top + $(document).scrollTop();
this.endIndex = Math.floor( this.addTop / this.trHeight ) + this.startIndex; //獲得結束位置的 index, Math.floor向下取整,ceil向上取整
this.endObj = $(this.startObj).parent().children().get( this.endIndex );
this.lesMove();
}
//創建一個跟隨鼠標的移動層
MoveTR.prototype.show_moveDiv = function (){
var floatdiv = $( this.startObj).eq(0).clone();//複製一個當前移動的對象
floatdiv.addClass("moveFloor"); //移動層
this.moveFloor_top = $(this.startObj).offset().top -5;
var left = $(this.startObj).offset().left -3;
floatdiv.css({'top':this.moveFloor_top +'px','left:':left +'px'}); //指定初始位置
var children = floatdiv.children();
if(children.length > 0){
var ths = $(this.startObj).parents("table").find("thead tr").eq(0).children(); //獲得標題元素
//alert(ths.length);
var ths_index = 0;
//獲取顯示的內容
//showWinMsg(tds.length,"OK",1);
for(var i =0 ;i< children.length;i++)
{
var width = $(ths[ths_index]).css("width");
if(width != "" && width !="undefined"){
$(children[i]).css({"width": width }) ;
if(ths_index < ths.length-1){
ths_index ++ ;
}
}else{
$(children[i]).css({"width": "50px" }) ;
}
}
}
$(this.startObj).parents('tbody').append(floatdiv);
$(this.startObj).parents('tbody').append("<div id='moveMsg' class='moveMsg' hidden></div>");
}
//移動 效果層
MoveTR.prototype.move_moveDiv = function (){
var hiddenHeight = $(document).scrollTop(); //滾動條上部隱藏高度
var documentHeight = $(document).height(); //顯示區域總高度,隱藏+顯示
var showHeight = $(window).height(); //當前框架的高度
var floatdiv =$(".moveFloor");
this.addTop = this.mouseShowHeight - $(this.startObj).offset().top + hiddenHeight;
this.moveFloor_top = $(this.startObj).offset().top - 5 + this.addTop;
//var trHeight = $(this.startObj).css("height").replace("px","");
//showWinMsg(showHeight+"|"+maxTop+"|"+mouseShowHeight+"|"+top,"OK",1);
if( this.mouseShowHeight > 0 && this.mouseShowHeight < hiddenHeight){
$(document).scrollTop(hiddenHeight - this.trHeight ); //鼠標在顯示區域上部,向上滾動
}
if( this.mouseShowHeight > showHeight - 2 * this.trHeight ){
$(document).scrollTop(hiddenHeight -( - this.trHeight )); //鼠標持續向下移動,向下滾動
}
//var startIndex =$("#tableList tbody tr").index(this.startObj);
//var endIndex = Math.floor( this.addTop/this.trHeight ) + this.startIndex;
if( this.moveFloor_top < this.minTop ){
this.moveFloor_top = this.minTop - this.trHeight ;
}
if(this.moveFloor_top > this.maxTop){
this.moveFloor_top = this.maxTop + Math.ceil(this.trHeight /3) ;
}
floatdiv.css({'top':this.moveFloor_top+'px'});
this.presentObj = $(this.startObj).parent().children().get(this.endIndex );
}
MoveTR.prototype.lesMove = function(){
if(this.startIndex == this.endIndex){
return;
}else if(this.endIndex >= 0 && this.endIndex < this.count){
//拖動後,如果目的位置與原位置的首頁顯示屬性不一致,則修改爲目的位置的值
if(this.startIndex < this.endIndex){
//往下拖動
$(this.startObj).insertAfter(this.endObj);
}else{
//往上拖動
$(this.startObj).insertBefore(this.endObj);
}
}
}
MoveTR.prototype.show_moveMsg = function (){
//輔助性提示信息
//moveFlag ()
var showStr = "移動到";
var moveMsg_left = this.trHeight - (-5);
var moveMsg_top = this.moveFloor_top -(-this.trHeight-5) ;
$(".moveMsg").css({'top':moveMsg_top+'px','left': moveMsg_left+'px'});
$(".moveMsg").hide();
if(showStr != ""){
$(".moveMsg").html("<font>"+showStr+"</font>");
$(".moveMsg").show();
}
}
//禁用鼠標選擇文字
MoveTR.prototype.unselect = function(){
$('body').each(function() {
$(this).attr('unselectable', 'on').css({
'-moz-user-select':'none',
'-webkit-user-select':'none',
'user-select':'none'
}).each(function() {
this.onselectstart = function() { return false; };
});
});
}
//啓用鼠標選擇文字
MoveTR.prototype.onselect = function(){
$('body').each(function() {
$(this).attr('unselectable', '').css({
'-moz-user-select':'',
'-webkit-user-select':'',
'user-select':''
});
});
}
//幫助
MoveTR.prototype.help = function(){
return
"爲行添加移動動作:<br>"
+"使用方法 var movetr = new MoveTR($('tbody tr') ); 參數爲jQuery對象(tr數組)<br>"
+" //移動時輔助提示信息,重寫<br>"
+" MoveTR.prototype.show_moveMsg = function(){<br>"
+" show_moveMsg(this);<br>"
+" };<br>"
+" //移動結果控制 重寫<br>"
+" MoveTR.prototype.lesMove = function(){<br>"
+" lesMove(this);<br>"
+" };<br>"
+"複用根據需要重寫 show_moveMsg() lesMove() 方法<br>";
}
參考資料:
認識JS中的FUNCTION和THIS:
http://www.cnblogs.com/yuzhongwusan/archive/2012/04/09/2438569.html