diff --git a/.changeset/twelve-dolphins-add.md b/.changeset/twelve-dolphins-add.md new file mode 100644 index 000000000..8cf4e9357 --- /dev/null +++ b/.changeset/twelve-dolphins-add.md @@ -0,0 +1,5 @@ +--- +"@mochi-ui/pagination": minor +--- + +Add custom page input diff --git a/apps/mochi-web/components/Profile/TransactionSection.tsx b/apps/mochi-web/components/Profile/TransactionSection.tsx index 1f50b1dc8..ad12414a9 100644 --- a/apps/mochi-web/components/Profile/TransactionSection.tsx +++ b/apps/mochi-web/components/Profile/TransactionSection.tsx @@ -95,6 +95,7 @@ export const TransactionOverviewSection = () => { onItemPerPageChange: setSize, onPageChange: setPage, className: 'px-4', + allowCustomPage: true, }, }} onRow={(tx) => { diff --git a/apps/mochi-web/components/explore/index/sections/TransactionSection.tsx b/apps/mochi-web/components/explore/index/sections/TransactionSection.tsx index accef9fe8..f4bc1aaef 100644 --- a/apps/mochi-web/components/explore/index/sections/TransactionSection.tsx +++ b/apps/mochi-web/components/explore/index/sections/TransactionSection.tsx @@ -61,6 +61,7 @@ export const TransactionSection = () => { totalItems: total, onItemPerPageChange: setSize, onPageChange: setPage, + allowCustomPage: true, }, }} className="px-6" diff --git a/packages/components/pagination/package.json b/packages/components/pagination/package.json index d5b36fe95..1edf74e31 100644 --- a/packages/components/pagination/package.json +++ b/packages/components/pagination/package.json @@ -35,7 +35,9 @@ "dependencies": { "@mochi-ui/icons": "workspace:*", "@mochi-ui/select": "workspace:*", - "@mochi-ui/theme": "workspace:*" + "@mochi-ui/theme": "workspace:*", + "@mochi-ui/separator": "workspace:*", + "@mochi-ui/input": "workspace:*" }, "clean-package": "../../../clean-package.config.json" } diff --git a/packages/components/pagination/src/pagination.tsx b/packages/components/pagination/src/pagination.tsx index 78cbb34af..f0214f0f4 100644 --- a/packages/components/pagination/src/pagination.tsx +++ b/packages/components/pagination/src/pagination.tsx @@ -9,6 +9,8 @@ import { SelectTrigger, SelectValue, } from '@mochi-ui/select' +import { Separator } from '@mochi-ui/separator' +import { TextFieldInput } from '@mochi-ui/input' import { formatNumber } from './utils' const { @@ -34,6 +36,7 @@ interface PaginationProps { recordName?: string hideOnSinglePage?: boolean allowCustomItemsPerPage?: boolean + allowCustomPage?: boolean } function PageButton({ @@ -70,14 +73,17 @@ export default function Pagination({ recordName = 'members', hideOnSinglePage = false, allowCustomItemsPerPage = true, + allowCustomPage = false, }: PaginationProps) { const [currentPage, setCurrentPage] = useState(page) const [currentItemPerPage, setCurrentItemPerPage] = useState(initItemsPerPage) + const [customPage, setCustomPage] = useState('') useEffect(() => { if (onPageChange) { onPageChange(currentPage) } + setCustomPage('') }, [currentPage, onPageChange]) useEffect(() => { @@ -95,6 +101,17 @@ export default function Pagination({ const totalPages = Math.ceil(totalItems / currentItemPerPage) || initTotalPage + const onCustomPageChange = (value: string) => { + if (!value) return + const page = Number(value) + if (page >= 1 && page <= totalPages && Number.isInteger(page)) { + setCurrentPage(page) + } else if (page > totalPages && Number.isInteger(page)) { + setCurrentPage(totalPages) + } + setCustomPage('') + } + const renderPagination = () => { const pages = [] @@ -281,6 +298,24 @@ export default function Pagination({
{recordName} of {formatNumber(totalItems)}
+ {allowCustomPage && ( +
+ + Go to + setCustomPage(e.target.value)} + onBlur={(e) => onCustomPageChange(e.target.value)} + onKeyDown={(e) => { + if (e.key === 'Enter') { + onCustomPageChange(e.currentTarget.value) + } + }} + /> + Page +
+ )} )} diff --git a/packages/components/pagination/stories/pagination.stories.tsx b/packages/components/pagination/stories/pagination.stories.tsx index 61d3080d1..b3d2b3410 100644 --- a/packages/components/pagination/stories/pagination.stories.tsx +++ b/packages/components/pagination/stories/pagination.stories.tsx @@ -61,3 +61,27 @@ export const Default: Story = { ) }, } + +export const AllowCustomPage: Story = { + render: () => { + // eslint-disable-next-line react-hooks/rules-of-hooks -- we're in a component + const [currentPage, setCurrentPage] = useState(1) + // eslint-disable-next-line react-hooks/rules-of-hooks -- we're in a component + const [itemPerPage, setItemPerPage] = useState(15) + + return ( +
+ + +
+ ) + }, +} diff --git a/packages/theme/src/components/pagination.ts b/packages/theme/src/components/pagination.ts index 31712950b..42d645596 100644 --- a/packages/theme/src/components/pagination.ts +++ b/packages/theme/src/components/pagination.ts @@ -26,12 +26,18 @@ const paginationEllipsisButtonClsx = ({ const paginationWrapperClsx = ({ className = '', }: { className?: string } = {}) => - clsx('flex items-center justify-between w-full sm:space-x-6', className) + clsx( + 'flex items-center justify-between w-full sm:gap-x-6 sm:gap-y-4 flex-wrap', + className, + ) const paginationAmountPerPageWrapperClsx = ({ className = '', }: { className?: string } = {}) => - clsx('hidden sm:inline-flex justify-start items-center space-x-2', className) + clsx( + 'hidden sm:inline-flex justify-start items-center gap-x-2 gap-y-4 flex-wrap', + className, + ) const paginationPageNavigateButtonGroupClsx = ({ className = '', @@ -42,7 +48,7 @@ const paginationNavigationClsx = ({ className = '', }: { className?: string } = {}) => clsx( - 'flex-1 flex justify-center sm:justify-end items-center space-x-2', + 'flex items-center justify-center space-x-2 flex-1 sm:flex-none', className, ) diff --git a/pnpm-lock.yaml b/pnpm-lock.yaml index 51d28e230..8877320b6 100644 --- a/pnpm-lock.yaml +++ b/pnpm-lock.yaml @@ -110,7 +110,7 @@ importers: version: 7.2.0(@swc/core@1.3.96)(ts-node@10.9.1)(typescript@5.2.2) turbo: specifier: latest - version: 1.12.2 + version: 1.10.15 typescript: specifier: ^5.2.2 version: 5.2.2 @@ -1340,9 +1340,15 @@ importers: '@mochi-ui/icons': specifier: workspace:* version: link:../../icons + '@mochi-ui/input': + specifier: workspace:* + version: link:../input '@mochi-ui/select': specifier: workspace:* version: link:../select + '@mochi-ui/separator': + specifier: workspace:* + version: link:../separator '@mochi-ui/theme': specifier: workspace:* version: link:../../theme @@ -25325,64 +25331,64 @@ packages: safe-buffer: 5.2.1 dev: false - /turbo-darwin-64@1.12.2: - resolution: {integrity: sha512-Aq/ePQ5KNx6XGwlZWTVTqpQYfysm1vkwkI6kAYgrX5DjMWn+tUXrSgNx4YNte0F+V4DQ7PtuWX+jRG0h0ZNg0A==} + /turbo-darwin-64@1.10.15: + resolution: {integrity: sha512-Sik5uogjkRTe1XVP9TC2GryEMOJCaKE2pM/O9uLn4koQDnWKGcLQv+mDU+H+9DXvKLnJnKCD18OVRkwK5tdpoA==} cpu: [x64] os: [darwin] requiresBuild: true dev: true optional: true - /turbo-darwin-arm64@1.12.2: - resolution: {integrity: sha512-wTr+dqkwJo/eXE+4SPTSeNBKyyfQJhI6I9sKVlCSBmtaNEqoGNgdVzgMUdqrg9AIFzLIiKO+zhfskNaSWpVFow==} + /turbo-darwin-arm64@1.10.15: + resolution: {integrity: sha512-xwqyFDYUcl2xwXyGPmHkmgnNm4Cy0oNzMpMOBGRr5x64SErS7QQLR4VHb0ubiR+VAb8M+ECPklU6vD1Gm+wekg==} cpu: [arm64] os: [darwin] requiresBuild: true dev: true optional: true - /turbo-linux-64@1.12.2: - resolution: {integrity: sha512-BggBKrLojGarDaa2zBo+kUR3fmjpd6bLA8Unm3Aa2oJw0UvEi3Brd+w9lNsPZHXXQYBUzNUY2gCdxf3RteWb0g==} + /turbo-linux-64@1.10.15: + resolution: {integrity: sha512-dM07SiO3RMAJ09Z+uB2LNUSkPp3I1IMF8goH5eLj+d8Kkwoxd/+qbUZOj9RvInyxU/IhlnO9w3PGd3Hp14m/nA==} cpu: [x64] os: [linux] requiresBuild: true dev: true optional: true - /turbo-linux-arm64@1.12.2: - resolution: {integrity: sha512-v/apSRvVuwYjq1D9MJFsHv2EpGd1S4VoSdZvVfW6FaM06L8CFZa92urNR1svdGYN28YVKwK9Ikc9qudC6t/d5A==} + /turbo-linux-arm64@1.10.15: + resolution: {integrity: sha512-MkzKLkKYKyrz4lwfjNXH8aTny5+Hmiu4SFBZbx+5C0vOlyp6fV5jZANDBvLXWiDDL4DSEAuCEK/2cmN6FVH1ow==} cpu: [arm64] os: [linux] requiresBuild: true dev: true optional: true - /turbo-windows-64@1.12.2: - resolution: {integrity: sha512-3uDdwXcRGkgopYFdPDpxQiuQjfQ12Fxq0fhj+iGymav0eWA4W4wzYwSdlUp6rT22qOBIzaEsrIspRwx1DsMkNg==} + /turbo-windows-64@1.10.15: + resolution: {integrity: sha512-3TdVU+WEH9ThvQGwV3ieX/XHebtYNHv9HARHauPwmVj3kakoALkpGxLclkHFBLdLKkqDvmHmXtcsfs6cXXRHJg==} cpu: [x64] os: [win32] requiresBuild: true dev: true optional: true - /turbo-windows-arm64@1.12.2: - resolution: {integrity: sha512-zNIHnwtQfJSjFi7movwhPQh2rfrcKZ7Xv609EN1yX0gEp9GxooCUi2yNnBQ8wTqFjioA2M5hZtGJQ0RrKaEm/Q==} + /turbo-windows-arm64@1.10.15: + resolution: {integrity: sha512-l+7UOBCbfadvPMYsX08hyLD+UIoAkg6ojfH+E8aud3gcA1padpjCJTh9gMpm3QdMbKwZteT5uUM+wyi6Rbbyww==} cpu: [arm64] os: [win32] requiresBuild: true dev: true optional: true - /turbo@1.12.2: - resolution: {integrity: sha512-BcoQjBZ+LJCMdjzWhzQflOinUjek28rWXj07aaaAQ8T3Ehs0JFSjIsXOm4qIbo52G4xk3gFVcUtJhh/QRADl7g==} + /turbo@1.10.15: + resolution: {integrity: sha512-mKKkqsuDAQy1wCCIjCdG+jOCwUflhckDMSRoeBPcIL/CnCl7c5yRDFe7SyaXloUUkt4tUR0rvNIhVCcT7YeQpg==} hasBin: true optionalDependencies: - turbo-darwin-64: 1.12.2 - turbo-darwin-arm64: 1.12.2 - turbo-linux-64: 1.12.2 - turbo-linux-arm64: 1.12.2 - turbo-windows-64: 1.12.2 - turbo-windows-arm64: 1.12.2 + turbo-darwin-64: 1.10.15 + turbo-darwin-arm64: 1.10.15 + turbo-linux-64: 1.10.15 + turbo-linux-arm64: 1.10.15 + turbo-windows-64: 1.10.15 + turbo-windows-arm64: 1.10.15 dev: true /tweetnacl@1.0.3: