IntersectionObserver的基本用法

138 阅读2分钟

IntersectionObserver 是一个现代浏览器提供的 API,用于监控一个元素是否与另一个元素(通常是视口)相交。这个 API 非常有用,特别是在实现懒加载图片、无限滚动、动态加载内容等场景中。

IntersectionObserver 的基本用法

1. 创建 IntersectionObserver 实例

javascript
const observer = new IntersectionObserver((entries, observer) => {
  entries.forEach(entry => {
    if (entry.isIntersecting) {
      console.log('Element is visible');
      // 执行相关操作
    } else {
      console.log('Element is not visible');
    }
  });
}, {
  threshold: 0.5 // 触发条件,当元素与视口相交比例达到 0.5 时触发
});

2. 观察目标元素

javascript
const targetElement = document.querySelector('#target');
observer.observe(targetElement);

常用参数

threshold

threshold 参数是一个数组,表示元素与视口相交的比例。默认值为 [0],即完全进入视口时触发。

javascript
new IntersectionObserver(callback, {
  threshold: [0, 0.5, 1] // 当相交比例分别为 0、0.5、1 时触发
});

root

root 参数指定相对于哪个元素观察。默认值为 null,即相对于视口观察。

javascript
new IntersectionObserver(callback, {
  root: document.querySelector('#container')
});

rootMargin

rootMargin 参数用于指定相对于 root 元素的偏移量。可以用来扩展或缩小观察区域。

javascript
new IntersectionObserver(callback, {
  rootMargin: '0px 0px 100px 0px' // 下方扩展 100px
});

懒加载图片示例

HTML 结构

html
<div class="container">
  <img class="lazy" data-src="image1.jpg" alt="Image 1">
  <img class="lazy" data-src="image2.jpg" alt="Image 2">
  <img class="lazy" data-src="image3.jpg" alt="Image 3">
</div>

JavaScript 代码

javascript
const lazyImages = document.querySelectorAll('.lazy');

const lazyLoad = (entries, observer) => {
  entries.forEach(entry => {
    if (entry.isIntersecting) {
      const img = entry.target;
      img.src = img.getAttribute('data-src');
      img.classList.remove('lazy');
      observer.unobserve(img); // 停止观察已加载的图片
    }
  });
};

const observer = new IntersectionObserver(lazyLoad, {
  threshold: 0.5
});

lazyImages.forEach(img => {
  observer.observe(img);
});

无限滚动示例

HTML 结构

html
<div class="scroll-container">
  <div class="item">Item 1</div>
  <div class="item">Item 2</div>
  <div class="item">Item 3</div>
  <!-- 更多 item -->
</div>

JavaScript 代码

javascript
const container = document.querySelector('.scroll-container');
const items = document.querySelectorAll('.item');

const loadMore = (entries, observer) => {
  entries.forEach(entry => {
    if (entry.isIntersecting) {
      console.log('Loading more items...');
      // 加载更多内容
      observer.unobserve(entry.target); // 停止观察当前元素
    }
  });
};

const observer = new IntersectionObserver(loadMore, {
  threshold: 0.5
});

items.forEach(item => {
  observer.observe(item);
});

清理和取消观察

在不需要继续观察时,可以调用 disconnect 方法来清理资源。

javascript
observer.disconnect(); // 清理所有观察

也可以单独取消对某个元素的观察:

javascript
observer.unobserve(targetElement); // 取消对特定元素的观察

适用场景

  • 懒加载图片:只在图片进入视口时加载,节省带宽。
  • 无限滚动:当用户滚动到底部时加载更多内容。
  • 动态加载内容:根据用户行为动态加载新的内容。
  • 性能优化:减少不必要的资源加载,提高页面性能。

总结

IntersectionObserver 是一个非常强大且实用的 API,可以帮助开发者实现多种动态加载和性能优化的功能。通过合理配置参数,可以实现高效且流畅的用户体验。掌握 IntersectionObserver 的基本用法和应用场景,可以在现代 Web 开发中发挥重要作用。