0


【前端】IntersectionObserver 实现图片懒加载和无限滚动

【前端】IntersectionObserver 实现图片懒加载和无限滚动

在前端开发中,性能优化是一个重要的考量因素。随着现代网页和应用的复杂性增加,确保页面快速加载和流畅运行变得越来越重要。本文将介绍一种强大的工具——

IntersectionObserver

API,并结合 Vue 项目,讲解如何使用它来实现图片懒加载和无限滚动。
在这里插入图片描述

IntersectionObserver API 简介

IntersectionObserver

API 是现代浏览器提供的一种异步观察者,它可以监视一个元素与视口(或某个特定祖先元素)交叉状态的变化。它的主要用途包括:

  • 图片懒加载
  • 无限滚动加载内容
  • 实现元素的延迟加载
  • 触发动画效果

IntersectionObserver 的基本用法

要使用

IntersectionObserver

,首先需要创建一个

IntersectionObserver

实例,并传入一个回调函数和一些配置选项:

const observer =newIntersectionObserver(callback, options);
  • callback: 每当被观察的元素的可见性变化时,调用的回调函数。该函数接收两个参数: - entries: 被观察元素的列表,每个元素都是一个 IntersectionObserverEntry 对象。- observer: IntersectionObserver 实例本身。
  • options: 一个可选参数对象,用于配置观察器的行为。包括以下属性: - root: 用于观察的祖先元素,默认为视口。- rootMargin: 根元素的外边距,用于扩大或缩小根元素的判定区域。- threshold: 一个数组,规定在什么可见比例下触发回调。

回调函数

回调函数处理

IntersectionObserverEntry

对象的数组,每个对象包含了元素的交叉信息:

constcallback=(entries, observer)=>{
  entries.forEach(entry=>{if(entry.isIntersecting){// 元素进入视口
      console.log('Element is in viewport:', entry.target);// 执行懒加载操作,如加载图片const img = entry.target;
      img.src = img.dataset.src;// 停止观察当前元素
      observer.unobserve(entry.target);}});};

配置选项示例

const options ={root:null,// 默认为视口rootMargin:'0px',// 没有外边距threshold:0.1// 当 10% 的目标元素可见时触发回调};

观察目标元素

创建

IntersectionObserver

实例后,可以使用

observe

方法来观察目标元素:

const img = document.querySelector('img');
observer.observe(img);

完整示例

以下是一个完整的示例,展示如何使用

IntersectionObserver

实现图片懒加载:

document.addEventListener('DOMContentLoaded',()=>{const images = document.querySelectorAll('img[data-src]');constcallback=(entries, observer)=>{
    entries.forEach(entry=>{if(entry.isIntersecting){const img = entry.target;
        img.src = img.dataset.src;
        observer.unobserve(img);}});};const options ={root:null,rootMargin:'0px',threshold:0.1};const observer =newIntersectionObserver(callback, options);

  images.forEach(image=>{
    observer.observe(image);});});

更加深入的学习我推荐:阮一峰的帖子

在 Vue 项目中实现图片懒加载

接下来,我们将结合 Vue 项目,使用

IntersectionObserver

实现图片懒加载。首先,我们需要创建一个自定义指令

v-lazy

创建自定义指令

在 Vue 中,我们可以通过自定义指令来实现懒加载。以下是一个简单的实现:

Vue.directive('lazy',{inserted:function(el, binding){let observer;if(IntersectionObserver){
      observer =newIntersectionObserver(entries=>{
        entries.forEach(entry=>{if(entry.isIntersecting){
            observer.unobserve(el);const src = binding.value;
            el.src = src;}});});
      observer.observe(el);}else{// 如果浏览器不支持 IntersectionObserver,需要提供一个降级方案
      el.src = binding.value;}}});

在模板中使用指令

<template><div><imgv-lazy="imageSource"alt="Lazy loaded image"/></div></template><script>exportdefault{data(){return{imageSource:'path/to/image.jpg'};}};</script>

这样,当图片进入视口时,

v-lazy

指令会触发加载图片,从而实现懒加载。

在 Vue 项目中实现无限滚动

除了图片懒加载,我们还可以使用

IntersectionObserver

实现无限滚动加载内容。以下是实现步骤:

创建无限滚动组件

Vue.component('infinite-scroll',{data(){return{items:[],page:1,observer:null,};},mounted(){this.loadItems();this.createObserver();},methods:{loadItems(){// 模拟加载数据fetch(`https://api.example.com/items?page=${this.page}`).then(response=> response.json()).then(data=>{this.items =[...this.items,...data];this.page +=1;});},createObserver(){const options ={root:null,rootMargin:'0px',threshold:1.0};this.observer =newIntersectionObserver((entries, observer)=>{
        entries.forEach(entry=>{if(entry.isIntersecting){this.loadItems();}});}, options);this.$nextTick(()=>{const sentinel =this.$refs.sentinel;this.observer.observe(sentinel);});}},template:`
    <div>
      <div v-for="item in items" :key="item.id" class="item">
        {{ item.name }}
      </div>
      <div ref="sentinel" class="sentinel"></div>
    </div>
  `});

在主应用中使用组件

<template><divid="app"><infinite-scroll></infinite-scroll></div></template><script>import InfiniteScroll from'./components/InfiniteScroll.vue';exportdefault{components:{
    InfiniteScroll
  }};</script>

在这个示例中,当用户滚动到页面底部时,

IntersectionObserver

会触发回调函数,加载更多数据并更新页面内容,从而实现无限滚动。


本文转载自: https://blog.csdn.net/qq_41883423/article/details/140183785
版权归原作者 帅比九日 所有, 如有侵权,请联系我们删除。

“【前端】IntersectionObserver 实现图片懒加载和无限滚动”的评论:

还没有评论