最近需要用到拖拽,前端人员找了个拖拽代码,主要都是从网上下的,代码如下:
$.fn.extend({
Drag: function() {
$(this).attr("isDrag", 1);
$(this).mousedown(function(e) {
if ($(this).attr("isDrag") == 0) return;
$(this).attr("drag", 1);
$(this).css("position", "absolute");
$(this).css("cursor", "default");
var currentTarget = $(this);
var currentDisX = e.pageX - $(this).offset().left;
var currentDisY = e.pageY - $(this).offset().top;
$(document).mousemove(function(event) {
if ($(currentTarget).attr("drag") == 0 || $(currentTarget).attr("mode") == "re") return;
var currentX = event.clientX;
var currentY = event.clientY;
var cursorX = event.pageX - currentDisX; // $(this).offset().left;
var cursorY = event.pageY - currentDisY; //-$(this).offset().top;
$(currentTarget).css("top", cursorY "px").css("left", cursorX "px");
});
$(document).mouseup(function() {
$(currentTarget).attr("drag", 0);
});
});
},
DisDrag: function() {
$(this).attr("isDrag", 0);
$(this).attr("drag", 0);
},
Resize: function() {
var currentDisTance = 5;
var resizeMode = 0;
var isResize=false;
var isStartResize=false;
$(this).mousemove(function(e) {
var currentDisX = e.pageX - $(this).offset().left;
var currentDisY = e.pageY - $(this).offset().top;
if ($(this).width() - currentDisX < currentDisTance && ($(this).height() - currentDisY) < currentDisTance) {
$(this).css("cursor", "nw-resize");
} else if ($(this).width() - currentDisX < currentDisTance) {
$(this).css("cursor", "e-resize");
} else if ($(this).height() - currentDisY < currentDisTance) {
$(this).css("cursor", "n-resize");
} else {
if(isStartResize==true)return;
$(this).css("cursor", "default");
}
});
$(this).mousedown(function(e) {
isResize=true;
var currentDisX = e.pageX - $(this).offset().left;
var currentDisY = e.pageY - $(this).offset().top;
if ($(this).width() - currentDisX < currentDisTance && ($(this).height() - currentDisY) < currentDisTance) {
$(this).css("cursor", "nw-resize");
$(this).attr("mode", "re");
resizeMode = 0;
} else if ($(this).width() - currentDisX < currentDisTance ) {
$(this).css("cursor", "e-resize");
$(this).attr("mode", "re");
resizeMode = 1;
} else if ($(this).height() - currentDisY < currentDisTance) {
$(this).css("cursor", "n-resize");
$(this).attr("mode", "re");
resizeMode = 2;
} else {
if(isStartResize==true)return;
$(this).css("cursor", "default");
$(this).attr("mode", "me");
}
var currentTarget = $(this);
var offsetWidth=$(this).width()-$(currentTarget).offset().left;
var offsetHeight=$(this).height()-$(currentTarget).offset().top;
//$(this).css("width",currentWidth currentDisX);
$(document).mousemove(function(event) {
if ($(currentTarget).attr("mode") == "me"||isResize==false) return;
isStartResize=true;
var currentX = event.clientX;
var currentY = event.clientY;
var cursorX = event.pageX - currentDisX; // $(this).offset().left;
var cursorY = event.pageY - currentDisY; //-$(this).offset().top;
if (resizeMode == 0) $(currentTarget).css("height", cursorY offsetHeight "px").css("width", cursorX offsetWidth "px");
else if (resizeMode == 1) $(currentTarget).css("width", cursorX offsetWidth "px");
else $(currentTarget).css("height", cursorY offsetHeight "px");
});
});
$(document).mouseup(function() {
isResize=false;
isStartResize=false;
});
}
});
在这里的代码有如下几个问题,resize上绑定move事件,效率太低,而且碰到滚动条时move事件失效,而且事件绑定后没有移除,随着点击次数越多,执行的次数将越多,所以讲代码改成如下:
1.参考jquery UI的risize代码,给div里面添加3个div,用来实现右边右下角下边的resize,去除div的move事件,而且滚动条也不会失效,可以继续拖拽。
2.mouseup事件中移除了所有事件。
3.点击div中的一些特殊控件比方说INPUT时阻止事件继续执行。
4.e.preventDefault(),阻止move事件会选中其他元素
var cancelNodeName = [ "INPUT", "TEXTAREA", "BUTTON" ];
$.fn.extend({
Drag : function(opts) {
$(this).mousedown(function(e) {
if (cancelNodeName.indexOf(e.target.nodeName) >= 0)
return true;
if($( e.target ).closest( ".resizable" ).length > 0)
return true;
console.info("Drag");
var currentTarget = $(this);
var currentDisX = e.pageX - $(this).offset().left;
var currentDisY = e.pageY - $(this).offset().top;
var mousemoveEvent = function(event) {
if ($(event.target).closest(".resizable").length > 0)
return true;
if (opts && opts.beginmove) {
// beginmove返回true则继续执行,否则不执行
if (!opts.beginmove(event)) {
return true;
}
}
currentTarget.attr("moved", 1);
currentTarget.css("position", "absolute");
currentTarget.css("cursor", "hand");
var currentX = event.clientX;
var currentY = event.clientY;
var cursorX = event.pageX - currentDisX; // +$(this).offset().left;
var cursorY = event.pageY - currentDisY; // -$(this).offset().top;
$(currentTarget).css("top", cursorY + "px").css("left", cursorX + "px");
if (opts && opts.resize) {
opts.resize(event, {
'width' : $(currentTarget).width(),
'height' : $(currentTarget).height()
});
}
};
$(document).on("mousemove", mousemoveEvent);
var mouseupEvent = function() {
$(document).off("mousemove", mousemoveEvent);
$(document).off("mouseup", mouseupEvent);
}
$(document).on("mouseup", mouseupEvent);
if (opts && opts.stopDefault) {
opts.stopDefault(e);
}
});
},
DisDrag : function() {
$(this).attr("isDrag", 0);
$(this).attr("drag", 0);
},
Resize : function(opts) {
var options={
mode:{"se-resize":0,"e-resize":1,"s-resize":2}
};
var currentTarget = $(this);
var currentDisTance = 5;
var resizeMode = 0;
var isResize = false;
var isStartResize = false;
// 创建3个div来实现拖动按钮。
$(this).append("<div class='resizable'style='cursor:e-resize;width:7px;right:-5px;height:100%;top:0;z-index:99;position:absolute'></div>");
$(this).append("<div class='resizable' style='cursor:s-resize;height:7px;bottom:-5px;width:100%;left:0;z-index:99;position:absolute'></div>");
$(this).append("<div class='resizable' style='cursor:se-resize;width:16px;height:16px;z-index:99;right:1px;bottom:1px;position:absolute'></div>");
$(this).mousedown(function(e) {
console.info($( e.target ).closest( ".resizable" ).length < 0);
if (cancelNodeName.indexOf(e.target.nodeName) >= 0)
return true;
if($( e.target ).closest( ".resizable" ).length <=0)
return true;
console.info("move");
var currentDisX = e.pageX - $(this).offset().left;
var currentDisY = e.pageY - $(this).offset().top;
var offsetWidth = $(this).width() - $(currentTarget).offset().left;
var offsetHeight = $(this).height() - $(currentTarget).offset().top;
var rmousemoveEvent = function(event) {
var currentX = event.clientX;
var currentY = event.clientY;
var cursorX = event.pageX - currentDisX; // +$(this).offset().left;
var cursorY = event.pageY - currentDisY; // -$(this).offset().top;
var resizeMode=options.mode[$(e.target).css("cursor")];
if (resizeMode == 0)
$(currentTarget).css("height", cursorY + offsetHeight + "px").css("width", cursorX + offsetWidth + "px");
else if (resizeMode == 1)
$(currentTarget).css("width", cursorX + offsetWidth + "px");
else
$(currentTarget).css("height", cursorY + offsetHeight + "px");
if (opts && opts.resize) {
opts.resize(event, {
'width' : $(currentTarget).width(),
'height' : $(currentTarget).height()
});
}
};
$(document).on("mousemove", rmousemoveEvent);
var rmouseupEvent = function(event) {
$(document).off("mousemove", rmousemoveEvent);
$(document).off("mouseup", rmouseupEvent);
};
$(document).on("mouseup", rmouseupEvent);
e.preventDefault();
});
}
});
$(function() {
$("#dragDiv").Drag();
$("#dragDiv").Resize();
});