@devalok/shilp-sutra 0.44.1 → 0.45.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/AGENTS.md +13 -11
- package/BREAKING.json +209 -27
- package/MIGRATION.md +34 -0
- package/README.md +12 -0
- package/dist/_chunks/badge-group.js +1 -0
- package/dist/_chunks/badge-group.js.map +1 -1
- package/dist/_chunks/block-shell.js +25 -0
- package/dist/_chunks/block-shell.js.map +1 -0
- package/dist/_chunks/chat.js +4 -2
- package/dist/_chunks/chat.js.map +1 -1
- package/dist/_chunks/document-preview.js +1 -1
- package/dist/_chunks/image-preview.js +4 -4
- package/dist/_chunks/shared.js +65 -78
- package/dist/_chunks/shared.js.map +1 -1
- package/dist/_chunks/success.js +108 -106
- package/dist/_chunks/success.js.map +1 -1
- package/dist/ai/blocks/block-shell.d.ts +19 -0
- package/dist/ai/blocks/block-shell.d.ts.map +1 -0
- package/dist/ai/blocks/block-table.d.ts.map +1 -1
- package/dist/ai/blocks/confirm.d.ts.map +1 -1
- package/dist/ai/blocks/error.d.ts.map +1 -1
- package/dist/ai/blocks/error.js +5 -5
- package/dist/ai/blocks/error.js.map +1 -1
- package/dist/ai/blocks/success.d.ts.map +1 -1
- package/dist/ai/blocks/text.d.ts.map +1 -1
- package/dist/ai/blocks/text.js +4 -3
- package/dist/ai/blocks/text.js.map +1 -1
- package/dist/composed/activity-feed.d.ts.map +1 -1
- package/dist/composed/activity-feed.js +14 -12
- package/dist/composed/activity-feed.js.map +1 -1
- package/dist/composed/file-preview/audio-preview.d.ts.map +1 -1
- package/dist/composed/file-preview/shared.d.ts +10 -0
- package/dist/composed/file-preview/shared.d.ts.map +1 -1
- package/dist/composed/file-preview/video-preview.d.ts.map +1 -1
- package/dist/composed/file-preview.js +149 -188
- package/dist/composed/file-preview.js.map +1 -1
- package/dist/composed/master-detail.d.ts.map +1 -1
- package/dist/composed/master-detail.js +13 -4
- package/dist/composed/master-detail.js.map +1 -1
- package/dist/composed/schedule-view.d.ts.map +1 -1
- package/dist/composed/schedule-view.js +52 -39
- package/dist/composed/schedule-view.js.map +1 -1
- package/dist/shell/notification-preferences.d.ts.map +1 -1
- package/dist/shell/notification-preferences.js +115 -114
- package/dist/shell/notification-preferences.js.map +1 -1
- package/dist/ui/badge-group.d.ts.map +1 -1
- package/dist/ui/card.d.ts +66 -16
- package/dist/ui/card.d.ts.map +1 -1
- package/dist/ui/card.js +85 -60
- package/dist/ui/card.js.map +1 -1
- package/dist/ui/chat/message.d.ts.map +1 -1
- package/dist/ui/color-input.d.ts.map +1 -1
- package/dist/ui/color-input.js +18 -18
- package/dist/ui/color-input.js.map +1 -1
- package/dist/ui/data-table-body.d.ts.map +1 -1
- package/dist/ui/data-table-body.js +94 -64
- package/dist/ui/data-table-body.js.map +1 -1
- package/dist/ui/data-table-card.d.ts.map +1 -1
- package/dist/ui/data-table-card.js +50 -43
- package/dist/ui/data-table-card.js.map +1 -1
- package/dist/ui/data-table-context.d.ts +0 -4
- package/dist/ui/data-table-context.d.ts.map +1 -1
- package/dist/ui/data-table-context.js +8 -12
- package/dist/ui/data-table-context.js.map +1 -1
- package/dist/ui/data-table-header.d.ts.map +1 -1
- package/dist/ui/data-table-header.js +2 -2
- package/dist/ui/data-table-header.js.map +1 -1
- package/dist/ui/data-table.d.ts.map +1 -1
- package/dist/ui/data-table.js +185 -182
- package/dist/ui/data-table.js.map +1 -1
- package/dist/ui/index.d.ts +3 -2
- package/dist/ui/index.d.ts.map +1 -1
- package/dist/ui/index.js +59 -58
- package/dist/ui/index.js.map +1 -1
- package/dist/ui/segmented-control.js +4 -4
- package/dist/ui/segmented-control.js.map +1 -1
- package/dist/ui/separator.d.ts +6 -5
- package/dist/ui/separator.d.ts.map +1 -1
- package/dist/ui/separator.js +7 -10
- package/dist/ui/separator.js.map +1 -1
- package/dist/ui/split-button.d.ts.map +1 -1
- package/dist/ui/split-button.js +62 -129
- package/dist/ui/split-button.js.map +1 -1
- package/dist/ui/stat-card.d.ts +7 -0
- package/dist/ui/stat-card.d.ts.map +1 -1
- package/dist/ui/stat-card.js +144 -126
- package/dist/ui/stat-card.js.map +1 -1
- package/dist/ui/table-row-link.d.ts +45 -0
- package/dist/ui/table-row-link.d.ts.map +1 -0
- package/dist/ui/table-row-link.js +16 -0
- package/dist/ui/table-row-link.js.map +1 -0
- package/dist/ui/table.d.ts +49 -5
- package/dist/ui/table.d.ts.map +1 -1
- package/dist/ui/table.js +39 -29
- package/dist/ui/table.js.map +1 -1
- package/dist/ui/toast-types.d.ts +10 -0
- package/dist/ui/toast-types.d.ts.map +1 -1
- package/dist/ui/toast.d.ts +6 -2
- package/dist/ui/toast.d.ts.map +1 -1
- package/dist/ui/toast.js +56 -54
- package/dist/ui/toast.js.map +1 -1
- package/docs/components/composed/content-card.md +2 -0
- package/docs/components/ui/button.md +3 -3
- package/docs/components/ui/card.md +27 -10
- package/docs/components/ui/color-input.md +2 -2
- package/docs/components/ui/data-table.md +8 -1
- package/docs/components/ui/segmented-control.md +2 -2
- package/docs/components/ui/separator.md +3 -1
- package/docs/components/ui/split-button.md +3 -0
- package/docs/components/ui/stat-card.md +10 -2
- package/docs/components/ui/table-row-link.md +41 -0
- package/docs/components/ui/table.md +69 -0
- package/docs/components/ui/toast.md +10 -6
- package/docs/recipes/install-next-app-router.md +1 -1
- package/docs/recipes/troubleshoot.md +1 -1
- package/llms.txt +159 -781
- package/make-kit/components/card.md +54 -16
- package/make-kit/components/table.md +45 -7
- package/make-kit/foundations/spacing.md +3 -1
- package/make-kit/foundations/surfaces.md +1 -1
- package/mcp-manifest.json +12349 -0
- package/mcp-manifest.schema.json +232 -0
- package/package.json +3 -3
- package/skill/README.md +0 -1
- package/skill/SKILL.md +9 -8
- package/skill/references/components.md +159 -781
- package/skill/references/setup-next-app-router.md +1 -1
- package/skill/references/troubleshoot.md +1 -1
- package/llms-full.txt +0 -7198
- package/llms-quick.txt +0 -251
- package/skill/references/components-full.md +0 -7200
|
@@ -1,21 +1,23 @@
|
|
|
1
1
|
"use client";
|
|
2
|
-
import {
|
|
3
|
-
import {
|
|
4
|
-
import {
|
|
5
|
-
import {
|
|
6
|
-
import
|
|
7
|
-
import {
|
|
8
|
-
import {
|
|
2
|
+
import { springs as e } from "./lib/motion.js";
|
|
3
|
+
import { cn as t } from "./lib/utils.js";
|
|
4
|
+
import { getColumnMetaClasses as n, getPinnedCellStyle as r, isColumnEditable as i, useDataTableContext as a } from "./data-table-context.js";
|
|
5
|
+
import { Skeleton as o } from "./skeleton.js";
|
|
6
|
+
import { TableBody as s, TableCell as c, TableRow as l } from "./table.js";
|
|
7
|
+
import u, { useCallback as d, useEffect as f, useRef as p, useState as m } from "react";
|
|
8
|
+
import { jsx as h, jsxs as g } from "react/jsx-runtime";
|
|
9
|
+
import { AnimatePresence as _, motion as v, useReducedMotion as y } from "framer-motion";
|
|
10
|
+
import { flexRender as b } from "@tanstack/react-table";
|
|
9
11
|
//#region src/ui/data-table-body.tsx
|
|
10
|
-
function
|
|
11
|
-
let [i, a] =
|
|
12
|
-
|
|
12
|
+
function x({ initialValue: e, onSave: n, onCancel: r }) {
|
|
13
|
+
let [i, a] = m(e), o = p(null);
|
|
14
|
+
f(() => {
|
|
13
15
|
o.current?.focus(), o.current?.select();
|
|
14
16
|
}, []);
|
|
15
|
-
let s =
|
|
17
|
+
let s = d(() => {
|
|
16
18
|
n(i);
|
|
17
19
|
}, [n, i]);
|
|
18
|
-
return /* @__PURE__ */
|
|
20
|
+
return /* @__PURE__ */ h("input", {
|
|
19
21
|
ref: o,
|
|
20
22
|
type: "text",
|
|
21
23
|
value: i,
|
|
@@ -24,83 +26,111 @@ function _({ initialValue: t, onSave: n, onCancel: r }) {
|
|
|
24
26
|
onKeyDown: (e) => {
|
|
25
27
|
e.key === "Enter" ? (e.preventDefault(), s()) : e.key === "Escape" && (e.preventDefault(), r());
|
|
26
28
|
},
|
|
27
|
-
className:
|
|
29
|
+
className: t("h-ds-xs-plus w-full rounded-control", "border border-accent-7 bg-surface-raised-hover", "px-ds-02 text-ds-sm", "text-surface-fg placeholder:text-surface-fg-subtle", "outline-hidden focus:border-accent-7"),
|
|
28
30
|
"aria-label": "Edit cell value"
|
|
29
31
|
});
|
|
30
32
|
}
|
|
31
|
-
function
|
|
32
|
-
let { table:
|
|
33
|
-
|
|
34
|
-
}, [
|
|
35
|
-
return /* @__PURE__ */
|
|
36
|
-
"data-state":
|
|
33
|
+
function S({ row: e, style: o }) {
|
|
34
|
+
let { table: s, columnPinningState: u, editable: f, editingCell: p, setEditingCell: m, onCellEdit: g, virtualRows: _, onRowClick: v } = a(), y = d((t) => {
|
|
35
|
+
v && (t.target.closest("button, a, input, select, textarea, [role=\"checkbox\"]") || v(e.original));
|
|
36
|
+
}, [v, e.original]), S = e.getVisibleCells();
|
|
37
|
+
return /* @__PURE__ */ h(l, {
|
|
38
|
+
"data-state": e.getIsSelected() && "selected",
|
|
37
39
|
style: o,
|
|
38
|
-
className:
|
|
39
|
-
onClick:
|
|
40
|
-
children:
|
|
41
|
-
let o =
|
|
42
|
-
return /* @__PURE__ */
|
|
43
|
-
className:
|
|
40
|
+
className: t(_ ? "absolute w-full flex" : void 0, v && "cursor-pointer"),
|
|
41
|
+
onClick: v ? y : void 0,
|
|
42
|
+
children: S.map((a) => {
|
|
43
|
+
let o = r(a.column.id, u), l = p?.rowIndex === e.index && p?.columnId === a.column.id;
|
|
44
|
+
return /* @__PURE__ */ h(c, {
|
|
45
|
+
className: t(o.className, _ && "flex-1", n(a.column.columnDef.meta)),
|
|
44
46
|
style: o.style,
|
|
45
47
|
onDoubleClick: () => {
|
|
46
|
-
|
|
47
|
-
rowIndex:
|
|
48
|
-
columnId:
|
|
48
|
+
i(a.column.id, f, s) && m({
|
|
49
|
+
rowIndex: e.index,
|
|
50
|
+
columnId: a.column.id
|
|
49
51
|
});
|
|
50
52
|
},
|
|
51
|
-
children:
|
|
52
|
-
initialValue: String(
|
|
53
|
-
onSave: (
|
|
54
|
-
|
|
53
|
+
children: l ? /* @__PURE__ */ h(x, {
|
|
54
|
+
initialValue: String(a.getValue() ?? ""),
|
|
55
|
+
onSave: (t) => {
|
|
56
|
+
g?.(e.index, a.column.id, t), m(null);
|
|
55
57
|
},
|
|
56
|
-
onCancel: () =>
|
|
57
|
-
}) :
|
|
58
|
-
},
|
|
58
|
+
onCancel: () => m(null)
|
|
59
|
+
}) : b(a.column.columnDef.cell, a.getContext())
|
|
60
|
+
}, a.id);
|
|
59
61
|
})
|
|
60
62
|
});
|
|
61
63
|
}
|
|
62
|
-
function
|
|
63
|
-
let { allColumns: r, expandable:
|
|
64
|
-
|
|
64
|
+
function C({ row: t, style: n }) {
|
|
65
|
+
let { allColumns: r, expandable: i, renderExpanded: o, virtualRows: s } = a(), u = y();
|
|
66
|
+
if (!i || !o) return null;
|
|
67
|
+
let d = t.getIsExpanded();
|
|
68
|
+
return s ? d ? /* @__PURE__ */ h(l, {
|
|
65
69
|
style: n,
|
|
66
|
-
className:
|
|
67
|
-
children: /* @__PURE__ */
|
|
70
|
+
className: "absolute w-full flex",
|
|
71
|
+
children: /* @__PURE__ */ h(c, {
|
|
68
72
|
colSpan: r.length,
|
|
69
|
-
className:
|
|
73
|
+
className: "bg-surface-base p-ds-05 flex-1",
|
|
70
74
|
children: o(t.original)
|
|
71
75
|
})
|
|
76
|
+
}) : null : /* @__PURE__ */ h(_, {
|
|
77
|
+
initial: !1,
|
|
78
|
+
children: d && /* @__PURE__ */ h(l, {
|
|
79
|
+
style: n,
|
|
80
|
+
children: /* @__PURE__ */ h(c, {
|
|
81
|
+
colSpan: r.length,
|
|
82
|
+
className: "bg-surface-base p-0",
|
|
83
|
+
children: /* @__PURE__ */ h(v.div, {
|
|
84
|
+
className: "overflow-hidden",
|
|
85
|
+
initial: u ? !1 : {
|
|
86
|
+
height: 0,
|
|
87
|
+
opacity: 0
|
|
88
|
+
},
|
|
89
|
+
animate: {
|
|
90
|
+
height: "auto",
|
|
91
|
+
opacity: 1
|
|
92
|
+
},
|
|
93
|
+
exit: u ? void 0 : {
|
|
94
|
+
height: 0,
|
|
95
|
+
opacity: 0
|
|
96
|
+
},
|
|
97
|
+
transition: u ? { duration: 0 } : { ...e.smooth },
|
|
98
|
+
children: /* @__PURE__ */ h("div", {
|
|
99
|
+
className: "p-ds-05",
|
|
100
|
+
children: o(t.original)
|
|
101
|
+
})
|
|
102
|
+
})
|
|
103
|
+
})
|
|
104
|
+
})
|
|
72
105
|
});
|
|
73
106
|
}
|
|
74
|
-
function
|
|
75
|
-
let { allColumns: n
|
|
107
|
+
function w({ rowCount: e }) {
|
|
108
|
+
let { allColumns: n } = a(), r = n.length, i = [
|
|
76
109
|
"w-3/4",
|
|
77
110
|
"w-1/2",
|
|
78
111
|
"w-2/3",
|
|
79
112
|
"w-full"
|
|
80
113
|
];
|
|
81
|
-
return /* @__PURE__ */
|
|
82
|
-
|
|
83
|
-
|
|
84
|
-
|
|
85
|
-
|
|
86
|
-
|
|
87
|
-
|
|
88
|
-
|
|
89
|
-
|
|
90
|
-
animation: "pulse"
|
|
91
|
-
})
|
|
92
|
-
}, `skeleton-${i}-${o}`)) }, `skeleton-${i}`)) });
|
|
114
|
+
return /* @__PURE__ */ h(s, { children: Array.from({ length: e }, (e, a) => /* @__PURE__ */ h(l, { children: Array.from({ length: r }, (e, r) => /* @__PURE__ */ h(c, { children: (n[r]?.id ?? n[r]?.header) === "_select" ? /* @__PURE__ */ h(o, {
|
|
115
|
+
variant: "text",
|
|
116
|
+
className: "h-4 w-4",
|
|
117
|
+
animation: "pulse"
|
|
118
|
+
}) : /* @__PURE__ */ h(o, {
|
|
119
|
+
variant: "text",
|
|
120
|
+
className: t("h-4", i[r % i.length]),
|
|
121
|
+
animation: "pulse"
|
|
122
|
+
}) }, `skeleton-${a}-${r}`)) }, `skeleton-${a}`)) });
|
|
93
123
|
}
|
|
94
|
-
function
|
|
95
|
-
let { table: f, allColumns: p, virtualRows:
|
|
96
|
-
return
|
|
124
|
+
function T({ loading: e, skeletonRowCount: n, noResultsText: r, emptyState: i, virtualItems: o, totalVirtualSize: d }) {
|
|
125
|
+
let { table: f, allColumns: p, virtualRows: m } = a(), _ = f.getRowModel().rows;
|
|
126
|
+
return e ? /* @__PURE__ */ h(w, { rowCount: n }) : _.length ? m && o ? /* @__PURE__ */ h(s, {
|
|
97
127
|
style: {
|
|
98
128
|
height: `${d}px`,
|
|
99
129
|
position: "relative"
|
|
100
130
|
},
|
|
101
|
-
children:
|
|
131
|
+
children: o.map((e) => {
|
|
102
132
|
let t = _[e.index];
|
|
103
|
-
return /* @__PURE__ */
|
|
133
|
+
return /* @__PURE__ */ h(S, {
|
|
104
134
|
row: t,
|
|
105
135
|
style: {
|
|
106
136
|
position: "absolute",
|
|
@@ -112,11 +142,11 @@ function x({ loading: t, skeletonRowCount: n, noResultsText: r, emptyState: a, v
|
|
|
112
142
|
}
|
|
113
143
|
}, t.id);
|
|
114
144
|
})
|
|
115
|
-
}) : /* @__PURE__ */
|
|
145
|
+
}) : /* @__PURE__ */ h(s, { children: _.map((e) => /* @__PURE__ */ g(u.Fragment, { children: [/* @__PURE__ */ h(S, { row: e }), /* @__PURE__ */ h(C, { row: e })] }, e.id)) }) : /* @__PURE__ */ h(s, { children: /* @__PURE__ */ h(l, { children: /* @__PURE__ */ h(c, {
|
|
116
146
|
colSpan: p.length,
|
|
117
|
-
className:
|
|
118
|
-
children:
|
|
147
|
+
className: t("py-ds-07 text-center", !i && "text-surface-fg-subtle"),
|
|
148
|
+
children: i || r || "No results."
|
|
119
149
|
}) }) });
|
|
120
150
|
}
|
|
121
151
|
//#endregion
|
|
122
|
-
export {
|
|
152
|
+
export { T as DataTableBody };
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"data-table-body.js","names":[],"sources":["../../src/ui/data-table-body.tsx"],"sourcesContent":["'use client'\n\nimport { flexRender,type Row } from '@tanstack/react-table'\nimport { type VirtualItem } from '@tanstack/react-virtual'\nimport React, { useCallback, useEffect, useRef, useState } from 'react'\n\nimport {\n getColumnMetaClasses,\n getPinnedCellStyle,\n INTERACTIVE_SELECTOR,\n isColumnEditable,\n useDataTableContext,\n} from './data-table-context'\nimport { cn } from './lib/utils'\nimport { Skeleton } from './skeleton'\nimport { TableBody, TableCell, TableRow } from './table'\n\n// ── CellEditInput ───────────────────────────────────────────────\n\n/**\n * Inline edit input rendered inside a table cell.\n * Auto-focuses, saves on Enter/blur, cancels on Escape.\n */\nfunction CellEditInput({\n initialValue,\n onSave,\n onCancel,\n}: {\n initialValue: string\n onSave: (value: string) => void\n onCancel: () => void\n}) {\n const [value, setValue] = useState(initialValue)\n const inputRef = useRef<HTMLInputElement>(null)\n\n useEffect(() => {\n inputRef.current?.focus()\n inputRef.current?.select()\n }, [])\n\n const handleSave = useCallback(() => {\n onSave(value)\n }, [onSave, value])\n\n return (\n <input\n ref={inputRef}\n type=\"text\"\n value={value}\n onChange={(e) => setValue(e.target.value)}\n onBlur={handleSave}\n onKeyDown={(e) => {\n if (e.key === 'Enter') {\n e.preventDefault()\n handleSave()\n } else if (e.key === 'Escape') {\n e.preventDefault()\n onCancel()\n }\n }}\n className={cn(\n 'h-ds-xs-plus w-full rounded-control',\n 'border border-accent-7 bg-surface-raised-hover',\n 'px-ds-02 text-ds-sm',\n 'text-surface-fg placeholder:text-surface-fg-subtle',\n 'outline-hidden focus:border-accent-7',\n )}\n aria-label=\"Edit cell value\"\n />\n )\n}\n\n// ── DataRow ─────────────────────────────────────────────────────\n\n/** Render a single data row (shared between virtual and non-virtual paths) */\nfunction DataTableRow<TData>({\n row,\n style,\n}: {\n row: Row<TData>\n style?: React.CSSProperties\n}) {\n const {\n table,\n cellPadding,\n columnPinningState,\n editable,\n editingCell,\n setEditingCell,\n onCellEdit,\n virtualRows,\n onRowClick,\n } = useDataTableContext<TData>()\n\n const handleRowClick = useCallback(\n (e: React.MouseEvent<HTMLTableRowElement>) => {\n if (!onRowClick) return\n const target = e.target as HTMLElement\n if (target.closest(INTERACTIVE_SELECTOR)) return\n onRowClick(row.original)\n },\n [onRowClick, row.original],\n )\n\n const visibleCells = row.getVisibleCells()\n\n return (\n <TableRow\n data-state={row.getIsSelected() && 'selected'}\n style={style}\n className={cn(\n virtualRows ? 'absolute w-full flex' : undefined,\n onRowClick && 'cursor-pointer',\n )}\n onClick={onRowClick ? handleRowClick : undefined}\n >\n {visibleCells.map((cell) => {\n const pinned = getPinnedCellStyle(cell.column.id, columnPinningState)\n const isEditing =\n editingCell?.rowIndex === row.index &&\n editingCell?.columnId === cell.column.id\n\n return (\n <TableCell\n key={cell.id}\n className={cn(\n cellPadding,\n pinned.className,\n virtualRows && 'flex-1',\n getColumnMetaClasses(\n cell.column.columnDef.meta as Record<string, unknown>,\n ),\n )}\n style={pinned.style}\n onDoubleClick={() => {\n if (isColumnEditable(cell.column.id, editable, table)) {\n setEditingCell({\n rowIndex: row.index,\n columnId: cell.column.id,\n })\n }\n }}\n >\n {isEditing ? (\n <CellEditInput\n initialValue={String(cell.getValue() ?? '')}\n onSave={(value) => {\n onCellEdit?.(row.index, cell.column.id, value)\n setEditingCell(null)\n }}\n onCancel={() => setEditingCell(null)}\n />\n ) : (\n flexRender(cell.column.columnDef.cell, cell.getContext())\n )}\n </TableCell>\n )\n })}\n </TableRow>\n )\n}\n\n// ── ExpandedRow ─────────────────────────────────────────────────\n\n/** Render expanded content row below the data row */\nfunction DataTableExpandedRow<TData>({\n row,\n style,\n}: {\n row: Row<TData>\n style?: React.CSSProperties\n}) {\n const { allColumns, expandable, renderExpanded, virtualRows } =\n useDataTableContext<TData>()\n\n if (!expandable || !row.getIsExpanded() || !renderExpanded) return null\n\n return (\n <TableRow\n style={style}\n className={virtualRows ? 'absolute w-full flex' : undefined}\n >\n <TableCell\n colSpan={allColumns.length}\n className={cn(\n 'bg-surface-raised p-ds-05',\n virtualRows && 'flex-1',\n )}\n >\n {renderExpanded(row.original)}\n </TableCell>\n </TableRow>\n )\n}\n\n// ── SkeletonRows ────────────────────────────────────────────────\n\nfunction DataTableSkeletonRows({\n rowCount,\n}: {\n rowCount: number\n}) {\n const { allColumns, cellPadding } = useDataTableContext()\n const visibleColumnCount = allColumns.length\n const skeletonWidths = ['w-3/4', 'w-1/2', 'w-2/3', 'w-full']\n\n return (\n <TableBody>\n {Array.from({ length: rowCount }, (_, rowIdx) => (\n <TableRow key={`skeleton-${rowIdx}`}>\n {Array.from({ length: visibleColumnCount }, (_, colIdx) => {\n const colId = allColumns[colIdx]?.id ?? allColumns[colIdx]?.header\n const isSelect = colId === '_select'\n return (\n <TableCell\n key={`skeleton-${rowIdx}-${colIdx}`}\n className={cellPadding}\n >\n {isSelect ? (\n <Skeleton\n variant=\"text\"\n className=\"h-4 w-4\"\n animation=\"pulse\"\n />\n ) : (\n <Skeleton\n variant=\"text\"\n className={cn(\n 'h-4',\n skeletonWidths[colIdx % skeletonWidths.length],\n )}\n animation=\"pulse\"\n />\n )}\n </TableCell>\n )\n })}\n </TableRow>\n ))}\n </TableBody>\n )\n}\n\n// ── DataTableBody (orchestrates all body rendering) ─────────────\n\nexport function DataTableBody<TData>({\n loading,\n skeletonRowCount,\n noResultsText,\n emptyState,\n virtualItems,\n totalVirtualSize,\n}: {\n loading?: boolean\n skeletonRowCount: number\n noResultsText?: string\n emptyState?: React.ReactNode\n virtualItems?: VirtualItem[]\n totalVirtualSize?: number\n}) {\n const { table, allColumns, virtualRows } = useDataTableContext<TData>()\n const rows = table.getRowModel().rows\n\n // Loading state: show skeleton rows\n if (loading) {\n return <DataTableSkeletonRows rowCount={skeletonRowCount} />\n }\n\n if (!rows.length) {\n return (\n <TableBody>\n <TableRow>\n <TableCell\n colSpan={allColumns.length}\n className={cn(\n 'h-24 text-center',\n !emptyState && 'text-surface-fg-subtle',\n )}\n >\n {emptyState || noResultsText || 'No results.'}\n </TableCell>\n </TableRow>\n </TableBody>\n )\n }\n\n if (virtualRows && virtualItems) {\n return (\n <TableBody\n style={{\n height: `${totalVirtualSize}px`,\n position: 'relative',\n }}\n >\n {virtualItems.map((virtualRow) => {\n const row = rows[virtualRow.index]\n return (\n <DataTableRow\n key={row.id}\n row={row}\n style={{\n position: 'absolute',\n top: 0,\n left: 0,\n width: '100%',\n height: `${virtualRow.size}px`,\n transform: `translateY(${virtualRow.start}px)`,\n }}\n />\n )\n })}\n </TableBody>\n )\n }\n\n // Standard (non-virtual) rendering\n return (\n <TableBody>\n {rows.map((row) => (\n <React.Fragment key={row.id}>\n <DataTableRow row={row} />\n <DataTableExpandedRow row={row} />\n </React.Fragment>\n ))}\n </TableBody>\n )\n}\n"],"mappings":"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"}
|
|
1
|
+
{"version":3,"file":"data-table-body.js","names":[],"sources":["../../src/ui/data-table-body.tsx"],"sourcesContent":["'use client'\n\nimport { flexRender,type Row } from '@tanstack/react-table'\nimport { type VirtualItem } from '@tanstack/react-virtual'\nimport { AnimatePresence, motion, useReducedMotion } from 'framer-motion'\nimport React, { useCallback, useEffect, useRef, useState } from 'react'\n\nimport {\n getColumnMetaClasses,\n getPinnedCellStyle,\n INTERACTIVE_SELECTOR,\n isColumnEditable,\n useDataTableContext,\n} from './data-table-context'\nimport { springs } from './lib/motion'\nimport { cn } from './lib/utils'\nimport { Skeleton } from './skeleton'\nimport { TableBody, TableCell, TableRow } from './table'\n\n// ── CellEditInput ───────────────────────────────────────────────\n\n/**\n * Inline edit input rendered inside a table cell.\n * Auto-focuses, saves on Enter/blur, cancels on Escape.\n */\nfunction CellEditInput({\n initialValue,\n onSave,\n onCancel,\n}: {\n initialValue: string\n onSave: (value: string) => void\n onCancel: () => void\n}) {\n const [value, setValue] = useState(initialValue)\n const inputRef = useRef<HTMLInputElement>(null)\n\n useEffect(() => {\n inputRef.current?.focus()\n inputRef.current?.select()\n }, [])\n\n const handleSave = useCallback(() => {\n onSave(value)\n }, [onSave, value])\n\n return (\n <input\n ref={inputRef}\n type=\"text\"\n value={value}\n onChange={(e) => setValue(e.target.value)}\n onBlur={handleSave}\n onKeyDown={(e) => {\n if (e.key === 'Enter') {\n e.preventDefault()\n handleSave()\n } else if (e.key === 'Escape') {\n e.preventDefault()\n onCancel()\n }\n }}\n className={cn(\n 'h-ds-xs-plus w-full rounded-control',\n 'border border-accent-7 bg-surface-raised-hover',\n 'px-ds-02 text-ds-sm',\n 'text-surface-fg placeholder:text-surface-fg-subtle',\n 'outline-hidden focus:border-accent-7',\n )}\n aria-label=\"Edit cell value\"\n />\n )\n}\n\n// ── DataRow ─────────────────────────────────────────────────────\n\n/** Render a single data row (shared between virtual and non-virtual paths) */\nfunction DataTableRow<TData>({\n row,\n style,\n}: {\n row: Row<TData>\n style?: React.CSSProperties\n}) {\n const {\n table,\n columnPinningState,\n editable,\n editingCell,\n setEditingCell,\n onCellEdit,\n virtualRows,\n onRowClick,\n } = useDataTableContext<TData>()\n\n const handleRowClick = useCallback(\n (e: React.MouseEvent<HTMLTableRowElement>) => {\n if (!onRowClick) return\n const target = e.target as HTMLElement\n if (target.closest(INTERACTIVE_SELECTOR)) return\n onRowClick(row.original)\n },\n [onRowClick, row.original],\n )\n\n const visibleCells = row.getVisibleCells()\n\n return (\n <TableRow\n data-state={row.getIsSelected() && 'selected'}\n style={style}\n className={cn(\n virtualRows ? 'absolute w-full flex' : undefined,\n onRowClick && 'cursor-pointer',\n )}\n onClick={onRowClick ? handleRowClick : undefined}\n >\n {visibleCells.map((cell) => {\n const pinned = getPinnedCellStyle(cell.column.id, columnPinningState)\n const isEditing =\n editingCell?.rowIndex === row.index &&\n editingCell?.columnId === cell.column.id\n\n return (\n <TableCell\n key={cell.id}\n className={cn(\n pinned.className,\n virtualRows && 'flex-1',\n getColumnMetaClasses(\n cell.column.columnDef.meta as Record<string, unknown>,\n ),\n )}\n style={pinned.style}\n onDoubleClick={() => {\n if (isColumnEditable(cell.column.id, editable, table)) {\n setEditingCell({\n rowIndex: row.index,\n columnId: cell.column.id,\n })\n }\n }}\n >\n {isEditing ? (\n <CellEditInput\n initialValue={String(cell.getValue() ?? '')}\n onSave={(value) => {\n onCellEdit?.(row.index, cell.column.id, value)\n setEditingCell(null)\n }}\n onCancel={() => setEditingCell(null)}\n />\n ) : (\n flexRender(cell.column.columnDef.cell, cell.getContext())\n )}\n </TableCell>\n )\n })}\n </TableRow>\n )\n}\n\n// ── ExpandedRow ─────────────────────────────────────────────────\n\n/** Render expanded content row below the data row */\nfunction DataTableExpandedRow<TData>({\n row,\n style,\n}: {\n row: Row<TData>\n style?: React.CSSProperties\n}) {\n const { allColumns, expandable, renderExpanded, virtualRows } =\n useDataTableContext<TData>()\n // Self-guarded (StatFlash pattern) — reveal collapses to an instant swap\n // without relying on a consumer MotionProvider.\n const prefersReduced = useReducedMotion()\n\n if (!expandable || !renderExpanded) return null\n\n const expanded = row.getIsExpanded()\n\n // Virtual rows are absolutely positioned with measured heights — a height\n // animation would fight the virtualizer, so the reveal is instant there.\n if (virtualRows) {\n if (!expanded) return null\n return (\n <TableRow style={style} className=\"absolute w-full flex\">\n <TableCell\n colSpan={allColumns.length}\n className=\"bg-surface-base p-ds-05 flex-1\"\n >\n {renderExpanded(row.original)}\n </TableCell>\n </TableRow>\n )\n }\n\n return (\n <AnimatePresence initial={false}>\n {expanded && (\n <TableRow style={style}>\n <TableCell\n colSpan={allColumns.length}\n // A recess, not a raised layer — surface-raised would vanish on a\n // card. Padding moves to the inner div so the collapsed state has\n // zero height.\n className=\"bg-surface-base p-0\"\n >\n <motion.div\n className=\"overflow-hidden\"\n initial={prefersReduced ? false : { height: 0, opacity: 0 }}\n animate={{ height: 'auto', opacity: 1 }}\n exit={prefersReduced ? undefined : { height: 0, opacity: 0 }}\n transition={\n prefersReduced ? { duration: 0 } : { ...springs.smooth }\n }\n >\n <div className=\"p-ds-05\">{renderExpanded(row.original)}</div>\n </motion.div>\n </TableCell>\n </TableRow>\n )}\n </AnimatePresence>\n )\n}\n\n// ── SkeletonRows ────────────────────────────────────────────────\n\nfunction DataTableSkeletonRows({\n rowCount,\n}: {\n rowCount: number\n}) {\n const { allColumns } = useDataTableContext()\n const visibleColumnCount = allColumns.length\n const skeletonWidths = ['w-3/4', 'w-1/2', 'w-2/3', 'w-full']\n\n return (\n <TableBody>\n {Array.from({ length: rowCount }, (_, rowIdx) => (\n <TableRow key={`skeleton-${rowIdx}`}>\n {Array.from({ length: visibleColumnCount }, (_, colIdx) => {\n const colId = allColumns[colIdx]?.id ?? allColumns[colIdx]?.header\n const isSelect = colId === '_select'\n return (\n <TableCell key={`skeleton-${rowIdx}-${colIdx}`}>\n {isSelect ? (\n <Skeleton\n variant=\"text\"\n className=\"h-4 w-4\"\n animation=\"pulse\"\n />\n ) : (\n <Skeleton\n variant=\"text\"\n className={cn(\n 'h-4',\n skeletonWidths[colIdx % skeletonWidths.length],\n )}\n animation=\"pulse\"\n />\n )}\n </TableCell>\n )\n })}\n </TableRow>\n ))}\n </TableBody>\n )\n}\n\n// ── DataTableBody (orchestrates all body rendering) ─────────────\n\nexport function DataTableBody<TData>({\n loading,\n skeletonRowCount,\n noResultsText,\n emptyState,\n virtualItems,\n totalVirtualSize,\n}: {\n loading?: boolean\n skeletonRowCount: number\n noResultsText?: string\n emptyState?: React.ReactNode\n virtualItems?: VirtualItem[]\n totalVirtualSize?: number\n}) {\n const { table, allColumns, virtualRows } = useDataTableContext<TData>()\n const rows = table.getRowModel().rows\n\n // Loading state: show skeleton rows\n if (loading) {\n return <DataTableSkeletonRows rowCount={skeletonRowCount} />\n }\n\n if (!rows.length) {\n return (\n <TableBody>\n <TableRow>\n <TableCell\n colSpan={allColumns.length}\n className={cn(\n 'py-ds-07 text-center',\n !emptyState && 'text-surface-fg-subtle',\n )}\n >\n {emptyState || noResultsText || 'No results.'}\n </TableCell>\n </TableRow>\n </TableBody>\n )\n }\n\n if (virtualRows && virtualItems) {\n return (\n <TableBody\n style={{\n height: `${totalVirtualSize}px`,\n position: 'relative',\n }}\n >\n {virtualItems.map((virtualRow) => {\n const row = rows[virtualRow.index]\n return (\n <DataTableRow\n key={row.id}\n row={row}\n style={{\n position: 'absolute',\n top: 0,\n left: 0,\n width: '100%',\n height: `${virtualRow.size}px`,\n transform: `translateY(${virtualRow.start}px)`,\n }}\n />\n )\n })}\n </TableBody>\n )\n }\n\n // Standard (non-virtual) rendering\n return (\n <TableBody>\n {rows.map((row) => (\n <React.Fragment key={row.id}>\n <DataTableRow row={row} />\n <DataTableExpandedRow row={row} />\n </React.Fragment>\n ))}\n </TableBody>\n )\n}\n"],"mappings":"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"}
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"data-table-card.d.ts","sourceRoot":"","sources":["../../src/ui/data-table-card.tsx"],"names":[],"mappings":"AAGA,OAAO,KAAK,MAAM,OAAO,CAAA;
|
|
1
|
+
{"version":3,"file":"data-table-card.d.ts","sourceRoot":"","sources":["../../src/ui/data-table-card.tsx"],"names":[],"mappings":"AAGA,OAAO,KAAK,MAAM,OAAO,CAAA;AAazB,wBAAgB,cAAc,CAAC,KAAK,EAAE,EACpC,OAAO,EACP,gBAAgB,EAChB,aAAa,EACb,UAAU,GACX,EAAE;IACD,OAAO,CAAC,EAAE,OAAO,CAAA;IACjB,gBAAgB,EAAE,MAAM,CAAA;IACxB,aAAa,CAAC,EAAE,MAAM,CAAA;IACtB,UAAU,CAAC,EAAE,KAAK,CAAC,SAAS,CAAA;CAC7B,2CAkHA"}
|
|
@@ -1,86 +1,93 @@
|
|
|
1
1
|
"use client";
|
|
2
2
|
import { cn as e } from "./lib/utils.js";
|
|
3
|
-
import {
|
|
4
|
-
import {
|
|
5
|
-
import {
|
|
3
|
+
import { Card as t, CardContent as n } from "./card.js";
|
|
4
|
+
import { Checkbox as r } from "./checkbox.js";
|
|
5
|
+
import { useDataTableContext as i } from "./data-table-context.js";
|
|
6
|
+
import { Skeleton as a } from "./skeleton.js";
|
|
6
7
|
import "react";
|
|
7
|
-
import { jsx as
|
|
8
|
-
import { flexRender as
|
|
8
|
+
import { Fragment as o, jsx as s, jsxs as c } from "react/jsx-runtime";
|
|
9
|
+
import { flexRender as l } from "@tanstack/react-table";
|
|
9
10
|
//#region src/ui/data-table-card.tsx
|
|
10
|
-
function
|
|
11
|
-
let { table:
|
|
12
|
-
return
|
|
11
|
+
function u({ loading: u, skeletonRowCount: d, noResultsText: f, emptyState: p }) {
|
|
12
|
+
let { table: m, selectable: h } = i(), g = m.getRowModel().rows;
|
|
13
|
+
return u ? /* @__PURE__ */ s("div", {
|
|
13
14
|
className: "flex flex-col gap-ds-03",
|
|
14
|
-
children: Array.from({ length:
|
|
15
|
-
|
|
16
|
-
|
|
15
|
+
children: Array.from({ length: d }, (e, r) => /* @__PURE__ */ s(t, {
|
|
16
|
+
size: "sm",
|
|
17
|
+
variant: "outline",
|
|
18
|
+
children: /* @__PURE__ */ c(n, { children: [/* @__PURE__ */ s(a, {
|
|
17
19
|
variant: "text",
|
|
18
20
|
className: "mb-ds-03 h-5 w-2/3",
|
|
19
21
|
animation: "pulse"
|
|
20
|
-
}), /* @__PURE__ */
|
|
22
|
+
}), /* @__PURE__ */ c("div", {
|
|
21
23
|
className: "flex flex-col gap-ds-02",
|
|
22
24
|
children: [
|
|
23
|
-
/* @__PURE__ */
|
|
25
|
+
/* @__PURE__ */ s(a, {
|
|
24
26
|
variant: "text",
|
|
25
27
|
className: "h-4 w-full",
|
|
26
28
|
animation: "pulse"
|
|
27
29
|
}),
|
|
28
|
-
/* @__PURE__ */
|
|
30
|
+
/* @__PURE__ */ s(a, {
|
|
29
31
|
variant: "text",
|
|
30
32
|
className: "h-4 w-3/4",
|
|
31
33
|
animation: "pulse"
|
|
32
34
|
}),
|
|
33
|
-
/* @__PURE__ */
|
|
35
|
+
/* @__PURE__ */ s(a, {
|
|
34
36
|
variant: "text",
|
|
35
37
|
className: "h-4 w-1/2",
|
|
36
38
|
animation: "pulse"
|
|
37
39
|
})
|
|
38
40
|
]
|
|
39
|
-
})]
|
|
40
|
-
}, `card-skeleton-${
|
|
41
|
-
}) :
|
|
41
|
+
})] })
|
|
42
|
+
}, `card-skeleton-${r}`))
|
|
43
|
+
}) : g.length ? /* @__PURE__ */ s("div", {
|
|
42
44
|
className: "flex flex-col gap-ds-03",
|
|
43
45
|
role: "list",
|
|
44
|
-
children:
|
|
45
|
-
let
|
|
46
|
-
return /* @__PURE__ */
|
|
46
|
+
children: g.map((i) => {
|
|
47
|
+
let a = i.getVisibleCells().filter((e) => e.column.id !== "_select" && e.column.id !== "_expand"), u = a[0], d = a.slice(1), f = i.getIsSelected();
|
|
48
|
+
return /* @__PURE__ */ c(t, {
|
|
47
49
|
role: "listitem",
|
|
48
|
-
|
|
49
|
-
|
|
50
|
-
|
|
51
|
-
|
|
50
|
+
size: "sm",
|
|
51
|
+
variant: "outline",
|
|
52
|
+
className: e(f && "ring-2 ring-accent-9"),
|
|
53
|
+
children: [/* @__PURE__ */ c(n, {
|
|
54
|
+
className: "flex items-start justify-between gap-ds-03",
|
|
55
|
+
children: [/* @__PURE__ */ s("div", {
|
|
52
56
|
className: "min-w-0 flex-1 font-medium text-surface-fg",
|
|
53
|
-
children:
|
|
54
|
-
}),
|
|
57
|
+
children: u && l(u.column.columnDef.cell, u.getContext())
|
|
58
|
+
}), h && /* @__PURE__ */ s(r, {
|
|
55
59
|
size: "sm",
|
|
56
|
-
checked:
|
|
57
|
-
disabled: !
|
|
58
|
-
onCheckedChange: (e) =>
|
|
60
|
+
checked: f,
|
|
61
|
+
disabled: !i.getCanSelect(),
|
|
62
|
+
onCheckedChange: (e) => i.toggleSelected(!!e),
|
|
59
63
|
"aria-label": "Select row",
|
|
60
64
|
className: "shrink-0"
|
|
61
65
|
})]
|
|
62
|
-
}),
|
|
63
|
-
|
|
64
|
-
|
|
66
|
+
}), d.length > 0 && /* @__PURE__ */ c(o, { children: [/* @__PURE__ */ s("div", {
|
|
67
|
+
"aria-hidden": "true",
|
|
68
|
+
className: "h-px w-full bg-surface-border-subtle"
|
|
69
|
+
}), /* @__PURE__ */ s(n, {
|
|
70
|
+
className: "flex flex-col gap-ds-01",
|
|
71
|
+
children: d.map((e) => {
|
|
65
72
|
let t = e.column.columnDef.meta;
|
|
66
|
-
return t?.hideBelow === "md" || t?.hideBelow, /* @__PURE__ */
|
|
73
|
+
return t?.hideBelow === "md" || t?.hideBelow, /* @__PURE__ */ c("div", {
|
|
67
74
|
className: "flex justify-between gap-ds-03 text-ds-sm",
|
|
68
|
-
children: [/* @__PURE__ */
|
|
75
|
+
children: [/* @__PURE__ */ s("span", {
|
|
69
76
|
className: "shrink-0 text-surface-fg-muted",
|
|
70
77
|
children: typeof e.column.columnDef.header == "string" ? e.column.columnDef.header : e.column.id
|
|
71
|
-
}), /* @__PURE__ */
|
|
78
|
+
}), /* @__PURE__ */ s("span", {
|
|
72
79
|
className: "min-w-0 text-right text-surface-fg",
|
|
73
|
-
children:
|
|
80
|
+
children: l(e.column.columnDef.cell, e.getContext())
|
|
74
81
|
})]
|
|
75
82
|
}, e.id);
|
|
76
83
|
})
|
|
77
|
-
})]
|
|
78
|
-
},
|
|
84
|
+
})] })]
|
|
85
|
+
}, i.id);
|
|
79
86
|
})
|
|
80
|
-
}) : /* @__PURE__ */
|
|
81
|
-
className: e("py-ds-07 text-center", !
|
|
82
|
-
children:
|
|
87
|
+
}) : /* @__PURE__ */ s("div", {
|
|
88
|
+
className: e("py-ds-07 text-center", !p && "text-surface-fg-subtle"),
|
|
89
|
+
children: p || f || "No results."
|
|
83
90
|
});
|
|
84
91
|
}
|
|
85
92
|
//#endregion
|
|
86
|
-
export {
|
|
93
|
+
export { u as DataTableCards };
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"data-table-card.js","names":[],"sources":["../../src/ui/data-table-card.tsx"],"sourcesContent":["'use client'\n\nimport { flexRender } from '@tanstack/react-table'\nimport React from 'react'\n\nimport { Checkbox } from './checkbox'\nimport { useDataTableContext } from './data-table-context'\nimport { cn } from './lib/utils'\nimport { Skeleton } from './skeleton'\n\n// ── DataTableCards ─────────────────────────────────────────────\n// Renders rows as vertically stacked cards for small (< sm) viewports.\n// Consumes the same TanStack Table instance from context — sorting,\n// filtering, pagination, and selection all work identically.\n\nexport function DataTableCards<TData>({\n loading,\n skeletonRowCount,\n noResultsText,\n emptyState,\n}: {\n loading?: boolean\n skeletonRowCount: number\n noResultsText?: string\n emptyState?: React.ReactNode\n}) {\n const { table, selectable } = useDataTableContext<TData>()\n const rows = table.getRowModel().rows\n\n // Loading skeleton\n if (loading) {\n return (\n <div className=\"flex flex-col gap-ds-03\">\n {Array.from({ length: skeletonRowCount }, (_, i) => (\n <
|
|
1
|
+
{"version":3,"file":"data-table-card.js","names":[],"sources":["../../src/ui/data-table-card.tsx"],"sourcesContent":["'use client'\n\nimport { flexRender } from '@tanstack/react-table'\nimport React from 'react'\n\nimport { Card, CardContent } from './card'\nimport { Checkbox } from './checkbox'\nimport { useDataTableContext } from './data-table-context'\nimport { cn } from './lib/utils'\nimport { Skeleton } from './skeleton'\n\n// ── DataTableCards ─────────────────────────────────────────────\n// Renders rows as vertically stacked cards for small (< sm) viewports.\n// Consumes the same TanStack Table instance from context — sorting,\n// filtering, pagination, and selection all work identically.\n\nexport function DataTableCards<TData>({\n loading,\n skeletonRowCount,\n noResultsText,\n emptyState,\n}: {\n loading?: boolean\n skeletonRowCount: number\n noResultsText?: string\n emptyState?: React.ReactNode\n}) {\n const { table, selectable } = useDataTableContext<TData>()\n const rows = table.getRowModel().rows\n\n // Loading skeleton\n if (loading) {\n return (\n <div className=\"flex flex-col gap-ds-03\">\n {Array.from({ length: skeletonRowCount }, (_, i) => (\n <Card key={`card-skeleton-${i}`} size=\"sm\" variant=\"outline\">\n <CardContent>\n <Skeleton variant=\"text\" className=\"mb-ds-03 h-5 w-2/3\" animation=\"pulse\" />\n <div className=\"flex flex-col gap-ds-02\">\n <Skeleton variant=\"text\" className=\"h-4 w-full\" animation=\"pulse\" />\n <Skeleton variant=\"text\" className=\"h-4 w-3/4\" animation=\"pulse\" />\n <Skeleton variant=\"text\" className=\"h-4 w-1/2\" animation=\"pulse\" />\n </div>\n </CardContent>\n </Card>\n ))}\n </div>\n )\n }\n\n // Empty state\n if (!rows.length) {\n return (\n <div className={cn('py-ds-07 text-center', !emptyState && 'text-surface-fg-subtle')}>\n {emptyState || noResultsText || 'No results.'}\n </div>\n )\n }\n\n return (\n <div className=\"flex flex-col gap-ds-03\" role=\"list\">\n {rows.map((row) => {\n const cells = row.getVisibleCells()\n // Skip internal columns (_select, _expand) for card content\n const contentCells = cells.filter(\n (cell) => cell.column.id !== '_select' && cell.column.id !== '_expand',\n )\n const primaryCell = contentCells[0]\n const restCells = contentCells.slice(1)\n const isSelected = row.getIsSelected()\n\n return (\n <Card\n key={row.id}\n role=\"listitem\"\n size=\"sm\"\n // outline, not default — a phone screen of stacked shadow cards\n // accumulates lift (make-kit dense-list rule).\n variant=\"outline\"\n className={cn(isSelected && 'ring-2 ring-accent-9')}\n >\n {/* Header row: primary field + optional selection checkbox */}\n <CardContent className=\"flex items-start justify-between gap-ds-03\">\n <div className=\"min-w-0 flex-1 font-medium text-surface-fg\">\n {primaryCell &&\n flexRender(primaryCell.column.columnDef.cell, primaryCell.getContext())}\n </div>\n {selectable && (\n <Checkbox\n size=\"sm\"\n checked={isSelected}\n disabled={!row.getCanSelect()}\n onCheckedChange={(v) => row.toggleSelected(!!v)}\n aria-label=\"Select row\"\n className=\"shrink-0\"\n />\n )}\n </CardContent>\n\n {/* Label-value pairs for remaining columns, behind a full-width rule */}\n {restCells.length > 0 && (\n <>\n <div aria-hidden=\"true\" className=\"h-px w-full bg-surface-border-subtle\" />\n <CardContent className=\"flex flex-col gap-ds-01\">\n {restCells.map((cell) => {\n // Respect hideBelow column meta — skip hidden columns\n const meta = cell.column.columnDef.meta as\n | { hideBelow?: string }\n | undefined\n // In card mode on mobile, hideBelow='sm' columns are still useful\n // since we're showing all data in a card layout. Only skip if\n // the column is explicitly hidden via visibility toggle.\n if (meta?.hideBelow === 'md' || meta?.hideBelow === 'lg') {\n // These would normally be hidden at this breakpoint in table\n // mode too, so skip them in cards for consistency\n }\n\n // Derive header label text\n const header =\n typeof cell.column.columnDef.header === 'string'\n ? cell.column.columnDef.header\n : cell.column.id\n\n return (\n <div key={cell.id} className=\"flex justify-between gap-ds-03 text-ds-sm\">\n <span className=\"shrink-0 text-surface-fg-muted\">{header}</span>\n <span className=\"min-w-0 text-right text-surface-fg\">\n {flexRender(cell.column.columnDef.cell, cell.getContext())}\n </span>\n </div>\n )\n })}\n </CardContent>\n </>\n )}\n </Card>\n )\n })}\n </div>\n )\n}\n"],"mappings":";;;;;;;;;;AAgBA,SAAgB,EAAsB,EACpC,YACA,qBACA,kBACA,iBAMC;CACD,IAAM,EAAE,UAAO,kBAAe,GAA4B,EACpD,IAAO,EAAM,aAAa,CAAC;AA+BjC,QA5BI,IAEA,kBAAC,OAAD;EAAK,WAAU;YACZ,MAAM,KAAK,EAAE,QAAQ,GAAkB,GAAG,GAAG,MAC5C,kBAAC,GAAD;GAAiC,MAAK;GAAK,SAAQ;aACjD,kBAAC,GAAD,EAAA,UAAA,CACE,kBAAC,GAAD;IAAU,SAAQ;IAAO,WAAU;IAAqB,WAAU;IAAU,CAAA,EAC5E,kBAAC,OAAD;IAAK,WAAU;cAAf;KACE,kBAAC,GAAD;MAAU,SAAQ;MAAO,WAAU;MAAa,WAAU;MAAU,CAAA;KACpE,kBAAC,GAAD;MAAU,SAAQ;MAAO,WAAU;MAAY,WAAU;MAAU,CAAA;KACnE,kBAAC,GAAD;MAAU,SAAQ;MAAO,WAAU;MAAY,WAAU;MAAU,CAAA;KAC/D;MACM,EAAA,CAAA;GACT,EATI,iBAAiB,IASrB,CACP;EACE,CAAA,GAKL,EAAK,SASR,kBAAC,OAAD;EAAK,WAAU;EAA0B,MAAK;YAC3C,EAAK,KAAK,MAAQ;GAGjB,IAAM,IAFQ,EAAI,iBAAiB,CAER,QACxB,MAAS,EAAK,OAAO,OAAO,aAAa,EAAK,OAAO,OAAO,UAC9D,EACK,IAAc,EAAa,IAC3B,IAAY,EAAa,MAAM,EAAE,EACjC,IAAa,EAAI,eAAe;AAEtC,UACE,kBAAC,GAAD;IAEE,MAAK;IACL,MAAK;IAGL,SAAQ;IACR,WAAW,EAAG,KAAc,uBAAuB;cAPrD,CAUE,kBAAC,GAAD;KAAa,WAAU;eAAvB,CACE,kBAAC,OAAD;MAAK,WAAU;gBACZ,KACC,EAAW,EAAY,OAAO,UAAU,MAAM,EAAY,YAAY,CAAC;MACrE,CAAA,EACL,KACC,kBAAC,GAAD;MACE,MAAK;MACL,SAAS;MACT,UAAU,CAAC,EAAI,cAAc;MAC7B,kBAAkB,MAAM,EAAI,eAAe,CAAC,CAAC,EAAE;MAC/C,cAAW;MACX,WAAU;MACV,CAAA,CAEQ;QAGb,EAAU,SAAS,KAClB,kBAAA,GAAA,EAAA,UAAA,CACA,kBAAC,OAAD;KAAK,eAAY;KAAO,WAAU;KAAyC,CAAA,EAC3E,kBAAC,GAAD;KAAa,WAAU;eACpB,EAAU,KAAK,MAAS;MAEvB,IAAM,IAAO,EAAK,OAAO,UAAU;AAiBnC,aAXI,GAAM,cAAc,QAAQ,GAAM,WAYpC,kBAAC,OAAD;OAAmB,WAAU;iBAA7B,CACE,kBAAC,QAAD;QAAM,WAAU;kBANlB,OAAO,EAAK,OAAO,UAAU,UAAW,WACpC,EAAK,OAAO,UAAU,SACtB,EAAK,OAAO;QAIkD,CAAA,EAChE,kBAAC,QAAD;QAAM,WAAU;kBACb,EAAW,EAAK,OAAO,UAAU,MAAM,EAAK,YAAY,CAAC;QACrD,CAAA,CACH;SALI,EAAK,GAKT;OAER;KACU,CAAA,CACX,EAAA,CAAA,CAEA;MA9DA,EAAI,GA8DJ;IAET;EACE,CAAA,GArFJ,kBAAC,OAAD;EAAK,WAAW,EAAG,wBAAwB,CAAC,KAAc,yBAAyB;YAChF,KAAc,KAAiB;EAC5B,CAAA"}
|
|
@@ -1,14 +1,12 @@
|
|
|
1
1
|
"use client";
|
|
2
2
|
import { ColumnPinningState, Table } from '@tanstack/react-table';
|
|
3
3
|
import { default as React } from 'react';
|
|
4
|
-
import { Density } from './data-table-toolbar';
|
|
5
4
|
/** Editing state: which cell is currently in edit mode */
|
|
6
5
|
export type EditingCell = {
|
|
7
6
|
rowIndex: number;
|
|
8
7
|
columnId: string;
|
|
9
8
|
} | null;
|
|
10
9
|
export declare function getColumnMetaClasses(meta?: Record<string, unknown>): string;
|
|
11
|
-
export declare const densityPaddingMap: Record<Density, string>;
|
|
12
10
|
/** Interactive element selectors for row click filtering */
|
|
13
11
|
export declare const INTERACTIVE_SELECTOR = "button, a, input, select, textarea, [role=\"checkbox\"]";
|
|
14
12
|
export interface DataTableContextValue<TData = unknown> {
|
|
@@ -18,8 +16,6 @@ export interface DataTableContextValue<TData = unknown> {
|
|
|
18
16
|
id?: string;
|
|
19
17
|
header?: unknown;
|
|
20
18
|
}[];
|
|
21
|
-
/** Current cell padding class based on density */
|
|
22
|
-
cellPadding: string;
|
|
23
19
|
/** Column pinning state for sticky positioning */
|
|
24
20
|
columnPinningState: ColumnPinningState;
|
|
25
21
|
/** Whether sorting is enabled */
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"data-table-context.d.ts","sourceRoot":"","sources":["../../src/ui/data-table-context.tsx"],"names":[],"mappings":"AAEA,OAAO,EAAE,KAAK,kBAAkB,EAAE,KAAK,KAAK,EAAE,MAAM,uBAAuB,CAAA;AAC3E,OAAO,KAAK,MAAM,OAAO,CAAA;
|
|
1
|
+
{"version":3,"file":"data-table-context.d.ts","sourceRoot":"","sources":["../../src/ui/data-table-context.tsx"],"names":[],"mappings":"AAEA,OAAO,EAAE,KAAK,kBAAkB,EAAE,KAAK,KAAK,EAAE,MAAM,uBAAuB,CAAA;AAC3E,OAAO,KAAK,MAAM,OAAO,CAAA;AAIzB,0DAA0D;AAC1D,MAAM,MAAM,WAAW,GAAG;IAAE,QAAQ,EAAE,MAAM,CAAC;IAAC,QAAQ,EAAE,MAAM,CAAA;CAAE,GAAG,IAAI,CAAA;AAIvE,wBAAgB,oBAAoB,CAAC,IAAI,CAAC,EAAE,MAAM,CAAC,MAAM,EAAE,OAAO,CAAC,GAAG,MAAM,CAS3E;AAED,4DAA4D;AAC5D,eAAO,MAAM,oBAAoB,4DACwB,CAAA;AAIzD,MAAM,WAAW,qBAAqB,CAAC,KAAK,GAAG,OAAO;IACpD,KAAK,EAAE,KAAK,CAAC,KAAK,CAAC,CAAA;IACnB,yDAAyD;IACzD,UAAU,EAAE;QAAE,EAAE,CAAC,EAAE,MAAM,CAAC;QAAC,MAAM,CAAC,EAAE,OAAO,CAAA;KAAE,EAAE,CAAA;IAC/C,kDAAkD;IAClD,kBAAkB,EAAE,kBAAkB,CAAA;IACtC,iCAAiC;IACjC,QAAQ,EAAE,OAAO,CAAA;IACjB,6CAA6C;IAC7C,UAAU,EAAE,OAAO,CAAA;IACnB,wCAAwC;IACxC,QAAQ,EAAE,OAAO,CAAA;IACjB,uCAAuC;IACvC,UAAU,EAAE,OAAO,CAAA;IACnB,uCAAuC;IACvC,WAAW,EAAE,OAAO,CAAA;IACpB,uCAAuC;IACvC,UAAU,EAAE,OAAO,CAAA;IACnB,uBAAuB;IACvB,UAAU,EAAE,MAAM,GAAG,OAAO,CAAA;IAC5B,2BAA2B;IAC3B,WAAW,EAAE,WAAW,CAAA;IACxB,uBAAuB;IACvB,cAAc,EAAE,CAAC,IAAI,EAAE,WAAW,KAAK,IAAI,CAAA;IAC3C,2CAA2C;IAC3C,UAAU,CAAC,EAAE,CAAC,QAAQ,EAAE,MAAM,EAAE,QAAQ,EAAE,MAAM,EAAE,KAAK,EAAE,OAAO,KAAK,IAAI,CAAA;IACzE,+CAA+C;IAC/C,cAAc,CAAC,EAAE,CAAC,GAAG,EAAE,KAAK,KAAK,KAAK,CAAC,SAAS,CAAA;IAChD,wBAAwB;IACxB,UAAU,CAAC,EAAE,CAAC,GAAG,EAAE,KAAK,KAAK,IAAI,CAAA;CAClC;AAID,wBAAgB,iBAAiB,CAAC,KAAK,EAAE,EACvC,QAAQ,EACR,KAAK,GACN,EAAE;IACD,QAAQ,EAAE,KAAK,CAAC,SAAS,CAAA;IACzB,KAAK,EAAE,qBAAqB,CAAC,KAAK,CAAC,CAAA;CACpC,2CAMA;AAED,wBAAgB,mBAAmB,CAAC,KAAK,GAAG,OAAO,KAGnC,qBAAqB,CAAC,KAAK,CAAC,CAC3C;AAID,2DAA2D;AAC3D,wBAAgB,kBAAkB,CAChC,QAAQ,EAAE,MAAM,EAChB,kBAAkB,EAAE,kBAAkB;;WASZ,KAAK,CAAC,aAAa;EAU9C;AAED,uCAAuC;AACvC,wBAAgB,gBAAgB,CAAC,KAAK,EACpC,QAAQ,EAAE,MAAM,EAChB,QAAQ,EAAE,OAAO,EACjB,KAAK,EAAE,KAAK,CAAC,KAAK,CAAC,GAClB,OAAO,CAYT"}
|
|
@@ -7,23 +7,19 @@ function n(e) {
|
|
|
7
7
|
let t = [];
|
|
8
8
|
return e.align === "right" && t.push("text-right tabular-nums"), e.align === "center" && t.push("text-center"), e.hideBelow === "sm" && t.push("hidden sm:table-cell"), e.hideBelow === "md" && t.push("hidden md:table-cell"), e.hideBelow === "lg" && t.push("hidden lg:table-cell"), t.join(" ");
|
|
9
9
|
}
|
|
10
|
-
var r =
|
|
11
|
-
|
|
12
|
-
|
|
13
|
-
comfortable: "py-ds-07"
|
|
14
|
-
}, i = "button, a, input, select, textarea, [role=\"checkbox\"]", a = e.createContext(null);
|
|
15
|
-
function o({ children: e, value: n }) {
|
|
16
|
-
return /* @__PURE__ */ t(a.Provider, {
|
|
10
|
+
var r = "button, a, input, select, textarea, [role=\"checkbox\"]", i = e.createContext(null);
|
|
11
|
+
function a({ children: e, value: n }) {
|
|
12
|
+
return /* @__PURE__ */ t(i.Provider, {
|
|
17
13
|
value: n,
|
|
18
14
|
children: e
|
|
19
15
|
});
|
|
20
16
|
}
|
|
21
|
-
function
|
|
22
|
-
let t = e.useContext(
|
|
17
|
+
function o() {
|
|
18
|
+
let t = e.useContext(i);
|
|
23
19
|
if (!t) throw Error("useDataTableContext must be used within DataTableProvider");
|
|
24
20
|
return t;
|
|
25
21
|
}
|
|
26
|
-
function
|
|
22
|
+
function s(e, t) {
|
|
27
23
|
let { left: n = [], right: r = [] } = t, i = n.indexOf(e), a = r.indexOf(e);
|
|
28
24
|
return i === -1 ? a === -1 ? {
|
|
29
25
|
className: "",
|
|
@@ -36,10 +32,10 @@ function c(e, t) {
|
|
|
36
32
|
style: { left: 0 }
|
|
37
33
|
};
|
|
38
34
|
}
|
|
39
|
-
function
|
|
35
|
+
function c(e, t, n) {
|
|
40
36
|
if (!t || e === "_select" || e === "_expand") return !1;
|
|
41
37
|
let r = n.getColumn(e);
|
|
42
38
|
return !(!r || r.columnDef.meta?.enableEditing === !1);
|
|
43
39
|
}
|
|
44
40
|
//#endregion
|
|
45
|
-
export {
|
|
41
|
+
export { a as DataTableProvider, r as INTERACTIVE_SELECTOR, n as getColumnMetaClasses, s as getPinnedCellStyle, c as isColumnEditable, o as useDataTableContext };
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"data-table-context.js","names":[],"sources":["../../src/ui/data-table-context.tsx"],"sourcesContent":["'use client'\n\nimport { type ColumnPinningState, type Table } from '@tanstack/react-table'\nimport React from 'react'\n\
|
|
1
|
+
{"version":3,"file":"data-table-context.js","names":[],"sources":["../../src/ui/data-table-context.tsx"],"sourcesContent":["'use client'\n\nimport { type ColumnPinningState, type Table } from '@tanstack/react-table'\nimport React from 'react'\n\n// ── Shared types ────────────────────────────────────────────────\n\n/** Editing state: which cell is currently in edit mode */\nexport type EditingCell = { rowIndex: number; columnId: string } | null\n\n// ── Utility functions ───────────────────────────────────────────\n\nexport function getColumnMetaClasses(meta?: Record<string, unknown>): string {\n if (!meta) return ''\n const classes: string[] = []\n if (meta.align === 'right') classes.push('text-right tabular-nums')\n if (meta.align === 'center') classes.push('text-center')\n if (meta.hideBelow === 'sm') classes.push('hidden sm:table-cell')\n if (meta.hideBelow === 'md') classes.push('hidden md:table-cell')\n if (meta.hideBelow === 'lg') classes.push('hidden lg:table-cell')\n return classes.join(' ')\n}\n\n/** Interactive element selectors for row click filtering */\nexport const INTERACTIVE_SELECTOR =\n 'button, a, input, select, textarea, [role=\"checkbox\"]'\n\n// ── Context ─────────────────────────────────────────────────────\n\nexport interface DataTableContextValue<TData = unknown> {\n table: Table<TData>\n /** All assembled columns (including _select, _expand) */\n allColumns: { id?: string; header?: unknown }[]\n /** Column pinning state for sticky positioning */\n columnPinningState: ColumnPinningState\n /** Whether sorting is enabled */\n sortable: boolean\n /** Whether per-column filters are enabled */\n filterable: boolean\n /** Whether inline editing is enabled */\n editable: boolean\n /** Whether row expansion is enabled */\n expandable: boolean\n /** Whether virtual rows are enabled */\n virtualRows: boolean\n /** Whether row selection is enabled */\n selectable: boolean\n /** Mobile view mode */\n mobileView: 'card' | 'table'\n /** Current editing cell */\n editingCell: EditingCell\n /** Set editing cell */\n setEditingCell: (cell: EditingCell) => void\n /** Callback when a cell value is edited */\n onCellEdit?: (rowIndex: number, columnId: string, value: unknown) => void\n /** Render function for expanded row content */\n renderExpanded?: (row: TData) => React.ReactNode\n /** Row click handler */\n onRowClick?: (row: TData) => void\n}\n\nconst DataTableContext = React.createContext<DataTableContextValue | null>(null)\n\nexport function DataTableProvider<TData>({\n children,\n value,\n}: {\n children: React.ReactNode\n value: DataTableContextValue<TData>\n}) {\n return (\n <DataTableContext.Provider value={value as DataTableContextValue}>\n {children}\n </DataTableContext.Provider>\n )\n}\n\nexport function useDataTableContext<TData = unknown>() {\n const ctx = React.useContext(DataTableContext)\n if (!ctx) throw new Error('useDataTableContext must be used within DataTableProvider')\n return ctx as DataTableContextValue<TData>\n}\n\n// ── Shared helpers ──────────────────────────────────────────────\n\n/** Compute sticky positioning styles for pinned columns */\nexport function getPinnedCellStyle(\n columnId: string,\n columnPinningState: ColumnPinningState,\n) {\n const { left = [], right = [] } = columnPinningState\n const leftIndex = left.indexOf(columnId)\n const rightIndex = right.indexOf(columnId)\n\n if (leftIndex !== -1) {\n return {\n className: 'sticky bg-surface-base z-raised',\n style: { left: 0 } as React.CSSProperties,\n }\n }\n if (rightIndex !== -1) {\n return {\n className: 'sticky bg-surface-base z-raised',\n style: { right: 0 } as React.CSSProperties,\n }\n }\n return { className: '', style: {} as React.CSSProperties }\n}\n\n/** Check if a column allows editing */\nexport function isColumnEditable<TData>(\n columnId: string,\n editable: boolean,\n table: Table<TData>,\n): boolean {\n if (!editable) return false\n // Internal columns are never editable\n if (columnId === '_select' || columnId === '_expand') return false\n const col = table.getColumn(columnId)\n if (!col) return false\n const meta = col.columnDef.meta as\n | { enableEditing?: boolean }\n | undefined\n // Editable by default unless explicitly disabled\n if (meta?.enableEditing === false) return false\n return true\n}\n"],"mappings":";;;;AAYA,SAAgB,EAAqB,GAAwC;AAC3E,KAAI,CAAC,EAAM,QAAO;CAClB,IAAM,IAAoB,EAAE;AAM5B,QALI,EAAK,UAAU,WAAS,EAAQ,KAAK,0BAA0B,EAC/D,EAAK,UAAU,YAAU,EAAQ,KAAK,cAAc,EACpD,EAAK,cAAc,QAAM,EAAQ,KAAK,uBAAuB,EAC7D,EAAK,cAAc,QAAM,EAAQ,KAAK,uBAAuB,EAC7D,EAAK,cAAc,QAAM,EAAQ,KAAK,uBAAuB,EAC1D,EAAQ,KAAK,IAAI;;AAI1B,IAAa,IACX,2DAoCI,IAAmB,EAAM,cAA4C,KAAK;AAEhF,SAAgB,EAAyB,EACvC,aACA,YAIC;AACD,QACE,kBAAC,EAAiB,UAAlB;EAAkC;EAC/B;EACyB,CAAA;;AAIhC,SAAgB,IAAuC;CACrD,IAAM,IAAM,EAAM,WAAW,EAAiB;AAC9C,KAAI,CAAC,EAAK,OAAU,MAAM,4DAA4D;AACtF,QAAO;;AAMT,SAAgB,EACd,GACA,GACA;CACA,IAAM,EAAE,UAAO,EAAE,EAAE,WAAQ,EAAE,KAAK,GAC5B,IAAY,EAAK,QAAQ,EAAS,EAClC,IAAa,EAAM,QAAQ,EAAS;AAc1C,QAZI,MAAc,KAMd,MAAe,KAMZ;EAAE,WAAW;EAAI,OAAO,EAAE;EAAyB,GALjD;EACL,WAAW;EACX,OAAO,EAAE,OAAO,GAAG;EACpB,GATM;EACL,WAAW;EACX,OAAO,EAAE,MAAM,GAAG;EACnB;;AAYL,SAAgB,EACd,GACA,GACA,GACS;AAGT,KAFI,CAAC,KAED,MAAa,aAAa,MAAa,UAAW,QAAO;CAC7D,IAAM,IAAM,EAAM,UAAU,EAAS;AAOrC,QADA,EALI,CAAC,KACQ,EAAI,UAAU,MAIjB,kBAAkB"}
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"data-table-header.d.ts","sourceRoot":"","sources":["../../src/ui/data-table-header.tsx"],"names":[],"mappings":"AAqBA;;;GAGG;AACH,iBAAS,mBAAmB,CAAC,EAAE,YAAY,EAAE,EAAE;IAAE,YAAY,CAAC,EAAE,OAAO,CAAA;CAAE,
|
|
1
|
+
{"version":3,"file":"data-table-header.d.ts","sourceRoot":"","sources":["../../src/ui/data-table-header.tsx"],"names":[],"mappings":"AAqBA;;;GAGG;AACH,iBAAS,mBAAmB,CAAC,EAAE,YAAY,EAAE,EAAE;IAAE,YAAY,CAAC,EAAE,OAAO,CAAA;CAAE,2CAwJxE;AAED,OAAO,EAAE,mBAAmB,IAAI,eAAe,EAAE,CAAA"}
|
|
@@ -13,7 +13,7 @@ import { flexRender as g } from "@tanstack/react-table";
|
|
|
13
13
|
function _({ stickyHeader: _ }) {
|
|
14
14
|
let { table: v, sortable: y, filterable: b, columnPinningState: x } = a();
|
|
15
15
|
return /* @__PURE__ */ u(s, {
|
|
16
|
-
className: t(_ && "sticky top-0 z-10 bg-surface-
|
|
16
|
+
className: t(_ && "sticky top-0 z-10 bg-surface-raised"),
|
|
17
17
|
children: [v.getHeaderGroups().map((a) => /* @__PURE__ */ l(c, { children: a.headers.map((a) => {
|
|
18
18
|
let s = y && a.column.getCanSort(), c = a.column.getIsSorted(), _ = i(a.column.id, x);
|
|
19
19
|
return /* @__PURE__ */ l(o, {
|
|
@@ -22,7 +22,7 @@ function _({ stickyHeader: _ }) {
|
|
|
22
22
|
"aria-sort": s ? c === "asc" ? "ascending" : c === "desc" ? "descending" : "none" : void 0,
|
|
23
23
|
children: a.isPlaceholder ? null : s ? /* @__PURE__ */ u("button", {
|
|
24
24
|
type: "button",
|
|
25
|
-
className: t("flex items-center gap-ds-01 font-medium", "cursor-pointer select-none", "-ml-ds-01 rounded-control-inner px-ds-01 py-ds-01", "hover:bg-surface-raised transition-colors"),
|
|
25
|
+
className: t("flex items-center gap-ds-01 font-medium", "cursor-pointer select-none", "-ml-ds-01 rounded-control-inner px-ds-01 py-ds-01", "hover:bg-surface-raised-hover transition-colors"),
|
|
26
26
|
onClick: a.column.getToggleSortingHandler(),
|
|
27
27
|
"aria-label": `Sort by ${typeof a.column.columnDef.header == "string" ? a.column.columnDef.header : a.column.id}`,
|
|
28
28
|
children: [g(a.column.columnDef.header, a.getContext()), /* @__PURE__ */ l(m, {
|