首先,先看效果圖,點擊小圖,放大,大圖變小。
然後想一下,叉,這麼難的效果,可以實現麼
1 接着,言歸正傳,如何實現呢,先看圖,和九宮格很像吧。我的實現思路,先佈局
<div class="wrap">
<div class="big" data-row="0" data-col="0">1</div>
<div data-row="0" data-col="2">2</div>
<div data-row="1" data-col="2">3</div>
<div data-row="2" data-col="0">4</div>
<div data-row="2" data-col="1">5</div>
<div data-row="2" data-col="2">6</div>
</div>
2 然後寫樣式,用什麼定位好,FLOAT就好佈局,易維護,但實現功能,一定要絕對定位,所以先用FLOAT定位
如下:
*{
padding: 0;
margin: 0;
}
.wrap{
width: 400px;
height: 400px;
}
.wrap div{
float: left;
margin-bottom: 8px;
margin-right: 8px;
width: 125px;
height: 125px;
background: green;
}
.wrap .big{width: 258px;
height: 258px;
background: blue;}
3 寫JS,先把定位轉換成絕對的。 var pos =[]; //用來存放原來的位置,佈局由FLOAT轉爲POSITION
var $divs = $('.wrap div');
var len = $divs.length;
for(var i=0;i<len;i++){
var $div = $divs.eq(i);
pos.push([$div.position().left,$div.position().top]);
}
$('.wrap div').each(function(i,item){
$(item).css({
left:pos[i][0],
top:pos[i][1],
position : 'absolute',
margin : '0px'
});
})
4 接着寫思路,這個效果很容易聯想到九宮格 ,那生成一個九宮格的數組
for(var i =0; i<3;i++){
for(var j =0; j<3;j++){
arr.push([i,j]);
}
}
結果就是[[0,0],[0,1],[0,2],...]
有什麼用呢,代表它的位置
5 圖中有六個DIV,那我就給它一個定位信息 data-row, data-col 表示它的位置,因爲第一個就四個格,所以如下面表示
<div class="big" data-row="0" data-col="0">1</div>
<div data-row="0" data-col="2">2</div>
<div data-row="1" data-col="2">3</div>
<div data-row="2" data-col="0">4</div>
<div data-row="2" data-col="1">5</div>
<div data-row="2" data-col="2">6</div>
6 點擊小圖,放大,所以可以理解成,寬高和位置改變了。位置怎樣改變呢,可以看成,是看成是九宮格里,旁邊的最早出現的格子的定位,如我就擊的 2,2 那它相鄰的格子有,[1,1],[1,2],[2,1]和自己[2,2]
用JS就可以理解成
Math.abs(arr[i][0] - x) <=1 && Math.abs(arr[i][1] - y) <=1
************************************接着說原理*****************************************
從九宮格中,抽出六個項,表示放大的位置,和另外五個,不在放大區域的五個位置
我用兩個數組,一個存放放大的方塊的位置,雖然只一個項,
另外一個數組,是有五項,存放其他五個小格的位置。 那如果相鄰的不僅四個,怎麼辦,我用了一個LEN,只取四個,所以變成
if(Math.abs(arr[i][0] - x) <=1 && Math.abs(arr[i][1] - y) <=1 && len<4){
if(!lock){
arr1 =[arr[i][0],arr[i][1]];
lock = true;
}
len ++;
}else{
arr2.push(arr[i]);
}
}
arr1 是大方塊的位置, arr2 爲小方塊的位置 ,arr爲九宮格位置,有九項,但我們只要六項
所以有三項是沒用的,如上圖所示,[1,2],[2,1],[2,2] ,這裏我用了一個LOCK。 目的是遍功九宮格的項,把第一個爲它相鄰的項取出來,表示大方塊要移到的位置
接下來處理小方格的位置,把其他五項塞進ARR2裏就行了。
如上圖,點[1,2] ,紅框表示他相鄰的DIV,因爲我設len < 4 的原因,所以會取到 [0,1][0,2][1,1][1,2] 這裏沒問題
但如果是
這樣,因爲九宮格遍歷的關係,根據上面思路
if(Math.abs(arr[i][0] - x) <=1 && Math.abs(arr[i][1] - y) <=1 && len<4){
if(!lock){
arr1 =[arr[i][0],arr[i][1]];
lock = true;
}
len ++;
}else{
arr2.push(arr[i]);
}
它只會取到上面所標紅色字的1,2,3,4 格。
而我所需要的是1,2,4,和點擊的那一格,所以這裏要特別處理一下。
if(y==1){
if(Math.abs(arr[i][0] - x) <=1 && (arr[i][1] - y) >=0 && len<4){
if(!lock){
arr1 =[arr[i][0],arr[i][1]];
lock = true;
}
len ++;
}else{
arr2.push(arr[i]);
}
}
(arr[i][1] - y) >=0 這裏作處理
接着就是移動後更新DIV的新位置
全部代碼
<!doctype html>
<html>
<head lang="zh">
<meta charset="utf-8">
<title>靈域</title>
<meta name="renderer" content="webkit">
<script src="http://yygame.duowan.com/Web/Public/Jcode/js/jquery.min.js"></script>
<link rel="alternate" media="only screen and(max-width:640px)" href="http://m.lizhi.fm/">
<script>
$(function(){
var pos =[]; //用來存放原來的位置,佈局由FLOAT轉爲POSITION
var arr = []; //存放九宮格
var arr1 =[]; //用來存放放大方塊的位置
var arr2 = [] ; // 用來存放5個小方塊的位置
for(var i =0; i<3;i++){
for(var j =0; j<3;j++){
arr.push([i,j]);
}
}
var $divs = $('.wrap div');
var len = $divs.length;
for(var i=0;i<len;i++){
var $div = $divs.eq(i);
pos.push([$div.position().left,$div.position().top]);
}
$('.wrap div').each(function(i,item){
$(item).css({
left:pos[i][0],
top:pos[i][1],
position : 'absolute',
margin : '0px'
});
})
$('.wrap').on('mouseover','div',function(){
if($('div:animated').length>0) return;
var x = $(this).data('row');
var y = $(this).data('col');
getPos(x,y);
$(this).animate({
left: arr1[1]*133,
top: arr1[0]*133,
width : 258,
height: 258
},function(){
$(this).data({
col:arr1[1],
row:arr1[0]
})
})
var $curDiv = $(this);
$('.wrap div').not($curDiv).each(function(i,item){
$(this).animate({
width:125,
height:125,
top: arr2[i][0]*133,
left:arr2[i][1]*133
}).data({
col:arr2[i][1],
row:arr2[i][0]
})
})
})
function getPos(x,y){
var lock = false;
arr2 =[];
len = 0;
for(var i = 0; i<arr.length;i++){
//要對Y=1進行額外處理,因爲如果Y=1時,如果Math.abs(arr[i][0] - x) <=1 && Math.abs(arr[i][1] - y) <=1 作判斷會產生6個[x,y]
if(y==1){
if(Math.abs(arr[i][0] - x) <=1 && (arr[i][1] - y) >=0 && len<4){
if(!lock){
arr1 =[arr[i][0],arr[i][1]];
lock = true;
}
len ++;
}else{
arr2.push(arr[i]);
}
}else{
if(Math.abs(arr[i][0] - x) <=1 && Math.abs(arr[i][1] - y) <=1 && len<4){
if(!lock){
arr1 =[arr[i][0],arr[i][1]];
lock = true;
}
len ++;
}else{
arr2.push(arr[i]);
}
}
}
}
})
</script>
<style>
*{
padding: 0;
margin: 0;
}
.wrap{
width: 400px;
height: 400px;
}
.wrap div{
float: left;
margin-bottom: 8px;
margin-right: 8px;
width: 125px;
height: 125px;
background: green;
}
.wrap .big{width: 258px;
height: 258px;
background: blue;}
</style>
</head>
<body >
<div class="wrap">
<div class="big" data-row="0" data-col="0">1</div>
<div data-row="0" data-col="2">2</div>
<div data-row="1" data-col="2">3</div>
<div data-row="2" data-col="0">4</div>
<div data-row="2" data-col="1">5</div>
<div data-row="2" data-col="2">6</div>
</div>
</body>
</html>
大功告成。有新的想法,你也可告訴我