mirror of
https://github.com/carbon-design-system/carbon-components-svelte.git
synced 2025-09-14 18:01:06 +00:00
parent
1462b2ee9c
commit
2df7b92269
9 changed files with 218 additions and 25 deletions
|
@ -991,8 +991,8 @@ export interface DataTableCell {
|
||||||
| selectable | <code>let</code> | Yes | <code>boolean</code> | <code>false</code> | Set to `true` for the selectable variant<br />Automatically set to `true` if `radio` or `batchSelection` are `true` |
|
| selectable | <code>let</code> | Yes | <code>boolean</code> | <code>false</code> | Set to `true` for the selectable variant<br />Automatically set to `true` if `radio` or `batchSelection` are `true` |
|
||||||
| expandedRowIds | <code>let</code> | Yes | <code>DataTableRowId[]</code> | <code>[]</code> | Specify the row ids to be expanded |
|
| expandedRowIds | <code>let</code> | Yes | <code>DataTableRowId[]</code> | <code>[]</code> | Specify the row ids to be expanded |
|
||||||
| expandable | <code>let</code> | Yes | <code>boolean</code> | <code>false</code> | Set to `true` for the expandable variant<br />Automatically set to `true` if `batchExpansion` is `true` |
|
| expandable | <code>let</code> | Yes | <code>boolean</code> | <code>false</code> | Set to `true` for the expandable variant<br />Automatically set to `true` if `batchExpansion` is `true` |
|
||||||
| rows | <code>let</code> | Yes | <code>DataTableRow[]</code> | <code>[]</code> | Specify the rows the data table should render<br />keys defined in `headers` are used for the row ids |
|
|
||||||
| headers | <code>let</code> | No | <code>DataTableHeader[]</code> | <code>[]</code> | Specify the data table headers |
|
| headers | <code>let</code> | No | <code>DataTableHeader[]</code> | <code>[]</code> | Specify the data table headers |
|
||||||
|
| rows | <code>let</code> | No | <code>DataTableRow[]</code> | <code>[]</code> | Specify the rows the data table should render<br />keys defined in `headers` are used for the row ids |
|
||||||
| size | <code>let</code> | No | <code>"compact" | "short" | "medium" | "tall"</code> | <code>undefined</code> | Set the size of the data table |
|
| size | <code>let</code> | No | <code>"compact" | "short" | "medium" | "tall"</code> | <code>undefined</code> | Set the size of the data table |
|
||||||
| title | <code>let</code> | No | <code>string</code> | <code>""</code> | Specify the title of the data table |
|
| title | <code>let</code> | No | <code>string</code> | <code>""</code> | Specify the title of the data table |
|
||||||
| description | <code>let</code> | No | <code>string</code> | <code>""</code> | Specify the description of the data table |
|
| description | <code>let</code> | No | <code>string</code> | <code>""</code> | Specify the description of the data table |
|
||||||
|
@ -4640,14 +4640,15 @@ None.
|
||||||
|
|
||||||
### Props
|
### Props
|
||||||
|
|
||||||
| Prop name | Kind | Reactive | Type | Default value | Description |
|
| Prop name | Kind | Reactive | Type | Default value | Description |
|
||||||
| :--------- | :--------------- | :------- | :---------------------------------------- | ------------------ | --------------------------------------------- |
|
| :--------------- | :--------------- | :------- | :---------------------------------------------------------------------------------------------------------------------- | ------------------ | ----------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------- |
|
||||||
| ref | <code>let</code> | Yes | <code>null | HTMLInputElement</code> | <code>null</code> | Obtain a reference to the input HTML element |
|
| ref | <code>let</code> | Yes | <code>null | HTMLInputElement</code> | <code>null</code> | Obtain a reference to the input HTML element |
|
||||||
| expanded | <code>let</code> | Yes | <code>boolean</code> | <code>false</code> | Set to `true` to expand the search bar |
|
| expanded | <code>let</code> | Yes | <code>boolean</code> | <code>false</code> | Set to `true` to expand the search bar |
|
||||||
| value | <code>let</code> | Yes | <code>number | string</code> | <code>""</code> | Specify the value of the search input |
|
| value | <code>let</code> | Yes | <code>number | string</code> | <code>""</code> | Specify the value of the search input |
|
||||||
| persistent | <code>let</code> | No | <code>boolean</code> | <code>false</code> | Set to `true` to keep the search bar expanded |
|
| persistent | <code>let</code> | No | <code>boolean</code> | <code>false</code> | Set to `true` to keep the search bar expanded |
|
||||||
| disabled | <code>let</code> | No | <code>boolean</code> | <code>false</code> | Set to `true` to disable the search bar |
|
| disabled | <code>let</code> | No | <code>boolean</code> | <code>false</code> | Set to `true` to disable the search bar |
|
||||||
| tabindex | <code>let</code> | No | <code>string</code> | <code>"0"</code> | Specify the tabindex |
|
| shouldFilterRows | <code>let</code> | No | <code>boolean | ((rows: import("./DataTable.svelte").DataTableRow, value: number | string) => boolean)</code> | <code>false</code> | Set to `true` to filter table rows using the search value.<br /><br />If `true`, the default search excludes `id`, `cells` fields and<br />only does a basic comparison on string and number type cell values.<br /><br />To implement your own client-side filtering, pass a function<br />that accepts a row and value and returns a boolean. |
|
||||||
|
| tabindex | <code>let</code> | No | <code>string</code> | <code>"0"</code> | Specify the tabindex |
|
||||||
|
|
||||||
### Slots
|
### Slots
|
||||||
|
|
||||||
|
|
|
@ -2282,7 +2282,7 @@
|
||||||
"isFunction": false,
|
"isFunction": false,
|
||||||
"isFunctionDeclaration": false,
|
"isFunctionDeclaration": false,
|
||||||
"constant": false,
|
"constant": false,
|
||||||
"reactive": true
|
"reactive": false
|
||||||
},
|
},
|
||||||
{
|
{
|
||||||
"name": "size",
|
"name": "size",
|
||||||
|
@ -13218,6 +13218,17 @@
|
||||||
"constant": false,
|
"constant": false,
|
||||||
"reactive": false
|
"reactive": false
|
||||||
},
|
},
|
||||||
|
{
|
||||||
|
"name": "shouldFilterRows",
|
||||||
|
"kind": "let",
|
||||||
|
"description": "Set to `true` to filter table rows using the search value.\n\nIf `true`, the default search excludes `id`, `cells` fields and\nonly does a basic comparison on string and number type cell values.\n\nTo implement your own client-side filtering, pass a function\nthat accepts a row and value and returns a boolean.",
|
||||||
|
"type": "boolean | ((rows: import(\"./DataTable.svelte\").DataTableRow, value: number | string) => boolean)",
|
||||||
|
"value": "false",
|
||||||
|
"isFunction": false,
|
||||||
|
"isFunctionDeclaration": false,
|
||||||
|
"constant": false,
|
||||||
|
"reactive": false
|
||||||
|
},
|
||||||
{
|
{
|
||||||
"name": "tabindex",
|
"name": "tabindex",
|
||||||
"kind": "let",
|
"kind": "let",
|
||||||
|
|
|
@ -464,6 +464,22 @@ title="Load balancers" description="Your organization's active load balancers."
|
||||||
</Toolbar>
|
</Toolbar>
|
||||||
</DataTable>
|
</DataTable>
|
||||||
|
|
||||||
|
### Filterable
|
||||||
|
|
||||||
|
By default, `ToolbarSearch` will not filter `DataTable` rows.
|
||||||
|
|
||||||
|
Set `shouldFilterRows` to `true` to enable client-side filtering. The default filtering performs a basic string comparison on cell values that are of a string or a number type.
|
||||||
|
|
||||||
|
Note that in-memory filtering is not optimal for large data sets, where you might consider using server-side search.
|
||||||
|
|
||||||
|
<FileSource src="/framed/DataTable/DataTableFilterable" />
|
||||||
|
|
||||||
|
### Filterable (custom)
|
||||||
|
|
||||||
|
`shouldFilterRows` also accepts a function and passes it the current row and value. It expects the function to return a boolean.
|
||||||
|
|
||||||
|
<FileSource src="/framed/DataTable/DataTableFilterCustom" />
|
||||||
|
|
||||||
### Zebra stripes
|
### Zebra stripes
|
||||||
|
|
||||||
<DataTable zebra
|
<DataTable zebra
|
||||||
|
|
55
docs/src/pages/framed/DataTable/DataTableFilterCustom.svelte
Normal file
55
docs/src/pages/framed/DataTable/DataTableFilterCustom.svelte
Normal file
|
@ -0,0 +1,55 @@
|
||||||
|
<script>
|
||||||
|
import {
|
||||||
|
DataTable,
|
||||||
|
Toolbar,
|
||||||
|
ToolbarContent,
|
||||||
|
ToolbarSearch,
|
||||||
|
ToolbarMenu,
|
||||||
|
ToolbarMenuItem,
|
||||||
|
Button,
|
||||||
|
} from "carbon-components-svelte";
|
||||||
|
|
||||||
|
let rows = Array.from({ length: 10 }).map((_, i) => ({
|
||||||
|
id: i,
|
||||||
|
name: "Load Balancer " + (i + 1),
|
||||||
|
protocol: "HTTP",
|
||||||
|
port: 3000 + i * 10,
|
||||||
|
rule: i % 2 ? "Round robin" : "DNS delegation",
|
||||||
|
}));
|
||||||
|
</script>
|
||||||
|
|
||||||
|
<DataTable
|
||||||
|
sortable
|
||||||
|
title="Load balancers"
|
||||||
|
description="Your organization's active load balancers."
|
||||||
|
headers="{[
|
||||||
|
{ key: 'name', value: 'Name' },
|
||||||
|
{ key: 'protocol', value: 'Protocol' },
|
||||||
|
{ key: 'port', value: 'Port' },
|
||||||
|
{ key: 'rule', value: 'Rule' },
|
||||||
|
]}"
|
||||||
|
rows="{rows}"
|
||||||
|
>
|
||||||
|
<Toolbar>
|
||||||
|
<ToolbarContent>
|
||||||
|
<ToolbarSearch
|
||||||
|
persistent
|
||||||
|
value="round"
|
||||||
|
shouldFilterRows="{(row, value) => {
|
||||||
|
return (
|
||||||
|
/(6|8)$/.test(row.name) &&
|
||||||
|
row.rule.toLowerCase().includes(value.toLowerCase())
|
||||||
|
);
|
||||||
|
}}"
|
||||||
|
/>
|
||||||
|
<ToolbarMenu>
|
||||||
|
<ToolbarMenuItem primaryFocus>Restart all</ToolbarMenuItem>
|
||||||
|
<ToolbarMenuItem href="https://cloud.ibm.com/docs/loadbalancer-service">
|
||||||
|
API documentation
|
||||||
|
</ToolbarMenuItem>
|
||||||
|
<ToolbarMenuItem hasDivider danger>Stop all</ToolbarMenuItem>
|
||||||
|
</ToolbarMenu>
|
||||||
|
<Button>Create balancer</Button>
|
||||||
|
</ToolbarContent>
|
||||||
|
</Toolbar>
|
||||||
|
</DataTable>
|
46
docs/src/pages/framed/DataTable/DataTableFilterable.svelte
Normal file
46
docs/src/pages/framed/DataTable/DataTableFilterable.svelte
Normal file
|
@ -0,0 +1,46 @@
|
||||||
|
<script>
|
||||||
|
import {
|
||||||
|
DataTable,
|
||||||
|
Toolbar,
|
||||||
|
ToolbarContent,
|
||||||
|
ToolbarSearch,
|
||||||
|
ToolbarMenu,
|
||||||
|
ToolbarMenuItem,
|
||||||
|
Button,
|
||||||
|
} from "carbon-components-svelte";
|
||||||
|
|
||||||
|
let rows = Array.from({ length: 10 }).map((_, i) => ({
|
||||||
|
id: i,
|
||||||
|
name: "Load Balancer " + (i + 1),
|
||||||
|
protocol: "HTTP",
|
||||||
|
port: 3000 + i * 10,
|
||||||
|
rule: i % 2 ? "Round robin" : "DNS delegation",
|
||||||
|
}));
|
||||||
|
</script>
|
||||||
|
|
||||||
|
<DataTable
|
||||||
|
sortable
|
||||||
|
title="Load balancers"
|
||||||
|
description="Your organization's active load balancers."
|
||||||
|
headers="{[
|
||||||
|
{ key: 'name', value: 'Name' },
|
||||||
|
{ key: 'protocol', value: 'Protocol' },
|
||||||
|
{ key: 'port', value: 'Port' },
|
||||||
|
{ key: 'rule', value: 'Rule' },
|
||||||
|
]}"
|
||||||
|
rows="{rows}"
|
||||||
|
>
|
||||||
|
<Toolbar>
|
||||||
|
<ToolbarContent>
|
||||||
|
<ToolbarSearch persistent value="round" shouldFilterRows />
|
||||||
|
<ToolbarMenu>
|
||||||
|
<ToolbarMenuItem primaryFocus>Restart all</ToolbarMenuItem>
|
||||||
|
<ToolbarMenuItem href="https://cloud.ibm.com/docs/loadbalancer-service">
|
||||||
|
API documentation
|
||||||
|
</ToolbarMenuItem>
|
||||||
|
<ToolbarMenuItem hasDivider danger>Stop all</ToolbarMenuItem>
|
||||||
|
</ToolbarMenu>
|
||||||
|
<Button>Create balancer</Button>
|
||||||
|
</ToolbarContent>
|
||||||
|
</Toolbar>
|
||||||
|
</DataTable>
|
|
@ -140,6 +140,7 @@
|
||||||
sortDirection: "none",
|
sortDirection: "none",
|
||||||
});
|
});
|
||||||
const headerItems = writable([]);
|
const headerItems = writable([]);
|
||||||
|
const tableRows = writable(rows);
|
||||||
const thKeys = derived(headerItems, () =>
|
const thKeys = derived(headerItems, () =>
|
||||||
headers
|
headers
|
||||||
.map(({ key }, i) => ({ key, id: key }))
|
.map(({ key }, i) => ({ key, id: key }))
|
||||||
|
@ -155,6 +156,7 @@
|
||||||
sortHeader,
|
sortHeader,
|
||||||
tableSortable,
|
tableSortable,
|
||||||
batchSelectedIds,
|
batchSelectedIds,
|
||||||
|
tableRows,
|
||||||
resetSelectedRowIds: () => {
|
resetSelectedRowIds: () => {
|
||||||
selectAll = false;
|
selectAll = false;
|
||||||
selectedRowIds = [];
|
selectedRowIds = [];
|
||||||
|
@ -173,7 +175,7 @@
|
||||||
let refSelectAll = null;
|
let refSelectAll = null;
|
||||||
|
|
||||||
$: batchSelectedIds.set(selectedRowIds);
|
$: batchSelectedIds.set(selectedRowIds);
|
||||||
$: rowIds = rows.map((row) => row.id);
|
$: rowIds = $tableRows.map((row) => row.id);
|
||||||
$: expandableRowIds = rowIds.filter(
|
$: expandableRowIds = rowIds.filter(
|
||||||
(id) => !nonExpandableRowIds.includes(id)
|
(id) => !nonExpandableRowIds.includes(id)
|
||||||
);
|
);
|
||||||
|
@ -193,23 +195,25 @@
|
||||||
$: if (radio || batchSelection) selectable = true;
|
$: if (radio || batchSelection) selectable = true;
|
||||||
$: tableSortable.set(sortable);
|
$: tableSortable.set(sortable);
|
||||||
$: headerKeys = headers.map(({ key }) => key);
|
$: headerKeys = headers.map(({ key }) => key);
|
||||||
$: rows = rows.map((row) => ({
|
$: tableRows.set(
|
||||||
...row,
|
rows.map((row) => ({
|
||||||
cells: headerKeys.map((key, index) => ({
|
...row,
|
||||||
key,
|
cells: headerKeys.map((key, index) => ({
|
||||||
value: resolvePath(row, key),
|
key,
|
||||||
display: headers[index].display,
|
value: resolvePath(row, key),
|
||||||
})),
|
display: headers[index].display,
|
||||||
}));
|
})),
|
||||||
$: sortedRows = rows;
|
}))
|
||||||
|
);
|
||||||
|
$: sortedRows = [...$tableRows];
|
||||||
$: ascending = $sortHeader.sortDirection === "ascending";
|
$: ascending = $sortHeader.sortDirection === "ascending";
|
||||||
$: sortKey = $sortHeader.key;
|
$: sortKey = $sortHeader.key;
|
||||||
$: sorting = sortable && sortKey != null;
|
$: sorting = sortable && sortKey != null;
|
||||||
$: if (sorting) {
|
$: if (sorting) {
|
||||||
if ($sortHeader.sortDirection === "none") {
|
if ($sortHeader.sortDirection === "none") {
|
||||||
sortedRows = rows;
|
sortedRows = $tableRows;
|
||||||
} else {
|
} else {
|
||||||
sortedRows = [...rows].sort((a, b) => {
|
sortedRows = [...$tableRows].sort((a, b) => {
|
||||||
const itemA = ascending
|
const itemA = ascending
|
||||||
? resolvePath(a, sortKey, "")
|
? resolvePath(a, sortKey, "")
|
||||||
: resolvePath(b, sortKey, "");
|
: resolvePath(b, sortKey, "");
|
||||||
|
@ -236,7 +240,7 @@
|
||||||
page && pageSize
|
page && pageSize
|
||||||
? rows.slice((page - 1) * pageSize, page * pageSize)
|
? rows.slice((page - 1) * pageSize, page * pageSize)
|
||||||
: rows;
|
: rows;
|
||||||
$: displayedRows = getDisplayedRows(rows, page, pageSize);
|
$: displayedRows = getDisplayedRows($tableRows, page, pageSize);
|
||||||
$: displayedSortedRows = getDisplayedRows(sortedRows, page, pageSize);
|
$: displayedSortedRows = getDisplayedRows(sortedRows, page, pageSize);
|
||||||
</script>
|
</script>
|
||||||
|
|
||||||
|
|
|
@ -16,6 +16,18 @@
|
||||||
/** Set to `true` to disable the search bar */
|
/** Set to `true` to disable the search bar */
|
||||||
export let disabled = false;
|
export let disabled = false;
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Set to `true` to filter table rows using the search value.
|
||||||
|
*
|
||||||
|
* If `true`, the default search excludes `id`, `cells` fields and
|
||||||
|
* only does a basic comparison on string and number type cell values.
|
||||||
|
*
|
||||||
|
* To implement your own client-side filtering, pass a function
|
||||||
|
* that accepts a row and value and returns a boolean.
|
||||||
|
* @type {boolean | ((rows: import("./DataTable.svelte").DataTableRow, value: number | string) => boolean)}
|
||||||
|
*/
|
||||||
|
export let shouldFilterRows = false;
|
||||||
|
|
||||||
/** Specify the tabindex */
|
/** Specify the tabindex */
|
||||||
export let tabindex = "0";
|
export let tabindex = "0";
|
||||||
|
|
||||||
|
@ -25,9 +37,36 @@
|
||||||
*/
|
*/
|
||||||
export let ref = null;
|
export let ref = null;
|
||||||
|
|
||||||
import { tick } from "svelte";
|
import { tick, getContext } from "svelte";
|
||||||
import Search from "../Search/Search.svelte";
|
import Search from "../Search/Search.svelte";
|
||||||
|
|
||||||
|
const { tableRows } = getContext("DataTable");
|
||||||
|
|
||||||
|
$: originalRows = tableRows ? [...$tableRows] : [];
|
||||||
|
$: if (shouldFilterRows) {
|
||||||
|
let rows = originalRows;
|
||||||
|
|
||||||
|
if (value.trim().length > 0) {
|
||||||
|
if (shouldFilterRows === true) {
|
||||||
|
rows = rows.filter((row) => {
|
||||||
|
return Object.entries(row)
|
||||||
|
.filter(([key]) => !["cells", "id"].includes(key))
|
||||||
|
.some(([key, _value]) => {
|
||||||
|
if (typeof _value === "string" || typeof _value === "number") {
|
||||||
|
return (_value + "")
|
||||||
|
?.toLowerCase()
|
||||||
|
.includes(value.trim().toLowerCase());
|
||||||
|
}
|
||||||
|
});
|
||||||
|
});
|
||||||
|
} else if (typeof shouldFilterRows === "function") {
|
||||||
|
rows = rows.filter((row) => shouldFilterRows(row, value) ?? false);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
tableRows.set(rows);
|
||||||
|
}
|
||||||
|
|
||||||
async function expandSearch() {
|
async function expandSearch() {
|
||||||
if (disabled || persistent || expanded) return;
|
if (disabled || persistent || expanded) return;
|
||||||
expanded = true;
|
expanded = true;
|
||||||
|
|
|
@ -109,7 +109,11 @@
|
||||||
>
|
>
|
||||||
<Toolbar>
|
<Toolbar>
|
||||||
<ToolbarContent>
|
<ToolbarContent>
|
||||||
<ToolbarSearch />
|
<ToolbarSearch
|
||||||
|
shouldFilterRows="{(row, value) => {
|
||||||
|
return true;
|
||||||
|
}}"
|
||||||
|
/>
|
||||||
<ToolbarMenu>
|
<ToolbarMenu>
|
||||||
<ToolbarMenuItem primaryFocus>Restart all</ToolbarMenuItem>
|
<ToolbarMenuItem primaryFocus>Restart all</ToolbarMenuItem>
|
||||||
<ToolbarMenuItem href="https://cloud.ibm.com/docs/loadbalancer-service">
|
<ToolbarMenuItem href="https://cloud.ibm.com/docs/loadbalancer-service">
|
||||||
|
|
17
types/DataTable/ToolbarSearch.svelte.d.ts
vendored
17
types/DataTable/ToolbarSearch.svelte.d.ts
vendored
|
@ -27,6 +27,23 @@ export interface ToolbarSearchProps
|
||||||
*/
|
*/
|
||||||
disabled?: boolean;
|
disabled?: boolean;
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Set to `true` to filter table rows using the search value.
|
||||||
|
*
|
||||||
|
* If `true`, the default search excludes `id`, `cells` fields and
|
||||||
|
* only does a basic comparison on string and number type cell values.
|
||||||
|
*
|
||||||
|
* To implement your own client-side filtering, pass a function
|
||||||
|
* that accepts a row and value and returns a boolean.
|
||||||
|
* @default false
|
||||||
|
*/
|
||||||
|
shouldFilterRows?:
|
||||||
|
| boolean
|
||||||
|
| ((
|
||||||
|
rows: import("./DataTable.svelte").DataTableRow,
|
||||||
|
value: number | string
|
||||||
|
) => boolean);
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Specify the tabindex
|
* Specify the tabindex
|
||||||
* @default "0"
|
* @default "0"
|
||||||
|
|
Loading…
Add table
Add a link
Reference in a new issue