用IntersectionObserver实现无限滚动和图片懒加载

之前H5中实现列表滚动到底部加载下一页数据,需要监听滚动事件,获取页面滚动的垂直距离、页面的总高度,处理浏览器兼容,计算是否滚动到底部,做节流等,这一套处理下来非常的麻烦。现如今随着技术的进步,浏览器推出了多种 观察器 ,让我们可以更便捷、高效的收集页面与元素的信息。比如 监听元素与视窗交叉状态 的观察器:IntersectionObserver(交叉观察器) 就可以实现无限滚动和图片懒加载。

在MDN文档上可以看IntersectionObserver的详细介绍Intersection Observer API

实现无限滚动

实现一个无限滚动的步骤如下:

  • 创建 IntersectionObserver 实例,并指定观察的目标元素,通常是页面底部的加载中占位符元素
  • 在回调函数中,判断目标元素是否进入视窗。
  • 若目标元素进入视窗,触发数据加载的操作,并更新页面内容。
js 复制代码
// 回调
// entries为一个 IntersectionObserverEntry 对象的数组,
// 每个被触发的阈值,都或多或少与指定阈值有偏差。
const cb = (entries) => {
    entries.forEach((entry) => {
        // isIntersecting是一个Boolean值,判断目标元素当前是否可见,
        // 返回一个布尔值,下列两种操作均会触发callback:
        // 1. 如果目标元素出现在可视区,返回true。
        // 2. 如果从可视区消失,返回false
        if (entry.isIntersecting) {
          getList({ page, pageSize ... }) // 触发数据加载操作
        }
    })
}

// 创建观察实例
const observer = new IntersectionObserver(cb)

// 获取占位符元素
const loading = document.querySelector('.loading')
// 观察加载中占位符元素
observer.observe(loading)

IntersectionObserver 实现无限滚动,可以平滑的加载体验,避免频繁的触发滚动事件,只在需要底部的加载中占位符元素出现时才进行相应列表请求,减少了无效的请求消耗。

实现懒加载

思路是在不可视区域内的图片资源延迟加载,在元素进入视窗时进行加载。

js 复制代码
const imgs = [...document.querySelectorAll('img')]

const cb = (entries) => {
    entries.forEach(item => {
        // isIntersecting是一个Boolean值,判断目标元素当前是否可见
        if (item.isIntersecting) {
            item.target.src = item.target.dataset.src
            // 图片加载后即停止监听该元素
            observer.unobserve(item.target)
        }
    })
}
const options = {
    root: document.querySelector('.root'),
    threshold: 0
}

const observer = new IntersectionObserver(cb, options)

// observe遍历监听所有img节点
imgs.forEach(img => observer.observe(img))

仅作记录项目经历,参考文章地址:

用IntersectionObserver实现无限滚动和图片懒加载

相关推荐
comelong10 分钟前
还有人不知道IntersectionObserver也可以实现懒加载吗
前端·javascript·面试
独立开阀者_FwtCoder28 分钟前
“复制党”完了!前端这6招让你的网站内容谁都复制不走!
前端·javascript·vue.js
10年前端老司机1 小时前
前端最强大的excel插件
前端·javascript·vue.js
小胖同学~1 小时前
插入排序C语言版
java·javascript·算法
大鱼七成饱2 小时前
彻底搞懂 react 的 use client
前端·javascript·next.js
Eliauk__2 小时前
深入浅出聊聊跨域:它到底是个啥,怎么破?
前端·javascript·面试
Vesper633 小时前
【Vue】Vue2/3全局属性配置全攻略
前端·javascript·vue.js
伍哥的传说3 小时前
React Toast组件Sonner使用详解、倒计时扩展
前端·javascript·react.js·前端框架·ecmascript
&白帝&3 小时前
Vue 3 常用响应式数据类型详解:ref、reactive、toRef 和 toRefs
前端·javascript·vue.js