当用户不断滚动时,停止多次调用函数

问题描述 投票:0回答:1

我有这个应用程序,当用户到达屏幕底部附近时,将从无限滚动方法中的 API 获取新内容。

但是,如果该用户在获取新内容时滚动得太快或只是不断滚动到底部,则该函数会多次触发,这会导致应用程序两次获取相同的内容,从而收到有关具有相同键的反应子项的错误。

这是检测用户何时接近底部的功能:

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]);

当用户在获取内容时滚动太快时,如何阻止该函数被多次调用?

javascript html reactjs redux react-redux
1个回答
0
投票

react-infinite-scrollable
是一个轻量级且易于使用的 React 组件,可在您的 Web 应用程序中实现无限滚动功能。使用此包,您可以轻松地实现长列表、网格或任何其他需要在用户滚动时动态加载的内容的无限滚动。

安装

要开始使用react-infinite-scrollable,只需通过 npm 安装软件包即可:

$ npm install react-infinite-scrollable --save

使用方法

import React from "react";
import InfiniteScrollable from "react-infinite-scrollable";

function YourComponent() {
  const [page, setPage] = useState(1);
  const [hasMore, setHasMore] = useState(true);
  const [loading, setLoadig] = useState(true);
  const [article, setArticle] = useState([]);

  const fetchPost = () => {
    setLoadig(true);
    fetch(`https://jsonplaceholder.typicode.com/posts?_page=${page}&_limit=10`)
      .then((data) => {
        setData((old) => [...old, ...data]);
      })
      .catch((error) => {
        setHasMore(false);
        console.log({ error });
      })
      .finally(() => {
        setLoadig(false);
      });
  };

  useEffect(() => {
    fetchPost();
  }, [page]);

  const loadMore = () => {
    setPage((pre) => pre + 1);
  };
  return (
    <InfiniteScroll
      onEnd={loadMore}
      loading={loading}
      hasMore={hasMore}
      loadingComponent={<center>my custom loading component</center>}
      noMoreComponent={<center>my custom No more Post</center>}
      offset={300}
    >
      {articles.map((article) => (
        <div key={article.id} style={{ marginBottom: 16 }}>
          <h2>{article.title}</h2>
          <p>{article.body}</p>
        </div> // your component here
      ))}
    </InfiniteScroll>
  );
}

参数表

姓名 描述 类型 默认
hasMore
指示是否还有更多项目需要加载。
boolean
true
loading
指示组件当前是否正在加载更多项目。
boolean
false
loadingComponent
加载时显示的可选加载组件。
React.ReactNode
<center>loading..</center>
noMoreComponent
可选不再显示数据组件。
React.ReactNode
<center>no more</center>
onEnd
加载更多项目的功能。
Function
-
offset
触发加载更多项目的偏移值。
Number
0
© www.soinside.com 2019 - 2024. All rights reserved.