{"version":3,"file":"use-pagination.mjs","names":[],"sources":["../../src/use-pagination/use-pagination.ts"],"sourcesContent":["import { useCallback, useMemo } from 'react';\nimport { useUncontrolled } from '../use-uncontrolled/use-uncontrolled';\n\nfunction range(start: number, end: number) {\n  const length = end - start + 1;\n  return Array.from({ length }, (_, index) => index + start);\n}\n\nexport const DOTS = 'dots';\n\nexport interface UsePaginationOptions {\n  /** Page selected on initial render, defaults to 1 or startValue if provided */\n  initialPage?: number;\n\n  /** Controlled active page number */\n  page?: number;\n\n  /** Total amount of pages */\n  total: number;\n\n  /** Siblings amount on left/right side of selected page, defaults to 1 */\n  siblings?: number;\n\n  /** Amount of elements visible on left/right edges, defaults to 1  */\n  boundaries?: number;\n\n  /** Callback fired after change of each page */\n  onChange?: (page: number) => void;\n\n  /** Starting page number, defaults to 1 */\n  startValue?: number;\n}\n\nexport interface UsePaginationReturnValue {\n  /** Array of page numbers and dots */\n  range: (number | 'dots')[];\n\n  /** Active page number */\n  active: number;\n\n  /** Function to set active page */\n  setPage: (page: number) => void;\n\n  /** Function to go to next page */\n  next: () => void;\n\n  /** Function to go to previous page */\n  previous: () => void;\n\n  /** Function to go to first page */\n  first: () => void;\n\n  /** Function to go to last page */\n  last: () => void;\n}\n\nexport function usePagination({\n  total,\n  siblings = 1,\n  boundaries = 1,\n  page,\n  initialPage,\n  onChange,\n  startValue = 1,\n}: UsePaginationOptions): UsePaginationReturnValue {\n  const _startValue = Math.max(Math.trunc(startValue), 1);\n  const _endValue = Math.max(Math.trunc(total), _startValue);\n  const _total = _endValue - _startValue + 1;\n  const _initialPage = initialPage ?? _startValue;\n\n  const [activePage, setActivePage] = useUncontrolled({\n    value: page,\n    onChange,\n    defaultValue: _initialPage,\n    finalValue: _initialPage,\n  });\n\n  const setPage = useCallback(\n    (pageNumber: number) => {\n      if (pageNumber < _startValue) {\n        setActivePage(_startValue);\n      } else if (pageNumber > _endValue) {\n        setActivePage(_endValue);\n      } else {\n        setActivePage(pageNumber);\n      }\n    },\n    [_startValue, _endValue, setActivePage]\n  );\n\n  const next = useCallback(() => setPage(activePage + 1), [activePage, setPage]);\n  const previous = useCallback(() => setPage(activePage - 1), [activePage, setPage]);\n  const first = useCallback(() => setPage(_startValue), [setPage, _startValue]);\n  const last = useCallback(() => setPage(_endValue), [_endValue, setPage]);\n\n  const paginationRange = useMemo((): (number | 'dots')[] => {\n    const totalPageNumbers = siblings * 2 + 3 + boundaries * 2;\n    if (totalPageNumbers >= _total) {\n      return range(_startValue, _endValue);\n    }\n\n    const leftSiblingIndex = Math.max(activePage - siblings, _startValue + boundaries - 1);\n    const rightSiblingIndex = Math.min(activePage + siblings, _endValue - boundaries);\n\n    const shouldShowLeftDots = leftSiblingIndex > _startValue + boundaries + 1;\n    const shouldShowRightDots = rightSiblingIndex < _endValue - boundaries;\n\n    if (!shouldShowLeftDots && shouldShowRightDots) {\n      const leftItemCount = siblings * 2 + boundaries + 2;\n      return [\n        ...range(_startValue, _startValue + leftItemCount - 1),\n        DOTS,\n        ...range(_endValue - (boundaries - 1), _endValue),\n      ];\n    }\n\n    if (shouldShowLeftDots && !shouldShowRightDots) {\n      const rightItemCount = boundaries + 1 + 2 * siblings;\n      return [\n        ...range(_startValue, _startValue + boundaries - 1),\n        DOTS,\n        ...range(_endValue - rightItemCount, _endValue),\n      ];\n    }\n\n    return [\n      ...range(_startValue, _startValue + boundaries - 1),\n      DOTS,\n      ...range(leftSiblingIndex, rightSiblingIndex),\n      DOTS,\n      ...range(_endValue - boundaries + 1, _endValue),\n    ];\n  }, [_total, siblings, activePage, _startValue, _endValue, boundaries]);\n\n  return {\n    range: paginationRange,\n    active: activePage,\n    setPage,\n    next,\n    previous,\n    first,\n    last,\n  };\n}\n\nexport namespace usePagination {\n  export type Options = UsePaginationOptions;\n  export type ReturnValue = UsePaginationReturnValue;\n}\n"],"mappings":";;;;AAGA,SAAS,MAAM,OAAe,KAAa;CACzC,MAAM,SAAS,MAAM,QAAQ;AAC7B,QAAO,MAAM,KAAK,EAAE,QAAQ,GAAG,GAAG,UAAU,QAAQ,MAAM;;AAG5D,MAAa,OAAO;AAgDpB,SAAgB,cAAc,EAC5B,OACA,WAAW,GACX,aAAa,GACb,MACA,aACA,UACA,aAAa,KACoC;CACjD,MAAM,cAAc,KAAK,IAAI,KAAK,MAAM,WAAW,EAAE,EAAE;CACvD,MAAM,YAAY,KAAK,IAAI,KAAK,MAAM,MAAM,EAAE,YAAY;CAC1D,MAAM,SAAS,YAAY,cAAc;CACzC,MAAM,eAAe,eAAe;CAEpC,MAAM,CAAC,YAAY,iBAAiB,gBAAgB;EAClD,OAAO;EACP;EACA,cAAc;EACd,YAAY;EACb,CAAC;CAEF,MAAM,UAAU,aACb,eAAuB;AACtB,MAAI,aAAa,YACf,eAAc,YAAY;WACjB,aAAa,UACtB,eAAc,UAAU;MAExB,eAAc,WAAW;IAG7B;EAAC;EAAa;EAAW;EAAc,CACxC;CAED,MAAM,OAAO,kBAAkB,QAAQ,aAAa,EAAE,EAAE,CAAC,YAAY,QAAQ,CAAC;CAC9E,MAAM,WAAW,kBAAkB,QAAQ,aAAa,EAAE,EAAE,CAAC,YAAY,QAAQ,CAAC;CAClF,MAAM,QAAQ,kBAAkB,QAAQ,YAAY,EAAE,CAAC,SAAS,YAAY,CAAC;CAC7E,MAAM,OAAO,kBAAkB,QAAQ,UAAU,EAAE,CAAC,WAAW,QAAQ,CAAC;AAyCxE,QAAO;EACL,OAxCsB,cAAmC;AAEzD,OADyB,WAAW,IAAI,IAAI,aAAa,KACjC,OACtB,QAAO,MAAM,aAAa,UAAU;GAGtC,MAAM,mBAAmB,KAAK,IAAI,aAAa,UAAU,cAAc,aAAa,EAAE;GACtF,MAAM,oBAAoB,KAAK,IAAI,aAAa,UAAU,YAAY,WAAW;GAEjF,MAAM,qBAAqB,mBAAmB,cAAc,aAAa;GACzE,MAAM,sBAAsB,oBAAoB,YAAY;AAE5D,OAAI,CAAC,sBAAsB,oBAEzB,QAAO;IACL,GAAG,MAAM,aAAa,eAFF,WAAW,IAAI,aAAa,KAEI,EAAE;IACtD;IACA,GAAG,MAAM,aAAa,aAAa,IAAI,UAAU;IAClD;AAGH,OAAI,sBAAsB,CAAC,qBAAqB;IAC9C,MAAM,iBAAiB,aAAa,IAAI,IAAI;AAC5C,WAAO;KACL,GAAG,MAAM,aAAa,cAAc,aAAa,EAAE;KACnD;KACA,GAAG,MAAM,YAAY,gBAAgB,UAAU;KAChD;;AAGH,UAAO;IACL,GAAG,MAAM,aAAa,cAAc,aAAa,EAAE;IACnD;IACA,GAAG,MAAM,kBAAkB,kBAAkB;IAC7C;IACA,GAAG,MAAM,YAAY,aAAa,GAAG,UAAU;IAChD;KACA;GAAC;GAAQ;GAAU;GAAY;GAAa;GAAW;GAAW,CAAC;EAIpE,QAAQ;EACR;EACA;EACA;EACA;EACA;EACD"}