mirror of
https://github.com/carbon-design-system/carbon-components-svelte.git
synced 2025-09-15 02:11:05 +00:00
parent
024d77493c
commit
ed3928bb01
7 changed files with 102 additions and 20 deletions
|
@ -2682,10 +2682,11 @@ None.
|
||||||
### Props
|
### Props
|
||||||
|
|
||||||
| Prop name | Required | Kind | Reactive | Type | Default value | Description |
|
| Prop name | Required | Kind | Reactive | Type | Default value | Description |
|
||||||
| :-------------------- | :------- | :--------------- | :------- | ---------------------------------------------------------------- | ------------------------------------------------------------------------------------------- | ------------------------------------------------ |
|
| :-------------------- | :------- | :--------------- | :------- | ---------------------------------------------------------------- | ------------------------------------------------------------------------------------------- | --------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------- |
|
||||||
| pageSize | No | <code>let</code> | Yes | <code>number</code> | <code>10</code> | Specify the number of items to display in a page |
|
| pageSize | No | <code>let</code> | Yes | <code>number</code> | <code>10</code> | Specify the number of items to display in a page |
|
||||||
| page | No | <code>let</code> | Yes | <code>number</code> | <code>1</code> | Specify the current page index |
|
| page | No | <code>let</code> | Yes | <code>number</code> | <code>1</code> | Specify the current page index |
|
||||||
| totalItems | No | <code>let</code> | No | <code>number</code> | <code>0</code> | Specify the total number of items |
|
| totalItems | No | <code>let</code> | No | <code>number</code> | <code>0</code> | Specify the total number of items |
|
||||||
|
| pageWindow | No | <code>let</code> | No | <code>number</code> | <code>1000</code> | If `totalItems` is a large number, it can affect the<br />rendering performance of this component since its value<br />is used to calculate the number of pages in the native<br />select dropdown. This value creates a small window of<br />pages rendered around the current page. By default,<br />a maximum of 1000 select items are rendered. |
|
||||||
| disabled | No | <code>let</code> | No | <code>boolean</code> | <code>false</code> | Set to `true` to disable the pagination |
|
| disabled | No | <code>let</code> | No | <code>boolean</code> | <code>false</code> | Set to `true` to disable the pagination |
|
||||||
| forwardText | No | <code>let</code> | No | <code>string</code> | <code>"Next page"</code> | Specify the forward button text |
|
| forwardText | No | <code>let</code> | No | <code>string</code> | <code>"Next page"</code> | Specify the forward button text |
|
||||||
| backwardText | No | <code>let</code> | No | <code>string</code> | <code>"Previous page"</code> | Specify the backward button text |
|
| backwardText | No | <code>let</code> | No | <code>string</code> | <code>"Previous page"</code> | Specify the backward button text |
|
||||||
|
|
|
@ -10048,6 +10048,18 @@
|
||||||
"constant": false,
|
"constant": false,
|
||||||
"reactive": false
|
"reactive": false
|
||||||
},
|
},
|
||||||
|
{
|
||||||
|
"name": "pageWindow",
|
||||||
|
"kind": "let",
|
||||||
|
"description": "If `totalItems` is a large number, it can affect the\nrendering performance of this component since its value\nis used to calculate the number of pages in the native\nselect dropdown. This value creates a small window of\npages rendered around the current page. By default,\na maximum of 1000 select items are rendered.",
|
||||||
|
"type": "number",
|
||||||
|
"value": "1000",
|
||||||
|
"isFunction": false,
|
||||||
|
"isFunctionDeclaration": false,
|
||||||
|
"isRequired": false,
|
||||||
|
"constant": false,
|
||||||
|
"reactive": false
|
||||||
|
},
|
||||||
{
|
{
|
||||||
"name": "disabled",
|
"name": "disabled",
|
||||||
"kind": "let",
|
"kind": "let",
|
||||||
|
|
|
@ -19,6 +19,19 @@ components: ["Pagination", "PaginationSkeleton"]
|
||||||
|
|
||||||
<Pagination totalItems={102} pageSizes="{[16, 36, 99]}" pageSize="{36}" />
|
<Pagination totalItems={102} pageSizes="{[16, 36, 99]}" pageSize="{36}" />
|
||||||
|
|
||||||
|
## Page window
|
||||||
|
|
||||||
|
The number of native select items rendered is derived from the value of `totalItems`.
|
||||||
|
|
||||||
|
If `totalItems` is a very large number, this can impact rendering performance since
|
||||||
|
thousands of elements may be rendered. By default, the window of rendered items is
|
||||||
|
capped at 1,000. For example, if `totalItems=100_000` and the `pageSize=10`,
|
||||||
|
1,000 select options are rendered.
|
||||||
|
|
||||||
|
Use the `pageWindow` prop to increase this value.
|
||||||
|
|
||||||
|
<Pagination totalItems={100_000} pageSizes={[10, 15, 20]} />
|
||||||
|
|
||||||
## Hidden page input
|
## Hidden page input
|
||||||
|
|
||||||
<Pagination totalItems={102} pageInputDisabled />
|
<Pagination totalItems={102} pageInputDisabled />
|
||||||
|
|
|
@ -12,6 +12,16 @@
|
||||||
/** Specify the total number of items */
|
/** Specify the total number of items */
|
||||||
export let totalItems = 0;
|
export let totalItems = 0;
|
||||||
|
|
||||||
|
/**
|
||||||
|
* If `totalItems` is a large number, it can affect the
|
||||||
|
* rendering performance of this component since its value
|
||||||
|
* is used to calculate the number of pages in the native
|
||||||
|
* select dropdown. This value creates a small window of
|
||||||
|
* pages rendered around the current page. By default,
|
||||||
|
* a maximum of 1000 select items are rendered.
|
||||||
|
*/
|
||||||
|
export let pageWindow = 1000;
|
||||||
|
|
||||||
/** Set to `true` to disable the pagination */
|
/** Set to `true` to disable the pagination */
|
||||||
export let disabled = false;
|
export let disabled = false;
|
||||||
|
|
||||||
|
@ -81,6 +91,21 @@
|
||||||
|
|
||||||
const dispatch = createEventDispatcher();
|
const dispatch = createEventDispatcher();
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Returns a subset of page numbers centered around the current page to prevent
|
||||||
|
* performance issues with large datasets. Creates a capped window of pages
|
||||||
|
* instead of potentially thousands, improving render speed and memory usage.
|
||||||
|
* @param {number} currentPage - The current page number
|
||||||
|
* @param {number} totalPages - Total number of pages
|
||||||
|
* @param {number} window - How many pages to show before/after current page
|
||||||
|
* @returns {number[]} Array of page numbers to display
|
||||||
|
*/
|
||||||
|
function getWindowedPages(currentPage, totalPages, window) {
|
||||||
|
const start = Math.max(1, currentPage - window);
|
||||||
|
const end = Math.min(totalPages, currentPage + window);
|
||||||
|
return Array.from({ length: end - start + 1 }, (_, i) => start + i);
|
||||||
|
}
|
||||||
|
|
||||||
afterUpdate(() => {
|
afterUpdate(() => {
|
||||||
if (page > totalPages) {
|
if (page > totalPages) {
|
||||||
page = totalPages;
|
page = totalPages;
|
||||||
|
@ -89,7 +114,7 @@
|
||||||
|
|
||||||
$: dispatch("update", { pageSize, page });
|
$: dispatch("update", { pageSize, page });
|
||||||
$: totalPages = Math.max(Math.ceil(totalItems / pageSize), 1);
|
$: totalPages = Math.max(Math.ceil(totalItems / pageSize), 1);
|
||||||
$: selectItems = Array.from({ length: totalPages }, (_, i) => i);
|
$: selectItems = getWindowedPages(page, totalPages, pageWindow);
|
||||||
$: backButtonDisabled = disabled || page === 1;
|
$: backButtonDisabled = disabled || page === 1;
|
||||||
$: forwardButtonDisabled = disabled || page === totalPages;
|
$: forwardButtonDisabled = disabled || page === totalPages;
|
||||||
</script>
|
</script>
|
||||||
|
@ -146,7 +171,7 @@
|
||||||
bind:selected={page}
|
bind:selected={page}
|
||||||
>
|
>
|
||||||
{#each selectItems as size, i (size)}
|
{#each selectItems as size, i (size)}
|
||||||
<SelectItem value={size + 1} text={(size + 1).toString()} />
|
<SelectItem value={size} text={size.toString()} />
|
||||||
{/each}
|
{/each}
|
||||||
</Select>
|
</Select>
|
||||||
<span class:bx--pagination__text={true}>
|
<span class:bx--pagination__text={true}>
|
||||||
|
|
|
@ -11,6 +11,7 @@
|
||||||
export let pageSizeInputDisabled = false;
|
export let pageSizeInputDisabled = false;
|
||||||
export let pageSize = 10;
|
export let pageSize = 10;
|
||||||
export let pageSizes: ReadonlyArray<number> = [10];
|
export let pageSizes: ReadonlyArray<number> = [10];
|
||||||
|
export let pageWindow: undefined | number = undefined;
|
||||||
export let pagesUnknown = false;
|
export let pagesUnknown = false;
|
||||||
</script>
|
</script>
|
||||||
|
|
||||||
|
@ -23,6 +24,7 @@
|
||||||
{itemsPerPageText}
|
{itemsPerPageText}
|
||||||
{pageInputDisabled}
|
{pageInputDisabled}
|
||||||
{pageSizeInputDisabled}
|
{pageSizeInputDisabled}
|
||||||
|
{pageWindow}
|
||||||
bind:pageSize
|
bind:pageSize
|
||||||
{pageSizes}
|
{pageSizes}
|
||||||
{pagesUnknown}
|
{pagesUnknown}
|
||||||
|
|
|
@ -196,4 +196,22 @@ describe("Pagination", () => {
|
||||||
|
|
||||||
expect(screen.getByText("0–0 of 0 items")).toBeInTheDocument();
|
expect(screen.getByText("0–0 of 0 items")).toBeInTheDocument();
|
||||||
});
|
});
|
||||||
|
|
||||||
|
it("renders a cap of 1000 page numbers by default", () => {
|
||||||
|
render(Pagination, {
|
||||||
|
props: { totalItems: 100_000 },
|
||||||
|
});
|
||||||
|
|
||||||
|
const pageNumbers = screen.getByLabelText(/Page number, of 10000 pages/);
|
||||||
|
expect(pageNumbers).toHaveLength(1_000 + 1);
|
||||||
|
});
|
||||||
|
|
||||||
|
it("renders a custom page window", () => {
|
||||||
|
render(Pagination, {
|
||||||
|
props: { totalItems: 100_000, pageWindow: 100 },
|
||||||
|
});
|
||||||
|
|
||||||
|
const pageNumbers = screen.getByLabelText(/Page number, of 10000 pages/);
|
||||||
|
expect(pageNumbers).toHaveLength(100 + 1);
|
||||||
|
});
|
||||||
});
|
});
|
||||||
|
|
11
types/Pagination/Pagination.svelte.d.ts
vendored
11
types/Pagination/Pagination.svelte.d.ts
vendored
|
@ -16,6 +16,17 @@ type $Props = {
|
||||||
*/
|
*/
|
||||||
totalItems?: number;
|
totalItems?: number;
|
||||||
|
|
||||||
|
/**
|
||||||
|
* If `totalItems` is a large number, it can affect the
|
||||||
|
* rendering performance of this component since its value
|
||||||
|
* is used to calculate the number of pages in the native
|
||||||
|
* select dropdown. This value creates a small window of
|
||||||
|
* pages rendered around the current page. By default,
|
||||||
|
* a maximum of 1000 select items are rendered.
|
||||||
|
* @default 1000
|
||||||
|
*/
|
||||||
|
pageWindow?: number;
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Set to `true` to disable the pagination
|
* Set to `true` to disable the pagination
|
||||||
* @default false
|
* @default false
|
||||||
|
|
Loading…
Add table
Add a link
Reference in a new issue