import React, { useEffect, useMemo } from 'react' import PaginationPrevious from './pagination-previous' import PaginationNext from './pagination-next' import PaginationPages from './pagination-pages' import { PaginationContext, PaginationConfig, PaginationUpdateType } from './pagination-context' import useCurrentState from '../utils/use-current-state' import { pickChild } from '../utils/collections' import { NormalSizes } from '../utils/prop-types' interface Props { size?: NormalSizes page?: number initialPage?: number count?: number limit?: number onChange?: (val: number) => void } const defaultProps = { size: 'medium' as NormalSizes, initialPage: 1, count: 1, limit: 7 } type NativeAttrs = Omit, keyof Props> export type PaginationProps = Props & typeof defaultProps & NativeAttrs type PaginationSize = { font: string width: string } const getPaginationSizes = (size: NormalSizes) => { const sizes: { [key in NormalSizes]: PaginationSize } = { mini: { font: '.75rem', width: '1.25rem' }, small: { font: '.75rem', width: '1.65rem' }, medium: { font: '.875rem', width: '2rem' }, large: { font: '1rem', width: '2.4rem' } } return sizes[size] } const Pagination: React.FC> = ({ page: customPage, initialPage, count, limit, size, children, onChange }) => { const [page, setPage, pageRef] = useCurrentState(initialPage) const [, prevChildren] = pickChild(children, PaginationPrevious) const [, nextChildren] = pickChild(children, PaginationNext) const [prevItem, nextItem] = useMemo(() => { const hasChildren = (c: any) => React.Children.count(c) > 0 const prevDefault = prev const nextDefault = next return [ hasChildren(prevChildren) ? prevChildren : prevDefault, hasChildren(nextChildren) ? nextChildren : nextDefault ] }, [prevChildren, nextChildren]) const { font, width } = useMemo(() => getPaginationSizes(size), [size]) const update = (type: PaginationUpdateType) => { if (type === 'prev' && pageRef.current > 1) { setPage((last) => last - 1) } if (type === 'next' && pageRef.current < count) { setPage((last) => last + 1) } } const values = useMemo( () => ({ isFirst: page <= 1, isLast: page >= count, update }), [page] ) useEffect(() => { onChange && onChange(page) }, [page]) useEffect(() => { if (customPage !== undefined) { setPage(customPage) } }, [customPage]) return ( ) } type MemoPaginationComponent

= React.NamedExoticComponent

& { Previous: typeof PaginationPrevious Next: typeof PaginationNext } type ComponentProps = Partial & Omit & NativeAttrs Pagination.defaultProps = defaultProps export default React.memo(Pagination) as MemoPaginationComponent