前因
事实上这一功能一开始并不在需求中有描述,初期和后端进行联调时,产品看着页面的数据忽然提出了这个问题,于是实现这个功能的漫长过程就开始了。
构思及问题
关于上拉加载
基于 h5 这种方式实现的上拉加载并不能很好的完美达到要求,只能说是有这一功能罢了。(也可能是我不会。)
初步的构思是监听页面的滚动距离,即获取页面的总高度、可视区的高度以及滚动的高度,这样当:滚动的高度 + 可视区高度 + h >= 总高度(h为一个预设的固定值,确保可以让等号左边一定大于右边)即视为可以去触发 fetch
请求,加载下一页的数据。
let clientHeight = dom.clientHeight; // 可视区高度
let scrollHeight = dom.scrollHeight; // 总高度
let scrollTop = dom.scrollTop || window.pageYOffset || document.body.scrollTop; // 滚动高度
// 滚动高度 + 可视区高度 + 100 >= 总高度 即视为到底
if (scrollTop + clientHeight + 100 >= scrollHeight) {
// do somethings
}
然后我们在 useEffect()
中监听页面滚动事件,相应的我们要根据数据的变动去触发对应的页面变化,所以第二个参数填写了3条。
useEffect(() => {
document.addEventListener('scroll', debounceFunc);
return () => {
document.removeEventListener('scroll', debounceFunc);
};
}, [concatActive, concatCarData, noConcatCarData]);
但这也产生了一个问题,就是每次页面执行对应的 fetch
请求都会执行3次,我们又不能再去引入另外的 state 去存储对应的 true or false 用以管理所执行的 fetch
方法,因为对应的 state 都需要被添加到 useEffect()
参数中,这样只会导致状态更加混乱。
这里不得不引入了额外的全局变量对对应页面的 fetch
请求进行管理。
let loading1 = false
let loading2 = false
...
if (tmp1 < pageCount1 && !loading1 && concatActive) {
setL1(true);
tmp1 += 1;
loading1 = !!1;
dropDownFetch(tmp1); // fetch 方法
}
...
const dropDownFetch = () => {
fetch().then(data => {
if (data.respCode == 0) {
...
loading1 = false // 请求到下一页数据,重新设定为 false
}
})
}
本来到这里,上拉加载其实可以告一段落了,这时产品又要求在页面到底部的时候添加上对应的 loading 标志,因为是临时的要求,所以并没有对应的设计,只能自行手绘了一个。
<style>
ul {
display: flex;
}
ul li {
list-style: none;
background: #ED4C67;
border-radius: 50%;
width: 8px;
height: 8px;
margin: 6px;
animation: animate .7s infinite linear alternate;
}
@keyframes animate {
0% {
transform: scale(0);
}
100% {
transform: scale(1);
}
}
ul li:nth-child(2) {
animation-delay: -.15s;
}
ul li:nth-child(3) {
animation-delay: -.3s;
}
</style>
<div className="xiansuo-loading">
<ul>
<li></li>
<li></li>
<li></li>
</ul>
or
"·我是有底线的·"
</div>
这里需要在页面初次进入时显示 ul 对应的 loading 效果,在页面上拉加载时没有后续数据的时候显示相应的文字,于是再一次引入了另外的全局变量,这里对变量进行了如下判断,如果当前页码不是最后一页则一直展示 loading 。
if (pageIndex < pageCount) {
setL1(true)
} else {
setL1(false)
}
存在的问题
目前页面只能说是可以使用,但是现有的逻辑比较混乱,方法没有进行抽离,且页面存在大量的全局变量,同时也设定了多个功能相对重复的 state 用以管理,后续待抽离相应的方法,理顺页面逻辑,同时考虑使用更好的方式去管理状态以及多余的全局变量。
结语
实际上这两天处理问题时候远没有我现在写的这么清晰,一方面需要考虑开发平台:PC端正常显示、Android端正常显示、IOS端无法显示,另一方面因为一直处于焦急的状态,所以代码写的十分混乱,同样由于对 hooks 以及移动端 的不够熟悉,coding过程中还是出现了很多意料之外的问题。
后续继续努力,调整心态,好好开发。
版权属于:ajycc20
本文链接:https://ajycc20.top/archives/23.html
所有原创文章采用知识共享署名-非商业性使用 4.0 国际许可协议进行许可。 您可以自由的转载和修改,但请务必注明文章来源并且不可用于商业目的。