HTML + JS+CSS實作瀑布流式布局(包含懶加載)
前幾天興致來了想做一個瀑布流布局的網頁,然后就有了各種“神操作”,也在網上看了一些相關的知識點;所以這里對自己這幾個小時來一個總結(附原始碼)
首先來說一下瀑布流的原理吧:瀑布流是許多資料塊組成的,可以是圖片,可以是div,但是它們都有一個特點,就是等寬不等高,正是因為它等寬不等高,所以如果按部就班的排布的話,才會出現很大的縫隙,特別不好看,說白了瀑布流布局就是充分利用圖片之間的空隙來合理的布局,使布局看起來好看,
首先上CSS布局(因為個人喜歡比較美的事物,所以寫的比較多……嘿)
*{
margin: 0 ;
padding: 0;
background-color: #333;
}
.container{
position: relative;
width: 1200px;
margin: 20px auto;
}
.container .box{
display: flex;
width: 178px;
margin: 20px 0 30px ;
padding: 5px 0 0 15px;
float: left;
overflow: hidden;
}
.container .box .active{
padding: 10px;
border: 1px solid #cccccc;
box-shadow: 0 0 5px #ccc;
border-radius: 5px;
}
.container .box img{
max-width: 100%;
}
.container .box h2{
margin: 10px 0 0;
padding: 0;
font-size: 20px;
color: white;
}
.container .box p{
margin: 0;
padding: 0 0 10px;
font-size: 16px;
color: floralwhite;
}
這里把HTML代碼也附上(這里我是把CSS和JS分開寫了)
<!DOCTYPE html>
<html>
<head>
<meta charset="utf-8">
<title></title>
</head>
<link href="css/falls.css" rel="stylesheet" />
<script src="js/falls.js"></script>
<body>
<div id="container" class="container">
<div class="box">
<div class="active">
<img src="img/1.png" />
<h2>this is title</h2>
<p>You just need to know what to look.</p>
</div>
</div>
<div class="box">
<div class="active">
<img src="img/2.png" />
<h2>this is title</h2>
<p>You just need to know what to look.</p>
</div>
</div>
<div class="box">
<div class="active">
<img src="img/3.jpg" />
<h2>this is title</h2>
<p>You just need to know what to look.</p>
</div>
</div>
<div class="box">
<div class="active">
<img src="img/4.png" />
<h2>this is title</h2>
<p>You just need to know what to look.</p>
</div>
</div>
<div class="box">
<div class="active">
<img src="img/5.png" />
<h2>this is title</h2>
<p>You just need to know what to look.</p>
</div>
</div>
<div class="box">
<div class="active">
<img src="img/6.png" />
<h2>this is title</h2>
<p>You just need to know what to look.</p>
</div>
</div>
<div class="box">
<div class="active">
<img src="img/7.jpg" />
<h2>this is title</h2>
<p>You just need to know what to look.</p>
</div>
</div>
<div class="box">
<div class="active">
<img src="img/8.png" />
<h2>this is title</h2>
<p>You just need to know what to look.</p>
</div>
</div>
</div>
</body>
</html>
沒有加入JS就是這副模樣

在明白了瀑布流的原理之后現在我們來實作瀑布流及自動加載;首先我們需要平鋪第一行,這里我們鋪了六張圖片,然后就該鋪第二行了,那這個待插入的圖片應該放在哪個位置呢,我們可以得到每一列的高度,也就是每一列的資料塊的高度加起來,得到六個高度的數值,我們算出哪一列高度最小就把待插入的圖片插入到那一列的正下方,利用絕對定位定位過去(因為是絕對定位,所以top是距離頁面頂部高度),left就是第幾列乘以資料塊寬度就可以了,如下圖,待插入圖片應該插入到這里
鋪墊了這么多,重點來了!上JS
window.onload=function(){
//開始即呼叫
waterfall('container','box')
var dataInt = {
"data": [
{"src": '1.png'},{"src": '2.png'},
{"src": '3.jpg'},{"src": '4.png'},
{"src": '5.png'},{"src": '6.png'},
{"src": '7.jpg'},{"src": '8.png'},
]
}
//監聽滾動條事件
window.onscroll=function(){
//檢查是否具備了滾動條件
if(checkScrollSlide){
var ocontent = document.getElementById('container');
//創建div,并將其加到所有box后面
for(var i = 0; i < dataInt.data.length; i++) {
var obox = document.createElement('div');
obox.className = 'box';
ocontent.appendChild(obox);
var opic = document.createElement('div');
opic.className = 'active';
obox.appendChild(opic);
var oimg = document.createElement('img');
oimg.src = "img/" + dataInt.data[i].src;
opic.appendChild(oimg);
var oh=document.createElement('h2')
oh.innerHTML='this is title'
opic.appendChild(oh);
var op=document.createElement('p')
op.innerHTML='You just need to know what to look.'
opic.appendChild(op)
}
waterfall('container', 'box');
}
}
}
function waterfall(content,box){
//獲取大盒子(container)里的所有小盒子(box)
var ocontent=document.getElementById(content);
var oboxs=getByClass(ocontent, box);
//計算整個頁面顯示的列數(頁面寬/box的寬);
var oboxW = oboxs[0].offsetWidth;
//Math.floor 向下取整
var cols = Math.floor(document.documentElement.clientWidth / oboxW);
//設定container的寬度(這里用剛剛計算出來的列數乘盒子的寬度(oboxW * cols)得到的)
ocontent.style.cssText = 'width:' + oboxW * cols + 'px;margin:20 auto';
var heightArr = [];
for(var i = 0; i < oboxs.length; i++) {
if(i < cols) {
// 將前cols張圖片的寬度記錄到hArr陣列中(第一行的高度)
heightArr.push(oboxs[i].offsetHeight);
} else {
//從第二行開始就開始找最小的高度了,決定帶插入圖片該插入到哪里
//js Math.min.apply()方法,取出陣列中的最小值
var minH = Math.min.apply(null, heightArr);
var index = getMinhIndex(heightArr, minH);
// 設定最小高度的圖片的style為絕對定位,并設定top和left
oboxs[i].style.position = 'absolute';
oboxs[i].style.top = minH + 'px';
oboxs[i].style.left = oboxs[index].offsetLeft+'px';
heightArr[index] += oboxs[i].offsetHeight;
}
}
}
//回傳所有的box盒子
function getByClass(content, cName){
var boxArr = new Array(),
oElements = content.getElementsByTagName('*');
for(var i = 0; i < oElements.length; i++) {
if(oElements[i].className == cName) {
boxArr.push(oElements[i]);
}
}
return boxArr;
}
//獲取陣列中最小值的下標值
function getMinhIndex(arr, val) {
for(var i in arr) {
if(arr[i] == val) {
return i;
}
}
}
//定義函式檢測是否具備了滾動加載資料塊的條件
function checkScrollSlide(){
var ocontent = document.getElementById('container');
var oboxs = getByClass(ocontent, 'box');
//獲取最后一個box到頂部的距離+ 它自身一半的距離
var lastboxH = oboxs[oboxs.length - 1].offsetTop + Math.floor(oboxs[oboxs.length - 1].offsetHeight / 2);
//獲取滾動條滾動距離(為了消除標準模式和怪異模式之間的差別而做的兼容)
var scrollTop = document.body.scrollTop || document.documentElement.scrollTop;
// 獲取window可視化的高度
var height = document.body.clientHeight || document.documentElement.clientHeight;
return(lastboxH < scrollTop + height) ? true : false;
}
代碼不復雜,多看幾遍多敲幾遍就能理解,這里主要講解一下最后“function checkScrollSlide()”的思想;因為我們這個要實作一直滑一直滑的效果(也就是懶加載),所以我們這里就拿最后一張圖片來做對比,通俗理解函式“checkScrollSlide()”的作用就是最后一張圖片露出一半了你就應該加載,
然后之前的“waterfall”函式里面的代碼實作了頁面縮小圖片的列數也會相應的改變哦~
這樣我們一個基本的瀑布流式布局就完成辣~ !
但是把頁面重新恢復之后會擠在一起,這個問題觸及到了我的知識盲區,所以如果有懂的小伙伴可以一起交流哦,
(碼字不易,能幫到看這篇文章的你就是我前進的動力,嘿咻
( ?? ω ?? )?)
轉載請註明出處,本文鏈接:https://www.uj5u.com/qianduan/241862.html
標籤:其他
上一篇:看完包會的Vuejs基礎
下一篇:論一個函授大專生的Java求職路
