谈谈IntersectionObserver懒加载的具体使用


Posted in Javascript onOctober 15, 2019

概念

IntersectionObserver接口(从属于Intersection Observer API)为开发者提供了一种可以异步监听目标元素与其祖先或视窗(viewport)交叉状态的手段。祖先元素与视窗(viewport)被称为根(root)。

这是MDN上给的官方概念,不用去管它,我粘出来只是为了显得专业点嘛...

重点看这里 监听目标元素与其祖先或视窗交叉状态的手段 ,其实就是观察一个元素是否在视窗可见。

谈谈IntersectionObserver懒加载的具体使用

可以看到,交叉了就是说明当前元素在视窗里,当前就是可见的了。

API

var io = new IntersectionObserver(callback, options)

其实就是一个简单的构造函数。

以上代码会返回一个 IntersectionObserver 实例, callback 是当元素的可见性变化时候的回调函数, options 是一些配置项(可选)。

我们使用返回的这个实例来进行一些操作。

io.observe(document.querySelector('img')) 开始观察,接受一个DOM节点对象
io.unobserve(element) 停止观察 接受一个element元素
io.disconnect() 关闭观察器

options

root

用于观察的根元素,默认是浏览器的视口,也可以指定具体元素,指定元素的时候用于观察的元素必须是指定元素的子元素

threshold

用来指定交叉比例,决定什么时候触发回调函数,是一个数组,默认是 [0]

const options = {
	root: null,
	threshold: [0, 0.5, 1]
}
var io = new IntersectionObserver(callback, options)
io.observe(document.querySelector('img'))

上面代码,我们指定了交叉比例为0,0.5,1,当观察元素img0%、50%、100%时候就会触发回调函数

rootMargin

用来扩大或者缩小视窗的的大小,使用css的定义方法, 10px 10px 30px 20px 表示top、right、bottom 和 left的值

const options = {
	root: document.querySelector('.box'),
	threshold: [0, 0.5, 1],
	rootMargin: '30px 100px 20px'
}

为了方便理解,我画了张图,如下

谈谈IntersectionObserver懒加载的具体使用

首先我们来看下图上的问题,蓝线是什么呢?他就是咱们定义的root元素,我们添加了 rootMargin 属性,将视窗的增大了,虚线就是现在的视窗,所以元素现在也就在视窗里面了。

由此可见,root元素只有在 rootMargin 为空的时候才是绝对的视窗。

说了简单的options,接下来我们看下 callback

callback

上面我们说到,当元素的可见性变化时,就会触发callback函数。

callback函数会触发两次,元素进入视窗(开始可见时)和元素离开视窗(开始不可见时)都会触发

var io = new IntersectionObserver((entries)=>{
	console.log(entries)
})

io.observe($0)

以上代码,请在chrome控制台进行调试,这里我使用了 $0 选择了上一次我审查元素的选择的节点

运行结果如下

谈谈IntersectionObserver懒加载的具体使用

我们可以看到callback函数有个 entries 参数,它是个 IntersectionObserverEntry 对象数组,接下来我们重点说下IntersectionObserverEntry对象

IntersectionObserverEntry

IntersectionObserverEntry 提供观察元素的信息,有七个属性。

boundingClientRect 目标元素的矩形信息 intersectionRatio 相交区域和目标元素的比例值 intersectionRect/boundingClientRect 不可见时小于等于0 intersectionRect 目标元素和视窗(根)相交的矩形信息 可以称为相交区域 isIntersecting 目标元素当前是否可见 Boolean值 可见为true rootBounds 根元素的矩形信息,没有指定根元素就是当前视窗的矩形信息 target 观察的目标元素 time 返回一个记录从 IntersectionObserver 的时间到交叉被触发的时间的时间戳

上面几个矩形信息的关系如下

谈谈IntersectionObserver懒加载的具体使用

划重点

intersectionRatio和 isIntersecting 是用来判断元素是否可见的,押题咯...

懒加载

好了,通过上面一些概念我们大概了解了 IntersectionObserver 是个什么东西,接下来我们用它来写点代码,写什么呢?没错就是懒加载。

通过IntersectionObserver来实现懒加载,就简单的多了,我们只需要设置回调,判断当前元素是否可见,再进行渲染操作就行了,而不用去关心内部的计算。

主要代码如下

const io = new IntersectionObserver(()=>{ // 实例化 默认基于当前视窗
	
}) 

let ings = document.querySelectorAll('[data-src]') // 将图片的真实url设置为data-src src属性为占位图 元素可见时候替换src

function callback(entries){ 
	entries.forEach((item) => { // 遍历entries数组
		if(item.isIntersecting){ // 当前元素可见
			item.target.src = item.target.dataset.src // 替换src
			io.unobserve(item.target) // 停止观察当前元素 避免不可见时候再次调用callback函数
		}	
	})
}

imgs.forEach((item)=>{ // io.observe接受一个DOM元素,添加多个监听 使用forEach
	io.observe(item)
})

本想录制个GIF图,使用Recordlt始终上传不了,谁有好用的GIF图录制软件请推荐个,不胜感激。。

呐,给你花:rose:

因篇幅有限,完整代码请戳 github

注意

目前IntersectionObserver是一个实验中的功能,请酌情使用。

谈谈IntersectionObserver懒加载的具体使用

以上就是本文的全部内容,希望对大家的学习有所帮助,也希望大家多多支持三水点靠木。

Javascript 相关文章推荐
Js 冒泡事件阻止实现代码
Jan 27 Javascript
jquery实现实时改变网页字体大小、字体背景色和颜色的方法
Aug 05 Javascript
详解AngularJS中module模块的导入导出
Dec 10 Javascript
jQuery自定义滚动条完整实例
Jan 08 Javascript
利用原生js和jQuery实现单选框的勾选和取消操作的方法
Sep 04 Javascript
完美解决node.js中使用https请求报CERT_UNTRUSTED的问题
Jan 08 Javascript
jQuery实现搜索页面关键字的功能
Feb 16 Javascript
微信小程序 弹框和模态框实现代码
Mar 10 Javascript
Vue中的v-cloak使用解读
Mar 27 Javascript
dts文件中删除一个node或属性的操作方法
Aug 05 Javascript
微信小程序实现的一键拨号功能示例
Apr 24 Javascript
el-input 标签中密码的显示和隐藏功能的实例代码
Jul 19 Javascript
js实现开关灯效果
Mar 30 #Javascript
JS实现灯泡开关特效
Mar 30 #Javascript
浅谈微信小程序列表埋点曝光指南
Oct 15 #Javascript
javascript网页随机点名实现过程解析
Oct 15 #Javascript
javascript随机变色实例代码
Oct 15 #Javascript
vue中axios的二次封装实例讲解
Oct 14 #Javascript
Vue项目打包部署到iis服务器的配置方法
Oct 14 #Javascript
You might like
利用递归把多维数组转为一维数组的函数
2006/10/09 PHP
FCKeditor的安装(PHP)
2007/01/13 PHP
php实现zip压缩文件解压缩代码分享(简单易懂)
2014/05/10 PHP
纯JavaScript实现的完美渐变弹出层效果代码
2010/04/02 Javascript
javascript取消文本选定的实现代码
2010/11/14 Javascript
js 上传图片预览问题
2010/12/06 Javascript
javascript 主动派发事件总结
2011/08/09 Javascript
jQuery源码中的chunker 正则过滤符分析
2012/07/31 Javascript
js获得当前时区夏令时发生和终止的时间代码
2014/02/23 Javascript
jquery统计用户选中的复选框的个数
2014/06/06 Javascript
nodejs初步体验篇
2015/11/23 NodeJs
JS实现合并两个数组并去除重复项只留一个的方法
2015/12/17 Javascript
JS去除重复并统计数量的实现方法
2016/12/15 Javascript
three.js中文文档学习之通过模块导入
2017/11/20 Javascript
浅谈React 服务器端渲染的使用
2018/05/08 Javascript
浅谈Vue组件及组件的注册方法
2018/08/24 Javascript
一看就会的vuex实现登录验证(附案例)
2020/01/09 Javascript
JS实现容器模块左右拖动效果
2020/01/14 Javascript
手把手带你入门微信小程序新框架Kbone的使用
2020/02/25 Javascript
vue实现验证用户名是否可用
2021/01/20 Vue.js
python实现RSA加密(解密)算法
2016/02/17 Python
基于python实现的抓取腾讯视频所有电影的爬虫
2016/04/22 Python
python获取文件路径、文件名、后缀名的实例
2018/04/23 Python
在IPython中进行Python程序执行时间的测量方法
2018/11/01 Python
python通过paramiko复制远程文件及文件目录到本地
2019/04/30 Python
Python 20行简单实现有道在线翻译的详解
2019/05/15 Python
python实现控制COM口的示例
2019/07/03 Python
python 判断txt每行内容中是否包含子串并重新写入保存的实例
2020/03/12 Python
如何在Canvas中添加事件的方法示例
2019/05/21 HTML / CSS
励志演讲稿范文
2014/04/29 职场文书
学生不参加考试检讨书
2015/02/19 职场文书
美德少年主要事迹材料
2015/11/04 职场文书
2019森林防火宣传标语大全!
2019/07/03 职场文书
领导激励员工的演讲稿,各种会上用得到,建议收藏
2019/08/13 职场文书
golang elasticsearch Client的使用详解
2021/05/05 Golang
Centos7中MySQL数据库使用mysqldump进行每日自动备份的编写
2021/08/02 MySQL