<!DOCTYPE html>
<html>
<head>
<style>
* {margin:0; padding:0;}
#ul1 {width:660px; position:relative; margin:10px auto;}
#ul1 li {width:200px; height:150px; float:left; list-style:none; margin:10px; z-index:1;}
#ul1 .active {border:3px dashed red;}
</style>
<meta http-equiv="Content-Type" content="text/html; charset=utf-8" />
<title>照片墙应用</title>
<!-- js封装的运动框架 -->
<script src="move2.js"></script>
<script>
window.οnlοad=function ()
{
var oUl=document.getElementById('ul1');
var aLi=oUl.getElementsByTagName('li');
var aPos=[];
var iMinZindex=2;
var i=0;
//1.布局转换
for(i=0;i<aLi.length;i++)
{
//把每个li的left和top值存到一个数组里,以便后面使用
aPos[i]={left: aLi[i].offsetLeft, top: aLi[i].offsetTop};
}
for(i=0;i<aLi.length;i++)
{
//然后把每个left和top值赋给它们
aLi[i].style.left=aPos[i].left+'px';
aLi[i].style.top=aPos[i].top+'px';
//每个li绝对定位,并且把margin归零
aLi[i].style.position='absolute';
aLi[i].style.margin='0';
//给oLi加索引,以便后面使用
aLi[i].index=i;
}
//2.拖拽
for(i=0;i<aLi.length;i++)
{
setDrag(aLi[i]);
}
function setDrag(obj)
{
obj.οnmοusedοwn=function (ev)
{
var oEvent=ev||event;
//每次拖拽就把层级提高
obj.style.zIndex=iMinZindex++;
var disX=oEvent.clientX-obj.offsetLeft;
var disY=oEvent.clientY-obj.offsetTop;
document.οnmοusemοve=function (ev)
{
var oEvent=ev||event;
obj.style.left=oEvent.clientX-disX+'px';
obj.style.top=oEvent.clientY-disY+'px';
//把所有li的className置空
for(i=0;i<aLi.length;i++)
{
aLi[i].className='';
}
var oNear=findNearest(obj);
//判断最近的那个元素,并且的碰撞上了,则className为active
if(oNear)
{
oNear.className='active';
}
/*for(i=0;i<aLi.length;i++)
{
aLi[i].className='';
if(obj==aLi[i])continue;
if(cdTest(obj, aLi[i]))
{
aLi[i].className='active';
}
}*/
};
document.οnmοuseup=function ()
{
document.οnmοusemοve=null;
document.οnmοuseup=null;
var oNear=findNearest(obj);
//当鼠标松开,判断最近的元素并且是碰撞上了,则清空classname,则两个元素的层级++,并且两个元素互换位置
if(oNear)
{
/*oNear->obj
obj->oNear*/
oNear.className='';
oNear.style.zIndex=iMinZindex++;
obj.style.zIndex=iMinZindex++;
startMove(oNear, aPos[obj.index]);
startMove(obj, aPos[oNear.index]);
var tmp=0;
tmp=obj.index;
obj.index=oNear.index;
oNear.index=tmp;
}
else
{
//当没有元素碰撞时,则回到原来的位置
startMove(obj, aPos[obj.index]);
}
};
clearInterval(obj.timer);
//阻止默认事件
return false;
};
}
//碰撞检测
function cdTest(obj1, obj2)
{
var l1=obj1.offsetLeft;
var r1=obj1.offsetLeft+obj1.offsetWidth;
var t1=obj1.offsetTop;
var b1=obj1.offsetTop+obj1.offsetHeight;
var l2=obj2.offsetLeft;
var r2=obj2.offsetLeft+obj2.offsetWidth;
var t2=obj2.offsetTop;
var b2=obj2.offsetTop+obj2.offsetHeight;
if(r1<l2 || l1>r2 || b1<t2 || t1>b2)
{
return false;
}
else
{
return true;
}
}
//计算最近的元素,开根号a*a+b*b
function getDis(obj1, obj2)
{
var a=obj1.offsetLeft-obj2.offsetLeft;
var b=obj1.offsetTop-obj2.offsetTop;
return Math.sqrt(a*a+b*b);
}
function findNearest(obj) //找到碰上的,并且最近的
{
var iMin=999999999;
var iMinIndex=-1;
for(i=0;i<aLi.length;i++)
{
if(obj==aLi[i])continue;
if(cdTest(obj, aLi[i]))
{
var dis=getDis(obj, aLi[i]);
if(iMin>dis)
{
iMin=dis;
iMinIndex=i;
}
}
}
if(iMinIndex==-1)
{
return null;
}
else
{
return aLi[iMinIndex];
}
}
//运动
};
</script>
</head>
<body>
<ul id="ul1">
<li><img src="images/1.jpg" /></li>
<li><img src="images/2.jpg" /></li>
<li><img src="images/3.jpg" /></li>
<li><img src="images/4.jpg" /></li>
<li><img src="images/5.jpg" /></li>
<li><img src="images/1.jpg" /></li>
<li><img src="images/2.jpg" /></li>
<li><img src="images/3.jpg" /></li>
<li><img src="images/4.jpg" /></li>
<li><img src="images/5.jpg" /></li>
</ul>
</body>
</html>
move.js, 封装运动框架
function getStyle(obj, attr)
{
if(obj.currentStyle)
{
return obj.currentStyle[attr];
}
else
{
return getComputedStyle(obj, false)[attr];
}
}
function startMove(obj, json, fn)
{
clearInterval(obj.timer);
obj.timer=setInterval(function (){
var bStop=true; //��һ���˶��ͽ����ˡ������е�ֵ��������
for(var attr in json)
{
//1.ȡ��ǰ��ֵ
var iCur=0;
if(attr=='opacity')
{
iCur=parseInt(parseFloat(getStyle(obj, attr))*100);
}
else
{
iCur=parseInt(getStyle(obj, attr));
}
//2.���ٶ�
var iSpeed=(json[attr]-iCur)/8;
iSpeed=iSpeed>0?Math.ceil(iSpeed):Math.floor(iSpeed);
//3.���ֹͣ
if(iCur!=json[attr])
{
bStop=false;
}
if(attr=='opacity')
{
obj.style.filter='alpha(opacity:'+(iCur+iSpeed)+')';
obj.style.opacity=(iCur+iSpeed)/100;
}
else
{
obj.style[attr]=iCur+iSpeed+'px';
}
}
if(bStop)
{
clearInterval(obj.timer);
if(fn)
{
fn();
}
}
}, 30)
}