@godxjp/ui 31.4.0 → 31.6.0
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/agent/START-HERE.md +6 -6
- package/agent/components/BranchScopePicker.json +5 -0
- package/agent/components/Cascader.json +1 -1
- package/agent/components/CodeBlock.json +7 -1
- package/agent/components/DataTable.json +2 -2
- package/agent/components/InfiniteQueryState.json +6 -1
- package/agent/components/OrgChart.json +59 -0
- package/agent/components/RangeTimeline.json +6 -0
- package/agent/components/RecordPicker.json +10 -0
- package/agent/components/Transfer.json +5 -0
- package/agent/components/Tree.json +21 -4
- package/agent/components/TreeSelect.json +1 -1
- package/agent/components-index.json +5 -0
- package/agent/components.json +123 -10
- package/agent/index.json +7 -7
- package/agent/llms.txt +7 -7
- package/agent/tokens.json +114 -0
- package/dist/components/data-display/code-block.js +90 -4
- package/dist/components/data-display/data-table.d.ts +3 -0
- package/dist/components/data-display/data-table.js +415 -370
- package/dist/components/data-display/index.d.ts +2 -0
- package/dist/components/data-display/index.js +2 -0
- package/dist/components/data-display/org-chart.d.ts +5 -0
- package/dist/components/data-display/org-chart.js +169 -0
- package/dist/components/data-display/range-timeline.d.ts +20 -0
- package/dist/components/data-display/range-timeline.js +217 -197
- package/dist/components/data-display/tree.js +179 -23
- package/dist/components/data-entry/branch-scope-picker.d.ts +1 -0
- package/dist/components/data-entry/branch-scope-picker.js +2 -1
- package/dist/components/data-entry/cascader.js +4 -5
- package/dist/components/data-entry/record-picker.d.ts +2 -0
- package/dist/components/data-entry/record-picker.js +22 -3
- package/dist/components/data-entry/transfer.d.ts +1 -1
- package/dist/components/data-entry/transfer.js +5 -2
- package/dist/components/data-entry/tree-select.js +14 -5
- package/dist/components/general/typography.d.ts +32 -0
- package/dist/components/general/typography.js +11 -2
- package/dist/components/query/infinite-query-state.d.ts +1 -1
- package/dist/components/query/infinite-query-state.js +2 -1
- package/dist/contracts/measurement.json +1 -1
- package/dist/i18n/messages/en.json +26 -2
- package/dist/i18n/messages/ja.json +17 -2
- package/dist/i18n/messages/vi.json +17 -2
- package/dist/lib/hooks.d.ts +8 -4
- package/dist/lib/hooks.js +5 -2
- package/dist/lib/tree.d.ts +23 -0
- package/dist/lib/tree.js +29 -0
- package/dist/props/components/data-display.prop.d.ts +72 -3
- package/dist/props/components/data-entry.prop.d.ts +31 -4
- package/dist/props/components/query.prop.d.ts +8 -1
- package/dist/props/registry.d.ts +63 -6
- package/dist/props/registry.js +90 -4
- package/dist/props/vocabulary/data.prop.d.ts +32 -2
- package/dist/props/vocabulary/index.d.ts +1 -1
- package/dist/styles/data-display-layout.css +225 -0
- package/dist/styles/layers.json +14 -1
- package/dist/styles/table-layout.css +16 -1
- package/dist/tokens/base.css +1 -0
- package/dist/tokens/components/org-chart.css +27 -0
- package/dist/tokens/components/tree.css +2 -0
- package/docs/FRAME-COVERAGE-REPORT.md +3 -2
- package/docs/data-display/code-block.tsx +27 -0
- package/docs/data-display/data-table/examples/server-paged.tsx +23 -0
- package/docs/data-display/data-table/index.md +2 -0
- package/docs/data-display/org-chart.tsx +165 -0
- package/docs/data-display/timeline.tsx +33 -0
- package/docs/data-display/tree.tsx +154 -0
- package/docs/data-entry/branch-scope-picker.tsx +6 -1
- package/docs/data-entry/record-picker.tsx +1 -0
- package/docs/data-entry/transfer.tsx +1 -0
- package/docs/i18n/messages/en.json +19 -0
- package/docs/i18n/messages/ja.json +18 -0
- package/docs/i18n/messages/vi.json +18 -0
- package/docs/navigation/tabs.tsx +17 -15
- package/docs/query/data-state.tsx +2 -4
- package/docs/query/infinite-query-state.tsx +5 -1
- package/docs/roadmap/tree-components.md +2 -1
- package/docs/showcase/table-view-tabs.tsx +1 -1
- package/package.json +2 -2
- package/scripts/ui-audit.mjs +15 -5
|
@@ -336,7 +336,15 @@ function DataTable({
|
|
|
336
336
|
onFilterChange?.(merged);
|
|
337
337
|
};
|
|
338
338
|
const rowSelectionKeys = rowSelection?.selectedRowKeys;
|
|
339
|
-
const
|
|
339
|
+
const ownSelectionState = rowSelectionKeys !== void 0 ? Object.fromEntries(rowSelectionKeys.map((key) => [key, true])) : controlledSelected !== void 0 ? selectionFromSet(controlledSelected) : internalSelection;
|
|
340
|
+
const isRowLocked = (row) => !!rowSelection?.getCheckboxProps?.(row).disabled;
|
|
341
|
+
const matching = rowSelection?.matching;
|
|
342
|
+
const rowSelectionState = matching?.selected ? {
|
|
343
|
+
...ownSelectionState,
|
|
344
|
+
...Object.fromEntries(
|
|
345
|
+
data.filter((row) => !isRowLocked(row)).map((row) => [getRowId(row), true])
|
|
346
|
+
)
|
|
347
|
+
} : ownSelectionState;
|
|
340
348
|
const onSortingChange = (updater) => {
|
|
341
349
|
const next = typeof updater === "function" ? updater(sortingState) : updater;
|
|
342
350
|
if (columnSortOrders.length > 0) {
|
|
@@ -373,6 +381,9 @@ function DataTable({
|
|
|
373
381
|
}
|
|
374
382
|
}
|
|
375
383
|
const keys = Object.keys(next).filter((key) => next[key]);
|
|
384
|
+
if (matching?.selected && data.some((row) => !isRowLocked(row) && !next[getRowId(row)])) {
|
|
385
|
+
matching.onSelectedChange(false);
|
|
386
|
+
}
|
|
376
387
|
if (rowSelectionKeys === void 0 && controlledSelected === void 0) {
|
|
377
388
|
setInternalSelection(next);
|
|
378
389
|
}
|
|
@@ -418,7 +429,9 @@ function DataTable({
|
|
|
418
429
|
// rows unsliced. Page count still derives from `rowCount`/the pre-paginated model either way.
|
|
419
430
|
manualPagination: manualPagination || serverPaged || !paginationEngaged,
|
|
420
431
|
rowCount: paginationConfig?.total ?? rowCount,
|
|
421
|
-
|
|
432
|
+
// A function only when rows CAN be locked, so a table without `getCheckboxProps` is untouched.
|
|
433
|
+
// TanStack's page toggles and header tri-state then skip a locked row in both directions.
|
|
434
|
+
enableRowSelection: selectionEnabled && rowSelection?.getCheckboxProps ? (row) => !isRowLocked(row.original) : selectionEnabled,
|
|
422
435
|
state: {
|
|
423
436
|
sorting: sortingState,
|
|
424
437
|
columnFilters,
|
|
@@ -586,41 +599,49 @@ DataTable.SelectAll = function DataTableSelectAll() {
|
|
|
586
599
|
{
|
|
587
600
|
checked: allSelected ? true : someSelected ? "indeterminate" : false,
|
|
588
601
|
onCheckedChange: (v) => table.toggleAllPageRowsSelected(!!v),
|
|
589
|
-
"aria-label":
|
|
602
|
+
"aria-label": rowSelection?.selectAllLabel ?? // With `matching` on, the table is server-paged by declaration: this box selects the PAGE.
|
|
603
|
+
t(rowSelection?.matching ? "dataTable.selectPage" : "dataTable.selectAll")
|
|
590
604
|
}
|
|
591
605
|
);
|
|
592
606
|
if (rowSelection?.columnTitle !== void 0) return /* @__PURE__ */ jsx(Fragment, { children: rowSelection.columnTitle });
|
|
593
607
|
if (!rowSelection?.selections) return box;
|
|
594
608
|
const pageKeys = table.getRowModel().rows.map((row) => getRowId(row.original));
|
|
595
609
|
const selectedKeys = table.getSelectedRowModel().rows.map((row) => getRowId(row.original));
|
|
596
|
-
const builtIn =
|
|
597
|
-
{
|
|
610
|
+
const builtIn = {
|
|
611
|
+
SELECT_ALL: {
|
|
598
612
|
key: "all",
|
|
599
613
|
text: t("dataTable.selectAll"),
|
|
600
614
|
onSelect: () => table.toggleAllPageRowsSelected(true)
|
|
601
615
|
},
|
|
602
|
-
{
|
|
616
|
+
SELECT_INVERT: {
|
|
603
617
|
key: "invert",
|
|
604
618
|
text: t("dataTable.selectInvert"),
|
|
605
619
|
onSelect: () => {
|
|
606
620
|
table.setRowSelection(
|
|
607
621
|
Object.fromEntries(
|
|
608
|
-
table.getRowModel().rows.filter(
|
|
622
|
+
table.getRowModel().rows.filter(
|
|
623
|
+
(row) => (
|
|
624
|
+
// A locked row keeps its state; every other row flips.
|
|
625
|
+
row.getCanSelect() ? !row.getIsSelected() : row.getIsSelected()
|
|
626
|
+
)
|
|
627
|
+
).map((row) => [getRowId(row.original), true])
|
|
609
628
|
)
|
|
610
629
|
);
|
|
611
630
|
}
|
|
612
631
|
},
|
|
613
|
-
{
|
|
632
|
+
SELECT_NONE: {
|
|
614
633
|
key: "none",
|
|
615
634
|
text: t("dataTable.selectNone"),
|
|
616
635
|
onSelect: () => table.toggleAllPageRowsSelected(false)
|
|
617
636
|
}
|
|
618
|
-
|
|
619
|
-
const entries = rowSelection.selections === true ? builtIn : rowSelection.selections.map(
|
|
620
|
-
|
|
621
|
-
|
|
622
|
-
|
|
623
|
-
|
|
637
|
+
};
|
|
638
|
+
const entries = rowSelection.selections === true ? [builtIn.SELECT_ALL, builtIn.SELECT_INVERT, builtIn.SELECT_NONE] : rowSelection.selections.map(
|
|
639
|
+
(entry) => typeof entry === "string" ? builtIn[entry] : {
|
|
640
|
+
key: entry.key,
|
|
641
|
+
text: entry.text,
|
|
642
|
+
onSelect: () => entry.onSelect(pageKeys.length > 0 ? pageKeys : selectedKeys)
|
|
643
|
+
}
|
|
644
|
+
);
|
|
624
645
|
return /* @__PURE__ */ jsxs("span", { className: "ui-data-table-selection-menu", children: [
|
|
625
646
|
box,
|
|
626
647
|
/* @__PURE__ */ jsxs(DropdownMenu, { children: [
|
|
@@ -639,6 +660,9 @@ DataTable.SelectAll = function DataTableSelectAll() {
|
|
|
639
660
|
] });
|
|
640
661
|
};
|
|
641
662
|
DataTable.SelectAll.displayName = "DataTable.SelectAll";
|
|
663
|
+
DataTable.SELECTION_ALL = "SELECT_ALL";
|
|
664
|
+
DataTable.SELECTION_INVERT = "SELECT_INVERT";
|
|
665
|
+
DataTable.SELECTION_NONE = "SELECT_NONE";
|
|
642
666
|
DataTable.BulkActions = function DataTableBulkActions({
|
|
643
667
|
count,
|
|
644
668
|
children,
|
|
@@ -915,6 +939,13 @@ DataTable.Content = function DataTableContent() {
|
|
|
915
939
|
};
|
|
916
940
|
const dataRows = table.getRowModel().rows;
|
|
917
941
|
const rowCount = dataRows.length;
|
|
942
|
+
const matching = rowSelection?.type === "radio" ? void 0 : rowSelection?.matching;
|
|
943
|
+
const matchingOffered = !!matching && !matching.selected && rowCount > 0 && matching.total > rowCount && table.getIsAllPageRowsSelected();
|
|
944
|
+
const matchingShown = !!matching && (matching.selected || matchingOffered);
|
|
945
|
+
const clearMatching = () => {
|
|
946
|
+
if (dataRows.some((row) => row.getCanSelect())) table.toggleAllPageRowsSelected(false);
|
|
947
|
+
else matching?.onSelectedChange(false);
|
|
948
|
+
};
|
|
918
949
|
const scrollStyle = {};
|
|
919
950
|
const scrollVars = scrollStyle;
|
|
920
951
|
if (scroll?.x !== void 0) scrollVars["--table-scroll-inline-size"] = cssLength(scroll.x);
|
|
@@ -936,7 +967,7 @@ DataTable.Content = function DataTableContent() {
|
|
|
936
967
|
"data-scroll-y": scroll?.y !== void 0 ? "" : void 0,
|
|
937
968
|
"aria-busy": loading,
|
|
938
969
|
...scrolls ? { role: "group", "aria-label": scrollRegionLabel(label, t), tabIndex: 0 } : {},
|
|
939
|
-
children: /* @__PURE__ */
|
|
970
|
+
children: /* @__PURE__ */ jsxs(
|
|
940
971
|
"div",
|
|
941
972
|
{
|
|
942
973
|
className: "ui-data-table-surface",
|
|
@@ -944,386 +975,400 @@ DataTable.Content = function DataTableContent() {
|
|
|
944
975
|
"data-table-layout": fixedTableLayout ? "fixed" : void 0,
|
|
945
976
|
"data-striped": striped ? "" : void 0,
|
|
946
977
|
"data-hoverable": hoverable ? "" : void 0,
|
|
947
|
-
children:
|
|
948
|
-
|
|
949
|
-
|
|
950
|
-
|
|
951
|
-
|
|
952
|
-
|
|
953
|
-
|
|
954
|
-
|
|
955
|
-
|
|
956
|
-
|
|
957
|
-
|
|
958
|
-
|
|
959
|
-
|
|
960
|
-
|
|
961
|
-
|
|
962
|
-
|
|
963
|
-
|
|
964
|
-
|
|
965
|
-
|
|
966
|
-
|
|
967
|
-
|
|
968
|
-
|
|
969
|
-
|
|
970
|
-
|
|
971
|
-
|
|
972
|
-
|
|
973
|
-
),
|
|
974
|
-
|
|
975
|
-
|
|
976
|
-
|
|
977
|
-
className: cn(
|
|
978
|
-
"ui-data-table-select-column",
|
|
979
|
-
leadingFixed === "start" && "ui-data-table-pin-start"
|
|
980
|
-
),
|
|
981
|
-
...fixedCellProps("__select", leadingFixed),
|
|
982
|
-
style: leadingFixedStyle("__select"),
|
|
983
|
-
children: /* @__PURE__ */ jsx(DataTable.SelectAll, {})
|
|
984
|
-
}
|
|
985
|
-
),
|
|
986
|
-
visibleColumns.map((col) => {
|
|
987
|
-
const isSortable = columnIsSortable(col);
|
|
988
|
-
const activeDirection = directionOf(sortingState, col.key);
|
|
989
|
-
const sortIndicator = isSortable ? activeDirection ? activeDirection === "asc" ? /* @__PURE__ */ jsx(ArrowUp, { className: "ui-data-table-sort-icon", "aria-hidden": "true" }) : /* @__PURE__ */ jsx(ArrowDown, { className: "ui-data-table-sort-icon", "aria-hidden": "true" }) : /* @__PURE__ */ jsx(
|
|
990
|
-
ChevronsUpDown,
|
|
991
|
-
{
|
|
992
|
-
className: "ui-data-table-sort-icon text-muted-foreground",
|
|
993
|
-
"aria-hidden": "true"
|
|
994
|
-
}
|
|
995
|
-
) : null;
|
|
996
|
-
const headerEmpty = isEmptyHeader(col.header);
|
|
997
|
-
const headerContent = headerEmpty && col.ariaLabel ? /* @__PURE__ */ jsx("span", { className: "sr-only", children: col.ariaLabel }) : col.header;
|
|
998
|
-
const label2 = /* @__PURE__ */ jsxs("span", { className: "ui-data-table-sort-label", children: [
|
|
999
|
-
headerContent,
|
|
1000
|
-
sortIndicator
|
|
1001
|
-
] });
|
|
1002
|
-
const tooltipOn = col.showSorterTooltip ?? showSorterTooltip;
|
|
1003
|
-
const nextDirection = nextSortDirection(
|
|
1004
|
-
activeDirection,
|
|
1005
|
-
columnSortDirections(col, sortDirections)
|
|
1006
|
-
);
|
|
1007
|
-
const sortHint = nextDirection === "asc" ? t("dataTable.sortAscending") : nextDirection === "desc" ? t("dataTable.sortDescending") : t("dataTable.sortCancel");
|
|
1008
|
-
const sortButton = /* @__PURE__ */ jsx(
|
|
1009
|
-
"button",
|
|
978
|
+
children: [
|
|
979
|
+
matching ? /* @__PURE__ */ jsxs("div", { className: "ui-data-table-matching", "data-active": matchingShown ? "" : void 0, children: [
|
|
980
|
+
/* @__PURE__ */ jsx("span", { role: "status", children: matchingShown ? matching.selected ? t("dataTable.matchingSelected", { count: matching.total }) : t("dataTable.matchingPage", { count: rowCount }) : null }),
|
|
981
|
+
matchingShown ? /* @__PURE__ */ jsx(
|
|
982
|
+
Button,
|
|
983
|
+
{
|
|
984
|
+
variant: "link",
|
|
985
|
+
size: "sm",
|
|
986
|
+
onClick: matching.selected ? clearMatching : () => matching.onSelectedChange(true),
|
|
987
|
+
children: matching.selected ? t("dataTable.selectNone") : t("dataTable.matchingSelectAll", { count: matching.total })
|
|
988
|
+
}
|
|
989
|
+
) : null
|
|
990
|
+
] }) : null,
|
|
991
|
+
/* @__PURE__ */ jsxs(
|
|
992
|
+
Table,
|
|
993
|
+
{
|
|
994
|
+
scrollable: preset !== "default",
|
|
995
|
+
label,
|
|
996
|
+
preset,
|
|
997
|
+
collapseBelow,
|
|
998
|
+
bordered,
|
|
999
|
+
striped,
|
|
1000
|
+
children: [
|
|
1001
|
+
/* @__PURE__ */ jsx(
|
|
1002
|
+
TableHeader,
|
|
1003
|
+
{
|
|
1004
|
+
className: cn("bg-secondary", stickyHeader && "ui-data-table-sticky-header"),
|
|
1005
|
+
children: /* @__PURE__ */ jsxs(TableRow, { children: [
|
|
1006
|
+
expandColumnShown && /* @__PURE__ */ jsx(
|
|
1007
|
+
TableHead,
|
|
1010
1008
|
{
|
|
1011
|
-
|
|
1012
|
-
|
|
1013
|
-
|
|
1014
|
-
|
|
1015
|
-
|
|
1016
|
-
|
|
1009
|
+
className: cn(
|
|
1010
|
+
"ui-data-table-expand-column",
|
|
1011
|
+
leadingFixed === "start" && "ui-data-table-pin-start"
|
|
1012
|
+
),
|
|
1013
|
+
...fixedCellProps("__expand", leadingFixed),
|
|
1014
|
+
style: leadingFixedStyle("__expand"),
|
|
1015
|
+
children: /* @__PURE__ */ jsx("span", { className: "sr-only", children: expandable?.columnTitle ?? t("dataTable.expandColumn") })
|
|
1017
1016
|
}
|
|
1018
|
-
)
|
|
1019
|
-
|
|
1017
|
+
),
|
|
1018
|
+
selectable && /* @__PURE__ */ jsx(
|
|
1020
1019
|
TableHead,
|
|
1021
1020
|
{
|
|
1022
|
-
priority: col.priority,
|
|
1023
|
-
"data-empty": headerEmpty || void 0,
|
|
1024
|
-
"data-align": col.headerAlign ?? col.align,
|
|
1025
|
-
"aria-sort": isSortable ? activeDirection ? activeDirection === "asc" ? "ascending" : "descending" : "none" : void 0,
|
|
1026
|
-
...fixedCellProps(col.key, fixedEdge(col)),
|
|
1027
|
-
...columnHideBelowProps(col),
|
|
1028
|
-
style: columnCellStyle(col),
|
|
1029
1021
|
className: cn(
|
|
1030
|
-
|
|
1031
|
-
|
|
1032
|
-
// `align` otherwise. A table wanting centred headings
|
|
1033
|
-
// over start-aligned text could not say so before, and
|
|
1034
|
-
// consumers reached for `[&_th_button]:justify-center`.
|
|
1035
|
-
(col.headerAlign ?? col.align) === "right" && "text-end",
|
|
1036
|
-
(col.headerAlign ?? col.align) === "center" && "text-center",
|
|
1037
|
-
isSortable && "select-none"
|
|
1022
|
+
"ui-data-table-select-column",
|
|
1023
|
+
leadingFixed === "start" && "ui-data-table-pin-start"
|
|
1038
1024
|
),
|
|
1039
|
-
|
|
1040
|
-
|
|
1041
|
-
|
|
1042
|
-
|
|
1043
|
-
|
|
1044
|
-
|
|
1045
|
-
|
|
1046
|
-
|
|
1047
|
-
|
|
1048
|
-
|
|
1049
|
-
|
|
1050
|
-
|
|
1051
|
-
|
|
1052
|
-
|
|
1053
|
-
|
|
1054
|
-
|
|
1055
|
-
|
|
1056
|
-
|
|
1057
|
-
|
|
1058
|
-
|
|
1059
|
-
|
|
1060
|
-
|
|
1061
|
-
|
|
1025
|
+
...fixedCellProps("__select", leadingFixed),
|
|
1026
|
+
style: leadingFixedStyle("__select"),
|
|
1027
|
+
children: /* @__PURE__ */ jsx(DataTable.SelectAll, {})
|
|
1028
|
+
}
|
|
1029
|
+
),
|
|
1030
|
+
visibleColumns.map((col) => {
|
|
1031
|
+
const isSortable = columnIsSortable(col);
|
|
1032
|
+
const activeDirection = directionOf(sortingState, col.key);
|
|
1033
|
+
const sortIndicator = isSortable ? activeDirection ? activeDirection === "asc" ? /* @__PURE__ */ jsx(ArrowUp, { className: "ui-data-table-sort-icon", "aria-hidden": "true" }) : /* @__PURE__ */ jsx(ArrowDown, { className: "ui-data-table-sort-icon", "aria-hidden": "true" }) : /* @__PURE__ */ jsx(
|
|
1034
|
+
ChevronsUpDown,
|
|
1035
|
+
{
|
|
1036
|
+
className: "ui-data-table-sort-icon text-muted-foreground",
|
|
1037
|
+
"aria-hidden": "true"
|
|
1038
|
+
}
|
|
1039
|
+
) : null;
|
|
1040
|
+
const headerEmpty = isEmptyHeader(col.header);
|
|
1041
|
+
const headerContent = headerEmpty && col.ariaLabel ? /* @__PURE__ */ jsx("span", { className: "sr-only", children: col.ariaLabel }) : col.header;
|
|
1042
|
+
const label2 = /* @__PURE__ */ jsxs("span", { className: "ui-data-table-sort-label", children: [
|
|
1043
|
+
headerContent,
|
|
1044
|
+
sortIndicator
|
|
1045
|
+
] });
|
|
1046
|
+
const tooltipOn = col.showSorterTooltip ?? showSorterTooltip;
|
|
1047
|
+
const nextDirection = nextSortDirection(
|
|
1048
|
+
activeDirection,
|
|
1049
|
+
columnSortDirections(col, sortDirections)
|
|
1050
|
+
);
|
|
1051
|
+
const sortHint = nextDirection === "asc" ? t("dataTable.sortAscending") : nextDirection === "desc" ? t("dataTable.sortDescending") : t("dataTable.sortCancel");
|
|
1052
|
+
const sortButton = /* @__PURE__ */ jsx(
|
|
1053
|
+
"button",
|
|
1054
|
+
{
|
|
1055
|
+
type: "button",
|
|
1056
|
+
className: "ui-data-table-sort-button ui-focus-ring",
|
|
1057
|
+
onClick: () => {
|
|
1058
|
+
onHeaderClick(col);
|
|
1059
|
+
},
|
|
1060
|
+
children: label2
|
|
1061
|
+
}
|
|
1062
|
+
);
|
|
1063
|
+
return /* @__PURE__ */ jsxs(
|
|
1064
|
+
TableHead,
|
|
1065
|
+
{
|
|
1066
|
+
priority: col.priority,
|
|
1067
|
+
"data-empty": headerEmpty || void 0,
|
|
1068
|
+
"data-align": col.headerAlign ?? col.align,
|
|
1069
|
+
"aria-sort": isSortable ? activeDirection ? activeDirection === "asc" ? "ascending" : "descending" : "none" : void 0,
|
|
1070
|
+
...fixedCellProps(col.key, fixedEdge(col)),
|
|
1071
|
+
...columnHideBelowProps(col),
|
|
1072
|
+
style: columnCellStyle(col),
|
|
1073
|
+
className: cn(
|
|
1074
|
+
columnCellClass(col),
|
|
1075
|
+
// `headerAlign` when the heading differs from the rows,
|
|
1076
|
+
// `align` otherwise. A table wanting centred headings
|
|
1077
|
+
// over start-aligned text could not say so before, and
|
|
1078
|
+
// consumers reached for `[&_th_button]:justify-center`.
|
|
1079
|
+
(col.headerAlign ?? col.align) === "right" && "text-end",
|
|
1080
|
+
(col.headerAlign ?? col.align) === "center" && "text-center",
|
|
1081
|
+
isSortable && "select-none"
|
|
1082
|
+
),
|
|
1083
|
+
children: [
|
|
1084
|
+
isSortable ? tooltipOn ? /* @__PURE__ */ jsxs(Tooltip, { children: [
|
|
1085
|
+
/* @__PURE__ */ jsx(TooltipTrigger, { asChild: true, children: sortButton }),
|
|
1086
|
+
/* @__PURE__ */ jsx(TooltipContent, { children: sortHint })
|
|
1087
|
+
] }) : sortButton : label2,
|
|
1088
|
+
col.filters ? /* @__PURE__ */ jsx(ColumnFilterMenu, { column: col }) : null
|
|
1089
|
+
]
|
|
1090
|
+
},
|
|
1091
|
+
col.key
|
|
1092
|
+
);
|
|
1093
|
+
})
|
|
1094
|
+
] })
|
|
1095
|
+
}
|
|
1096
|
+
),
|
|
1097
|
+
/* @__PURE__ */ jsx(TableBody, { children: loading ? (
|
|
1098
|
+
// Shaped skeleton rows rendered INSIDE the real table grid so they
|
|
1099
|
+
// share its borders + column widths — no second framed container
|
|
1100
|
+
// (which double-borders when the table sits in a Card). Count is
|
|
1101
|
+
// bounded to the previous page so the height barely shifts.
|
|
1102
|
+
Array.from({ length: Math.min(Math.max(rowCount, 6), 10) }).map((_, i) => /* @__PURE__ */ jsxs(TableRow, { className: cn(rowPadding, "hover:bg-transparent"), children: [
|
|
1103
|
+
expandColumnShown && /* @__PURE__ */ jsx(TableCell, { className: cellPadding }),
|
|
1104
|
+
selectable && /* @__PURE__ */ jsx(TableCell, { className: cellPadding, children: /* @__PURE__ */ jsx("div", { className: "ui-skeleton-block ui-data-table-skeleton-check" }) }),
|
|
1105
|
+
visibleColumns.map((col, j) => /* @__PURE__ */ jsx(
|
|
1106
|
+
TableCell,
|
|
1107
|
+
{
|
|
1108
|
+
priority: col.priority,
|
|
1109
|
+
"data-align": col.align,
|
|
1110
|
+
...columnHideBelowProps(col),
|
|
1111
|
+
style: columnCellStyle(col),
|
|
1112
|
+
className: cn(cellPadding, columnCellClass(col)),
|
|
1113
|
+
children: /* @__PURE__ */ jsx(
|
|
1114
|
+
"div",
|
|
1115
|
+
{
|
|
1116
|
+
className: cn(
|
|
1117
|
+
"ui-skeleton-block ui-data-table-skeleton-line",
|
|
1118
|
+
j === 0 ? "w-1/2" : "w-3/4",
|
|
1119
|
+
col.align === "right" && "ms-auto",
|
|
1120
|
+
col.align === "center" && "mx-auto"
|
|
1121
|
+
)
|
|
1122
|
+
}
|
|
1123
|
+
)
|
|
1124
|
+
},
|
|
1125
|
+
col.key
|
|
1126
|
+
))
|
|
1127
|
+
] }, `skeleton-${i}`))
|
|
1128
|
+
) : isDenied ? (
|
|
1129
|
+
// repeating a 403 cannot succeed. `warning` (not destructive) keeps it a policy
|
|
1130
|
+
// statement rather than a system fault. Announced politely: a permission boundary
|
|
1131
|
+
// is expected information, not an interruption.
|
|
1132
|
+
/* @__PURE__ */ jsx(TableRow, { className: "hover:bg-transparent", children: /* @__PURE__ */ jsx(
|
|
1062
1133
|
TableCell,
|
|
1063
1134
|
{
|
|
1064
|
-
|
|
1065
|
-
"data-
|
|
1066
|
-
|
|
1067
|
-
|
|
1068
|
-
|
|
1069
|
-
children: /* @__PURE__ */ jsx(
|
|
1070
|
-
"div",
|
|
1135
|
+
colSpan: emptyColSpan,
|
|
1136
|
+
className: "ui-data-table-empty",
|
|
1137
|
+
"aria-live": "polite",
|
|
1138
|
+
children: denied === true ? /* @__PURE__ */ jsx(
|
|
1139
|
+
EmptyState,
|
|
1071
1140
|
{
|
|
1072
|
-
|
|
1073
|
-
|
|
1074
|
-
|
|
1075
|
-
|
|
1076
|
-
|
|
1077
|
-
)
|
|
1141
|
+
icon: ShieldAlert,
|
|
1142
|
+
tone: "warning",
|
|
1143
|
+
title: t("dataTable.denied"),
|
|
1144
|
+
description: t("dataTable.deniedDescription"),
|
|
1145
|
+
titleAs: "p"
|
|
1078
1146
|
}
|
|
1079
|
-
)
|
|
1080
|
-
}
|
|
1081
|
-
|
|
1082
|
-
|
|
1083
|
-
|
|
1084
|
-
|
|
1085
|
-
|
|
1086
|
-
|
|
1087
|
-
|
|
1088
|
-
|
|
1147
|
+
) : denied
|
|
1148
|
+
}
|
|
1149
|
+
) })
|
|
1150
|
+
) : isError ? (
|
|
1151
|
+
// Announced assertively (`role="alert"`) because the
|
|
1152
|
+
// user's request did not complete — unlike empty/denied, which are states of the data
|
|
1153
|
+
// itself. The role sits on an inner wrapper, never on the <td>: overriding a cell's
|
|
1154
|
+
// role would strip it out of the table's grid semantics for AT.
|
|
1155
|
+
/* @__PURE__ */ jsx(TableRow, { className: "hover:bg-transparent", children: /* @__PURE__ */ jsx(TableCell, { colSpan: emptyColSpan, className: "ui-data-table-empty", children: /* @__PURE__ */ jsx("div", { role: "alert", children: error === true ? /* @__PURE__ */ jsx(
|
|
1156
|
+
EmptyState,
|
|
1157
|
+
{
|
|
1158
|
+
icon: AlertCircle,
|
|
1159
|
+
tone: "destructive",
|
|
1160
|
+
title: t("dataTable.error"),
|
|
1161
|
+
description: t("dataTable.errorDescription"),
|
|
1162
|
+
titleAs: "p",
|
|
1163
|
+
action: onRetry ? /* @__PURE__ */ jsxs(Button, { variant: "outline", size: "sm", onClick: onRetry, children: [
|
|
1164
|
+
/* @__PURE__ */ jsx(RefreshCw, { "aria-hidden": "true" }),
|
|
1165
|
+
t("common.retry")
|
|
1166
|
+
] }) : void 0
|
|
1167
|
+
}
|
|
1168
|
+
) : error }) }) })
|
|
1169
|
+
) : rowCount === 0 ? /* @__PURE__ */ jsx(TableRow, { className: "hover:bg-transparent", children: /* @__PURE__ */ jsx(
|
|
1089
1170
|
TableCell,
|
|
1090
1171
|
{
|
|
1091
1172
|
colSpan: emptyColSpan,
|
|
1092
1173
|
className: "ui-data-table-empty",
|
|
1093
1174
|
"aria-live": "polite",
|
|
1094
|
-
children:
|
|
1095
|
-
EmptyState,
|
|
1096
|
-
{
|
|
1097
|
-
icon: ShieldAlert,
|
|
1098
|
-
tone: "warning",
|
|
1099
|
-
title: t("dataTable.denied"),
|
|
1100
|
-
description: t("dataTable.deniedDescription"),
|
|
1101
|
-
titleAs: "p"
|
|
1102
|
-
}
|
|
1103
|
-
) : denied
|
|
1175
|
+
children: empty ?? /* @__PURE__ */ jsx(EmptyState, { title: t("dataTable.empty"), titleAs: "p" })
|
|
1104
1176
|
}
|
|
1105
|
-
) })
|
|
1106
|
-
|
|
1107
|
-
|
|
1108
|
-
|
|
1109
|
-
|
|
1110
|
-
|
|
1111
|
-
|
|
1112
|
-
|
|
1113
|
-
|
|
1114
|
-
|
|
1115
|
-
|
|
1116
|
-
|
|
1117
|
-
|
|
1118
|
-
|
|
1119
|
-
|
|
1120
|
-
|
|
1121
|
-
|
|
1122
|
-
|
|
1123
|
-
|
|
1124
|
-
|
|
1125
|
-
|
|
1126
|
-
|
|
1127
|
-
|
|
1128
|
-
|
|
1129
|
-
|
|
1130
|
-
|
|
1131
|
-
|
|
1132
|
-
|
|
1133
|
-
|
|
1134
|
-
|
|
1135
|
-
|
|
1136
|
-
|
|
1137
|
-
|
|
1138
|
-
|
|
1139
|
-
|
|
1140
|
-
|
|
1141
|
-
|
|
1142
|
-
|
|
1143
|
-
|
|
1144
|
-
|
|
1145
|
-
|
|
1146
|
-
|
|
1147
|
-
|
|
1148
|
-
|
|
1149
|
-
|
|
1150
|
-
|
|
1151
|
-
|
|
1152
|
-
|
|
1153
|
-
|
|
1154
|
-
|
|
1155
|
-
|
|
1156
|
-
|
|
1157
|
-
|
|
1158
|
-
|
|
1159
|
-
|
|
1160
|
-
|
|
1161
|
-
|
|
1162
|
-
|
|
1163
|
-
|
|
1164
|
-
rowProps.onKeyDown?.(e);
|
|
1165
|
-
if (e.key !== "Enter" && e.key !== " ") return;
|
|
1166
|
-
if (e.target !== e.currentTarget) return;
|
|
1167
|
-
e.preventDefault();
|
|
1168
|
-
onRowClick?.(original);
|
|
1169
|
-
} : rowProps.onKeyDown,
|
|
1170
|
-
className: cn(
|
|
1171
|
-
rowPadding,
|
|
1172
|
-
// Hover highlight when rows are clickable OR explicitly hoverable… The
|
|
1173
|
-
// --accent step TableRow itself uses, not --muted/50: that sat BELOW the
|
|
1174
|
-
// zebra stripe (--muted/0.8, gh#700), so hovering a striped row lightened it.
|
|
1175
|
-
// Same token-driven formula as TableRow's own hover fill (gh#894) — a bare
|
|
1176
|
-
// `/70` here would silently outrank a theme's retuned default at equal
|
|
1177
|
-
// specificity, and `color-mix` (not `hsl(x / var(y, 70%))`) because a `/`
|
|
1178
|
-
// inside a Tailwind arbitrary property is read as ITS OWN opacity suffix.
|
|
1179
|
-
(onRowClick || hoverable) && "hover:[background-color:color-mix(in_oklab,hsl(var(--accent))_var(--table-row-hover-background-alpha,70%),transparent)]",
|
|
1180
|
-
// …but the affordance (cursor + focus mark) only when clickable.
|
|
1181
|
-
//
|
|
1182
|
-
// `ui-focus-ring` = the single focus source (styles/focus-ring.css). It
|
|
1183
|
-
// replaces `focus-visible:ring-ring focus-visible:ring-2
|
|
1184
|
-
// focus-visible:ring-inset`, which was a hand-rolled second ring: it read no
|
|
1185
|
-
// `--focus-ring-*` knob, so a service could not retune it, and — being a
|
|
1186
|
-
// utility — it painted regardless of the `--focus-outline` switch, which is
|
|
1187
|
-
// exactly the hole the switch exists to close.
|
|
1188
|
-
onRowClick && "ui-focus-ring cursor-pointer",
|
|
1189
|
-
isSelected && "bg-muted/30",
|
|
1190
|
-
rowProps.className,
|
|
1191
|
-
rowClassName?.(original)
|
|
1192
|
-
),
|
|
1193
|
-
children: [
|
|
1194
|
-
expandColumnShown && /* @__PURE__ */ jsx(
|
|
1195
|
-
TableCell,
|
|
1196
|
-
{
|
|
1197
|
-
className: cn(
|
|
1198
|
-
cellPadding,
|
|
1199
|
-
leadingFixed === "start" && "ui-data-table-pin-start"
|
|
1200
|
-
),
|
|
1201
|
-
...fixedCellProps("__expand", leadingFixed),
|
|
1202
|
-
style: leadingFixedStyle("__expand"),
|
|
1203
|
-
children: canExpand ? /* @__PURE__ */ jsx(
|
|
1204
|
-
Button,
|
|
1205
|
-
{
|
|
1206
|
-
variant: "ghost",
|
|
1207
|
-
size: "icon-xs",
|
|
1208
|
-
"aria-expanded": isExpanded,
|
|
1209
|
-
"aria-label": isExpanded ? t("dataTable.collapseRow") : t("dataTable.expandRow"),
|
|
1210
|
-
className: "ui-data-table-expand-trigger",
|
|
1211
|
-
onClick: (e) => {
|
|
1212
|
-
e.stopPropagation();
|
|
1213
|
-
toggleExpanded(rowKey);
|
|
1214
|
-
},
|
|
1215
|
-
children: isExpanded ? /* @__PURE__ */ jsx(
|
|
1216
|
-
ChevronDown,
|
|
1217
|
-
{
|
|
1218
|
-
className: "ui-data-table-sort-icon",
|
|
1219
|
-
"aria-hidden": "true"
|
|
1220
|
-
}
|
|
1221
|
-
) : /* @__PURE__ */ jsx(
|
|
1222
|
-
ChevronRight,
|
|
1223
|
-
{
|
|
1224
|
-
className: "ui-data-table-sort-icon",
|
|
1225
|
-
"aria-hidden": "true"
|
|
1226
|
-
}
|
|
1227
|
-
)
|
|
1228
|
-
}
|
|
1229
|
-
) : null
|
|
1230
|
-
}
|
|
1177
|
+
) }) : dataRows.map((row, rowIndex) => {
|
|
1178
|
+
const original = row.original;
|
|
1179
|
+
const rowKey = getRowId(original);
|
|
1180
|
+
const isSelected = row.getIsSelected();
|
|
1181
|
+
const checkboxProps = rowSelection?.getCheckboxProps?.(original) ?? {};
|
|
1182
|
+
const labelValue = selectLabelColumn ? original[selectLabelColumn.key] : void 0;
|
|
1183
|
+
const rowLabel = getRowLabel?.(original) ?? (typeof labelValue === "string" && labelValue.trim() !== "" || typeof labelValue === "number" ? String(labelValue) : row.id);
|
|
1184
|
+
const selectRowLabel = checkboxProps["aria-label"] ?? t("dataTable.selectRow", { id: rowLabel });
|
|
1185
|
+
const canExpand = expandColumnShown && (expandable?.rowExpandable?.(original) ?? true);
|
|
1186
|
+
const isExpanded = canExpand && expandedKeys.includes(rowKey);
|
|
1187
|
+
const rowProps = onRow?.(original, rowIndex) ?? {};
|
|
1188
|
+
const isInteractiveTarget = (target) => !!target.closest(
|
|
1189
|
+
"button, a, input, select, textarea, [role=menuitem], [role=checkbox], [role=radio]"
|
|
1190
|
+
);
|
|
1191
|
+
const expandByClick = canExpand && expandable?.expandRowByClick;
|
|
1192
|
+
return /* @__PURE__ */ jsxs(React.Fragment, { children: [
|
|
1193
|
+
/* @__PURE__ */ jsxs(
|
|
1194
|
+
TableRow,
|
|
1195
|
+
{
|
|
1196
|
+
...rowProps,
|
|
1197
|
+
"data-state": isSelected ? "selected" : void 0,
|
|
1198
|
+
"data-tone": rowTone?.(original),
|
|
1199
|
+
tabIndex: onRowClick ? 0 : rowProps.tabIndex,
|
|
1200
|
+
onClick: (e) => {
|
|
1201
|
+
rowProps.onClick?.(e);
|
|
1202
|
+
const target = e.target;
|
|
1203
|
+
if (isInteractiveTarget(target)) return;
|
|
1204
|
+
if (expandByClick) toggleExpanded(rowKey);
|
|
1205
|
+
onRowClick?.(original);
|
|
1206
|
+
},
|
|
1207
|
+
onKeyDown: onRowClick ? (e) => {
|
|
1208
|
+
rowProps.onKeyDown?.(e);
|
|
1209
|
+
if (e.key !== "Enter" && e.key !== " ") return;
|
|
1210
|
+
if (e.target !== e.currentTarget) return;
|
|
1211
|
+
e.preventDefault();
|
|
1212
|
+
onRowClick?.(original);
|
|
1213
|
+
} : rowProps.onKeyDown,
|
|
1214
|
+
className: cn(
|
|
1215
|
+
rowPadding,
|
|
1216
|
+
// Hover highlight when rows are clickable OR explicitly hoverable… The
|
|
1217
|
+
// --accent step TableRow itself uses, not --muted/50: that sat BELOW the
|
|
1218
|
+
// zebra stripe (--muted/0.8, gh#700), so hovering a striped row lightened it.
|
|
1219
|
+
// Same token-driven formula as TableRow's own hover fill (gh#894) — a bare
|
|
1220
|
+
// `/70` here would silently outrank a theme's retuned default at equal
|
|
1221
|
+
// specificity, and `color-mix` (not `hsl(x / var(y, 70%))`) because a `/`
|
|
1222
|
+
// inside a Tailwind arbitrary property is read as ITS OWN opacity suffix.
|
|
1223
|
+
(onRowClick || hoverable) && "hover:[background-color:color-mix(in_oklab,hsl(var(--accent))_var(--table-row-hover-background-alpha,70%),transparent)]",
|
|
1224
|
+
// …but the affordance (cursor + focus mark) only when clickable.
|
|
1225
|
+
//
|
|
1226
|
+
// `ui-focus-ring` = the single focus source (styles/focus-ring.css). It
|
|
1227
|
+
// replaces `focus-visible:ring-ring focus-visible:ring-2
|
|
1228
|
+
// focus-visible:ring-inset`, which was a hand-rolled second ring: it read no
|
|
1229
|
+
// `--focus-ring-*` knob, so a service could not retune it, and — being a
|
|
1230
|
+
// utility — it painted regardless of the `--focus-outline` switch, which is
|
|
1231
|
+
// exactly the hole the switch exists to close.
|
|
1232
|
+
onRowClick && "ui-focus-ring cursor-pointer",
|
|
1233
|
+
isSelected && "bg-muted/30",
|
|
1234
|
+
rowProps.className,
|
|
1235
|
+
rowClassName?.(original)
|
|
1231
1236
|
),
|
|
1232
|
-
|
|
1233
|
-
|
|
1234
|
-
|
|
1235
|
-
|
|
1236
|
-
|
|
1237
|
-
|
|
1238
|
-
|
|
1239
|
-
|
|
1240
|
-
|
|
1241
|
-
|
|
1242
|
-
|
|
1243
|
-
|
|
1244
|
-
// <tr> boundaries without rewriting the table's own semantics.
|
|
1245
|
-
/* @__PURE__ */ jsx(
|
|
1246
|
-
RadioGroupRoot,
|
|
1237
|
+
children: [
|
|
1238
|
+
expandColumnShown && /* @__PURE__ */ jsx(
|
|
1239
|
+
TableCell,
|
|
1240
|
+
{
|
|
1241
|
+
className: cn(
|
|
1242
|
+
cellPadding,
|
|
1243
|
+
leadingFixed === "start" && "ui-data-table-pin-start"
|
|
1244
|
+
),
|
|
1245
|
+
...fixedCellProps("__expand", leadingFixed),
|
|
1246
|
+
style: leadingFixedStyle("__expand"),
|
|
1247
|
+
children: canExpand ? /* @__PURE__ */ jsx(
|
|
1248
|
+
Button,
|
|
1247
1249
|
{
|
|
1248
|
-
|
|
1249
|
-
|
|
1250
|
-
|
|
1251
|
-
|
|
1250
|
+
variant: "ghost",
|
|
1251
|
+
size: "icon-xs",
|
|
1252
|
+
"aria-expanded": isExpanded,
|
|
1253
|
+
"aria-label": isExpanded ? t("dataTable.collapseRow") : t("dataTable.expandRow"),
|
|
1254
|
+
className: "ui-data-table-expand-trigger",
|
|
1255
|
+
onClick: (e) => {
|
|
1256
|
+
e.stopPropagation();
|
|
1257
|
+
toggleExpanded(rowKey);
|
|
1252
1258
|
},
|
|
1253
|
-
children: /* @__PURE__ */ jsx(
|
|
1254
|
-
|
|
1259
|
+
children: isExpanded ? /* @__PURE__ */ jsx(
|
|
1260
|
+
ChevronDown,
|
|
1255
1261
|
{
|
|
1256
|
-
|
|
1257
|
-
"aria-
|
|
1258
|
-
|
|
1259
|
-
|
|
1260
|
-
|
|
1262
|
+
className: "ui-data-table-sort-icon",
|
|
1263
|
+
"aria-hidden": "true"
|
|
1264
|
+
}
|
|
1265
|
+
) : /* @__PURE__ */ jsx(
|
|
1266
|
+
ChevronRight,
|
|
1267
|
+
{
|
|
1268
|
+
className: "ui-data-table-sort-icon",
|
|
1269
|
+
"aria-hidden": "true"
|
|
1261
1270
|
}
|
|
1262
1271
|
)
|
|
1263
1272
|
}
|
|
1264
|
-
)
|
|
1265
|
-
|
|
1266
|
-
|
|
1267
|
-
|
|
1268
|
-
checked: isSelected,
|
|
1269
|
-
disabled: checkboxProps.disabled,
|
|
1270
|
-
onCheckedChange: (v) => {
|
|
1271
|
-
row.toggleSelected(!!v);
|
|
1272
|
-
},
|
|
1273
|
-
"aria-label": selectRowLabel,
|
|
1274
|
-
onClick: (e) => {
|
|
1275
|
-
e.stopPropagation();
|
|
1276
|
-
}
|
|
1277
|
-
}
|
|
1278
|
-
)
|
|
1279
|
-
}
|
|
1280
|
-
),
|
|
1281
|
-
visibleColumns.map((col) => {
|
|
1282
|
-
const rendered = col.render ? col.render(original) : (() => {
|
|
1283
|
-
const v = original[col.key];
|
|
1284
|
-
const text = v == null || !(typeof v === "string" || typeof v === "number") ? "\u2014" : String(v);
|
|
1285
|
-
return /* @__PURE__ */ jsx("span", { "data-slot": "table-cell-text", children: text });
|
|
1286
|
-
})();
|
|
1287
|
-
const rawValue = original[col.key];
|
|
1288
|
-
const title = col.ellipsis && !col.render && (typeof rawValue === "string" || typeof rawValue === "number") ? String(rawValue) : void 0;
|
|
1289
|
-
return /* @__PURE__ */ jsx(
|
|
1273
|
+
) : null
|
|
1274
|
+
}
|
|
1275
|
+
),
|
|
1276
|
+
selectable && /* @__PURE__ */ jsx(
|
|
1290
1277
|
TableCell,
|
|
1291
1278
|
{
|
|
1292
|
-
|
|
1293
|
-
|
|
1294
|
-
|
|
1295
|
-
|
|
1296
|
-
...fixedCellProps(
|
|
1297
|
-
|
|
1298
|
-
|
|
1299
|
-
|
|
1300
|
-
|
|
1301
|
-
|
|
1302
|
-
|
|
1303
|
-
|
|
1304
|
-
|
|
1305
|
-
|
|
1306
|
-
|
|
1307
|
-
|
|
1308
|
-
|
|
1309
|
-
|
|
1310
|
-
|
|
1311
|
-
|
|
1312
|
-
|
|
1313
|
-
|
|
1314
|
-
|
|
1315
|
-
|
|
1316
|
-
|
|
1317
|
-
|
|
1318
|
-
|
|
1319
|
-
|
|
1320
|
-
|
|
1321
|
-
|
|
1322
|
-
|
|
1323
|
-
|
|
1324
|
-
|
|
1325
|
-
|
|
1326
|
-
|
|
1279
|
+
className: cn(
|
|
1280
|
+
cellPadding,
|
|
1281
|
+
leadingFixed === "start" && "ui-data-table-pin-start"
|
|
1282
|
+
),
|
|
1283
|
+
...fixedCellProps("__select", leadingFixed),
|
|
1284
|
+
style: leadingFixedStyle("__select"),
|
|
1285
|
+
children: rowSelection?.type === "radio" ? (
|
|
1286
|
+
// One choice per table, so each cell is its own single-item group:
|
|
1287
|
+
// Radix requires a Root for an Item, and a Root cannot legally span
|
|
1288
|
+
// <tr> boundaries without rewriting the table's own semantics.
|
|
1289
|
+
/* @__PURE__ */ jsx(
|
|
1290
|
+
RadioGroupRoot,
|
|
1291
|
+
{
|
|
1292
|
+
value: isSelected ? rowKey : "",
|
|
1293
|
+
disabled: checkboxProps.disabled,
|
|
1294
|
+
onValueChange: () => {
|
|
1295
|
+
row.toggleSelected(true);
|
|
1296
|
+
},
|
|
1297
|
+
children: /* @__PURE__ */ jsx(
|
|
1298
|
+
RadioItem,
|
|
1299
|
+
{
|
|
1300
|
+
value: rowKey,
|
|
1301
|
+
"aria-label": selectRowLabel,
|
|
1302
|
+
onClick: (e) => {
|
|
1303
|
+
e.stopPropagation();
|
|
1304
|
+
}
|
|
1305
|
+
}
|
|
1306
|
+
)
|
|
1307
|
+
}
|
|
1308
|
+
)
|
|
1309
|
+
) : /* @__PURE__ */ jsx(
|
|
1310
|
+
Checkbox,
|
|
1311
|
+
{
|
|
1312
|
+
checked: isSelected,
|
|
1313
|
+
disabled: checkboxProps.disabled,
|
|
1314
|
+
onCheckedChange: (v) => {
|
|
1315
|
+
row.toggleSelected(!!v);
|
|
1316
|
+
},
|
|
1317
|
+
"aria-label": selectRowLabel,
|
|
1318
|
+
onClick: (e) => {
|
|
1319
|
+
e.stopPropagation();
|
|
1320
|
+
}
|
|
1321
|
+
}
|
|
1322
|
+
)
|
|
1323
|
+
}
|
|
1324
|
+
),
|
|
1325
|
+
visibleColumns.map((col) => {
|
|
1326
|
+
const rendered = col.render ? col.render(original) : (() => {
|
|
1327
|
+
const v = original[col.key];
|
|
1328
|
+
const text = v == null || !(typeof v === "string" || typeof v === "number") ? "\u2014" : String(v);
|
|
1329
|
+
return /* @__PURE__ */ jsx("span", { "data-slot": "table-cell-text", children: text });
|
|
1330
|
+
})();
|
|
1331
|
+
const rawValue = original[col.key];
|
|
1332
|
+
const title = col.ellipsis && !col.render && (typeof rawValue === "string" || typeof rawValue === "number") ? String(rawValue) : void 0;
|
|
1333
|
+
return /* @__PURE__ */ jsx(
|
|
1334
|
+
TableCell,
|
|
1335
|
+
{
|
|
1336
|
+
priority: col.priority,
|
|
1337
|
+
"data-align": col.align,
|
|
1338
|
+
title,
|
|
1339
|
+
label: stacked ? stackedCellLabel(col) : void 0,
|
|
1340
|
+
...fixedCellProps(col.key, fixedEdge(col)),
|
|
1341
|
+
...columnHideBelowProps(col),
|
|
1342
|
+
style: columnCellStyle(col),
|
|
1343
|
+
flush: col.flush,
|
|
1344
|
+
className: cn(!col.flush && cellPadding, columnCellClass(col)),
|
|
1345
|
+
children: rendered
|
|
1346
|
+
},
|
|
1347
|
+
col.key
|
|
1348
|
+
);
|
|
1349
|
+
})
|
|
1350
|
+
]
|
|
1351
|
+
}
|
|
1352
|
+
),
|
|
1353
|
+
isExpanded && expandable?.expandedRowRender ? /* @__PURE__ */ jsx(
|
|
1354
|
+
TableRow,
|
|
1355
|
+
{
|
|
1356
|
+
className: "ui-data-table-expanded-row hover:bg-transparent",
|
|
1357
|
+
"data-expanded-row": "",
|
|
1358
|
+
children: /* @__PURE__ */ jsx(TableCell, { colSpan: emptyColSpan, flush: true, children: expandable.expandedRowRender(original, rowIndex, true) })
|
|
1359
|
+
}
|
|
1360
|
+
) : null
|
|
1361
|
+
] }, row.id);
|
|
1362
|
+
}) }),
|
|
1363
|
+
summary ? (
|
|
1364
|
+
// A real <tfoot>: the totals row belongs to the table's own grid, so it keeps the
|
|
1365
|
+
// column widths, the header association and the screen-reader row navigation.
|
|
1366
|
+
/* @__PURE__ */ jsx("tfoot", { "data-slot": "table-footer", className: "ui-data-table-summary", children: summary(dataRows.map((row) => row.original)) })
|
|
1367
|
+
) : null
|
|
1368
|
+
]
|
|
1369
|
+
}
|
|
1370
|
+
)
|
|
1371
|
+
]
|
|
1327
1372
|
}
|
|
1328
1373
|
)
|
|
1329
1374
|
}
|