DEV Community

Ajmal Hasan
Ajmal Hasan

Posted on

Pagination and Pull to refresh in Flatlist with custom hooks

1) The usePagination hook handles infinite scrolling.
It uses useState to keep track of the current page.
handleEndReached is a callback that checks if there are more pages, triggers the fetch function, and increments the page.

usePagination.jsx

import { useCallback, useState } from 'react';

const usePagination = ({ fetchFunction, totalPages, initialPage }) => {
  const [currentPage, setCurrentPage] = useState(initialPage);

  const handleEndReached = useCallback(() => {
    if (currentPage < totalPages) {
      fetchFunction(currentPage);
      setCurrentPage((prevPage) => prevPage + 1);
    }
  }, [currentPage, fetchFunction, totalPages]);

  return { currentPage, handleEndReached };
};

export default usePagination;
Enter fullscreen mode Exit fullscreen mode

2) The usePullToRefresh hook manages the pull-to-refresh functionality.
It uses the useState hook to track the refreshing state.
onRefreshHandler is a callback function that triggers the refresh, sets the refreshing state, calls the provided function, and then resets the state.

usePullToRefresh.jsx

import { useCallback, useState } from 'react';

const usePullToRefresh = ({ onRefreshFunction }) => {
  const [refreshing, setRefreshing] = useState(false);

  const onRefreshHandler = useCallback(async () => {
    try {
      setRefreshing(true);
      await onRefreshFunction();
    } finally {
      setRefreshing(false);
    }
  }, [onRefreshFunction]);

  return { refreshing, onRefreshHandler };
};

export default usePullToRefresh;
Enter fullscreen mode Exit fullscreen mode

3) USAGE:

App.jsx

import { ActivityIndicator, FlatList, RefreshControl, StyleSheet, Text, View } from 'react-native';
import React from 'react';
import { useDispatch } from 'react-redux';
import usePullToRefresh from './hooks/usePullToRefresh';
import usePagination from './hooks/usePagination';

const getMovies = () => null;
const addMovies = () => null;

const INITIAL_PAGE = 0;
const App = () => {
  const dispatch = useDispatch();
  const isLoading = true;
  const { refreshing, onRefreshHandler } = usePullToRefresh({
    onRefreshFunction() {
      dispatch(getMovies(INITIAL_PAGE));
    },
  });

  const { currentPage, handleEndReached } = usePagination({
    fetchFunction: () => {
      dispatch(addMovies(currentPage + 1));
    },
    totalPages: 10,
    initialPage: INITIAL_PAGE,
  });

  return (
    // The FlatList component integrates both hooks for a seamless experience.
    <FlatList
      data={[]}
      keyExtractor={(item) => item.id.toString()}
      renderItem={({ item }) => <View key={item} />}
      refreshControl={<RefreshControl refreshing={refreshing} onRefresh={onRefreshHandler} />}
      onEndReached={handleEndReached}
      onEndReachedThreshold={0.1}
      numColumns={2}
      ListFooterComponent={isLoading ? <ActivityIndicator size="large" /> : null}
    />
  );
};

export default App;
Enter fullscreen mode Exit fullscreen mode

Top comments (0)