平时,淘宝上我们经常会见到瀑布流效果,如下图~
这个效果用css3的一个分列效果就可以实现,今天我们用原生js来做一下这个效果。
首先我们来整理一下思路,先定义一个div,用做最大的布局盒子,并且实现图片的布局。然后定义一个pic,并且将float设置为left,让盒子横向排列。然后定义一个div 类名为box,给这个盒子设置边框,里面存放图片。在写样式表的时候,我们可以只设置图片的宽度,将每一张的图片宽度设置成统一的大小,然后就会发现图片确实会一张一张的横向排列,但是效果成了这样
所以,我们要换个思路咯,首先啊,我们可以获取一下屏幕的宽度,计算一下最多可以放置几张图片,然后利用cssText设置一下最外层盒子的大小和margin,让内容居中显示。在第一行的图片插入完成之后,我们可以获取一下现在每一列的高度,然后找到高度最小的那一列,将最新的一张图片插入到这个地方,然后每一次插入图片都查找一下最小高度,之后插入图片。
具体的代码如下:
<style>
*{padding: 0;margin: 0;}
#main{position: relative;}
.pic{padding: 10px;/*position: absolute;*/float: left;}
.box{width: 250px;padding: 10px;border: 1px solid #c7c8c9;}
.box img{width: 250px;height:auto;display: block;}
</style>
<div id="main">
<div class="pic">
<div class="box">
<img src="../images/0.jpg"/>
</div>
</div>
<div class="pic">
<div class="box">
<img src="../images/1.jpg"/>
</div>
</div>
<div class="pic">
<div class="box">
<img src="../images/2.jpg"/>
</div>
</div>
<div class="pic">
<div class="box">
<img src="../images/3.jpg"/>
</div>
</div>
<div class="pic">
<div class="box">
<img src="../images/4.jpg"/>
</div>
</div>
<div class="pic">
<div class="box">
<img src="../images/5.jpg"/>
</div>
</div>
<div class="pic">
<div class="box">
<img src="../images/6.jpg"/>
</div>
</div>
<div class="pic">
<div class="box">
<img src="../images/7.jpg"/>
</div>
</div>
<div class="pic">
<div class="box">
<img src="../images/8.jpg"/>
</div>
</div>
<div class="pic">
<div class="box">
<img src="../images/9.jpg"/>
</div>
</div>
<div class="pic">
<div class="box">
<img src="../images/11.jpg"/>
</div>
</div>
</div>
<script>
window.onload = function(){
var main = document.getElementById('main');
var pics = document.getElementsByClassName('pic');
var everypic = pics[0].offsetWidth;
var minHeight = [],minH= 0;
//获取每一行可以放置的最大图片数量
var num = Math.floor(document.documentElement.clientWidth/everypic);
//对main设置居中显示
main.style.cssText = 'width:'+num*everypic+'px;margin:0 auto;';
for(var i=0;i<pics.length;i++){
if(i<num){//放置第一列图片
pics[i].style.top = 0 +'px';
pics[i].style.left = i*everypic +'px';
minHeight[i] = pics[i].offsetHeight;
//用来存放每一列的最小高度
}else{
minH = Math.min.apply(null,minHeight);//查找最小高度
var j = minHeightIndex(minHeight,minH);//获取最小高度的索引值
minHeight[j] += pics[i].offsetHeight;//高度重置
pics[i].style.top = minH +'px';
pics[i].style.left = j*everypic +'px';
}
}
//此函数用来获取最小高度的索引值
function minHeightIndex(arr,minH){
for(var i in arr){
if(arr[i] == minH){
return i;
}
}
}
}
</script>
在写这个效果的时候,遇到了一个问题,在加载的时候,图片总是加载不上,布局也没有用,郁闷了好久,后来经大神指导,才顿悟了,,浏览器加载文件时,会西先加载js文件,加载完js文件之后,才会加载图片文件,所以要等图片文件加载完成之后再运行js,就不会出现这个问题啦~
学习本就是一个慢慢积累,慢慢找错误的过程,遇到的错误多了,解决的问题多了,渣渣也可以变成大神的~