效果图
页面下拉时,实现懒加载
有按钮可以可控制加载
每次加载10张
公用,不必改变部分
数据JS
共46张图片,重复放,如果放上去后图片变形,可在此处按比例修改图片高度,图片宽度不建议修改
let images = [
{
"path": "../images/1.jpeg",
"text": "花非花,雾非雾,夜半来,天明去,来如春梦不多时,去似朝云无觅处。花非花,雾非雾,夜半来,天明去,来如春梦不多时,去似朝云无觅处。",
"width": 232,
"height": 332
},
{
"path": "../images/2.jpeg",
"text": "花非花,雾非雾,夜半来,天明去,来如春梦不多时,去似朝云无觅处。花非花,雾非雾,夜半来,天明去,来如春梦不多时,去似朝云无觅处。",
"width": 232,
"height": 309
},
{
"path": "../images/3.jpeg",
"text": "花非花,雾非雾,夜半来,天明去,来如春梦不多时,去似朝云无觅处。花非花,雾非雾,夜半来,天明去,来如春梦不多时,去似朝云无觅处。",
"width": 232,
"height": 309
},
{
"path": "../images/4.jpg",
"text": "花非花,雾非雾,夜半来,天明去,来如春梦不多时,去似朝云无觅处。花非花,雾非雾,夜半来,天明去,来如春梦不多时,去似朝云无觅处。",
"width": 232,
"height": 348
},
{
"path": "../images/5.jpg",
"text": "花非花,雾非雾,夜半来,天明去,来如春梦不多时,去似朝云无觅处。花非花,雾非雾,夜半来,天明去,来如春梦不多时,去似朝云无觅处。",
"width": 232,
"height": 348
},
{
"path": "../images/6.jpg",
"text": "花非花,雾非雾,夜半来,天明去,来如春梦不多时,去似朝云无觅处。花非花,雾非雾,夜半来,天明去,来如春梦不多时,去似朝云无觅处。",
"width": 232,
"height": 348
},
{
"path": "../images/7.jpg",
"text": "花非花,雾非雾,夜半来,天明去,来如春梦不多时,去似朝云无觅处。花非花,雾非雾,夜半来,天明去,来如春梦不多时,去似朝云无觅处。",
"width": 232,
"height": 348
},
{
"path": "../images/8.jpg",
"text": "花非花,雾非雾,夜半来,天明去,来如春梦不多时,去似朝云无觅处。花非花,雾非雾,夜半来,天明去,来如春梦不多时,去似朝云无觅处。",
"width": 232,
"height": 376
},
{
"path": "../images/9.jpg",
"text": "花非花,雾非雾,夜半来,天明去,来如春梦不多时,去似朝云无觅处。花非花,雾非雾,夜半来,天明去,来如春梦不多时,去似朝云无觅处。",
"width": 232,
"height": 376
},
{
"path": "../images/10.jpg",
"text": "青花非花,雾非雾,夜半来,天明去,来如春梦不多时,去似朝云无觅处。花非花,雾非雾,夜半来,天明去,来如春梦不多时,去似朝云无觅处。",
"width": 232,
"height": 376
},
{
"path": "../images/11.jpg",
"text": "花非花,雾非雾,夜半来,天明去,来如春梦不多时,去似朝云无觅处。花非花,雾非雾,夜半来,天明去,来如春梦不多时,去似朝云无觅处。",
"width": 232,
"height": 376
},
{
"path": "../images/12.jpg",
"text": "花非花,雾非雾,夜半来,天明去,来如春梦不多时,去似朝云无觅处。花非花,雾非雾,夜半来,天明去,来如春梦不多时,去似朝云无觅处。",
"width": 232,
"height": 332
},
{
"path": "../images/13.jpg",
"text": "花非花,雾非雾,夜半来,天明去,来如春梦不多时,去似朝云无觅处。花非花,雾非雾,夜半来,天明去,来如春梦不多时,去似朝云无觅处。",
"width": 232,
"height": 412
},
{
"path": "../images/14.jpg",
"text": "花非花,雾非雾,夜半来,天明去,来如春梦不多时,去似朝云无觅处。花非花,雾非雾,夜半来,天明去,来如春梦不多时,去似朝云无觅处。",
"width": 232,
"height": 348
},
{
"path": "../images/15.jpg",
"text": "花非花,雾非雾,夜半来,天明去,来如春梦不多时,去似朝云无觅处。花非花,雾非雾,夜半来,天明去,来如春梦不多时,去似朝云无觅处。",
"width": 232,
"height": 348
},
{
"path": "../images/16.jpg",
"text": "花非花,雾非雾,夜半来,天明去,来如春梦不多时,去似朝云无觅处。花非花,雾非雾,夜半来,天明去,来如春梦不多时,去似朝云无觅处。",
"width": 232,
"height": 348
},
{
"path": "../images/17.jpg",
"text": "花非花,雾非雾,夜半来,天明去,来如春梦不多时,去似朝云无觅处。花非花,雾非雾,夜半来,天明去,来如春梦不多时,去似朝云无觅处。",
"width": 232,
"height": 332
},
{
"path": "../images/18.jpg",
"text": "花非花,雾非雾,夜半来,天明去,来如春梦不多时,去似朝云无觅处。花非花,雾非雾,夜半来,天明去,来如春梦不多时,去似朝云无觅处。!",
"width": 232,
"height": 376
},
{
"path": "../images/19.jpg",
"text": "花非花,雾非雾,夜半来,天明去,来如春梦不多时,去似朝云无觅处。花非花,雾非雾,夜半来,天明去,来如春梦不多时,去似朝云无觅处。",
"width": 232,
"height": 412
},
{
"path": "../images/20.jpg",
"text": "花非花,雾非雾,夜半来,天明去,来如春梦不多时,去似朝云无觅处。花非花,雾非雾,夜半来,天明去,来如春梦不多时,去似朝云无觅处。",
"width": 232,
"height": 412
},
{
"path": "../images/21.jpg",
"text": "花非花,雾非雾,夜半来,天明去,来如春梦不多时,去似朝云无觅处。花非花,雾非雾,夜半来,天明去,来如春梦不多时,去似朝云无觅处。",
"width": 232,
"height": 412
},
{
"path": "../images/22.jpg",
"text": "花非花,雾非雾,夜半来,天明去,来如春梦不多时,去似朝云无觅处。花非花,雾非雾,夜半来,天明去,来如春梦不多时,去似朝云无觅处。",
"width": 232,
"height": 376
},
{
"path": "../images/23.jpg",
"text": "花非花,雾非雾,夜半来,天明去,来如春梦不多时,去似朝云无觅处。花非花,雾非雾,夜半来,天明去,来如春梦不多时,去似朝云无觅处。",
"width": 232,
"height": 348
},
{
"path": "../images/24.jpg",
"text": "花非花,雾非雾,夜半来,天明去,来如春梦不多时,去似朝云无觅处。花非花,雾非雾,夜半来,天明去,来如春梦不多时,去似朝云无觅处。",
"width": 232,
"height": 376
},
{
"path": "../images/25.jpg",
"text": "花非花,雾非雾,夜半来,天明去,来如春梦不多时,去似朝云无觅处。花非花,雾非雾,夜半来,天明去,来如春梦不多时,去似朝云无觅处。",
"width": 232,
"height": 348
},
{
"path": "../images/26.jpg",
"text": "花非花,雾非雾,夜半来,天明去,来如春梦不多时,去似朝云无觅处。花非花,雾非雾,夜半来,天明去,来如春梦不多时,去似朝云无觅处。",
"width": 232,
"height": 331
},
{
"path": "../images/27.jpg",
"text": "花非花,雾非雾,夜半来,天明去,来如春梦不多时,去似朝云无觅处。花非花,雾非雾,夜半来,天明去,来如春梦不多时,去似朝云无觅处。!",
"width": 232,
"height": 331
},
{
"path": "../images/28.jpg",
"text": "花非花,雾非雾,夜半来,天明去,来如春梦不多时,去似朝云无觅处。花非花,雾非雾,夜半来,天明去,来如春梦不多时,去似朝云无觅处。",
"width": 232,
"height": 298
},
{
"path": "../images/29.jpg",
"text": "花非花,雾非雾,夜半来,天明去,来如春梦不多时,去似朝云无觅处。花非花,雾非雾,夜半来,天明去,来如春梦不多时,去似朝云无觅处。",
"width": 232,
"height": 371
},
{
"path": "../images/30.jpg",
"text": "花非花,雾非雾,夜半来,天明去,来如春梦不多时,去似朝云无觅处。花非花,雾非雾,夜半来,天明去,来如春梦不多时,去似朝云无觅处。",
"width": 232,
"height": 371
},
{
"path": "../images/31.jpeg",
"text": "花非花,雾非雾,夜半来,天明去,来如春梦不多时,去似朝云无觅处。花非花,雾非雾,夜半来,天明去,来如春梦不多时,去似朝云无觅处。!",
"width": 232,
"height": 502
},
{
"path": "../images/32.jpeg",
"text": "花非花,雾非雾,夜半来,天明去,来如春梦不多时,去似朝云无觅处。花非花,雾非雾,夜半来,天明去,来如春梦不多时,去似朝云无觅处。",
"width": 232,
"height": 412
},
{
"path": "../images/33.jpeg",
"text": "花非花,雾非雾,夜半来,天明去,来如春梦不多时,去似朝云无觅处。花非花,雾非雾,夜半来,天明去,来如春梦不多时,去似朝云无觅处。",
"width": 232,
"height": 483
},
{
"path": "../images/34.jpeg",
"text": "花非花,雾非雾,夜半来,天明去,来如春梦不多时,去似朝云无觅处。花非花,雾非雾,夜半来,天明去,来如春梦不多时,去似朝云无觅处。",
"width": 232,
"height": 348
},
{
"path": "../images/35.jpeg",
"text": "花非花,雾非雾,夜半来,天明去,来如春梦不多时,去似朝云无觅处。花非花,雾非雾,夜半来,天明去,来如春梦不多时,去似朝云无觅处。",
"width": 232,
"height": 376
},
{
"path": "../images/36.jpeg",
"text": "花非花,雾非雾,夜半来,天明去,来如春梦不多时,去似朝云无觅处。花非花,雾非雾,夜半来,天明去,来如春梦不多时,去似朝云无觅处。",
"width": 232,
"height": 376
},
{
"path": "../images/37.jpeg",
"text": "花非花,雾非雾,夜半来,天明去,来如春梦不多时,去似朝云无觅处。花非花,雾非雾,夜半来,天明去,来如春梦不多时,去似朝云无觅处。",
"width": 232,
"height": 412
},
{
"path": "../images/38.jpeg",
"text": "花非花,雾非雾,夜半来,天明去,来如春梦不多时,去似朝云无觅处。花非花,雾非雾,夜半来,天明去,来如春梦不多时,去似朝云无觅处。",
"width": 232,
"height": 412
},
{
"path": "../images/39.jpeg",
"text": "花非花,雾非雾,夜半来,天明去,来如春梦不多时,去似朝云无觅处。花非花,雾非雾,夜半来,天明去,来如春梦不多时,去似朝云无觅处。",
"width": 232,
"height": 348
},
{
"path": "../images/40.jpg",
"text": "花非花,雾非雾,夜半来,天明去,来如春梦不多时,去似朝云无觅处。花非花,雾非雾,夜半来,天明去,来如春梦不多时,去似朝云无觅处。",
"width": 232,
"height": 412
},
{
"path": "../images/41.jpg",
"text": "花非花,雾非雾,夜半来,天明去,来如春梦不多时,去似朝云无觅处。花非花,雾非雾,夜半来,天明去,来如春梦不多时,去似朝云无觅处。",
"width": 232,
"height": 348
},
{
"path": "../images/42.jpg",
"text": "花非花,雾非雾,夜半来,天明去,来如春梦不多时,去似朝云无觅处。花非花,雾非雾,夜半来,天明去,来如春梦不多时,去似朝云无觅处。",
"width": 232,
"height": 412
},
{
"path": "../images/43.jpg",
"text": "花非花,雾非雾,夜半来,天明去,来如春梦不多时,去似朝云无觅处。花非花,雾非雾,夜半来,天明去,来如春梦不多时,去似朝云无觅处。",
"width": 232,
"height": 412
},
{
"path": "../images/44.jpg",
"text": "花非花,雾非雾,夜半来,天明去,来如春梦不多时,去似朝云无觅处。花非花,雾非雾,夜半来,天明去,来如春梦不多时,去似朝云无觅处。",
"width": 232,
"height": 376
},
{
"path": "../images/45.jpg",
"text": "花非花,雾非雾,夜半来,天明去,来如春梦不多时,去似朝云无觅处。花非花,雾非雾,夜半来,天明去,来如春梦不多时,去似朝云无觅处。",
"width": 232,
"height": 412
},
{
"path": "../images/46.jpg",
"text": "花非花,雾非雾,夜半来,天明去,来如春梦不多时,去似朝云无觅处。花非花,雾非雾,夜半来,天明去,来如春梦不多时,去似朝云无觅处。",
"width": 232,
"height": 331
},
{
"path": "../images/17.jpg",
"text": "花非花,雾非雾,夜半来,天明去,来如春梦不多时,去似朝云无觅处。花非花,雾非雾,夜半来,天明去,来如春梦不多时,去似朝云无觅处。",
"width": 232,
"height": 332
},
{
"path": "../images/18.jpg",
"text": "花非花,雾非雾,夜半来,天明去,来如春梦不多时,去似朝云无觅处。花非花,雾非雾,夜半来,天明去,来如春梦不多时,去似朝云无觅处。",
"width": 232,
"height": 376
},
{
"path": "../images/19.jpg",
"text": "花非花,雾非雾,夜半来,天明去,来如春梦不多时,去似朝云无觅处。花非花,雾非雾,夜半来,天明去,来如春梦不多时,去似朝云无觅处。",
"width": 232,
"height": 412
},
{
"path": "../images/20.jpg",
"text": "花非花,雾非雾,夜半来,天明去,来如春梦不多时,去似朝云无觅处。花非花,雾非雾,夜半来,天明去,来如春梦不多时,去似朝云无觅处。",
"width": 232,
"height": 412
},
{
"path": "../images/21.jpg",
"text": "花非花,雾非雾,夜半来,天明去,来如春梦不多时,去似朝云无觅处。花非花,雾非雾,夜半来,天明去,来如春梦不多时,去似朝云无觅处。",
"width": 232,
"height": 412
},
{
"path": "../images/22.jpg",
"text": "花非花,雾非雾,夜半来,天明去,来如春梦不多时,去似朝云无觅处。花非花,雾非雾,夜半来,天明去,来如春梦不多时,去似朝云无觅处。",
"width": 232,
"height": 376
},
{
"path": "../images/23.jpg",
"text": "花非花,雾非雾,夜半来,天明去,来如春梦不多时,去似朝云无觅处。花非花,雾非雾,夜半来,天明去,来如春梦不多时,去似朝云无觅处。",
"width": 232,
"height": 348
},
{
"path": "../images/24.jpg",
"text": "花非花,雾非雾,夜半来,天明去,来如春梦不多时,去似朝云无觅处。花非花,雾非雾,夜半来,天明去,来如春梦不多时,去似朝云无觅处。",
"width": 232,
"height": 376
},
{
"path": "../images/25.jpg",
"text": "花非花,雾非雾,夜半来,天明去,来如春梦不多时,去似朝云无觅处。花非花,雾非雾,夜半来,天明去,来如春梦不多时,去似朝云无觅处。",
"width": 232,
"height": 348
},
{
"path": "../images/26.jpg",
"text": "花非花,雾非雾,夜半来,天明去,来如春梦不多时,去似朝云无觅处。花非花,雾非雾,夜半来,天明去,来如春梦不多时,去似朝云无觅处。",
"width": 232,
"height": 331
},
{
"path": "../images/27.jpg",
"text": "花非花,雾非雾,夜半来,天明去,来如春梦不多时,去似朝云无觅处。花非花,雾非雾,夜半来,天明去,来如春梦不多时,去似朝云无觅处。",
"width": 232,
"height": 331
},
{
"path": "../images/28.jpg",
"text": "花非花,雾非雾,夜半来,天明去,来如春梦不多时,去似朝云无觅处。花非花,雾非雾,夜半来,天明去,来如春梦不多时,去似朝云无觅处。",
"width": 232,
"height": 298
},
{
"path": "../images/29.jpg",
"text": "花非花,雾非雾,夜半来,天明去,来如春梦不多时,去似朝云无觅处。花非花,雾非雾,夜半来,天明去,来如春梦不多时,去似朝云无觅处。",
"width": 232,
"height": 371
},
{
"path": "../images/30.jpg",
"text": "花非花,雾非雾,夜半来,天明去,来如春梦不多时,去似朝云无觅处。花非花,雾非雾,夜半来,天明去,来如春梦不多时,去似朝云无觅处。",
"width": 232,
"height": 371
},
{
"path": "../images/1.jpeg",
"text": "花非花,雾非雾,夜半来,天明去,来如春梦不多时,去似朝云无觅处。花非花,雾非雾,夜半来,天明去,来如春梦不多时,去似朝云无觅处。",
"width": 232,
"height": 332
},
{
"path": "../images/2.jpeg",
"text": "花非花,雾非雾,夜半来,天明去,来如春梦不多时,去似朝云无觅处。花非花,雾非雾,夜半来,天明去,来如春梦不多时,去似朝云无觅处。",
"width": 232,
"height": 309
},
{
"path": "../images/3.jpeg",
"text": "花非花,雾非雾,夜半来,天明去,来如春梦不多时,去似朝云无觅处。花非花,雾非雾,夜半来,天明去,来如春梦不多时,去似朝云无觅处。!",
"width": 232,
"height": 309
},
{
"path": "../images/4.jpg",
"text": "花非花,雾非雾,夜半来,天明去,来如春梦不多时,去似朝云无觅处。花非花,雾非雾,夜半来,天明去,来如春梦不多时,去似朝云无觅处。",
"width": 232,
"height": 348
},
{
"path": "../images/35.jpeg",
"text": "花非花,雾非雾,夜半来,天明去,来如春梦不多时,去似朝云无觅处。花非花,雾非雾,夜半来,天明去,来如春梦不多时,去似朝云无觅处。",
"width": 232,
"height": 376
},
{
"path": "../images/36.jpeg",
"text": "花非花,雾非雾,夜半来,天明去,来如春梦不多时,去似朝云无觅处。花非花,雾非雾,夜半来,天明去,来如春梦不多时,去似朝云无觅处。",
"width": 232,
"height": 376
},
{
"path": "../images/37.jpeg",
"text": "花非花,雾非雾,夜半来,天明去,来如春梦不多时,去似朝云无觅处。花非花,雾非雾,夜半来,天明去,来如春梦不多时,去似朝云无觅处。!",
"width": 232,
"height": 412
},
{
"path": "../images/38.jpeg",
"text": "花非花,雾非雾,夜半来,天明去,来如春梦不多时,去似朝云无觅处。花非花,雾非雾,夜半来,天明去,来如春梦不多时,去似朝云无觅处。",
"width": 232,
"height": 412
},
{
"path": "../images/39.jpeg",
"text": "花非花,雾非雾,夜半来,天明去,来如春梦不多时,去似朝云无觅处。花非花,雾非雾,夜半来,天明去,来如春梦不多时,去似朝云无觅处。",
"width": 232,
"height": 348
}
];
HTML部分
<div class="box">
//之后追加时,按下方格式追加
<!-- <div class="item ">
<img src="../images/1.jpg" alt="">
<p>花非花,雾非雾,夜半来,天明去,来如春梦不多时,去似朝云无觅处。花非花,雾非雾,夜半来,天明去,来如春梦不多时,去似朝云无觅处。</p>
</div> -->
<div class="btn">加载更多</div>
<script src="../js/data.js"></script>
</div>
CSS部分
body {
margin: 0;
padding: 0;
font-family: "Microsoft Yahei";
}
.box {
position: relative;
width: 1200px;
margin: 0 auto;
}
.item {
width: 232px;
position: absolute;
box-shadow: 0 1px 3px rgba(0, 0, 0, 0.3);
overflow: hidden;
border-radius: 5%;
}
.item>img {
width: 100%;
display: block;
}
.item>p {
margin: 0;
padding: 10px;
background: #eee;
}
.btn {
width: 280px;
height: 40px;
margin: 30px auto;
text-align: center;
line-height: 40px;
background-color: black;
color: white;
border-radius: 6px;
font-size: 24px;
cursor: pointer;
}
.loading {
background-color: white;
color: black;
}
不同写法实现
普通写法
//获取元素
let box = document.querySelector('.box');
let btn = document.querySelector('.btn');
//设置每一页显示多少数据
let pageSize = 10;
//设置页码
let page = 1;
//设置间隔
let space = 8;
//获取页面宽度
let boxWidth = box.offsetWidth;
/************************************************************/
//获取数据 传递页码
function getData(tmpPage) {
//修改btn的状态
btn.innerHTML = '加载中...';
btn.classList.add('loading');
//延时器
setTimeout(function () {
//获取数组分割开始位置和结束位置
//开始位置,(页码-1)*每页的数据数量
let start = (tmpPage - 1) * pageSize;
//结束位置,页码*每页的数据数量
let end = tmpPage * pageSize;
//分割数组
let res = images.slice(start, end);
//将分割出来的数组添加到页面中
let html = '';
//forEach循环数组元素
res.forEach(ele => {
html += `<div class="item ">
<img src="${ele.path}" width="${ele.width}" height="${ele.height}" alt="">
<p>${ele.text}</p>
</div>`;
});
//将数组元素添加到页面中
box.innerHTML += html;
//排序函数
sortImg();
//修改btn的状态
btn.innerHTML = '点击继续加载';
btn.classList.remove('loading');
//如果切割出的数组长度为0,说明已没有数据
if (res.length == 0) {
btn.innerHTML = '所有数据已全部加载完成';
//清除点击事件
btn.removeEventListener('click', clickFn);
}
}, 1000);
}
/************************************************************/
//将页面中的图片排序
function sortImg() {
//获取图片的宽度
let imgWidth = box.firstElementChild.offsetWidth;
//计算每一列最多放几张图片 盒子的宽度/(一张图片宽度+间距)
let col = parseInt(boxWidth / (imgWidth + space));
//保存图片高度
let imgH = [];
//获取页面所有的图片元素,并将其转换为真数组
let resImg = [...box.children];
//循环遍历图片元素 k为下标,img是图片元素
resImg.forEach((img, k) => {
//如果图片元素下标小于每行的列数 说明是第一行元素,top值为0
if (k < col) {
//设置图片位置
//距上方0px
img.style.top = '0px';
//距左方 (图片宽度+间距)*下标
img.style.left = (img.offsetWidth + space) * k + 'px';
//记录第一行图片的高度,方便下面找出最短一列
imgH.push(img.offsetHeight)
} else {//不是第一行元素
//找出高度数组中最小的数 使用...展开数组,使用数学方法
let minNum = Math.min(...imgH);
//获取高度数组中最小数的索引
let minIndex = imgH.findIndex(item => item == minNum)
//设置位置 距上方的距离为高度最小的元素的高度加间距
img.style.top = minNum + space + 'px';
//距左边的距离与高度最小的元素距左边的宽度相等
img.style.left = resImg[minIndex].offsetLeft + 'px';
//更新高度数组
//原本高度最小的下标元素值更新为 原本的高度+间距+添加的图片高度
imgH[minIndex] = minNum + space + img.offsetHeight;
}
})
//设置box的高度,设置btn的位置
box.style.height = Math.max(...imgH) + 'px';
}
//默认调用获取数据函数
getData(page);
/************************************************************/
//点击加载 给btn绑定DOM2级点击事件
btn.addEventListener('click', clickFn);
function clickFn() {
getData(++page);
}
/************************************************************/
//懒加载
//可视区高度+滚动条高度>数据的高度 进行加载
//可视区高度
let ch = window.innerHeight;
//设置懒加载锁 false为开启状态,true为关闭状态
let lock = false;//默认开启
//窗口滚动事件
window.onscroll = function () {
//获取页面数据的高度
let dataH = box.lastElementChild.offsetTop;
//获取滚动条高度
let scroH = document.documentElement.scrollTop;
//如果可视区高度+滚动条高度>数据的高度并且锁为开启状态 进行加载
if (ch + scroH > dataH) {
//如果锁关闭状态,即lock为true时,不调用加载
if (lock) return;
//调用点击事件,进行加载
clickFn();
//加载一次后关锁
lock = true;
//设置延时器 1000ms后开锁
setTimeout(function () {
lock = false;
}, 1000)
}
}
</script>
构造函数
function Waterfall() {
//定义页码
this.page = 1;
//定义一页展示的数量
this.pageSize = 10;
//定义图片之间的间隔
this.space = 8;
//获取页面可视高度
this.clientH = window.innerHeight;
//设置锁 默认开锁
this.lock = true;
//获取数据,内调用排序
this.getData(this.page)
//单击事件
this.$('.btn').addEventListener('click', this.clickFn.bind(this));
//懒加载-----绑定滚动事件
window.addEventListener('scroll', this.scrollFn.bind(this));
}
//获取数据
Waterfall.prototype.getData = function (tmpPage) {
// console.log(this);
//改变加载按钮的状态
this.$('.btn').innerHTML = '加载中...';
this.$('.btn').classList.add("loading");
//设置延时器,模拟从后台加载数据
setTimeout(() => {
//设置开始位置
let start = (tmpPage - 1) * this.pageSize;
//结束位置
let end = tmpPage * this.pageSize;
//分割数组
let tmpImg = images.slice(start, end);
//循环追加
tmpImg.forEach(ele => {
this.$('.box').innerHTML += `<div class="item ">
<img src="${ele.path}" width="${ele.width}" height="${ele.height}" alt="">
<p>${ele.text}</p>
</div>`;
});
//排序
this.sortImg();
//改变加载按钮的状态
this.$('.btn').innerHTML = '点击加载';
this.$('.btn').classList.remove("loading");
//如果分割出的数组长度为0,说明数据已经全部加载完成
if (tmpImg.length == 0) {
this.$('.btn').innerHTML = '数据已全部加载';
}
}, 500)
}
//排序
Waterfall.prototype.sortImg = function () {
//获取单张图片的宽度
let imgWidth = this.$('.box').firstElementChild.offsetWidth;
//计算一行最多可以排几列
let col = parseInt(this.$('.box').offsetWidth / (this.space + imgWidth));
//获取页面所有的图片元素,并转化为数组
let boxImg = [...this.$('.box').children];
//声明数组记录每一列的高度
let imgH = [];
boxImg.forEach((img, key) => {
//如果下标小于一行的列数,说明在第一行,top值为0
if (key < col) {
// console.log(img);
img.style.top = '0px';
img.style.left = (imgWidth + this.space) * key + 'px';
imgH.push(img.offsetHeight);
} else {//表示不在第一行
//获取上一行高度最低的值
let minNum = Math.min(...imgH);
//获取高度最低值的索引
let minIndex = imgH.findIndex(item => item == minNum);
// console.log(img);
img.style.top = minNum + 'px';
img.style.left = boxImg[minIndex].offsetLeft + 'px';
//更新高度数组
imgH[minIndex] = minNum + this.space + img.offsetHeight;
}
})
//获取高度最大值,赋值给box的height,将btn挤下来
let maxNum = Math.max(...imgH);
this.$('.box').style.height = maxNum + 'px';
}
//点击事件
Waterfall.prototype.clickFn = function () {
this.getData(++this.page);
}
//绑定滚动事件
Waterfall.prototype.scrollFn = function () {
// console.log(this);
//获取内容的高度
let dataH = this.$('.box').offsetHeight;
//获取滚动条高度
let scroTop = document.documentElement.scrollTop;
//如果可视高度+滚动条高度大于内容高度,加载
if (this.clientH + scroTop > dataH) {
//如果处于锁定状态 直接return 下面的代码不再执行
if (!this.lock) return;
//加载一次,关锁
this.lock = false;
//如果执行到这一行,说明处于开锁状态 加载
this.getData(++this.page);
//设置延时器,1000ms后开锁
setTimeout(() => {
this.lock = true;
}, 1000)
}
}
Waterfall.prototype.$ = function (ele) {
ele = document.querySelectorAll(ele);
return ele.length == 1 ? ele[0] : ele;
}
new Waterfall();
class
class Waterfall {
constructor() {
//获取数据
this.box = document.querySelector('.box');
this.btn = document.querySelector('.btn');
//设置页码
this.page = 1;
//设置每页的数据数量
this.pageSize = 10;
//设置每一列的间隔
this.space = 8;
//获取盒子的宽度
this.boxWidth = this.box.offsetWidth;
//获取页面可视高度
this.clientTop = window.innerHeight;
//设置懒加载的锁 默认开启
this.lock = true;
/**********************页面追加******************************/
this.getData(this.page);
/**********************点击加载******************************/
this.btn.addEventListener('click', this.clickFn.bind(this));
/**********************懒加载******************************/
window.addEventListener('scroll', this.scrollFn.bind(this))
}
/**********************页面追加******************************/
getData(tmpPage) {
//修改btn状态
this.btn.innerHTML = '加载中...';
this.btn.classList.add('loading');
//设置延时器,500ms后执行,模拟从后台获取数据的效果
setTimeout(function () {
// console.log(this);
//分割数组
//开始位置,(页码-1)*每页的数据数量
let start = (tmpPage - 1) * this.pageSize;
//结束位置,页码*每页的数据数量
let end = tmpPage * this.pageSize;
//开始分割
let resImg = images.slice(start, end);
//追加到页面
let html = '';
resImg.forEach(eleImg => {
html += `<div class="item ">
<img src="${eleImg.path}" width="${eleImg.width}" height="${eleImg.height}" alt="">
<p>${eleImg.text}</p>
</div>`;
});
this.box.innerHTML += html;
//点击排序
this.sortImg();
this.btn.innerHTML = '点击加载';
this.btn.classList.remove('loading');
//如果分割出的数组长度为0,说明已经没有数据,清除点击事件
if (resImg.length == 0) {
this.btn.removeEventListener('click', this.clickFn.bind(this));
this.btn.innerHTML = '数据已全部加载完成';
}
}.bind(this), 500)
}
/**********************排序******************************/
sortImg() {
// console.log(this);
//获取页面所有的图片元素
let tmpImg = [...this.box.children];
//定义元素高度数组,保存元素高度,便于后面追加
let imgH = [];
//循环遍历,进行排序
tmpImg.forEach((img, key) => {
//获取单张图片的宽度
let imgWidth = img.offsetWidth;
//一行可以排几张,即可以排几列
let col = parseInt(this.boxWidth / (imgWidth + this.space));
//如果元素下标小于列数,说明在第一行,top值为0
if (key < col) {
img.style.top = '0px';
img.style.left = (imgWidth + this.space) * key + 'px';
imgH.push(img.offsetHeight);
} else {//说明不是第一行
//找到上一行高度最小值
let minNum = Math.min(...imgH);
//获取高度最小值索引
let minIndex = imgH.findIndex(item => item == minNum);
//将图片追加到高度最小的图片下方
img.style.top = minNum + this.space + 'px';
img.style.left = tmpImg[minIndex].offsetLeft + 'px';
//更新高度数组
imgH[minIndex] = minNum + this.space + img.offsetHeight;
}
})
//获取高度数组最大值,赋值给box的高度,将加载按钮挤下来
let maxNum = Math.max(...imgH);
//设置按钮的位置
this.box.style.height = maxNum + 'px';
}
/**********************点击加载******************************/
clickFn() {
this.getData(++this.page);
}
/**********************懒加载******************************/
scrollFn() {
//获取页面滚动距离
let scroTop = document.documentElement.scrollTop;
//获取内容高度
let dataH = this.box.offsetHeight;
if ((scroTop + this.clientTop) > dataH) {
//如果锁处于关闭状态,结束
if (!this.lock) return;
//如果锁处于开启状态,加载
this.clickFn();
//关锁
this.lock = false;
//设置延时器,1000ms开一次锁
setTimeout(function () {
this.lock = true;
}.bind(this), 1000)
}
}
}
new Waterfall();