JAVA

首屏加载速度优化——图片懒加载

2018-05-02  本文已影响58人  我向你奔
什么是懒加载

懒加载其实就是延迟加载,是一种对网页性能优化的方式,比如当访问一个页面的时候,优先显示可视区域的图片而不一次性加载所有图片,当需要显示的时候再发送图片请求,避免打开网页时加载过多资源。

原理

<img>标签有一个属性是src,用来表示图像的URL,当这个属性的值不为空时,浏览器就会根据这个值发送请求。如果没有src属性,就不会发送请求。我们先不给<img>设置src,把图片真正的URL放在另一个属性data-src中,在需要的时候也就是图片进入可视区域的之前,将URL取出放到src中。

实现

html结构

<div class="container">
  <div class="img-area">
    <img class="my-photo" alt="loading" data-src="./img/img1.png">
  </div>
  <div class="img-area">
    <img class="my-photo" alt="loading" data-src="./img/img2.png">
  </div>
  <div class="img-area">
    <img class="my-photo" alt="loading" data-src="./img/img3.png">
  </div>
  <div class="img-area">
    <img class="my-photo" alt="loading" data-src="./img/img4.png">
  </div>
  <div class="img-area">
    <img class="my-photo" alt="loading" data-src="./img/img5.png">
  </div>
</div>

仔细观察一下,<img>标签此时是没有src属性的,只有alt和data-src属性。
alt属性是一个必需的属性,它规定在图像无法显示时的替代文本。
data-* 全局属性:构成一类名称为自定义数据属性的属性,可以通过HTMLElement.dataset来访问。

如何判断元素是否在可视区域

方法一

① 通过document.documentElement.clientHeight获取屏幕可视窗口高度
② 通过element.offsetTop获取元素相对于文档顶部的距离
③ 通过document.documentElement.scrollTop获取浏览器窗口顶部与文档顶部之间的距离,也就是滚动条滚动的距离

然后判断③-②<①是否成立,如果成立,元素就在可视区域内。

方法二

通过getBoundingClientRect()方法来获取元素的大小以及位置:这个方法返回一个名为ClientRect的DOMRect对象,包含了top、right、botton、left、width、height这些值。

假设const bound = el.getBoundingClientRect();来表示图片到可视区域顶部距离;
并设 const clientHeight = window.innerHeight;来表示可视区域的高度。

随着滚动条的向下滚动,bound.top会越来越小,也就是图片到可视区域顶部的距离越来越小,当bound.top===clientHeight时,图片的上沿应该是位于可视区域下沿的位置的临界点,再滚动一点点,图片就会进入可视区域。也就是说,在bound.top<=clientHeight时,图片是在可视区域内的。

function isInSight(el) {
  const bound = el.getBoundingClientRect();
  const clientHeight = window.innerHeight;
  //如果只考虑向下滚动加载
  //const clientWidth = window.innerWeight;
  return bound.top <= clientHeight + 100;   // +100是为了提前加载。
}

页面打开时需要对所有图片进行检查,是否在可视区域内,如果是就加载。

function checkImgs() {
  const imgs = document.querySelectorAll('.my-photo');
  Array.from(imgs).forEach(el => {
    if (isInSight(el)) {
      loadImg(el);
    }
  })
}

function loadImg(el) {
  if (!el.src) {
    const source = el.dataset.src;
    el.src = source;
  }
}

JQ实现懒加载

有一款jquery的lazyload插件可以实现图片延迟加载的插件。依赖JQuery引入lazyload.js,对我们想要延迟加载的图片添加lazy样式,用"data-original"替换图片的引用路径。

<!-- 对img标签使用 -->
<img class="lazy" data-original="img/example.jpg">
<!-- 延迟加载元素的背景图 -->
<div class="lazy" data-original="img/bg.jpg">
    ...
</div>

在JS文件中调用lazyload()方法

$().ready(function(){
    //可任意选择你想延迟加载的目标元素,例如直接使用样式名lazy作为选择条件
    $("img .lazy").lazyload({
         placeholder : "img/grey.gif", //占位图
         effect: "fadeIn", // 加载效果
         threshold: 200, // 提前加载
         event: 'click',  // trigger
         container: $("#container"),  //指定容器
         failurelimit : 5 // 发生混乱时的hack手段
    })
})

placeholder:占位图片,图片路径值,图片加载时占位图自动隐藏;
effect:图片载入时动画效果,值有show(直接显示),fadeIn(淡入),slideDown(滑入)等jq常用效果;
threshold:提前开始加载高度;数字值,是离需要加载目标的高度。如设置为200,表示滚动条在离目标位置还有200的高度时就开始加载图片,避免用户看到图片加载过程;
event:图片加载trigger;值有click(点击),mouseover(鼠标划过),sporty(运动的),foobar(…);
container:指定容器;lazyload默认在滚动浏览器滚动条时生效,这个参数可以让你在滚动某DIV的滚动条时执行懒加载;
failurelimit:提高稳定性,若是某一张该被加载的图片未能正确加载,则加载其后的第N张图;

上一篇下一篇

猜你喜欢

热点阅读