图片懒加载可以减少不必要的图片资源请求,提高页面的加载速度,提升用户体验。我们实现页面懒加载的方案一般有三种方式:
我们先写HTML的DOM结构:
<style>
ul, li {
margin: 0px;
list-style: none;
}
li {
height: 500px;
}
img {
width: 1000px;
height: 100%;
}
</style>
<ul id="lazyload">
<li>
<img data-src="./images/1.png" alt="loading">
</li>
<li>
<img data-src="./images/2.png" alt="loading">
</li>
<li>
<img data-src="./images/3.png" alt="loading">
</li>
<li>
<img data-src="./images/4.png" alt="loading">
</li>
<li>
<img data-src="./images/5.png" alt="loading">
</li>
<li>
<img data-src="./images/6.png" alt="loading">
</li>
<li>
<img data-src="./images/7.png" alt="loading">
</li>
<li>
<img data-src="./images/8.png" alt="loading">
</li>
</ul>
在懒加载优化之前,我们使用全部加载的伪代码,根据islazyLoadBool()方法判断对应的懒加载逻辑。在实际开发过程中回去涉及到节流请求等操作。
let imgList = document.querySelectorAll('#lazyload img') || [];
let clientHeight = window.innerHeight;
loadimgListener();
window.onscroll = this.loadimgListener;
//图片加载监听器
function loadimgListener() {
Array.from(imgList).forEach(dom => {
islazyLoadBool(dom) && loadImg(dom);
})
}
//加载图片
function loadImg(img) {
if(!img || img.src) return;
img.src = img.getAttribute('data-src');
}
function islazyLoadBool(dom) {
return true; //TODO:懒加载核心:判断加载
}
我们首先了解常见的DOM元素位置属性:
let dom = document.body;
dom.clientHeight; //可见区域高度
dom.clientTop; //可见区域左边距
dom.offsetHeight; //可见区域左边距-带边框
dom.scrollTop;// 被隐藏的顶部
window.screen.height // 屏幕高度
我们的核心是根据图片的位置判断是否加载:
//判断加载
function islazyLoadBool(dom) {
let imgTop = dom.offsetTop; //获取响度浏览器可视区的高度
let srcollTop = document.documentElement.scrollTop || document.body.scrollTop;
return imgTop <= clientHeight + srcollTop ;
}
Element.getBoundingClientRect() 返回一个DOMRect对象,包含了描述元素的位置属性:left,right,top,bottom。rectObject = object.getBoundingClientRect();
我们可以使用定时器或者scroll事件,在回调函数调用元素的getBoundingClientRect()方法,获取元素的位置。
//懒加载核心:判断加载
function islazyLoadBool(dom) {
let imgTop = dom.getBoundingClientRect().top; //获取响度浏览器可视区的高度
let srcollTop = document.documentElement.scrollTop || document.body.scrollTop;
return imgTop <= clientHeight + 100 ;
}
因为getBoundingClientRect()会强制重新计算元素布局,所以这个方法存在一定的性能隐患,不建议使用。
IntersectionObserver 提供异步接口监听目标元素与其祖先元素(或者视窗viewport),
IntersectionObserver API 可以用来实现图片懒加载功能,在不支持该API的浏览器使用 polyfill
// 加载图片
function loadImg(ele) {
let target = ele && ele.target;
target.src = target.dataset.src;
console.log(target.src)
}
function callback (arr) {
arr.forEach(item => {
if(item.isIntersecting) {
loadImg(item);
io.unobserve(item.target)
}
})
}
var io = new IntersectionObserver(callback);
let imgs = document.querySelectorAll('img');
imgs.forEach(item => {
io.observe(item);
})
原创声明:本文系作者授权腾讯云开发者社区发表,未经许可,不得转载。
如有侵权,请联系 cloudcommunity@tencent.com 删除。
原创声明:本文系作者授权腾讯云开发者社区发表,未经许可,不得转载。
如有侵权,请联系 cloudcommunity@tencent.com 删除。