【react】滚动加载,请求下一页数据,加载时显示icon图标

1.定义监听对象

useInViewport:观察元素是否在可见区域,以及元素可见比例
const ref = useRef<HTMLDivElement>(null); 
const [inViewport] = useInViewport(ref);
const refScroll = useRef<HTMLDivElement>(null); 
const [requestingTree, setRequestingTree] = useState(false); //请求状态
const [treeData, setTreeData] = useState({} as { data: guideTree[]; recordsTotal: number }); //数据
const [defaultParams] = useState({
    length: 50,
    searchMap: { status: '1' },
    start: 0,
  });
  1. 接口调用
// getTree 接口地址
const { runAsync: runGuideTree, loading: treeLoading } = useRequest(getTree, {
    manual: true,
    onSuccess: (result: any, params) => {
      let newData = result?.data;
      if (params[0].start !== 0) {
        newData = treeData.data.concat(result.data);
      }
      setTreeData({ ...result, data: newData });
      setRequestingTree(false);
    },
    defaultParams: [defaultParams],
  });
  1. 根据inViewport 判断是否请求下一个数据
useUpdateEffect(() => {
    if (!requestingTree && inViewport && (treeData!.data || []).length < +treeData.recordsTotal) {
      setRequestingTree(true);
      const obj = Object.assign(defaultParams, {
        length: 50,
        searchMap: {
          status: '1' 
        },
        start: treeData.data ? treeData.data.length + 1 : 0,
      });
      runGuideTree(obj);
    }
  }, [inViewport]);
  1. 页面渲染
<Spin spinning={treeLoading}>
    <div className="tree">
      {treeData && treeData.data && treeData.data.length === 0 ? (
        <div className="tree-right-empty">
          <FrownOutlined />
          <div>暂无数据</div>
        </div>
      ) : (
        <Scrollbar ref={refScroll} style={{ zIndex: 999 }}>
          {treeData &&
            treeData.data &&
            treeData.data.map((value, index) => (
              <Itemdiv
                ref={ref}
                index={index}
                className="tree-item border-need"
                active={currentShop.id == value.id}
                key={Math.random()}
                onClick={async () => {
                  handlerCurrentSelect(value, {});
                  setCurrentShop(value);
                }}
              >
                <TableOverflowText style={{ overflow: 'auto' }} content={value.label || ''} />
              </Itemdiv>
            ))}
          {(treeData!.data || []).length < +treeData.recordsTotal && inViewport && (
            <div className="spins" style={{ zIndex: 1000 }}>
              <Spin spinning={requestingTree} />
            </div>
          )}
          {(treeData!.data || []).length + 1 === +treeData.recordsTotal && (
            <div className="footers">已经到底部啦~</div>
          )}
        </Scrollbar>
      )}
    </div>
</Spin>

你可能感兴趣的:(react.js,前端,javascript)