原生javascript实现DIV拖拽并计算重复面积
<!DOCTYPEhtmlPUBLIC"-//W3C//DTDXHTML1.0Transitional//EN""http://www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dtd"> <htmlxmlns="http://www.w3.org/1999/xhtml"> <head> <metahttp-equiv="Content-Type"content="text/html;charset=gb2312"/> <title>Table</title> </head> <styletype="text/css"> body{margin:0px;padding:0px;font-size:12px} .div{height:160px;width:160px;position:absolute;text-align:center;} .demo1{border:1pxsolid#96C2F1;background-color:#EFF7FF;left:150px;top:20px} .demo2{border:1pxsolid#9BDF70;background-color:#F0FBEB;left:450px;top:20px} .demo3{border:1pxsolid#BBE1F1;background-color:#EEFAFF;left:750px;top:20px} .demo4{border:1pxsolid#96C2F1;background-color:#EEFAFF;left:150px;top:220px} .demo5{border:1pxsolid#FFCC00;background-color:#FFFFF7;left:450px;top:220px} .demo6{border:1pxsolid#E3E197;background-color:#FFFFDD;left:750px;top:220px} .demo7{border:1pxsolid#ADCD3C;background-color:#F2FDDB;left:150px;top:420px} .demo8{border:1pxsolid#F8B3D0;background-color:#FFF5FA;left:450px;top:420px} .demo9{border:1pxsolid#D3D3D3;background-color:#F7F7F7;left:750px;top:420px} .focus{background-color:#990000;} </style> <body> <divid='demo1'class='divdemo1'>demo1</div> <divid='demo2'class='divdemo2'>demo2</div> <divid='demo3'class='divdemo3'>demo3</div> <divid='demo4'class='divdemo4'>demo4</div> <divid='demo5'class='divdemo5'>demo5</div> <divid='demo6'class='divdemo6'>demo6</div> <divid='demo7'class='divdemo7'>demo7</div> <divid='demo8'class='divdemo8'>demo8</div> <divid='demo9'class='divdemo9'>demo9</div> <scriptlanguage="javascript"> (function(window,undefined){ window.Sys=function(ua){ varb={ ie:/msie/.test(ua)&&!/opera/.test(ua), opera:/opera/.test(ua), safari:/webkit/.test(ua)&&!/chrome/.test(ua), firefox:/firefox/.test(ua), chrome:/chrome/.test(ua) },vMark=""; for(variinb){ if(b[i]){vMark="safari"==i?"version":i;break;} } b.version=vMark&&RegExp("(?:"+vMark+")[\\/:]([\\d.]+)").test(ua)?RegExp.$1:"0"; b.ie6=b.ie&&parseInt(b.version,10)==6; b.ie7=b.ie&&parseInt(b.version,10)==7; b.ie8=b.ie&&parseInt(b.version,10)==8; returnb; }(window.navigator.userAgent.toLowerCase());
window.Sys.ie6&&document.execCommand("BackgroundImageCache",false,true);
window.$=function(Id){ returndocument.getElementById(Id); }; window.addListener=function(element,e,fn){ !element.events&&(element.events={}); element.events[e]&&(element.events[e][addListener.guid++]=fn)||(element.events[e]={'0':fn}); element.addEventListener?element.addEventListener(e,fn,false):element.attachEvent("on"+e,fn); }; window.addListener.guid=1; window.removeListener=function(element,e,fn){ varhandlers=element.events[e],type; if(fn){ for(typeinhandlers) if(handlers[type]===fn){ element.removeEventListener?element.removeEventListener(e,fn,false):element.detachEvent("on"+e,fn); deletehandlers[type]; } }else{ for(typeinhandlers){ element.removeEventListener?element.removeEventListener(e,handlers[type],false):element.detachEvent("on"+e,handlers[type]); deletehandlers[type]; } } }; window.setStyle=function(e,o){ if(typeofo=="string") e.style.cssText=o; else for(variino) e.style[i]=o[i]; };
varslice=Array.prototype.slice; window.Bind=function(object,fun){ varargs=slice.call(arguments).slice(2); returnfunction(){ returnfun.apply(object,args); }; }; window.BindAsEventListener=function(object,fun,args){ varargs=slice.call(arguments).slice(2); returnfunction(event){ returnfun.apply(object,[event||window.event].concat(args)); } }; //copyfromjQ window.extend=function(){ vartarget=arguments[0]||{},i=1,length=arguments.length,deep=true,options; if(typeoftarget==="boolean"){ deep=target; target=arguments[1]||{}; i=2; } if(typeoftarget!=="object"&&Object.prototype.toString.call(target)!="[objectFunction]") target={}; for(;i<length;i++){ if((options=arguments[i])!=null) for(varnameinoptions){ varsrc=target[name],copy=options[name]; if(target===copy) continue; if(deep&©&&typeofcopy==="object"&&!copy.nodeType){ target[name]=arguments.callee(deep,src||(copy.length!=null?[]:{}),copy); } elseif(copy!==undefined) target[name]=copy; } } returntarget; }; //copyfromjQ window.each= function(object,callback,args){ varname,i=0,length=object.length; if(args){ args=Array.prototype.slice.call(arguments).slice(2); if(length===undefined){ for(nameinobject) if(callback.apply(object[name],[name,object[name]].concat(args))===false) break; }else for(;i<length;i++) if(callback.apply(object[i],[i,object[i]].concat(args))===false) // break; }else{ if(length===undefined){ for(nameinobject) if(callback.call(object[name],name,object[name])===false) break; }else for(varvalue=object[0]; i<length&&callback.call(value,i,value)!==false;value=object[++i]){} } returnobject; }; window.currentStyle=function(element){ returnelement.currentStyle||document.defaultView.getComputedStyle(element,null); }; window.objPos=function(elem){ varleft=0,top=0,right=0,bottom=0,doc=elem?elem.ownerDocument:document; if(!elem.getBoundingClientRect||window.Sys.ie8){ varn=elem; while(n){left+=n.offsetLeft,top+=n.offsetTop;n=n.offsetParent;}; right=left+elem.offsetWidth;bottom=top+elem.offsetHeight; }else{ varrect=elem.getBoundingClientRect(); left=right=doc.documentElement.scrollLeft||doc.body.scrollLeft; top=bottom=doc.documentElement.scrollLeft||doc.body.scrollLeft; left+=rect.left;right+=rect.right; top+=rect.top;bottom+=rect.bottom; } return{"left":left,"top":top,"right":right,"bottom":bottom}; }; window.hasClass=function(element,className){ returnelement.className.match(newRegExp('(\\s|^)'+className+'(\\s|$)')); }; window.addClass=function(element,className){ !window.hasClass(element,className)&&(element.className+=""+className); }; window.removeClass=function(element,className){ window.hasClass(element,className)&&(element.className=element.className.replace(newRegExp('(\\s|^)'+className+'(\\s|$)'),'')); } })(window);
varDrag={ elem :null, zindex :0, options:{}, init :function(){ each(arguments,function(i,elem,oThis){ addListener(elem,'mousedown',BindAsEventListener(oThis,oThis.start,elem)); },this); }, start:function(e,elem){ varelem=this.elem=elem; elem.style.zIndex=++this.zindex; this.x=e.clientX-elem.offsetLeft; this.y=e.clientY-elem.offsetTop; this.marginLeft=parseInt(currentStyle(elem).marginLeft)||0; this.marginTop =parseInt(currentStyle(elem).marginTop)||0; Sys.ie?elem.setCapture():e.preventDefault(); addListener(document,"mousemove",BindAsEventListener(this,this.move)); addListener(document,"mouseup",Bind(this,this.up)); this.options.callbackmove&&this.options.callbackmove(this.elem); }, move :function(e){ window.getSelection?window.getSelection().removeAllRanges():document.selection.empty(); variLeft=e.clientX-this.x,iTop=e.clientY-this.y;obj=this.elem; obj.style.left=iLeft-this.marginLeft+"px"; obj.style.top =iTop-this.marginTop+"px"; this.options.callbackmove&&this.options.callbackmove(this.elem); }, up :function(){ removeListener(document,'mousemove'); removeListener(document,'mouseup'); Sys.ie&&this.elem.releaseCapture(); this.options.callbackup&&this.options.callbackup(this.elem); } };
varoverlap={ hostel:{}, //所有需要计算重合的元素 overlapList:{}, //已经重合的元素 init:function(elems){ each(elems,function(i,elem,oThis){ elem.setAttribute('overlap',i); varret=objPos(elem),l=ret.left,t=ret.top,b=ret.bottom,r=ret.right; oThis.hostel[i]={elem:elem,leftTopDot:{x:l,y:t},leftBottomDot:{x:l,y:b},rightTopDot:{x:r,y:t},rightBottomDot:{x:r,y:b}}; },this); }, setElem:function(elem){ if(!elem)return; varret=objPos(elem),l=ret.left,t=ret.top,b=ret.bottom,r=ret.right; this.hostel[elem.getAttribute('overlap')]={elem:elem,leftTopDot:{x:l,y:t},leftBottomDot:{x:l,y:b},rightTopDot:{x:r,y:t},rightBottomDot:{x:r,y:b}}; }, //判断是否重合 isOverlap:function(my){ varobj={},my=this.hostel[my.getAttribute('overlap')]; each(this.hostel,function(key,config,oThis){ //是元素本身则返回 if(config.elem===my.elem)return; //判断2个div是否重合如果不重合则返回 if(my.leftBottomDot.y<=config.leftTopDot.y||my.leftTopDot.y>=config.leftBottomDot.y||my.rightTopDot.x<=config.leftTopDot.x||my.leftTopDot.x>=config.rightTopDot.x) return; obj[config.elem.getAttribute('overlap')]=[config.elem,oThis.howOverlap(my,config)]; },this); returnobj; }, //判断重合面积 howOverlap:function(my,other){ varl=other.leftBottomDot.x,r=other.rightTopDot.x,t=other.leftTopDot.y,b=other.leftBottomDot.y,arr=[], lt=this.include(my.leftTopDot,l,r,t,b,'leftTopDot-rightBottomDot'), lb=this.include(my.leftBottomDot,l,r,t,b,'leftBottomDot-rightTopDot'), rt=this.include(my.rightTopDot,l,r,t,b,'rightTopDot-leftBottomDot'), rb=this.include(my.rightBottomDot,l,r,t,b,'rightBottomDot-leftTopDot'); lt&&arr.push(lt)||lb&&arr.push(lb)||rt&&arr.push(rt)||rb&&arr.push(rb); if(!arr[0])return0; //一个点或者是2个点都在其中 计算方法是一样的 if(arr.length===1||arr.length===2){ varkey=arr[0].split('-'),x1=my[key[0]].x,y1=my[key[0]].y,x2=other[key[1]].x,y2=other[key[1]].y; returnMath.abs((x1-x2)*(y1-y2)); }; //完全重合 if(arr.length===4){ return162*162; }; }, //看点是不是在另一个div中 include:function(dot,l,r,t,b,key){ return(dot.x>=l&&dot.x<=r&&dot.y>=t&&dot.y<=b)?key:false; } }; window.onload=function(){ extend(Drag.options,{callbackmove:move,callbackup:up}); functionup(elem){ for(varninoverlap.overlapList) removeClass(overlap.overlapList[n][0],'focus') overlap.overlapList={}; Drag.elem.innerHTML=Drag.elem.id; }; functionmove(elem){ overlap.setElem(elem); //p为判断返回的obj是不是空的 varobj=overlap.isOverlap(elem),name,p=function(o){ for(nameino) returnfalse; returntrue; }(obj); //如果是个空对象则返回不进行下面的遍历 if(p){ up(); return; }; varstr=''; overlap.overlapList=obj; each(overlap.hostel,function(key,config){ if(obj[key]){ addClass(obj[key][0],'focus'); str=str+'与'+obj[key][0].id+'重合的面积为:'+obj[key][1]+'</br>'; }else{ removeClass(config.elem,'focus'); } }); Drag.elem.innerHTML=str; }; Drag.init($('demo1'),$('demo2'),$('demo3'),$('demo4'),$('demo5'),$('demo6'),$('demo7'),$('demo8'),$('demo9')); overlap.init([$('demo1'),$('demo2'),$('demo3'),$('demo4'),$('demo5'),$('demo6'),$('demo7'),$('demo8'),$('demo9')]); }; </script> </body> </html>