Nextjs + ChakraでPaginationのデザインを整える

作成:2022/10/09
更新:2022/10/22

useRouterを使い現在ページを目立たせる


こんなの作る。


まずmicroCMSの公式チュートリアルをこなす

Next.js(SSG)でページネーションを実装してみよう
https://blog.microcms.io/next-pagination/

チュートリアル終わった状態だとURLがblog/page/[id].jsになっているのidを取得してやれば、今いるページが分かる。

useRouterでパスからidを取得する部分のコード。

const router = useRouter();
const path = router.asPath;
const id = path.replace(/.*\//, "");



"blog/page/[id].js"のidがmapのnumberと一致する場合に目立つようにする。
トップページでもページネーション使いまわしたいため、"/"の場合もid===1と同じ扱いにする。
useStateとuseEffectを使う。

const [currentPage, setCurrentPage] = useState("1");
const router = useRouter();

useEffect(() => {
  const path = router.asPath;
  const id = path.replace(/.*\//, "");
  path === "/" ? setCurrentPage("1") : setCurrentPage(id);
}, [router]);



全体

import { useRouter } from "next/router";
import NextLink from "next/link";
import { Center, HStack, Button, Box } from "@chakra-ui/react";
import { useEffect, useState } from "react";


type Props = {
  totalCount: number;
};


export const Pagination = ({ totalCount }: Props) => {
  const [currentPage, setCurrentPage] = useState("1");
  const router = useRouter();
  const PER_PAGE = 5;


  useEffect(() => {
    const path = router.asPath;
    const id = path.replace(/.*\//, "");
    path === "/" ? setCurrentPage("1") : setCurrentPage(id);
  }, [router]);


  const range = (start: number, end: number) =>
    [...Array(end - start + 1)].map((_, i) => start + i);


  return (
    <Center mt={10} mb={10}>
      <HStack>
        {range(1, Math.ceil(totalCount / PER_PAGE)).map((number, index) => (
          <Box key={index}>
            {currentPage === String(number) ? (
              <NextLink href={`/blog/page/${number}`} key={number}>
                {/**現在ページ */}
                <a>
                  <Button colorScheme={"orange"}>{number}</Button>
                </a>
              </NextLink>
            ) : (
              <NextLink href={`/blog/page/${number}`} key={number}>
                {/** not 現在ページ */}
                <a>
                  <Button colorScheme={"orange"} variant="outline">
                    {number}
                  </Button>
                </a>
              </NextLink>
            )}
          </Box>
        ))}
      </HStack>
    </Center>
  );
};