react-glide-table 2.1.0 → 2.2.1
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/README.md +27 -9
- package/dist/compound.cjs +112 -21
- package/dist/compound.d.cts +2 -2
- package/dist/compound.d.ts +2 -2
- package/dist/compound.js +112 -21
- package/dist/core.cjs +98 -17
- package/dist/core.d.cts +24 -14
- package/dist/core.d.ts +24 -14
- package/dist/core.js +98 -17
- package/dist/index.cjs +112 -21
- package/dist/index.d.cts +2 -2
- package/dist/index.d.ts +2 -2
- package/dist/index.js +112 -21
- package/dist/{types-CMUGtH-c.d.cts → types-CnsQ8GZb.d.cts} +30 -3
- package/dist/{types-CMUGtH-c.d.ts → types-CnsQ8GZb.d.ts} +30 -3
- package/package.json +1 -1
package/README.md
CHANGED
|
@@ -259,6 +259,18 @@ import type { RowsPastePayload } from "react-glide-table/compound";
|
|
|
259
259
|
Related props: `onRowsPaste`, `enableInsertPaste`, `enableSubtreeCopy`, `onCopyActionsReady`.
|
|
260
260
|
Helpers (`/core`): `buildRowsPastePayload`, `parseClipboardTSV`, `parseClipboardTSVWithDepths`, `serializeSelectionToTSV`, …
|
|
261
261
|
|
|
262
|
+
## Column width
|
|
263
|
+
|
|
264
|
+
`Column.width` sets the default size. `minWidth` / `maxWidth` are CSS constraints on header and body cells — they do not clamp drag-resize.
|
|
265
|
+
|
|
266
|
+
```tsx
|
|
267
|
+
<ProductTable.Column field="note" minWidth={80} maxWidth={240}>
|
|
268
|
+
Note
|
|
269
|
+
</ProductTable.Column>
|
|
270
|
+
```
|
|
271
|
+
|
|
272
|
+
With `ColumnDef` (non-compound), put the same values on `meta.minWidth` / `meta.maxWidth`.
|
|
273
|
+
|
|
262
274
|
## Column resize
|
|
263
275
|
|
|
264
276
|
Opt in with `enableColumnResize`. Drag the handle on the right edge of a header cell; double-click resets to the column’s default `width` / `size`.
|
|
@@ -272,7 +284,12 @@ Opt in with `enableColumnResize`. Drag the handle on the right edge of a header
|
|
|
272
284
|
// onColumnSizingChange={setSizing}
|
|
273
285
|
>
|
|
274
286
|
<ProductTable.Header>
|
|
275
|
-
<ProductTable.Column
|
|
287
|
+
<ProductTable.Column
|
|
288
|
+
field="name"
|
|
289
|
+
width={200}
|
|
290
|
+
minResizeWidth={80}
|
|
291
|
+
maxResizeWidth={480}
|
|
292
|
+
>
|
|
276
293
|
Name
|
|
277
294
|
</ProductTable.Column>
|
|
278
295
|
<ProductTable.Column field="sku" resizable={false}>
|
|
@@ -282,14 +299,15 @@ Opt in with `enableColumnResize`. Drag the handle on the right edge of a header
|
|
|
282
299
|
</ProductTable>
|
|
283
300
|
```
|
|
284
301
|
|
|
285
|
-
| Prop
|
|
286
|
-
|
|
|
287
|
-
| `enableColumnResize`
|
|
288
|
-
| `columnSizing` / `onColumnSizingChange`
|
|
289
|
-
| `columnResizeMode`
|
|
290
|
-
| `Column.width`
|
|
291
|
-
| `Column.
|
|
292
|
-
| `
|
|
302
|
+
| Prop | Role |
|
|
303
|
+
| ------------------------------------------ | -------------------------------------------- |
|
|
304
|
+
| `enableColumnResize` | Turn on header drag resize (default `false`) |
|
|
305
|
+
| `columnSizing` / `onColumnSizingChange` | Controlled width map `{ [columnId]: px }` |
|
|
306
|
+
| `columnResizeMode` | `"onChange"` (live) or `"onEnd"` |
|
|
307
|
+
| `Column.width` | Default column size |
|
|
308
|
+
| `Column.minResizeWidth` / `maxResizeWidth` | Drag-resize clamp sizes |
|
|
309
|
+
| `Column.resizable={false}` | Disable resize for one column |
|
|
310
|
+
| `classNames.resizeHandle` | Style hook for the drag handle |
|
|
293
311
|
|
|
294
312
|
## Column reorder
|
|
295
313
|
|
package/dist/compound.cjs
CHANGED
|
@@ -531,15 +531,29 @@ function flattenHeaderLeaves(column) {
|
|
|
531
531
|
|
|
532
532
|
// src/components/ui/table/features/column-resize/columnResize.ts
|
|
533
533
|
function getColumnSizeStyle(size, options) {
|
|
534
|
-
const { force = false, lockMax = false } = options ?? {};
|
|
535
|
-
if (
|
|
534
|
+
const { force = false, lockMax = false, minWidth, maxWidth } = options ?? {};
|
|
535
|
+
if (lockMax) {
|
|
536
|
+
return {
|
|
537
|
+
width: size,
|
|
538
|
+
minWidth: size,
|
|
539
|
+
maxWidth: size
|
|
540
|
+
};
|
|
541
|
+
}
|
|
542
|
+
const hasExplicitSize = force || size !== DATA_TABLE_COLUMN_SIZE;
|
|
543
|
+
if (!hasExplicitSize && minWidth == null && maxWidth == null) {
|
|
536
544
|
return void 0;
|
|
537
545
|
}
|
|
538
|
-
|
|
539
|
-
|
|
540
|
-
|
|
541
|
-
|
|
542
|
-
}
|
|
546
|
+
const style = {};
|
|
547
|
+
if (hasExplicitSize) {
|
|
548
|
+
style.width = size;
|
|
549
|
+
style.minWidth = minWidth ?? size;
|
|
550
|
+
} else if (minWidth != null) {
|
|
551
|
+
style.minWidth = minWidth;
|
|
552
|
+
}
|
|
553
|
+
if (maxWidth != null) {
|
|
554
|
+
style.maxWidth = maxWidth;
|
|
555
|
+
}
|
|
556
|
+
return style;
|
|
543
557
|
}
|
|
544
558
|
|
|
545
559
|
// src/components/ui/table/features/inline-search/inlineSearch.ts
|
|
@@ -890,23 +904,49 @@ var useConvertTreeData = ({
|
|
|
890
904
|
function getRowFieldValue(row, key) {
|
|
891
905
|
return row[key];
|
|
892
906
|
}
|
|
893
|
-
function
|
|
907
|
+
function normalizeRowSpanParent(value) {
|
|
908
|
+
if (!value) return [];
|
|
909
|
+
return typeof value === "string" ? [value] : [...value];
|
|
910
|
+
}
|
|
911
|
+
function toParentSpanList(parentSpans) {
|
|
912
|
+
if (!parentSpans?.length) return [];
|
|
913
|
+
const first = parentSpans[0];
|
|
914
|
+
if (!Array.isArray(first)) {
|
|
915
|
+
return [parentSpans];
|
|
916
|
+
}
|
|
917
|
+
return parentSpans;
|
|
918
|
+
}
|
|
919
|
+
function buildStartRowLookup(spans) {
|
|
920
|
+
const startRows = new Array(spans.length);
|
|
921
|
+
let origin = 0;
|
|
922
|
+
for (let i = 0; i < spans.length; i++) {
|
|
923
|
+
if ((spans[i]?.rowSpan ?? 1) > 0) origin = i;
|
|
924
|
+
startRows[i] = origin;
|
|
925
|
+
}
|
|
926
|
+
return startRows;
|
|
927
|
+
}
|
|
928
|
+
function sharesParentGroup(parentStartRows, rowIndex) {
|
|
929
|
+
if (parentStartRows.length === 0 || rowIndex <= 0) return true;
|
|
930
|
+
return parentStartRows.every(
|
|
931
|
+
(startRows) => startRows[rowIndex - 1] === startRows[rowIndex]
|
|
932
|
+
);
|
|
933
|
+
}
|
|
934
|
+
function computeRowSpans(data, rowSpanKey, parentSpans) {
|
|
894
935
|
if (data.length === 0) return [];
|
|
936
|
+
const parentStartRows = toParentSpanList(parentSpans).map(buildStartRowLookup);
|
|
895
937
|
const result = [];
|
|
896
938
|
for (let index = 0; index < data.length; index++) {
|
|
897
939
|
const currentValue = getRowFieldValue(data[index], rowSpanKey);
|
|
898
940
|
const previousValue = index > 0 ? getRowFieldValue(data[index - 1], rowSpanKey) : void 0;
|
|
899
|
-
if (index > 0 && currentValue === previousValue) {
|
|
941
|
+
if (index > 0 && currentValue === previousValue && sharesParentGroup(parentStartRows, index)) {
|
|
900
942
|
result.push({ rowSpan: 0, isFirstInGroup: false });
|
|
901
943
|
continue;
|
|
902
944
|
}
|
|
903
945
|
let span = 1;
|
|
904
946
|
for (let nextIndex = index + 1; nextIndex < data.length; nextIndex++) {
|
|
905
|
-
if (getRowFieldValue(data[nextIndex], rowSpanKey)
|
|
906
|
-
|
|
907
|
-
|
|
908
|
-
break;
|
|
909
|
-
}
|
|
947
|
+
if (getRowFieldValue(data[nextIndex], rowSpanKey) !== currentValue) break;
|
|
948
|
+
if (!sharesParentGroup(parentStartRows, nextIndex)) break;
|
|
949
|
+
span++;
|
|
910
950
|
}
|
|
911
951
|
result.push({ rowSpan: span, isFirstInGroup: true });
|
|
912
952
|
}
|
|
@@ -928,10 +968,50 @@ function resolveRowSpanAt(rowSpans, rowIndex) {
|
|
|
928
968
|
}
|
|
929
969
|
return { startRow: rowIndex, rowSpan: 1 };
|
|
930
970
|
}
|
|
971
|
+
function findRowSpanColumn(spec, ref) {
|
|
972
|
+
return spec.find((column) => column.columnId === ref) ?? spec.find((column) => column.rowSpanKey === ref);
|
|
973
|
+
}
|
|
931
974
|
function buildColumnRowSpanMap(data, columnKeys) {
|
|
932
975
|
const map = /* @__PURE__ */ new Map();
|
|
933
|
-
|
|
934
|
-
|
|
976
|
+
const visiting = /* @__PURE__ */ new Set();
|
|
977
|
+
const warnedCycles = /* @__PURE__ */ new Set();
|
|
978
|
+
const virtualParents = /* @__PURE__ */ new Map();
|
|
979
|
+
const spansForColumn = (columnId) => {
|
|
980
|
+
const cached = map.get(columnId);
|
|
981
|
+
if (cached !== void 0) return cached;
|
|
982
|
+
const column = columnKeys.find((item) => item.columnId === columnId);
|
|
983
|
+
if (!column) return void 0;
|
|
984
|
+
if (visiting.has(columnId)) {
|
|
985
|
+
if (!warnedCycles.has(columnId)) {
|
|
986
|
+
warnedCycles.add(columnId);
|
|
987
|
+
console.warn(
|
|
988
|
+
`[rowSpan] rowSpanParent cycle detected at column "${columnId}"; dropping the cyclic parent reference.`
|
|
989
|
+
);
|
|
990
|
+
}
|
|
991
|
+
return void 0;
|
|
992
|
+
}
|
|
993
|
+
visiting.add(columnId);
|
|
994
|
+
const parentSpans = (column.rowSpanParent ?? []).map((ref) => spansForParentRef(ref)).filter((spans2) => Boolean(spans2));
|
|
995
|
+
visiting.delete(columnId);
|
|
996
|
+
const spans = computeRowSpans(
|
|
997
|
+
data,
|
|
998
|
+
column.rowSpanKey,
|
|
999
|
+
parentSpans.length > 0 ? parentSpans : void 0
|
|
1000
|
+
);
|
|
1001
|
+
map.set(columnId, spans);
|
|
1002
|
+
return spans;
|
|
1003
|
+
};
|
|
1004
|
+
const spansForParentRef = (ref) => {
|
|
1005
|
+
const parentColumn = findRowSpanColumn(columnKeys, ref);
|
|
1006
|
+
if (parentColumn) return spansForColumn(parentColumn.columnId);
|
|
1007
|
+
const cached = virtualParents.get(ref);
|
|
1008
|
+
if (cached !== void 0) return cached;
|
|
1009
|
+
const spans = computeRowSpans(data, ref);
|
|
1010
|
+
virtualParents.set(ref, spans);
|
|
1011
|
+
return spans;
|
|
1012
|
+
};
|
|
1013
|
+
for (const column of columnKeys) {
|
|
1014
|
+
spansForColumn(column.columnId);
|
|
935
1015
|
}
|
|
936
1016
|
return map;
|
|
937
1017
|
}
|
|
@@ -947,7 +1027,8 @@ function collectRowSpanColumns(columns) {
|
|
|
947
1027
|
if (!columnId || !columnDef.meta?.rowSpan) continue;
|
|
948
1028
|
result.push({
|
|
949
1029
|
columnId,
|
|
950
|
-
rowSpanKey: columnDef.meta.rowSpanKey ?? columnId
|
|
1030
|
+
rowSpanKey: columnDef.meta.rowSpanKey ?? columnId,
|
|
1031
|
+
rowSpanParent: normalizeRowSpanParent(columnDef.meta.rowSpanParent)
|
|
951
1032
|
});
|
|
952
1033
|
}
|
|
953
1034
|
};
|
|
@@ -1340,7 +1421,9 @@ function DataTableRow({
|
|
|
1340
1421
|
const hasSelectionEdges = hasCellSelectionEdges(selectionEdgeStyle);
|
|
1341
1422
|
const sizeStyle = getColumnSizeStyle(cell.column.getSize(), {
|
|
1342
1423
|
force: enableColumnResize,
|
|
1343
|
-
lockMax: enableColumnResize
|
|
1424
|
+
lockMax: enableColumnResize,
|
|
1425
|
+
minWidth: meta?.minWidth,
|
|
1426
|
+
maxWidth: meta?.maxWidth
|
|
1344
1427
|
});
|
|
1345
1428
|
const freezeOffset = enableColumnFreeze ? freezeOffsets.get(columnId) : void 0;
|
|
1346
1429
|
const freezeStyle = getColumnFreezeStyle(freezeOffset);
|
|
@@ -4163,7 +4246,9 @@ function DataTable({
|
|
|
4163
4246
|
const canResize = enableColumnResize && header.column.getCanResize();
|
|
4164
4247
|
const sizeStyle = getColumnSizeStyle(header.getSize(), {
|
|
4165
4248
|
force: enableColumnResize,
|
|
4166
|
-
lockMax: enableColumnResize
|
|
4249
|
+
lockMax: enableColumnResize,
|
|
4250
|
+
minWidth: header.column.columnDef.meta?.minWidth,
|
|
4251
|
+
maxWidth: header.column.columnDef.meta?.maxWidth
|
|
4167
4252
|
});
|
|
4168
4253
|
const freezeOffset = enableColumnFreeze ? resolveHeaderFreezeOffset(header.column, freezeOffsets) : void 0;
|
|
4169
4254
|
const freezeStyle = getColumnFreezeStyle(freezeOffset, {
|
|
@@ -4403,12 +4488,15 @@ function buildColumnDef(props, sort, onSort) {
|
|
|
4403
4488
|
width,
|
|
4404
4489
|
minWidth,
|
|
4405
4490
|
maxWidth,
|
|
4491
|
+
minResizeWidth,
|
|
4492
|
+
maxResizeWidth,
|
|
4406
4493
|
resizable,
|
|
4407
4494
|
reorderable,
|
|
4408
4495
|
frozen,
|
|
4409
4496
|
align,
|
|
4410
4497
|
rowSpan,
|
|
4411
4498
|
rowSpanKey,
|
|
4499
|
+
rowSpanParent,
|
|
4412
4500
|
editable,
|
|
4413
4501
|
editType,
|
|
4414
4502
|
editInputProps,
|
|
@@ -4422,8 +4510,8 @@ function buildColumnDef(props, sort, onSort) {
|
|
|
4422
4510
|
id: field,
|
|
4423
4511
|
...!virtual ? { accessorKey: field } : {},
|
|
4424
4512
|
size: width ?? DATA_TABLE_COLUMN_SIZE,
|
|
4425
|
-
...
|
|
4426
|
-
...
|
|
4513
|
+
...minResizeWidth != null ? { minSize: minResizeWidth } : {},
|
|
4514
|
+
...maxResizeWidth != null ? { maxSize: maxResizeWidth } : {},
|
|
4427
4515
|
...resizable === false ? { enableResizing: false } : {},
|
|
4428
4516
|
header: sortable ? () => /* @__PURE__ */ (0, import_jsx_runtime8.jsx)(
|
|
4429
4517
|
SortableHeader,
|
|
@@ -4443,6 +4531,7 @@ function buildColumnDef(props, sort, onSort) {
|
|
|
4443
4531
|
align,
|
|
4444
4532
|
rowSpan,
|
|
4445
4533
|
rowSpanKey,
|
|
4534
|
+
rowSpanParent,
|
|
4446
4535
|
editable,
|
|
4447
4536
|
editType,
|
|
4448
4537
|
editInputProps,
|
|
@@ -4451,6 +4540,8 @@ function buildColumnDef(props, sort, onSort) {
|
|
|
4451
4540
|
cellRender: render,
|
|
4452
4541
|
frozen,
|
|
4453
4542
|
reorderable,
|
|
4543
|
+
minWidth,
|
|
4544
|
+
maxWidth,
|
|
4454
4545
|
className,
|
|
4455
4546
|
headerClassName
|
|
4456
4547
|
}
|
package/dist/compound.d.cts
CHANGED
|
@@ -1,7 +1,7 @@
|
|
|
1
1
|
import * as react from 'react';
|
|
2
2
|
import { ReactNode, ReactElement } from 'react';
|
|
3
|
-
import { l as DataTableProps, r as TableColumnProps, T as TableColumnGroupProps, s as TableProps } from './types-
|
|
4
|
-
export { B as BuiltinCellKind, C as CellKind, a as CellRenderContext, b as CellRenderFn, c as CellRenderer, f as ColumnFreezeMeta, h as ColumnFreezeSide, i as DataTableClassNames, k as DataTableLabels, m as DataTableScrollSlotProps, n as DataTableSlots, P as PasteMode, R as RowSelectionMode, o as RowsPastePayload, p as SearchResultItem } from './types-
|
|
3
|
+
import { l as DataTableProps, r as TableColumnProps, T as TableColumnGroupProps, s as TableProps } from './types-CnsQ8GZb.cjs';
|
|
4
|
+
export { B as BuiltinCellKind, C as CellKind, a as CellRenderContext, b as CellRenderFn, c as CellRenderer, f as ColumnFreezeMeta, h as ColumnFreezeSide, i as DataTableClassNames, k as DataTableLabels, m as DataTableScrollSlotProps, n as DataTableSlots, P as PasteMode, R as RowSelectionMode, o as RowsPastePayload, p as SearchResultItem } from './types-CnsQ8GZb.cjs';
|
|
5
5
|
export { ColumnDef, ColumnOrderState, ColumnResizeMode, ColumnSizingState, RowSelectionState } from '@tanstack/react-table';
|
|
6
6
|
|
|
7
7
|
/**
|
package/dist/compound.d.ts
CHANGED
|
@@ -1,7 +1,7 @@
|
|
|
1
1
|
import * as react from 'react';
|
|
2
2
|
import { ReactNode, ReactElement } from 'react';
|
|
3
|
-
import { l as DataTableProps, r as TableColumnProps, T as TableColumnGroupProps, s as TableProps } from './types-
|
|
4
|
-
export { B as BuiltinCellKind, C as CellKind, a as CellRenderContext, b as CellRenderFn, c as CellRenderer, f as ColumnFreezeMeta, h as ColumnFreezeSide, i as DataTableClassNames, k as DataTableLabels, m as DataTableScrollSlotProps, n as DataTableSlots, P as PasteMode, R as RowSelectionMode, o as RowsPastePayload, p as SearchResultItem } from './types-
|
|
3
|
+
import { l as DataTableProps, r as TableColumnProps, T as TableColumnGroupProps, s as TableProps } from './types-CnsQ8GZb.js';
|
|
4
|
+
export { B as BuiltinCellKind, C as CellKind, a as CellRenderContext, b as CellRenderFn, c as CellRenderer, f as ColumnFreezeMeta, h as ColumnFreezeSide, i as DataTableClassNames, k as DataTableLabels, m as DataTableScrollSlotProps, n as DataTableSlots, P as PasteMode, R as RowSelectionMode, o as RowsPastePayload, p as SearchResultItem } from './types-CnsQ8GZb.js';
|
|
5
5
|
export { ColumnDef, ColumnOrderState, ColumnResizeMode, ColumnSizingState, RowSelectionState } from '@tanstack/react-table';
|
|
6
6
|
|
|
7
7
|
/**
|
package/dist/compound.js
CHANGED
|
@@ -503,15 +503,29 @@ function flattenHeaderLeaves(column) {
|
|
|
503
503
|
|
|
504
504
|
// src/components/ui/table/features/column-resize/columnResize.ts
|
|
505
505
|
function getColumnSizeStyle(size, options) {
|
|
506
|
-
const { force = false, lockMax = false } = options ?? {};
|
|
507
|
-
if (
|
|
506
|
+
const { force = false, lockMax = false, minWidth, maxWidth } = options ?? {};
|
|
507
|
+
if (lockMax) {
|
|
508
|
+
return {
|
|
509
|
+
width: size,
|
|
510
|
+
minWidth: size,
|
|
511
|
+
maxWidth: size
|
|
512
|
+
};
|
|
513
|
+
}
|
|
514
|
+
const hasExplicitSize = force || size !== DATA_TABLE_COLUMN_SIZE;
|
|
515
|
+
if (!hasExplicitSize && minWidth == null && maxWidth == null) {
|
|
508
516
|
return void 0;
|
|
509
517
|
}
|
|
510
|
-
|
|
511
|
-
|
|
512
|
-
|
|
513
|
-
|
|
514
|
-
}
|
|
518
|
+
const style = {};
|
|
519
|
+
if (hasExplicitSize) {
|
|
520
|
+
style.width = size;
|
|
521
|
+
style.minWidth = minWidth ?? size;
|
|
522
|
+
} else if (minWidth != null) {
|
|
523
|
+
style.minWidth = minWidth;
|
|
524
|
+
}
|
|
525
|
+
if (maxWidth != null) {
|
|
526
|
+
style.maxWidth = maxWidth;
|
|
527
|
+
}
|
|
528
|
+
return style;
|
|
515
529
|
}
|
|
516
530
|
|
|
517
531
|
// src/components/ui/table/features/inline-search/inlineSearch.ts
|
|
@@ -862,23 +876,49 @@ var useConvertTreeData = ({
|
|
|
862
876
|
function getRowFieldValue(row, key) {
|
|
863
877
|
return row[key];
|
|
864
878
|
}
|
|
865
|
-
function
|
|
879
|
+
function normalizeRowSpanParent(value) {
|
|
880
|
+
if (!value) return [];
|
|
881
|
+
return typeof value === "string" ? [value] : [...value];
|
|
882
|
+
}
|
|
883
|
+
function toParentSpanList(parentSpans) {
|
|
884
|
+
if (!parentSpans?.length) return [];
|
|
885
|
+
const first = parentSpans[0];
|
|
886
|
+
if (!Array.isArray(first)) {
|
|
887
|
+
return [parentSpans];
|
|
888
|
+
}
|
|
889
|
+
return parentSpans;
|
|
890
|
+
}
|
|
891
|
+
function buildStartRowLookup(spans) {
|
|
892
|
+
const startRows = new Array(spans.length);
|
|
893
|
+
let origin = 0;
|
|
894
|
+
for (let i = 0; i < spans.length; i++) {
|
|
895
|
+
if ((spans[i]?.rowSpan ?? 1) > 0) origin = i;
|
|
896
|
+
startRows[i] = origin;
|
|
897
|
+
}
|
|
898
|
+
return startRows;
|
|
899
|
+
}
|
|
900
|
+
function sharesParentGroup(parentStartRows, rowIndex) {
|
|
901
|
+
if (parentStartRows.length === 0 || rowIndex <= 0) return true;
|
|
902
|
+
return parentStartRows.every(
|
|
903
|
+
(startRows) => startRows[rowIndex - 1] === startRows[rowIndex]
|
|
904
|
+
);
|
|
905
|
+
}
|
|
906
|
+
function computeRowSpans(data, rowSpanKey, parentSpans) {
|
|
866
907
|
if (data.length === 0) return [];
|
|
908
|
+
const parentStartRows = toParentSpanList(parentSpans).map(buildStartRowLookup);
|
|
867
909
|
const result = [];
|
|
868
910
|
for (let index = 0; index < data.length; index++) {
|
|
869
911
|
const currentValue = getRowFieldValue(data[index], rowSpanKey);
|
|
870
912
|
const previousValue = index > 0 ? getRowFieldValue(data[index - 1], rowSpanKey) : void 0;
|
|
871
|
-
if (index > 0 && currentValue === previousValue) {
|
|
913
|
+
if (index > 0 && currentValue === previousValue && sharesParentGroup(parentStartRows, index)) {
|
|
872
914
|
result.push({ rowSpan: 0, isFirstInGroup: false });
|
|
873
915
|
continue;
|
|
874
916
|
}
|
|
875
917
|
let span = 1;
|
|
876
918
|
for (let nextIndex = index + 1; nextIndex < data.length; nextIndex++) {
|
|
877
|
-
if (getRowFieldValue(data[nextIndex], rowSpanKey)
|
|
878
|
-
|
|
879
|
-
|
|
880
|
-
break;
|
|
881
|
-
}
|
|
919
|
+
if (getRowFieldValue(data[nextIndex], rowSpanKey) !== currentValue) break;
|
|
920
|
+
if (!sharesParentGroup(parentStartRows, nextIndex)) break;
|
|
921
|
+
span++;
|
|
882
922
|
}
|
|
883
923
|
result.push({ rowSpan: span, isFirstInGroup: true });
|
|
884
924
|
}
|
|
@@ -900,10 +940,50 @@ function resolveRowSpanAt(rowSpans, rowIndex) {
|
|
|
900
940
|
}
|
|
901
941
|
return { startRow: rowIndex, rowSpan: 1 };
|
|
902
942
|
}
|
|
943
|
+
function findRowSpanColumn(spec, ref) {
|
|
944
|
+
return spec.find((column) => column.columnId === ref) ?? spec.find((column) => column.rowSpanKey === ref);
|
|
945
|
+
}
|
|
903
946
|
function buildColumnRowSpanMap(data, columnKeys) {
|
|
904
947
|
const map = /* @__PURE__ */ new Map();
|
|
905
|
-
|
|
906
|
-
|
|
948
|
+
const visiting = /* @__PURE__ */ new Set();
|
|
949
|
+
const warnedCycles = /* @__PURE__ */ new Set();
|
|
950
|
+
const virtualParents = /* @__PURE__ */ new Map();
|
|
951
|
+
const spansForColumn = (columnId) => {
|
|
952
|
+
const cached = map.get(columnId);
|
|
953
|
+
if (cached !== void 0) return cached;
|
|
954
|
+
const column = columnKeys.find((item) => item.columnId === columnId);
|
|
955
|
+
if (!column) return void 0;
|
|
956
|
+
if (visiting.has(columnId)) {
|
|
957
|
+
if (!warnedCycles.has(columnId)) {
|
|
958
|
+
warnedCycles.add(columnId);
|
|
959
|
+
console.warn(
|
|
960
|
+
`[rowSpan] rowSpanParent cycle detected at column "${columnId}"; dropping the cyclic parent reference.`
|
|
961
|
+
);
|
|
962
|
+
}
|
|
963
|
+
return void 0;
|
|
964
|
+
}
|
|
965
|
+
visiting.add(columnId);
|
|
966
|
+
const parentSpans = (column.rowSpanParent ?? []).map((ref) => spansForParentRef(ref)).filter((spans2) => Boolean(spans2));
|
|
967
|
+
visiting.delete(columnId);
|
|
968
|
+
const spans = computeRowSpans(
|
|
969
|
+
data,
|
|
970
|
+
column.rowSpanKey,
|
|
971
|
+
parentSpans.length > 0 ? parentSpans : void 0
|
|
972
|
+
);
|
|
973
|
+
map.set(columnId, spans);
|
|
974
|
+
return spans;
|
|
975
|
+
};
|
|
976
|
+
const spansForParentRef = (ref) => {
|
|
977
|
+
const parentColumn = findRowSpanColumn(columnKeys, ref);
|
|
978
|
+
if (parentColumn) return spansForColumn(parentColumn.columnId);
|
|
979
|
+
const cached = virtualParents.get(ref);
|
|
980
|
+
if (cached !== void 0) return cached;
|
|
981
|
+
const spans = computeRowSpans(data, ref);
|
|
982
|
+
virtualParents.set(ref, spans);
|
|
983
|
+
return spans;
|
|
984
|
+
};
|
|
985
|
+
for (const column of columnKeys) {
|
|
986
|
+
spansForColumn(column.columnId);
|
|
907
987
|
}
|
|
908
988
|
return map;
|
|
909
989
|
}
|
|
@@ -919,7 +999,8 @@ function collectRowSpanColumns(columns) {
|
|
|
919
999
|
if (!columnId || !columnDef.meta?.rowSpan) continue;
|
|
920
1000
|
result.push({
|
|
921
1001
|
columnId,
|
|
922
|
-
rowSpanKey: columnDef.meta.rowSpanKey ?? columnId
|
|
1002
|
+
rowSpanKey: columnDef.meta.rowSpanKey ?? columnId,
|
|
1003
|
+
rowSpanParent: normalizeRowSpanParent(columnDef.meta.rowSpanParent)
|
|
923
1004
|
});
|
|
924
1005
|
}
|
|
925
1006
|
};
|
|
@@ -1312,7 +1393,9 @@ function DataTableRow({
|
|
|
1312
1393
|
const hasSelectionEdges = hasCellSelectionEdges(selectionEdgeStyle);
|
|
1313
1394
|
const sizeStyle = getColumnSizeStyle(cell.column.getSize(), {
|
|
1314
1395
|
force: enableColumnResize,
|
|
1315
|
-
lockMax: enableColumnResize
|
|
1396
|
+
lockMax: enableColumnResize,
|
|
1397
|
+
minWidth: meta?.minWidth,
|
|
1398
|
+
maxWidth: meta?.maxWidth
|
|
1316
1399
|
});
|
|
1317
1400
|
const freezeOffset = enableColumnFreeze ? freezeOffsets.get(columnId) : void 0;
|
|
1318
1401
|
const freezeStyle = getColumnFreezeStyle(freezeOffset);
|
|
@@ -4158,7 +4241,9 @@ function DataTable({
|
|
|
4158
4241
|
const canResize = enableColumnResize && header.column.getCanResize();
|
|
4159
4242
|
const sizeStyle = getColumnSizeStyle(header.getSize(), {
|
|
4160
4243
|
force: enableColumnResize,
|
|
4161
|
-
lockMax: enableColumnResize
|
|
4244
|
+
lockMax: enableColumnResize,
|
|
4245
|
+
minWidth: header.column.columnDef.meta?.minWidth,
|
|
4246
|
+
maxWidth: header.column.columnDef.meta?.maxWidth
|
|
4162
4247
|
});
|
|
4163
4248
|
const freezeOffset = enableColumnFreeze ? resolveHeaderFreezeOffset(header.column, freezeOffsets) : void 0;
|
|
4164
4249
|
const freezeStyle = getColumnFreezeStyle(freezeOffset, {
|
|
@@ -4398,12 +4483,15 @@ function buildColumnDef(props, sort, onSort) {
|
|
|
4398
4483
|
width,
|
|
4399
4484
|
minWidth,
|
|
4400
4485
|
maxWidth,
|
|
4486
|
+
minResizeWidth,
|
|
4487
|
+
maxResizeWidth,
|
|
4401
4488
|
resizable,
|
|
4402
4489
|
reorderable,
|
|
4403
4490
|
frozen,
|
|
4404
4491
|
align,
|
|
4405
4492
|
rowSpan,
|
|
4406
4493
|
rowSpanKey,
|
|
4494
|
+
rowSpanParent,
|
|
4407
4495
|
editable,
|
|
4408
4496
|
editType,
|
|
4409
4497
|
editInputProps,
|
|
@@ -4417,8 +4505,8 @@ function buildColumnDef(props, sort, onSort) {
|
|
|
4417
4505
|
id: field,
|
|
4418
4506
|
...!virtual ? { accessorKey: field } : {},
|
|
4419
4507
|
size: width ?? DATA_TABLE_COLUMN_SIZE,
|
|
4420
|
-
...
|
|
4421
|
-
...
|
|
4508
|
+
...minResizeWidth != null ? { minSize: minResizeWidth } : {},
|
|
4509
|
+
...maxResizeWidth != null ? { maxSize: maxResizeWidth } : {},
|
|
4422
4510
|
...resizable === false ? { enableResizing: false } : {},
|
|
4423
4511
|
header: sortable ? () => /* @__PURE__ */ jsx8(
|
|
4424
4512
|
SortableHeader,
|
|
@@ -4438,6 +4526,7 @@ function buildColumnDef(props, sort, onSort) {
|
|
|
4438
4526
|
align,
|
|
4439
4527
|
rowSpan,
|
|
4440
4528
|
rowSpanKey,
|
|
4529
|
+
rowSpanParent,
|
|
4441
4530
|
editable,
|
|
4442
4531
|
editType,
|
|
4443
4532
|
editInputProps,
|
|
@@ -4446,6 +4535,8 @@ function buildColumnDef(props, sort, onSort) {
|
|
|
4446
4535
|
cellRender: render,
|
|
4447
4536
|
frozen,
|
|
4448
4537
|
reorderable,
|
|
4538
|
+
minWidth,
|
|
4539
|
+
maxWidth,
|
|
4449
4540
|
className,
|
|
4450
4541
|
headerClassName
|
|
4451
4542
|
}
|
package/dist/core.cjs
CHANGED
|
@@ -2296,23 +2296,49 @@ function applySelectionUpdater(mode, updater, previous) {
|
|
|
2296
2296
|
function getRowFieldValue(row, key) {
|
|
2297
2297
|
return row[key];
|
|
2298
2298
|
}
|
|
2299
|
-
function
|
|
2299
|
+
function normalizeRowSpanParent(value) {
|
|
2300
|
+
if (!value) return [];
|
|
2301
|
+
return typeof value === "string" ? [value] : [...value];
|
|
2302
|
+
}
|
|
2303
|
+
function toParentSpanList(parentSpans) {
|
|
2304
|
+
if (!parentSpans?.length) return [];
|
|
2305
|
+
const first = parentSpans[0];
|
|
2306
|
+
if (!Array.isArray(first)) {
|
|
2307
|
+
return [parentSpans];
|
|
2308
|
+
}
|
|
2309
|
+
return parentSpans;
|
|
2310
|
+
}
|
|
2311
|
+
function buildStartRowLookup(spans) {
|
|
2312
|
+
const startRows = new Array(spans.length);
|
|
2313
|
+
let origin = 0;
|
|
2314
|
+
for (let i = 0; i < spans.length; i++) {
|
|
2315
|
+
if ((spans[i]?.rowSpan ?? 1) > 0) origin = i;
|
|
2316
|
+
startRows[i] = origin;
|
|
2317
|
+
}
|
|
2318
|
+
return startRows;
|
|
2319
|
+
}
|
|
2320
|
+
function sharesParentGroup(parentStartRows, rowIndex) {
|
|
2321
|
+
if (parentStartRows.length === 0 || rowIndex <= 0) return true;
|
|
2322
|
+
return parentStartRows.every(
|
|
2323
|
+
(startRows) => startRows[rowIndex - 1] === startRows[rowIndex]
|
|
2324
|
+
);
|
|
2325
|
+
}
|
|
2326
|
+
function computeRowSpans(data, rowSpanKey, parentSpans) {
|
|
2300
2327
|
if (data.length === 0) return [];
|
|
2328
|
+
const parentStartRows = toParentSpanList(parentSpans).map(buildStartRowLookup);
|
|
2301
2329
|
const result = [];
|
|
2302
2330
|
for (let index = 0; index < data.length; index++) {
|
|
2303
2331
|
const currentValue = getRowFieldValue(data[index], rowSpanKey);
|
|
2304
2332
|
const previousValue = index > 0 ? getRowFieldValue(data[index - 1], rowSpanKey) : void 0;
|
|
2305
|
-
if (index > 0 && currentValue === previousValue) {
|
|
2333
|
+
if (index > 0 && currentValue === previousValue && sharesParentGroup(parentStartRows, index)) {
|
|
2306
2334
|
result.push({ rowSpan: 0, isFirstInGroup: false });
|
|
2307
2335
|
continue;
|
|
2308
2336
|
}
|
|
2309
2337
|
let span = 1;
|
|
2310
2338
|
for (let nextIndex = index + 1; nextIndex < data.length; nextIndex++) {
|
|
2311
|
-
if (getRowFieldValue(data[nextIndex], rowSpanKey)
|
|
2312
|
-
|
|
2313
|
-
|
|
2314
|
-
break;
|
|
2315
|
-
}
|
|
2339
|
+
if (getRowFieldValue(data[nextIndex], rowSpanKey) !== currentValue) break;
|
|
2340
|
+
if (!sharesParentGroup(parentStartRows, nextIndex)) break;
|
|
2341
|
+
span++;
|
|
2316
2342
|
}
|
|
2317
2343
|
result.push({ rowSpan: span, isFirstInGroup: true });
|
|
2318
2344
|
}
|
|
@@ -2334,10 +2360,50 @@ function resolveRowSpanAt(rowSpans, rowIndex) {
|
|
|
2334
2360
|
}
|
|
2335
2361
|
return { startRow: rowIndex, rowSpan: 1 };
|
|
2336
2362
|
}
|
|
2363
|
+
function findRowSpanColumn(spec, ref) {
|
|
2364
|
+
return spec.find((column) => column.columnId === ref) ?? spec.find((column) => column.rowSpanKey === ref);
|
|
2365
|
+
}
|
|
2337
2366
|
function buildColumnRowSpanMap(data, columnKeys) {
|
|
2338
2367
|
const map = /* @__PURE__ */ new Map();
|
|
2339
|
-
|
|
2340
|
-
|
|
2368
|
+
const visiting = /* @__PURE__ */ new Set();
|
|
2369
|
+
const warnedCycles = /* @__PURE__ */ new Set();
|
|
2370
|
+
const virtualParents = /* @__PURE__ */ new Map();
|
|
2371
|
+
const spansForColumn = (columnId) => {
|
|
2372
|
+
const cached = map.get(columnId);
|
|
2373
|
+
if (cached !== void 0) return cached;
|
|
2374
|
+
const column = columnKeys.find((item) => item.columnId === columnId);
|
|
2375
|
+
if (!column) return void 0;
|
|
2376
|
+
if (visiting.has(columnId)) {
|
|
2377
|
+
if (!warnedCycles.has(columnId)) {
|
|
2378
|
+
warnedCycles.add(columnId);
|
|
2379
|
+
console.warn(
|
|
2380
|
+
`[rowSpan] rowSpanParent cycle detected at column "${columnId}"; dropping the cyclic parent reference.`
|
|
2381
|
+
);
|
|
2382
|
+
}
|
|
2383
|
+
return void 0;
|
|
2384
|
+
}
|
|
2385
|
+
visiting.add(columnId);
|
|
2386
|
+
const parentSpans = (column.rowSpanParent ?? []).map((ref) => spansForParentRef(ref)).filter((spans2) => Boolean(spans2));
|
|
2387
|
+
visiting.delete(columnId);
|
|
2388
|
+
const spans = computeRowSpans(
|
|
2389
|
+
data,
|
|
2390
|
+
column.rowSpanKey,
|
|
2391
|
+
parentSpans.length > 0 ? parentSpans : void 0
|
|
2392
|
+
);
|
|
2393
|
+
map.set(columnId, spans);
|
|
2394
|
+
return spans;
|
|
2395
|
+
};
|
|
2396
|
+
const spansForParentRef = (ref) => {
|
|
2397
|
+
const parentColumn = findRowSpanColumn(columnKeys, ref);
|
|
2398
|
+
if (parentColumn) return spansForColumn(parentColumn.columnId);
|
|
2399
|
+
const cached = virtualParents.get(ref);
|
|
2400
|
+
if (cached !== void 0) return cached;
|
|
2401
|
+
const spans = computeRowSpans(data, ref);
|
|
2402
|
+
virtualParents.set(ref, spans);
|
|
2403
|
+
return spans;
|
|
2404
|
+
};
|
|
2405
|
+
for (const column of columnKeys) {
|
|
2406
|
+
spansForColumn(column.columnId);
|
|
2341
2407
|
}
|
|
2342
2408
|
return map;
|
|
2343
2409
|
}
|
|
@@ -2353,7 +2419,8 @@ function collectRowSpanColumns(columns) {
|
|
|
2353
2419
|
if (!columnId || !columnDef.meta?.rowSpan) continue;
|
|
2354
2420
|
result.push({
|
|
2355
2421
|
columnId,
|
|
2356
|
-
rowSpanKey: columnDef.meta.rowSpanKey ?? columnId
|
|
2422
|
+
rowSpanKey: columnDef.meta.rowSpanKey ?? columnId,
|
|
2423
|
+
rowSpanParent: normalizeRowSpanParent(columnDef.meta.rowSpanParent)
|
|
2357
2424
|
});
|
|
2358
2425
|
}
|
|
2359
2426
|
};
|
|
@@ -3055,15 +3122,29 @@ function ResolvedTableCell({
|
|
|
3055
3122
|
|
|
3056
3123
|
// src/components/ui/table/features/column-resize/columnResize.ts
|
|
3057
3124
|
function getColumnSizeStyle(size, options) {
|
|
3058
|
-
const { force = false, lockMax = false } = options ?? {};
|
|
3059
|
-
if (
|
|
3125
|
+
const { force = false, lockMax = false, minWidth, maxWidth } = options ?? {};
|
|
3126
|
+
if (lockMax) {
|
|
3127
|
+
return {
|
|
3128
|
+
width: size,
|
|
3129
|
+
minWidth: size,
|
|
3130
|
+
maxWidth: size
|
|
3131
|
+
};
|
|
3132
|
+
}
|
|
3133
|
+
const hasExplicitSize = force || size !== DATA_TABLE_COLUMN_SIZE;
|
|
3134
|
+
if (!hasExplicitSize && minWidth == null && maxWidth == null) {
|
|
3060
3135
|
return void 0;
|
|
3061
3136
|
}
|
|
3062
|
-
|
|
3063
|
-
|
|
3064
|
-
|
|
3065
|
-
|
|
3066
|
-
}
|
|
3137
|
+
const style = {};
|
|
3138
|
+
if (hasExplicitSize) {
|
|
3139
|
+
style.width = size;
|
|
3140
|
+
style.minWidth = minWidth ?? size;
|
|
3141
|
+
} else if (minWidth != null) {
|
|
3142
|
+
style.minWidth = minWidth;
|
|
3143
|
+
}
|
|
3144
|
+
if (maxWidth != null) {
|
|
3145
|
+
style.maxWidth = maxWidth;
|
|
3146
|
+
}
|
|
3147
|
+
return style;
|
|
3067
3148
|
}
|
|
3068
3149
|
|
|
3069
3150
|
// src/components/ui/table/features/column-reorder/useColumnReorder.ts
|