滚动加载
https://juejin.cn/post/6844903961862897672
# 业务场景
在编写帖子(例如百度贴吧、微博、知乎等)的时候,用户往往从上往下浏览,当浏览到底部时,需要加载新的数据。
滚动加载和分页是两种常见的解决方案,分页较为简单,而有些场景下,使用滚动加载更加合适。
# 封装一个自定义指令
因为项目里需要用到的滚动加载的地方比较多,因此封装为一个指令,在使用起来更加方便
# 逻辑
自定义指令接收一个对象作为参数,
{ container: '.content-wp', // CSS Selector 滚动的容器 callback: ()=>{}, // 回调函数,可以请求数据 scrollBottom: number // 距离底部请求数据的阈值 }1
2
3
4
5监听滚动的容器的 scroll 事件 为什么是 scroll 而不是 wheel
- wheel 事件先触发,scroll 后触发
- 只要鼠标滚轮在滚动,wheel 事件就会触发,而 scroll 事件在滚动条到底部或者顶部后,就不会触发
- 鼠标按住拖动滚动条时,wheel 事件不会触发(这里无法做到滚动条接近底部的时候请求新的数据)
使用节流函数,获取滚动条到底部的距离,如果到达阈值,就调用回调
当组件销毁的时候,移除监听,避免浪费性能
# 代码
import type { DirectiveBinding } from 'vue'
/** 传递的值为一个对象
*{
* container: '.content-wp', // CSS Selector 滚动的容器
* callback: ()=>{}, // 回调函数,可以请求数据
* scrollBottom: number // 距离底部请求数据的阈值
*}
*/
let scrollFn: any
export default {
mounted(el: HTMLElement, binding: DirectiveBinding) {
const dom = document.querySelector(binding.value.container)
// 监听容器
dom.addEventListener(
'scroll',
(scrollFn = useThrottleFn(() => {
// 节流函数
//vue中获取滚动条到底部的距离
const scrollBottom =
el.getBoundingClientRect().bottom - window.innerHeight
// 设置阈值,当小于阈值时,调用回调
if (scrollBottom < (binding.value.scrollBottom || 1400)) {
binding.value.callback()
}
}, 300))
)
},
beforeUnmount(el: HTMLElement, binding: DirectiveBinding) {
const dom = document.querySelector(binding.value.container)
dom.removeEventListener('scroll', scrollFn)
}
}
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
# 积累知识点
- Element 类型和 HTMLElement 类型不一样,Element 范围大得多 Element 是一个通用性非常强的基类,所有 Document 对象下的对象都继承自它。这个接口描述了所有相同种类的元素所普遍具有的方法和属性。一些接口继承自 Element 并且增加了一些额外功能的接口描述了具体的行为。例如, HTMLElement 接口是所有 HTML 元素的基本接口,而 SVGElement 接口是所有 SVG 元素的基础。大多数功能是在这个类的更深层级(hierarchy)的接口中被进一步制定的。
在 ts 中,通过 document.getElementById()返回 HTMLElement 类型,而 document.querySelect()返回 Element 类型。
- 节流函数不要自己写,使用最佳实践,避免一些错误,或者性能问题 useThrottleFn 来自 vueuse 工具,在官网 (opens new window)上可以看到使用说明,也可以配置自动导入 (opens new window)。
上次更新: 2023/12/16, 09:22:46