JavaScript中的懒加载——概念,作用,原理,实现步骤,以及3种原生js实现方式

1.什么是懒加载?

懒加载也就是延迟加载。

当访问一个页面的时候,先把img元素或是其他元素的背景图片路径替换成一张大小为1*1px图片的路径(这样就只需请求一次,俗称占位图),

只有当图片出现在浏览器的可视区域内时,才设置图片正真的路径,让图片显示出来。这就是图片懒加载。

2.为什么要使用懒加载?

很多页面,内容很丰富,页面很长,图片较多。比如说各种商城页面。这些页面图片数量多,而且比较大,少说百来K,多则上兆。

要是页面载入就一次性加载完毕。估计大家都会等到黄花变成黄花菜了。

3.懒加载的原理是什么?

页面中的img元素,如果没有src属性,浏览器就不会发出请求去下载图片,

只有通过javascript设置了图片路径,浏览器才会发送请求。

懒加载的原理就是先在页面中把所有的图片统一使用一张占位图进行占位,

把真正的路径存在元素的“data-url”(这个名字起个自己认识好记的就行)属性里,要用的时候就取出来,再设置;

4.懒加载的实现步骤?

1)首先,不要将图片地址放到src属性中,而是放到其它属性(data-original)中。

2)页面加载完成后,根据scrollTop判断图片是否在用户的视野内,如果在,则将data-original属性中的值取出存放到src属性中。

3)在滚动事件中重复判断图片是否进入视野,如果进入,则将data-original属性中的值取出存放到src属性中。

5.懒加载的优点是什么?

页面加载速度快、可以减轻服务器的压力、节约了流量,用户体验好

6:懒加载代码实现

方式一:


      元素距顶部的高度 - 页面被卷去的高度 <= 浏览器可视区的高度) 
      来判断是否符合我们想要的条件.需要实时监听页面滚动时 图片的高度变化

<!DOCTYPE html>
<html lang="en">
  <head>
    <meta charset="UTF-8" />
    <meta http-equiv="X-UA-Compatible" content="IE=edge" />
    <meta name="viewport" content="width=device-width, initial-scale=1.0" />
    <title>Document</title>
    <style>
      * {
        padding: 0;
        margin: 0;
        list-style: none;
      }
      img {
        width: 400px;
        height: 300px;
      }
    </style>
    <script>
      window.onload = function () {
        var imgs = document.querySelectorAll("img");
        // 初始化执行
        lazyLoad(imgs);
        // 滚动执行
        window.addEventListener("scroll", function () {
          lazyLoad(imgs);
        });

        function lazyLoad(imgs) {
          for (let i = 0; i < imgs.length; i++) {
            var imgoffsetT = imgs[i].offsetTop; // 图片的距顶部的高度
            var wheight = window.innerHeight; // 浏览器可视区的高度
            var scrollT = document.documentElement.scrollTop; // 页面被卷去的高度
            if (imgoffsetT - scrollT <= wheight) {
              // 判断图片是否将要出现
              imgs[i].src = imgs[i].dataset.src; // 出现后将自定义地址转为真实地址
            }
          }
        }
      };

      /* 
        obj.getAttribute("属性名")
        通过元素节点的属性名称获取属性的值。
        使用data-前缀设置我们需要的自定义属性,来进行一些数据的存放,
        dataset 获取自定义属性值的使用
      */
    </script>
  </head>
  <body>
    <ul>
      <li>
        <img data-src="./img/img1.gif" src="./img/loading.gif" alt="" />
      </li>
      <li>
        <img data-src="./img/img2.gif" src="./img/loading.gif" alt="" />
      </li>
      <li>
        <img data-src="./img/img3.gif" src="./img/loading.gif" alt="" />
      </li>
      <li>
        <img data-src="./img/img4.gif" src="./img/loading.gif" alt="" />
      </li>
      <li>
        <img data-src="./img/img5.png" src="./img/loading.gif" alt="" />
      </li>
    </ul>
  </body>
</html>

方式二       getBoundingClientRect()

<!DOCTYPE html>
<html lang="en">
  <head>
    <meta charset="UTF-8" />
    <meta http-equiv="X-UA-Compatible" content="IE=edge" />
    <meta name="viewport" content="width=device-width, initial-scale=1.0" />
    <title>Document</title>
    <style>
      * {
        padding: 0;
        margin: 0;
        list-style: none;
      }
      img {
        width: 400px;
        height: 300px;
      }
    </style>
    <script>
      window.onload = function () {
        var imgs = document.querySelectorAll("img");
        // 初始调动一次
        lazyLoad();
        window.addEventListener("scroll", throttle(lazyLoad, 1000), false);


        //函数1:封装判定图片是否在可视区
        function isInVisibleArea(imgOne) {
          const info = imgOne.getBoundingClientRect();
          //  获取页面可视区的高度,宽度
          let windowH = window.innerHeight;
          let windowW = window.innerWidth;
          // 限定参数在可视区内
          let res = info.bottom > 0 && info.top < windowH && info.right > 0 && info.left < windowW;
          return res;
        }


        //函数2: 封装滚动时重新加载函数
        function lazyLoad() {
          for (let i = 0; i < imgs.length; i++) {
            const imgOne = imgs[i];
            // 判定是否在可视区内
            if (isInVisibleArea(imgOne)) {
              // 替换src方法一:
              // imgOne.src = imgOne.getAttribute("data-src");
              // 替换src方法二:
              imgOne.src = imgOne.dataset.src;
              // imgs.splice(i,1)
              // i--;
            }
            console.log("我滚了"); //所以要做节流操作
          }
        }


        //函数3:节流函数
        /* 
        参数1: 函数
        参数2:执行时间
         */
        function throttle(fn, time = 250) {
          let lastTime = null;
          return function (...args) {
            const now = Date.now(); //当前时间
            if (now - lastTime >= time) {
              fn();//帮助执行函数,改变上下文
              lastTime = now;
            }
          };
        }

      };
   
      /* 
      getBoundingClientRect()
           ——获取元素位置,这个方法没有参数
           ——用于获得页面中某个元素的左,上,右和下分别相对浏览器视窗的位置。
           ——是DOM元素到浏览器可视范围的距离(不包含文档卷起的部分)。
      该函数返回一个Object对象,该对象有6个属性:top,lef,right,bottom,width,height;
 */

    </script>
  </head>
  <body>
    <ul>
      <li>
        <img data-src="./img/img1.gif" src="./img/loading.gif" alt="" />
      </li>
      <li>
        <img data-src="./img/img2.gif" src="./img/loading.gif" alt="" />
      </li>
      <li>
        <img data-src="./img/img3.gif" src="./img/loading.gif" alt="" />
      </li>
      <li>
        <img data-src="./img/img4.gif" src="./img/loading.gif" alt="" />
      </li>
      <li>
        <img data-src="./img/img5.png" src="./img/loading.gif" alt="" />
      </li>
    </ul>
  </body>
</html>

方式三:IntersectionObserver(callback)

<!DOCTYPE html>
<html lang="en">
  <head>
    <meta charset="UTF-8" />
    <meta http-equiv="X-UA-Compatible" content="IE=edge" />
    <meta name="viewport" content="width=device-width, initial-scale=1.0" />
    <title>Document</title>
    <style>
      * {
        padding: 0;
        margin: 0;
        list-style: none;
      }
      img {
        width: 400px;
        height: 300px;
      }
    </style>
  </head>
  <body>
    <ul id="view">
      <li>
        <img data-src="./img/img1.gif" src="./img/loading.gif" alt="" />
      </li>
      <li>
        <img data-src="./img/img2.gif" src="./img/loading.gif" alt="" />
      </li>
      <li>
        <img data-src="./img/img3.gif" src="./img/loading.gif" alt="" />
      </li>
      <li>
        <img data-src="./img/img4.gif" src="./img/loading.gif" alt="" />
      </li>
      <li>
        <img data-src="./img/img5.png" src="./img/loading.gif" alt="" />
      </li>
    </ul>

    <script>
      const imgs = document.querySelectorAll("img");
      const callback = (res) => {
        //res 是观察的元素数组   info 每个被观察的图片信息
        res.forEach((info) => {
          //  isIntersecting 目标是否被观察到,返回布尔值
          if (info.isIntersecting) {
            // img 就是当前的图片标签
            const img = info.target;
            img.src = img.getAttribute("data-src");
            // 真实地址替换后 取消对它的观察
            obs.unobserve(img);
            console.log("触发");
          }
        });
      };
      const obs = new IntersectionObserver(callback);// 实例化 IntersectionObserver
    //   遍历imgs所有的图片,然后给每个图片添加观察实例
      imgs.forEach((img) => {
        //  observe : 被调用的IntersectionObserver实例。给每个图片添加观察实例
        obs.observe(img);
      });

   /* IntersectionObserver(callback) 
        callback回调触发两次,看见了出发,看不见也触发
   */
    </script>
  </body>
</html>

  • 8
    点赞
  • 36
    收藏
    觉得还不错? 一键收藏
  • 打赏
    打赏
  • 0
    评论
懒加载(Lazy Loading)是一优化网页性能的技术,它可以在页面加载完毕后,延迟加载一些不是必要的资源,比如图片、视频等,从而减少页面的加载时间,提高用户的体验。 下面是用 JavaScript 实现懒加载的简单示例: 首先,我们需要在 HTML 将需要延迟加载的资源(比如图片)的 `src` 属性替换为 `data-src` 属性,如下所示: ```html <img data-src="path/to/image.jpg"> ``` 接下来,我们需要编写 JavaScript 代码来实现懒加载。具体实现步骤如下: 1. 获取所有需要延迟加载的元素 2. 监听滚动事件,当元素出现在视口内时,动态加载资源 3. 将 `data-src` 属性的值赋给 `src` 属性 下面是完整的 JavaScript 代码: ```javascript window.addEventListener('DOMContentLoaded', function() { const lazyImages = document.querySelectorAll('img[data-src]'); const windowHeight = window.innerHeight; function lazyLoad() { lazyImages.forEach(image => { const imageTop = image.getBoundingClientRect().top; if (imageTop < windowHeight) { image.src = image.dataset.src; image.removeAttribute('data-src'); } }); } window.addEventListener('scroll', lazyLoad); window.addEventListener('resize', lazyLoad); }); ``` 在这段代码,我们首先使用 `document.querySelectorAll` 获取所有带有 `data-src` 属性的图片元素。接着,我们获取浏览器窗口的高度,并定义 `lazyLoad` 函数,用于实现懒加载。在 `lazyLoad` 函数,我们遍历所有需要延迟加载的图片元素,并使用 `getBoundingClientRect()` 方法获取元素的位置信息。如果元素的顶部位置小于浏览器窗口的高度,就将 `data-src` 属性的值赋给 `src` 属性,并移除 `data-src` 属性。 最后,我们监听 `scroll` 和 `resize` 事件,当页面滚动或窗口大小发生变化时,重新执行 `lazyLoad` 函数,以确保所有需要延迟加载的元素都能被正确加载。 注意:以上代码仅为示例,实际应用需要根据具体情况进行修改。

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包

打赏作者

燕穗子博客

你的鼓励将是我创作的最大动力

¥1 ¥2 ¥4 ¥6 ¥10 ¥20
扫码支付:¥1
获取中
扫码支付

您的余额不足,请更换扫码支付或充值

打赏作者

实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值