1. 程式人生 > >基於浮動的移動端兩列可延時載入的瀑布流佈局

基於浮動的移動端兩列可延時載入的瀑布流佈局

由於工作需要需要寫一個移動端可以延時載入的瀑布流佈局頁面,於是開始查資料,百度,對瀑布流有了一些理解,一直以來都有寫部落格的想法,於是有了這篇博文!

幾點說明
1.本文所說的瀑布流指的是等寬不等高的瀑布流
2.本問純屬記錄用,筆者水平有限,如有錯誤歡迎指正
3.本文使用的方法可以使用圖片延時載入而不會影響瀑布流效果

延時載入瀑布流實現的主要問題
主要的問題在於延時與圖片高度計算的衝突,延時載入完成前後圖片的高度是會發生變化的,瀑布流函式計算的每列高度不一定準確,定位會出現問題。筆者先嚐試過使用絕對定位實現瀑布流佈局,但是因為延時載入問題,出來的效果並不是很理想,也嘗試過使用onload事件來觸發瀑布流函式,但是不知道具體什麼原因定位還是不準確。所以為了儘快完成工作任務,使用了本文的這個方式,思想基本相同,只是定位元素位置的方式是使用浮動。因此也侷限了瀑布流的列數只能是兩列,應對移動端應該是夠用了。

瀑布流的幾種實現方式
1.絕對定位實現,通過JS計算每一列的高度,然後通過絕對定位來實現每個元素位置的排列以實現瀑布流的形式。
2.將螢幕分成等寬的若干列,每一列都是一個容器,通過計算每個容器的高度,將元素放在高度最低的容器中。
3.使用CSS3的多列布局,這個方法個人認為實現起來比較簡單,但是有一個問題,重新載入的內容是頁面右側,而不是在頁面下方。想要用這種方法的去百度一下CSS3實現瀑布流網上有很多例項。

本文實現的程式碼
JS程式碼如下:

function water(){
            var arrBox=$('#content').children('.box'
);// box物件 var arrBoxH=[];//陣列,用於儲存左側列中的所有塊框相加的高度 var arrBoxR=[];//陣列,用於儲存右側列中的所有塊框相加的高度 for(var i=0;i<arrBox.length;i++){ //遍歷box var boxH=arrBox.eq(i).innerHeight(); //獲得box的高度 if(i==0){ arrBox.eq(i).addClass("left"
); //第一行中的第一個塊box新增左浮動(left是自己寫好的有float:left屬性的選擇器名) arrBoxH[i]=boxH; //第一行中的第一個塊box 先新增進陣列arrBoxH }else if(i==1){ arrBox.eq(i).addClass("right");//第一行中的第一個塊box新增右浮動 arrBoxR[i]=boxH; //第一行中的第二個個塊box 先新增進陣列arrBoxR }else{ var leftNum = arrBoxH.reduce(function (x, y) { return x + y; });//計算左側列的高度 var rightNum = arrBoxR.reduce(function (x, y) { return x + y; });//計算右側列的高度 if(leftNum > rightNum) //比較兩側高度大小,決定為該box新增左浮動還是右浮動 { arrBox.eq(i).removeClass(); arrBox.eq(i).addClass("box right"); //左側較高為該box新增右浮動 arrBoxR[i]=boxH; //將高度新增在右側陣列 }else { arrBox.eq(i).removeClass(); arrBox.eq(i).addClass("box left"); //右側較高為該box新增左浮動 arrBoxH[i]=boxH; //將高度新增在左側陣列 } } } }

html程式碼+css程式碼

<!DOCTYPE html>
<html lang="en">
<head>
    <meta charset="UTF-8">
    <meta name="format-detection" content="telephone=no">
    <meta name="viewport" content="width=device-width, initial-scale=1.0, maximum-scale=1.0, user-scalable=no">
    <title>瀑布流-jquery</title>
    <style>
        *{margin:0;padding:0;}
        #content{position: relative;margin:0 auto;}
        .box{width: 50%;float: left;}
        .box img{width: 100%;height:auto;display: block;}
        .left{float: left;}
        .right{float: right;}
    </style>
    <script src="js/jquery.min.js"></script>
    <script src="js/jquery.lazyload.js"></script>
</head>
<body>
<div id="content">
    <div class="box"><img onload="water()" class="lazy" src="image/20-1.png" alt="" data-original="image/1.jpg"></div><!-- box每一個內容塊,使用img的onload事件觸發瀑布流函式,以免圖片尺寸未載入完全影響排列 -->
    <div class="box"><img onload="water()" class="lazy" src="image/20-1.png" alt="" data-original="image/2.jpg"></div>
    <div class="box"><img onload="water()" class="lazy" src="image/20-1.png" alt="" data-original="image/3.jpg"></div>
    <div class="box"><img onload="water()" class="lazy" src="image/20-1.png" alt="" data-original="image/4.jpg"></div>
    <div class="box"><img onload="water()" class="lazy" src="image/20-1.png" alt="" data-original="image/5.jpg"></div>
    <div class="box"><img onload="water()" class="lazy" src="image/20-1.png" alt="" data-original="image/6.jpg"></div>
    <div class="box"><img onload="water()" class="lazy" src="image/20-1.png" alt="" data-original="image/7.jpg"></div>
    <div class="box"><img onload="water()" class="lazy" src="image/20-1.png" alt="" data-original="image/8.jpg"></div>
    <div class="box"><img onload="water()" class="lazy" src="image/20-1.png" alt="" data-original="image/9.jpg"></div>
    <div class="box"><img onload="water()" class="lazy" src="image/20-1.png" alt="" data-original="image/10.jpg"></div>
    <div class="box"><img onload="water()" class="lazy" src="image/20-1.png" alt="" data-original="image/11.jpg"></div>
</div>
</body>
</html>

第一次寫部落格,還有許多問題!另外這個方法應該還有很多改進的地方,例如每一次圖片載入完成都要觸發一次函式來排列,但是由於時間問題以及這個方案的侷限性,所以筆者也沒有去改進,有興趣的朋友可以一起討論!