[英]Stop Function being called multiple times when scrolling
我在我的 react/redux 应用程序中使用无限滚动,当用户接近页面底部时,将加载更多内容。
但是如果用户滚动太快,并且在从服务器获取内容时一直滚动,则负责滚动效果的 function 会触发多次,并且 API 会获得相同的内容,这会导致错误,因为具有相同 Keys 的相同项目将被加载。
const [isFetching, setIsFetching] = useState(false);
// Fire Upon Reaching the Bottom of the Page
const handleScroll = () => {
if (
window.innerHeight +
Math.max(
window.pageYOffset,
document.documentElement.scrollTop,
document.body.scrollTop
) >
document.documentElement.offsetHeight - 100
) {
setIsFetching(true);
} else {
return;
}
};
// Debounce the Scroll Event Function and Cancel it When Called
const debounceHandleScroll = debounce(handleScroll, 500);
useEffect(() => {
window.addEventListener("scroll", debounceHandleScroll);
return () => window.removeEventListener("scroll", debounceHandleScroll);
}, [debounceHandleScroll]);
debounceHandleScroll.cancel();
// Get More Posts
const loadMoreItems = useCallback(() => {
dispatch(getMorePosts(moreApiAddress));
setIsFetching(false);
}, [dispatch, moreApiAddress]);
useEffect(() => {
if (!isFetching) return;
loadMoreItems();
}, [isFetching, loadMoreItems]);
当获取新内容和/或用户滚动速度过快时,有什么办法可以阻止 function 多次触发?
您的handleScroll
function 更新 state,这会导致组件重新渲染。
这意味着您将在每次渲染时拥有新的handleScroll
实例(和 debounceHandleScroll)。
由于您在debounceHandleScroll
依赖数组中有useEffect
,并且它在每次渲染时都会发生变化 - 您正在获得一种“无限循环”。
尝试使用useCallback
钩子来记忆函数或重写组件并尝试将这些函数移到组件之外。
我的意思是这样的:
const handleScroll = useCallback(() => {
if (
window.innerHeight +
Math.max(
window.pageYOffset,
document.documentElement.scrollTop,
document.body.scrollTop
) >
document.documentElement.offsetHeight - 100
) {
setIsFetching(true);
} else {
return;
}
}, []);
// Debounce the Scroll Event Function and Cancel it When Called
const debounceHandleScroll = useCallback(() => debounce(handleScroll, 500), [handleScroll]);
阅读有关useCallback
的更多信息: https://reactjs.org/docs/hooks-reference.html#usecallback
声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.