@jielga/tmdatagrid 2.3.0 → 2.5.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/dist/index.d.ts +289 -9
- package/dist/index.js +1418 -1280
- package/dist/index.js.map +1 -1
- package/docs/columns.md +8 -0
- package/docs/editors.md +31 -0
- package/docs/filtering.md +2 -1
- package/docs/grouping.md +1 -1
- package/docs/localization.md +3 -3
- package/docs/persistence.md +88 -0
- package/docs/typed-deep-links.md +169 -0
- package/package.json +1 -1
- package/skills/appearance/SKILL.md +1 -1
- package/skills/appearance/references/labels.md +3 -3
- package/skills/cell-selection/SKILL.md +1 -1
- package/skills/columns/SKILL.md +5 -2
- package/skills/columns/references/columns-api.md +1 -0
- package/skills/data/SKILL.md +1 -1
- package/skills/editing/SKILL.md +15 -2
- package/skills/editing/references/editing-api.md +2 -1
- package/skills/editing/references/editors-and-validation.md +24 -0
- package/skills/filtering/SKILL.md +3 -2
- package/skills/getting-started/SKILL.md +2 -2
- package/skills/grouping/SKILL.md +2 -2
- package/skills/migrating-to-2/SKILL.md +1 -1
- package/skills/options/SKILL.md +30 -6
- package/skills/options/references/typed-links.md +134 -0
- package/skills/rows/SKILL.md +1 -1
- package/skills/server-side/SKILL.md +1 -1
- package/skills/testing/SKILL.md +1 -1
- package/skills/testing-components/SKILL.md +1 -1
- package/skills/testing-editing/SKILL.md +1 -1
- package/src/components/TMDataGridFilterPills.tsx +15 -1
- package/src/components/TMDataGridGroupColumn.tsx +19 -4
- package/src/components/TMDataGridHeaderFilterRow.tsx +7 -1
- package/src/core/editEngine.ts +101 -5
- package/src/core/filterOperators.ts +41 -18
- package/src/core/grouping.ts +11 -3
- package/src/core/labels.ts +4 -3
- package/src/core/persistence.ts +9 -1
- package/src/core/urlState.ts +439 -0
- package/src/core/valueText.ts +46 -0
- package/src/index.ts +15 -0
- package/src/useTMDataGrid.tsx +51 -8
|
@@ -0,0 +1,46 @@
|
|
|
1
|
+
import type { TMDataGridOption } from "./columnOptions";
|
|
2
|
+
import type { TMDataGridColumnType } from "./filterOperators";
|
|
3
|
+
import type { TMDataGridLabels } from "./labels";
|
|
4
|
+
|
|
5
|
+
/** The English boolean labels - the defaults `TMDATAGRID_LABELS_EN` takes. */
|
|
6
|
+
export const BOOLEAN_LABELS_EN = {
|
|
7
|
+
booleanTrue: "Yes",
|
|
8
|
+
booleanFalse: "No",
|
|
9
|
+
} as const satisfies Pick<TMDataGridLabels, "booleanTrue" | "booleanFalse">;
|
|
10
|
+
|
|
11
|
+
export type TMDataGridValueTextOptions = {
|
|
12
|
+
/** The column's `meta.type`. A `boolean` column's `"true"` / `"false"` filter strings read as booleans. */
|
|
13
|
+
type?: TMDataGridColumnType;
|
|
14
|
+
/** The column's resolved options: a value with an option reads as its label. */
|
|
15
|
+
options?: ReadonlyArray<TMDataGridOption>;
|
|
16
|
+
/** What `true` and `false` read as. Defaults to English. */
|
|
17
|
+
labels?: Pick<TMDataGridLabels, "booleanTrue" | "booleanFalse">;
|
|
18
|
+
};
|
|
19
|
+
|
|
20
|
+
/**
|
|
21
|
+
* A value as the grid's chrome writes it in words - on a filter pill, in a
|
|
22
|
+
* group row - rather than `String(value)`, which writes `true`, an option's
|
|
23
|
+
* key instead of its label, and a `Date` as an English timestamp.
|
|
24
|
+
*/
|
|
25
|
+
export function formatValueText(
|
|
26
|
+
value: unknown,
|
|
27
|
+
{ type, options, labels = BOOLEAN_LABELS_EN }: TMDataGridValueTextOptions = {},
|
|
28
|
+
): string {
|
|
29
|
+
if (Array.isArray(value)) {
|
|
30
|
+
return value
|
|
31
|
+
.map((entry) => formatValueText(entry, { type, options, labels }))
|
|
32
|
+
.join(", ");
|
|
33
|
+
}
|
|
34
|
+
if (value === true || (type === "boolean" && value === "true")) {
|
|
35
|
+
return labels.booleanTrue;
|
|
36
|
+
}
|
|
37
|
+
if (value === false || (type === "boolean" && value === "false")) {
|
|
38
|
+
return labels.booleanFalse;
|
|
39
|
+
}
|
|
40
|
+
if (value instanceof Date) {
|
|
41
|
+
return Number.isNaN(value.getTime()) ? "" : value.toLocaleDateString();
|
|
42
|
+
}
|
|
43
|
+
const text = String(value);
|
|
44
|
+
const option = options?.find((candidate) => candidate.value === text);
|
|
45
|
+
return option?.label ?? text;
|
|
46
|
+
}
|
package/src/index.ts
CHANGED
|
@@ -110,6 +110,8 @@ export {
|
|
|
110
110
|
type TMDataGridEditRowProjection,
|
|
111
111
|
type TMDataGridEditRowSnapshot,
|
|
112
112
|
type TMDataGridEditState,
|
|
113
|
+
type TMDataGridEditCommitMap,
|
|
114
|
+
type TMDataGridEditCommitMapArgs,
|
|
113
115
|
type TMDataGridEditValueMap,
|
|
114
116
|
type TMDataGridEditValueMapArgs,
|
|
115
117
|
type TMDataGridFieldValidate,
|
|
@@ -264,6 +266,19 @@ export {
|
|
|
264
266
|
type TMDataGridStorageMode,
|
|
265
267
|
type TMDataGridUrlStorage,
|
|
266
268
|
} from "./core/persistence";
|
|
269
|
+
export {
|
|
270
|
+
createTMDataGridUrlState,
|
|
271
|
+
type TMDataGridColumnInfo,
|
|
272
|
+
type TMDataGridColumnInfoOf,
|
|
273
|
+
type TMDataGridDateInput,
|
|
274
|
+
type TMDataGridTypedColumn,
|
|
275
|
+
type TMDataGridUrlFiltersInput,
|
|
276
|
+
type TMDataGridUrlInput,
|
|
277
|
+
type TMDataGridUrlPayload,
|
|
278
|
+
type TMDataGridUrlSearchStorage,
|
|
279
|
+
type TMDataGridUrlSortableId,
|
|
280
|
+
type TMDataGridUrlState,
|
|
281
|
+
} from "./core/urlState";
|
|
267
282
|
export type {
|
|
268
283
|
TMDataGridCellEventArgs,
|
|
269
284
|
TMDataGridRowContextMenuArgs,
|
package/src/useTMDataGrid.tsx
CHANGED
|
@@ -77,6 +77,7 @@ import {
|
|
|
77
77
|
import {
|
|
78
78
|
emptyValueForOperator,
|
|
79
79
|
type TMDataGridColumnType,
|
|
80
|
+
type TMDataGridFilterOperator,
|
|
80
81
|
tmDataGridFilterFn,
|
|
81
82
|
} from "./core/filterOperators";
|
|
82
83
|
import {
|
|
@@ -137,6 +138,12 @@ import {
|
|
|
137
138
|
type TMDataGridQueryTable,
|
|
138
139
|
} from "./core/pageReset";
|
|
139
140
|
import type { TMDataGridCellRange } from "./core/cellRange";
|
|
141
|
+
import type {
|
|
142
|
+
TMDataGridAccessorColumnId,
|
|
143
|
+
TMDataGridColumnInfoHints,
|
|
144
|
+
TMDataGridColumnInfoOf,
|
|
145
|
+
TMDataGridTypedColumn,
|
|
146
|
+
} from "./core/urlState";
|
|
140
147
|
import {
|
|
141
148
|
resolveExportOptions,
|
|
142
149
|
type TMDataGridExportOptions,
|
|
@@ -361,6 +368,13 @@ type WithRowTypedMeta<TDef, TData extends RowData> = TDef extends unknown
|
|
|
361
368
|
* TanStack's column helper with `meta` typed against `TData`, so the
|
|
362
369
|
* `meta.options` and `meta.edit.enabled` callbacks receive
|
|
363
370
|
* `Row<TMDataGridFeatures, TData>`.
|
|
371
|
+
*
|
|
372
|
+
* Every column it returns also carries `TMDataGridColumnInfo` in its type,
|
|
373
|
+
* read from the literal values of `id`, `meta.type`,
|
|
374
|
+
* `meta.filter.operators`, `meta.filter.url`, `enableColumnFilter` and
|
|
375
|
+
* `enableSorting`. `createTMDataGridUrlState` reads it to type the links into
|
|
376
|
+
* the grid. TanStack's own return type keeps none of this: it types
|
|
377
|
+
* `accessorKey` as a plain string.
|
|
364
378
|
*/
|
|
365
379
|
export type TMDataGridColumnHelper<TData extends RowData> = {
|
|
366
380
|
accessor: <
|
|
@@ -370,6 +384,12 @@ export type TMDataGridColumnHelper<TData extends RowData> = {
|
|
|
370
384
|
: TAccessor extends DeepKeys<TData>
|
|
371
385
|
? DeepValue<TData, TAccessor>
|
|
372
386
|
: never,
|
|
387
|
+
const TId extends string = never,
|
|
388
|
+
TType extends TMDataGridColumnType = "string",
|
|
389
|
+
TOperator extends TMDataGridFilterOperator = TMDataGridFilterOperator,
|
|
390
|
+
TFilterable extends boolean = true,
|
|
391
|
+
TSortable extends boolean = true,
|
|
392
|
+
TUrl extends boolean = true,
|
|
373
393
|
>(
|
|
374
394
|
accessor: TAccessor,
|
|
375
395
|
column: WithRowTypedMeta<
|
|
@@ -377,20 +397,43 @@ export type TMDataGridColumnHelper<TData extends RowData> = {
|
|
|
377
397
|
? DisplayColumnDef<TMDataGridFeatures, TData, TValue>
|
|
378
398
|
: IdentifiedColumnDef<TMDataGridFeatures, TData, TValue>,
|
|
379
399
|
TData
|
|
380
|
-
|
|
381
|
-
|
|
400
|
+
> &
|
|
401
|
+
TMDataGridColumnInfoHints<
|
|
402
|
+
TId,
|
|
403
|
+
TType,
|
|
404
|
+
TOperator,
|
|
405
|
+
TFilterable,
|
|
406
|
+
TSortable,
|
|
407
|
+
TUrl
|
|
408
|
+
>,
|
|
409
|
+
) => (TAccessor extends AccessorFn<TData>
|
|
382
410
|
? AccessorFnColumnDef<TMDataGridFeatures, TData, TValue>
|
|
383
|
-
: AccessorKeyColumnDef<TMDataGridFeatures, TData, TValue
|
|
411
|
+
: AccessorKeyColumnDef<TMDataGridFeatures, TData, TValue>) &
|
|
412
|
+
TMDataGridTypedColumn<{
|
|
413
|
+
id: TMDataGridAccessorColumnId<TAccessor, TId>;
|
|
414
|
+
type: TType;
|
|
415
|
+
value: TValue;
|
|
416
|
+
operators: TOperator;
|
|
417
|
+
filterable: TFilterable;
|
|
418
|
+
sortable: TSortable;
|
|
419
|
+
url: TUrl;
|
|
420
|
+
}>;
|
|
384
421
|
columns: ColumnHelper<TMDataGridFeatures, TData>["columns"];
|
|
385
422
|
display: (
|
|
386
423
|
column: WithRowTypedMeta<DisplayColumnDef<TMDataGridFeatures, TData>, TData>,
|
|
387
424
|
) => DisplayColumnDef<TMDataGridFeatures, TData, unknown>;
|
|
388
|
-
group
|
|
425
|
+
/** A header group. Carries the column info of every column under it. */
|
|
426
|
+
group: <
|
|
427
|
+
const TChildren extends ReadonlyArray<
|
|
428
|
+
ColumnDef<TMDataGridFeatures, TData, any>
|
|
429
|
+
>,
|
|
430
|
+
>(
|
|
389
431
|
column: WithRowTypedMeta<
|
|
390
|
-
GroupColumnDef<TMDataGridFeatures, TData, unknown>,
|
|
432
|
+
Omit<GroupColumnDef<TMDataGridFeatures, TData, unknown>, "columns">,
|
|
391
433
|
TData
|
|
392
|
-
|
|
393
|
-
) => GroupColumnDef<TMDataGridFeatures, TData, unknown
|
|
434
|
+
> & { columns: TChildren },
|
|
435
|
+
) => GroupColumnDef<TMDataGridFeatures, TData, unknown> &
|
|
436
|
+
TMDataGridTypedColumn<TMDataGridColumnInfoOf<TChildren[number]>>;
|
|
394
437
|
};
|
|
395
438
|
|
|
396
439
|
export function createTMDataGridColumnHelper<
|
|
@@ -734,7 +777,7 @@ type TMDataGridEditingCallbacks<TData extends RowData> = {
|
|
|
734
777
|
* One TanStack Form per editing row; drafts survive scrolling because the
|
|
735
778
|
* forms live outside the DOM, keyed by row id. Which columns edit, and with
|
|
736
779
|
* what, is declared per column under `meta.edit`: `meta.type` picks the
|
|
737
|
-
* built-in editor, and `enabled`, `field`, `editor`, `validate` and `
|
|
780
|
+
* built-in editor, and `enabled`, `field`, `editor`, `validate`, `mapValue` and `mapCommitValue`
|
|
738
781
|
* override the rest.
|
|
739
782
|
*/
|
|
740
783
|
export type TMDataGridEditingOptions<TData extends RowData> =
|