@ai-matrx/design-system 0.18.7 → 0.18.9
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/CHANGELOG.md +22 -0
- package/dist/data-table/index.cjs +434 -541
- package/dist/data-table/index.cjs.map +1 -1
- package/dist/data-table/index.js +434 -546
- package/dist/data-table/index.js.map +1 -1
- package/dist/styles.css +4 -1
- package/package.json +1 -1
|
@@ -6,9 +6,6 @@ var __getOwnPropDesc = Object.getOwnPropertyDescriptor;
|
|
|
6
6
|
var __getOwnPropNames = Object.getOwnPropertyNames;
|
|
7
7
|
var __getProtoOf = Object.getPrototypeOf;
|
|
8
8
|
var __hasOwnProp = Object.prototype.hasOwnProperty;
|
|
9
|
-
var __esm = (fn, res) => function __init() {
|
|
10
|
-
return fn && (res = (0, fn[__getOwnPropNames(fn)[0]])(fn = 0)), res;
|
|
11
|
-
};
|
|
12
9
|
var __export = (target, all) => {
|
|
13
10
|
for (var name in all)
|
|
14
11
|
__defProp(target, name, { get: all[name], enumerable: true });
|
|
@@ -31,406 +28,6 @@ var __toESM = (mod, isNodeMode, target) => (target = mod != null ? __create(__ge
|
|
|
31
28
|
));
|
|
32
29
|
var __toCommonJS = (mod) => __copyProps(__defProp({}, "__esModule", { value: true }), mod);
|
|
33
30
|
|
|
34
|
-
// src/data-table/layered-filters.ts
|
|
35
|
-
function operatorsForLayeredField(field) {
|
|
36
|
-
if (field.operators) return field.operators;
|
|
37
|
-
if (field.kind === "number") return NUMBER_OPERATORS;
|
|
38
|
-
if (field.kind === "select") return SELECT_OPERATORS;
|
|
39
|
-
return TEXT_OPERATORS;
|
|
40
|
-
}
|
|
41
|
-
function layeredFilterNeedsValue(operator) {
|
|
42
|
-
return operator !== "is_empty" && operator !== "is_not_empty";
|
|
43
|
-
}
|
|
44
|
-
function isCompleteLayeredFilterRule(rule) {
|
|
45
|
-
if (!layeredFilterNeedsValue(rule.operator)) return true;
|
|
46
|
-
if (rule.value.trim() === "") return false;
|
|
47
|
-
return rule.operator !== "between" || Boolean(rule.valueTo?.trim());
|
|
48
|
-
}
|
|
49
|
-
function completeLayeredFilterRules(rules) {
|
|
50
|
-
return (rules ?? []).filter(isCompleteLayeredFilterRule);
|
|
51
|
-
}
|
|
52
|
-
function isLayeredFilterOperator(value) {
|
|
53
|
-
return LAYERED_FILTER_OPERATORS.some((operator) => operator === value);
|
|
54
|
-
}
|
|
55
|
-
function normalizedText(value) {
|
|
56
|
-
if (value === null || value === void 0) return "";
|
|
57
|
-
return String(value).trim().toLocaleLowerCase();
|
|
58
|
-
}
|
|
59
|
-
function words(value) {
|
|
60
|
-
return value.split(/[^\p{L}\p{N}]+/u).filter(Boolean);
|
|
61
|
-
}
|
|
62
|
-
function layeredFilterMatchesValue(value, rule) {
|
|
63
|
-
const actual = normalizedText(value);
|
|
64
|
-
const expected = rule.value.trim().toLocaleLowerCase();
|
|
65
|
-
const expectedTo = rule.valueTo?.trim().toLocaleLowerCase() ?? "";
|
|
66
|
-
switch (rule.operator) {
|
|
67
|
-
case "contains":
|
|
68
|
-
return actual.includes(expected);
|
|
69
|
-
case "not_contains":
|
|
70
|
-
return !actual.includes(expected);
|
|
71
|
-
case "equals":
|
|
72
|
-
return actual === expected;
|
|
73
|
-
case "not_equals":
|
|
74
|
-
return actual !== expected;
|
|
75
|
-
case "starts_with":
|
|
76
|
-
return actual.startsWith(expected);
|
|
77
|
-
case "ends_with":
|
|
78
|
-
return actual.endsWith(expected);
|
|
79
|
-
case "word":
|
|
80
|
-
return words(actual).includes(expected);
|
|
81
|
-
case "not_word":
|
|
82
|
-
return !words(actual).includes(expected);
|
|
83
|
-
case "is_empty":
|
|
84
|
-
return actual === "";
|
|
85
|
-
case "is_not_empty":
|
|
86
|
-
return actual !== "";
|
|
87
|
-
case "greater_than":
|
|
88
|
-
return Number(actual) > Number(expected);
|
|
89
|
-
case "greater_or_equal":
|
|
90
|
-
return Number(actual) >= Number(expected);
|
|
91
|
-
case "less_than":
|
|
92
|
-
return Number(actual) < Number(expected);
|
|
93
|
-
case "less_or_equal":
|
|
94
|
-
return Number(actual) <= Number(expected);
|
|
95
|
-
case "between": {
|
|
96
|
-
const numeric = Number(actual);
|
|
97
|
-
return numeric >= Number(expected) && numeric <= Number(expectedTo);
|
|
98
|
-
}
|
|
99
|
-
}
|
|
100
|
-
}
|
|
101
|
-
function layeredFilterRuleSummary(rule, fields) {
|
|
102
|
-
const field = fields.find((candidate) => candidate.id === rule.field);
|
|
103
|
-
const fieldLabel = field?.label ?? rule.field;
|
|
104
|
-
const operator = LAYERED_FILTER_OPERATOR_LABELS[rule.operator];
|
|
105
|
-
if (!layeredFilterNeedsValue(rule.operator))
|
|
106
|
-
return `${fieldLabel} ${operator}`;
|
|
107
|
-
const selectedLabel = field?.kind === "select" ? field.options.find((option) => option.value === rule.value)?.label : void 0;
|
|
108
|
-
const value = selectedLabel ?? rule.value;
|
|
109
|
-
return rule.operator === "between" ? `${fieldLabel} ${operator} ${value} and ${rule.valueTo ?? ""}` : `${fieldLabel} ${operator} ${value}`;
|
|
110
|
-
}
|
|
111
|
-
var import_zod, LAYERED_FILTER_OPERATORS, layeredFilterRuleSchema, layeredFilterRulesSchema, TEXT_OPERATORS, NUMBER_OPERATORS, SELECT_OPERATORS, LAYERED_FILTER_OPERATOR_LABELS;
|
|
112
|
-
var init_layered_filters = __esm({
|
|
113
|
-
"src/data-table/layered-filters.ts"() {
|
|
114
|
-
"use strict";
|
|
115
|
-
import_zod = require("zod");
|
|
116
|
-
LAYERED_FILTER_OPERATORS = [
|
|
117
|
-
"contains",
|
|
118
|
-
"not_contains",
|
|
119
|
-
"equals",
|
|
120
|
-
"not_equals",
|
|
121
|
-
"starts_with",
|
|
122
|
-
"ends_with",
|
|
123
|
-
"word",
|
|
124
|
-
"not_word",
|
|
125
|
-
"is_empty",
|
|
126
|
-
"is_not_empty",
|
|
127
|
-
"greater_than",
|
|
128
|
-
"greater_or_equal",
|
|
129
|
-
"less_than",
|
|
130
|
-
"less_or_equal",
|
|
131
|
-
"between"
|
|
132
|
-
];
|
|
133
|
-
layeredFilterRuleSchema = import_zod.z.object({
|
|
134
|
-
id: import_zod.z.string().min(1),
|
|
135
|
-
field: import_zod.z.string().min(1),
|
|
136
|
-
operator: import_zod.z.enum(LAYERED_FILTER_OPERATORS),
|
|
137
|
-
value: import_zod.z.string(),
|
|
138
|
-
valueTo: import_zod.z.string().optional()
|
|
139
|
-
});
|
|
140
|
-
layeredFilterRulesSchema = import_zod.z.array(layeredFilterRuleSchema).max(20);
|
|
141
|
-
TEXT_OPERATORS = [
|
|
142
|
-
"contains",
|
|
143
|
-
"not_contains",
|
|
144
|
-
"equals",
|
|
145
|
-
"not_equals",
|
|
146
|
-
"starts_with",
|
|
147
|
-
"ends_with",
|
|
148
|
-
"word",
|
|
149
|
-
"not_word",
|
|
150
|
-
"is_empty",
|
|
151
|
-
"is_not_empty"
|
|
152
|
-
];
|
|
153
|
-
NUMBER_OPERATORS = [
|
|
154
|
-
"equals",
|
|
155
|
-
"not_equals",
|
|
156
|
-
"greater_than",
|
|
157
|
-
"greater_or_equal",
|
|
158
|
-
"less_than",
|
|
159
|
-
"less_or_equal",
|
|
160
|
-
"between",
|
|
161
|
-
"is_empty",
|
|
162
|
-
"is_not_empty"
|
|
163
|
-
];
|
|
164
|
-
SELECT_OPERATORS = [
|
|
165
|
-
"equals",
|
|
166
|
-
"not_equals",
|
|
167
|
-
"is_empty",
|
|
168
|
-
"is_not_empty"
|
|
169
|
-
];
|
|
170
|
-
LAYERED_FILTER_OPERATOR_LABELS = {
|
|
171
|
-
contains: "contains",
|
|
172
|
-
not_contains: "doesn't contain",
|
|
173
|
-
equals: "is",
|
|
174
|
-
not_equals: "is not",
|
|
175
|
-
starts_with: "starts with",
|
|
176
|
-
ends_with: "ends with",
|
|
177
|
-
word: "has the word",
|
|
178
|
-
not_word: "doesn't have the word",
|
|
179
|
-
is_empty: "is empty",
|
|
180
|
-
is_not_empty: "is not empty",
|
|
181
|
-
greater_than: "is greater than",
|
|
182
|
-
greater_or_equal: "is at least",
|
|
183
|
-
less_than: "is less than",
|
|
184
|
-
less_or_equal: "is at most",
|
|
185
|
-
between: "is between"
|
|
186
|
-
};
|
|
187
|
-
}
|
|
188
|
-
});
|
|
189
|
-
|
|
190
|
-
// src/data-table/filter-engine.ts
|
|
191
|
-
function columnId(col) {
|
|
192
|
-
if (col.id) return col.id;
|
|
193
|
-
if (col.accessorKey) return String(col.accessorKey);
|
|
194
|
-
throw new Error("MatrxDataTable column requires `id` or `accessorKey`");
|
|
195
|
-
}
|
|
196
|
-
function getCellValue(row, col) {
|
|
197
|
-
if (col.accessorFn) return col.accessorFn(row);
|
|
198
|
-
if (col.accessorKey) {
|
|
199
|
-
return row[col.accessorKey];
|
|
200
|
-
}
|
|
201
|
-
return void 0;
|
|
202
|
-
}
|
|
203
|
-
function getFilterValue(row, col) {
|
|
204
|
-
return col.filterValue ? col.filterValue(row) : getCellValue(row, col);
|
|
205
|
-
}
|
|
206
|
-
function getSortValue(row, col) {
|
|
207
|
-
return col.sortValue ? col.sortValue(row) : getCellValue(row, col);
|
|
208
|
-
}
|
|
209
|
-
function stringifyCellValue(value) {
|
|
210
|
-
if (value == null) return "";
|
|
211
|
-
if (typeof value === "string") return value;
|
|
212
|
-
if (typeof value === "number" || typeof value === "boolean") {
|
|
213
|
-
return String(value);
|
|
214
|
-
}
|
|
215
|
-
if (value instanceof Date) return value.toISOString();
|
|
216
|
-
try {
|
|
217
|
-
return JSON.stringify(value);
|
|
218
|
-
} catch {
|
|
219
|
-
return String(value);
|
|
220
|
-
}
|
|
221
|
-
}
|
|
222
|
-
function tableSearchWords(value) {
|
|
223
|
-
return value.toLocaleLowerCase().split(/[^\p{L}\p{N}]+/u).filter(Boolean);
|
|
224
|
-
}
|
|
225
|
-
function matchesTableSearch(searchableText, query, mode = "contains") {
|
|
226
|
-
const normalizedQuery = query.trim().toLocaleLowerCase();
|
|
227
|
-
if (!normalizedQuery) return true;
|
|
228
|
-
if (mode === "contains") {
|
|
229
|
-
return searchableText.toLocaleLowerCase().includes(normalizedQuery);
|
|
230
|
-
}
|
|
231
|
-
const actualWords = new Set(tableSearchWords(searchableText));
|
|
232
|
-
const expectedWords = tableSearchWords(normalizedQuery);
|
|
233
|
-
return expectedWords.length > 0 && expectedWords.every((word) => actualWords.has(word));
|
|
234
|
-
}
|
|
235
|
-
function compareValues(a, b) {
|
|
236
|
-
if (a == null && b == null) return 0;
|
|
237
|
-
if (a == null) return -1;
|
|
238
|
-
if (b == null) return 1;
|
|
239
|
-
if (typeof a === "number" && typeof b === "number") return a - b;
|
|
240
|
-
if (typeof a === "boolean" && typeof b === "boolean") {
|
|
241
|
-
return Number(a) - Number(b);
|
|
242
|
-
}
|
|
243
|
-
return stringifyCellValue(a).localeCompare(stringifyCellValue(b), void 0, {
|
|
244
|
-
numeric: true,
|
|
245
|
-
sensitivity: "base"
|
|
246
|
-
});
|
|
247
|
-
}
|
|
248
|
-
function passesColumnFilter(value, filter) {
|
|
249
|
-
const matches = (() => {
|
|
250
|
-
switch (filter.kind) {
|
|
251
|
-
case "text": {
|
|
252
|
-
const s = stringifyCellValue(value);
|
|
253
|
-
if (filter.mode === "null") return value == null;
|
|
254
|
-
if (filter.mode === "not_null") return value != null;
|
|
255
|
-
if (filter.mode === "empty") return s.trim() === "";
|
|
256
|
-
if (filter.mode === "not_empty") return s.trim() !== "";
|
|
257
|
-
const q = filter.value.trim().toLowerCase();
|
|
258
|
-
if (!q) return true;
|
|
259
|
-
return s.toLowerCase().includes(q);
|
|
260
|
-
}
|
|
261
|
-
case "select": {
|
|
262
|
-
const selected = filter.values ?? (filter.value && filter.value !== "__all__" ? [filter.value] : []);
|
|
263
|
-
if (selected.length === 0) return true;
|
|
264
|
-
const s = stringifyCellValue(value);
|
|
265
|
-
return selected.some(
|
|
266
|
-
(v) => v === SELECT_EMPTY_VALUE ? s === "" : v === SELECT_NOT_EMPTY_VALUE ? s !== "" : s === v
|
|
267
|
-
);
|
|
268
|
-
}
|
|
269
|
-
case "boolean": {
|
|
270
|
-
return Boolean(value) === filter.value;
|
|
271
|
-
}
|
|
272
|
-
case "number": {
|
|
273
|
-
const n = typeof value === "number" ? value : Number(stringifyCellValue(value).replace(/[^0-9.-]/g, ""));
|
|
274
|
-
if (Number.isNaN(n)) return false;
|
|
275
|
-
if (filter.min !== void 0 && n < filter.min) return false;
|
|
276
|
-
if (filter.max !== void 0 && n > filter.max) return false;
|
|
277
|
-
return true;
|
|
278
|
-
}
|
|
279
|
-
}
|
|
280
|
-
})();
|
|
281
|
-
return filter.negated ? !matches : matches;
|
|
282
|
-
}
|
|
283
|
-
function filterAndSortRows(rows, columns, columnFilters, sort, globalSearch, anyOf, layeredFilters, globalSearchMode = "contains", searchText) {
|
|
284
|
-
const colById = new Map(columns.map((c) => [columnId(c), c]));
|
|
285
|
-
const q = globalSearch.trim().toLowerCase();
|
|
286
|
-
const anyQ = anyOf?.query.trim().toLowerCase() ?? "";
|
|
287
|
-
const activeLayeredFilters = completeLayeredFilterRules(layeredFilters);
|
|
288
|
-
let result = rows.filter((row) => {
|
|
289
|
-
for (const [id, filter] of Object.entries(columnFilters)) {
|
|
290
|
-
if (!filter) continue;
|
|
291
|
-
const col = colById.get(id);
|
|
292
|
-
if (!col || col.filter === false) continue;
|
|
293
|
-
if (!passesColumnFilter(getFilterValue(row, col), filter)) return false;
|
|
294
|
-
}
|
|
295
|
-
for (const rule of activeLayeredFilters) {
|
|
296
|
-
const col = colById.get(rule.field);
|
|
297
|
-
if (!col || !layeredFilterMatchesValue(getFilterValue(row, col), rule)) {
|
|
298
|
-
return false;
|
|
299
|
-
}
|
|
300
|
-
}
|
|
301
|
-
if (anyQ && anyOf) {
|
|
302
|
-
const hit = anyOf.columnIds.some((id) => {
|
|
303
|
-
const col = colById.get(id);
|
|
304
|
-
if (!col) return false;
|
|
305
|
-
return stringifyCellValue(getFilterValue(row, col)).toLowerCase().includes(anyQ);
|
|
306
|
-
});
|
|
307
|
-
if (!hit) return false;
|
|
308
|
-
}
|
|
309
|
-
if (!q) return true;
|
|
310
|
-
const searchableValues = columns.filter(
|
|
311
|
-
(col) => col.filter !== false || Boolean(col.accessorKey || col.accessorFn)
|
|
312
|
-
).map((col) => stringifyCellValue(getFilterValue(row, col)));
|
|
313
|
-
const additionalSearchText = searchText?.(row);
|
|
314
|
-
if (additionalSearchText) searchableValues.push(additionalSearchText);
|
|
315
|
-
if (globalSearchMode === "contains") {
|
|
316
|
-
return searchableValues.some(
|
|
317
|
-
(value) => matchesTableSearch(value, q, "contains")
|
|
318
|
-
);
|
|
319
|
-
}
|
|
320
|
-
return matchesTableSearch(searchableValues.join(" "), q, "whole_words");
|
|
321
|
-
});
|
|
322
|
-
if (sort) {
|
|
323
|
-
const col = colById.get(sort.id);
|
|
324
|
-
if (col && col.sortable !== false) {
|
|
325
|
-
const dir = sort.direction === "asc" ? 1 : -1;
|
|
326
|
-
result = [...result].sort((a, b) => {
|
|
327
|
-
const va = getSortValue(a, col);
|
|
328
|
-
const vb = getSortValue(b, col);
|
|
329
|
-
const ea = va == null || stringifyCellValue(va) === "";
|
|
330
|
-
const eb = vb == null || stringifyCellValue(vb) === "";
|
|
331
|
-
if (ea !== eb) return ea ? 1 : -1;
|
|
332
|
-
return compareValues(va, vb) * dir;
|
|
333
|
-
});
|
|
334
|
-
}
|
|
335
|
-
}
|
|
336
|
-
return result;
|
|
337
|
-
}
|
|
338
|
-
function countActiveColumnFilters(filters) {
|
|
339
|
-
let n = 0;
|
|
340
|
-
for (const f of Object.values(filters)) {
|
|
341
|
-
if (!f) continue;
|
|
342
|
-
switch (f.kind) {
|
|
343
|
-
case "text":
|
|
344
|
-
if (f.value.trim() || f.mode && f.mode !== "contains") n += 1;
|
|
345
|
-
break;
|
|
346
|
-
case "select":
|
|
347
|
-
if (f.values ? f.values.length > 0 : f.value && f.value !== "__all__")
|
|
348
|
-
n += 1;
|
|
349
|
-
break;
|
|
350
|
-
case "boolean":
|
|
351
|
-
n += 1;
|
|
352
|
-
break;
|
|
353
|
-
case "number":
|
|
354
|
-
if (f.min !== void 0 || f.max !== void 0) n += 1;
|
|
355
|
-
break;
|
|
356
|
-
}
|
|
357
|
-
}
|
|
358
|
-
return n;
|
|
359
|
-
}
|
|
360
|
-
function isColumnFilterActive(filter) {
|
|
361
|
-
if (!filter) return false;
|
|
362
|
-
switch (filter.kind) {
|
|
363
|
-
case "text":
|
|
364
|
-
return filter.value.trim().length > 0 || filter.mode !== void 0 && filter.mode !== "contains";
|
|
365
|
-
case "select":
|
|
366
|
-
return filter.values ? filter.values.length > 0 : Boolean(filter.value) && filter.value !== "__all__";
|
|
367
|
-
case "boolean":
|
|
368
|
-
return true;
|
|
369
|
-
case "number":
|
|
370
|
-
return filter.min !== void 0 || filter.max !== void 0;
|
|
371
|
-
}
|
|
372
|
-
}
|
|
373
|
-
function applyRowEdits(row, edits) {
|
|
374
|
-
if (!edits || Object.keys(edits).length === 0) return row;
|
|
375
|
-
return { ...row, ...edits };
|
|
376
|
-
}
|
|
377
|
-
var SELECT_EMPTY_VALUE, SELECT_NOT_EMPTY_VALUE;
|
|
378
|
-
var init_filter_engine = __esm({
|
|
379
|
-
"src/data-table/filter-engine.ts"() {
|
|
380
|
-
"use strict";
|
|
381
|
-
init_layered_filters();
|
|
382
|
-
SELECT_EMPTY_VALUE = "__empty__";
|
|
383
|
-
SELECT_NOT_EMPTY_VALUE = "__not_empty__";
|
|
384
|
-
}
|
|
385
|
-
});
|
|
386
|
-
|
|
387
|
-
// src/data-table/tableXlsx.ts
|
|
388
|
-
var tableXlsx_exports = {};
|
|
389
|
-
__export(tableXlsx_exports, {
|
|
390
|
-
downloadTableAsXlsx: () => downloadTableAsXlsx
|
|
391
|
-
});
|
|
392
|
-
function downloadTableAsXlsx({
|
|
393
|
-
rows,
|
|
394
|
-
columns,
|
|
395
|
-
label
|
|
396
|
-
}) {
|
|
397
|
-
const visibleColumns = columns.filter(
|
|
398
|
-
(column) => column.filter !== false || column.accessorKey
|
|
399
|
-
);
|
|
400
|
-
const headers = visibleColumns.map(
|
|
401
|
-
(column) => typeof column.header === "string" ? column.header : columnId(column)
|
|
402
|
-
);
|
|
403
|
-
const values = rows.map(
|
|
404
|
-
(row) => visibleColumns.map(
|
|
405
|
-
(column) => stringifyCellValue(getCellValue(row, column))
|
|
406
|
-
)
|
|
407
|
-
);
|
|
408
|
-
const worksheet = XLSX.utils.aoa_to_sheet([headers, ...values]);
|
|
409
|
-
const workbook = XLSX.utils.book_new();
|
|
410
|
-
const sheetName = label.replace(/[\\/?*[\]:]/g, " ").trim().slice(0, 31) || "Data";
|
|
411
|
-
XLSX.utils.book_append_sheet(workbook, worksheet, sheetName);
|
|
412
|
-
const bytes = XLSX.write(workbook, {
|
|
413
|
-
type: "array",
|
|
414
|
-
bookType: "xlsx",
|
|
415
|
-
compression: true
|
|
416
|
-
});
|
|
417
|
-
const blob = new Blob([bytes], { type: "application/vnd.openxmlformats-officedocument.spreadsheetml.sheet" });
|
|
418
|
-
const url = URL.createObjectURL(blob);
|
|
419
|
-
const anchor = document.createElement("a");
|
|
420
|
-
anchor.href = url;
|
|
421
|
-
anchor.download = `${label.toLowerCase().replace(/[^a-z0-9]+/g, "-") || "table"}.xlsx`;
|
|
422
|
-
anchor.click();
|
|
423
|
-
URL.revokeObjectURL(url);
|
|
424
|
-
}
|
|
425
|
-
var XLSX;
|
|
426
|
-
var init_tableXlsx = __esm({
|
|
427
|
-
"src/data-table/tableXlsx.ts"() {
|
|
428
|
-
"use strict";
|
|
429
|
-
XLSX = __toESM(require("xlsx"), 1);
|
|
430
|
-
init_filter_engine();
|
|
431
|
-
}
|
|
432
|
-
});
|
|
433
|
-
|
|
434
31
|
// src/data-table/index.ts
|
|
435
32
|
var data_table_exports = {};
|
|
436
33
|
__export(data_table_exports, {
|
|
@@ -3850,56 +3447,391 @@ function SourceConfiguration({
|
|
|
3850
3447
|
}
|
|
3851
3448
|
)
|
|
3852
3449
|
}
|
|
3853
|
-
);
|
|
3450
|
+
);
|
|
3451
|
+
}
|
|
3452
|
+
|
|
3453
|
+
// src/data-table/copy-payload.ts
|
|
3454
|
+
function tableAgentText(value) {
|
|
3455
|
+
if (typeof value === "string") return value;
|
|
3456
|
+
const attributes = Object.entries(value.attributes ?? {}).filter(([, entry]) => entry !== null && entry !== void 0 && entry !== "").map(([key, entry]) => ` ${key}="${String(entry)}"`).join("");
|
|
3457
|
+
const context = Object.entries(value.context ?? {}).filter(([, entry]) => entry !== null && entry !== void 0 && entry !== "").map(([key, entry]) => `<${key}>${String(entry)}</${key}>`).join("\n");
|
|
3458
|
+
const url = typeof window === "undefined" ? "" : window.location.href;
|
|
3459
|
+
const route = typeof window === "undefined" ? "" : window.location.pathname;
|
|
3460
|
+
return `<${value.kind}${attributes}>
|
|
3461
|
+
<context>
|
|
3462
|
+
<location>${value.location}</location>
|
|
3463
|
+
${url ? `<url>${url}</url>` : ""}
|
|
3464
|
+
${route ? `<route>${route}</route>` : ""}
|
|
3465
|
+
<copied>${value.description}</copied>
|
|
3466
|
+
<copied-at>${(/* @__PURE__ */ new Date()).toISOString()}</copied-at>
|
|
3467
|
+
${context}
|
|
3468
|
+
</context>
|
|
3469
|
+
${value.summary ? `<summary>
|
|
3470
|
+
${value.summary}
|
|
3471
|
+
</summary>
|
|
3472
|
+
` : ""}<data format="json">
|
|
3473
|
+
\`\`\`json
|
|
3474
|
+
${JSON.stringify(value.data, null, 2)}
|
|
3475
|
+
\`\`\`
|
|
3476
|
+
</data>
|
|
3477
|
+
</${value.kind}>`;
|
|
3478
|
+
}
|
|
3479
|
+
|
|
3480
|
+
// src/data-table/copy.tsx
|
|
3481
|
+
var import_jsx_runtime23 = require("react/jsx-runtime");
|
|
3482
|
+
function CopyButtons(props) {
|
|
3483
|
+
const { CopyControls } = useMatrxDataTableHost();
|
|
3484
|
+
const copyProps = props.export?.sheetRows ? { ...props, primarySource: "table" } : props;
|
|
3485
|
+
if (CopyControls) return /* @__PURE__ */ (0, import_jsx_runtime23.jsx)(CopyControls, { ...copyProps });
|
|
3486
|
+
return /* @__PURE__ */ (0, import_jsx_runtime23.jsx)(MatrxCopyMenu, { ...copyProps });
|
|
3487
|
+
}
|
|
3488
|
+
|
|
3489
|
+
// src/data-table/CopySubset.tsx
|
|
3490
|
+
var import_react4 = require("react");
|
|
3491
|
+
var import_clipboard = require("@ai-matrx/kit/clipboard");
|
|
3492
|
+
|
|
3493
|
+
// src/data-table/layered-filters.ts
|
|
3494
|
+
var import_zod = require("zod");
|
|
3495
|
+
var LAYERED_FILTER_OPERATORS = [
|
|
3496
|
+
"contains",
|
|
3497
|
+
"not_contains",
|
|
3498
|
+
"equals",
|
|
3499
|
+
"not_equals",
|
|
3500
|
+
"starts_with",
|
|
3501
|
+
"ends_with",
|
|
3502
|
+
"word",
|
|
3503
|
+
"not_word",
|
|
3504
|
+
"is_empty",
|
|
3505
|
+
"is_not_empty",
|
|
3506
|
+
"greater_than",
|
|
3507
|
+
"greater_or_equal",
|
|
3508
|
+
"less_than",
|
|
3509
|
+
"less_or_equal",
|
|
3510
|
+
"between"
|
|
3511
|
+
];
|
|
3512
|
+
var layeredFilterRuleSchema = import_zod.z.object({
|
|
3513
|
+
id: import_zod.z.string().min(1),
|
|
3514
|
+
field: import_zod.z.string().min(1),
|
|
3515
|
+
operator: import_zod.z.enum(LAYERED_FILTER_OPERATORS),
|
|
3516
|
+
value: import_zod.z.string(),
|
|
3517
|
+
valueTo: import_zod.z.string().optional()
|
|
3518
|
+
});
|
|
3519
|
+
var layeredFilterRulesSchema = import_zod.z.array(layeredFilterRuleSchema).max(20);
|
|
3520
|
+
var TEXT_OPERATORS = [
|
|
3521
|
+
"contains",
|
|
3522
|
+
"not_contains",
|
|
3523
|
+
"equals",
|
|
3524
|
+
"not_equals",
|
|
3525
|
+
"starts_with",
|
|
3526
|
+
"ends_with",
|
|
3527
|
+
"word",
|
|
3528
|
+
"not_word",
|
|
3529
|
+
"is_empty",
|
|
3530
|
+
"is_not_empty"
|
|
3531
|
+
];
|
|
3532
|
+
var NUMBER_OPERATORS = [
|
|
3533
|
+
"equals",
|
|
3534
|
+
"not_equals",
|
|
3535
|
+
"greater_than",
|
|
3536
|
+
"greater_or_equal",
|
|
3537
|
+
"less_than",
|
|
3538
|
+
"less_or_equal",
|
|
3539
|
+
"between",
|
|
3540
|
+
"is_empty",
|
|
3541
|
+
"is_not_empty"
|
|
3542
|
+
];
|
|
3543
|
+
var SELECT_OPERATORS = [
|
|
3544
|
+
"equals",
|
|
3545
|
+
"not_equals",
|
|
3546
|
+
"is_empty",
|
|
3547
|
+
"is_not_empty"
|
|
3548
|
+
];
|
|
3549
|
+
var LAYERED_FILTER_OPERATOR_LABELS = {
|
|
3550
|
+
contains: "contains",
|
|
3551
|
+
not_contains: "doesn't contain",
|
|
3552
|
+
equals: "is",
|
|
3553
|
+
not_equals: "is not",
|
|
3554
|
+
starts_with: "starts with",
|
|
3555
|
+
ends_with: "ends with",
|
|
3556
|
+
word: "has the word",
|
|
3557
|
+
not_word: "doesn't have the word",
|
|
3558
|
+
is_empty: "is empty",
|
|
3559
|
+
is_not_empty: "is not empty",
|
|
3560
|
+
greater_than: "is greater than",
|
|
3561
|
+
greater_or_equal: "is at least",
|
|
3562
|
+
less_than: "is less than",
|
|
3563
|
+
less_or_equal: "is at most",
|
|
3564
|
+
between: "is between"
|
|
3565
|
+
};
|
|
3566
|
+
function operatorsForLayeredField(field) {
|
|
3567
|
+
if (field.operators) return field.operators;
|
|
3568
|
+
if (field.kind === "number") return NUMBER_OPERATORS;
|
|
3569
|
+
if (field.kind === "select") return SELECT_OPERATORS;
|
|
3570
|
+
return TEXT_OPERATORS;
|
|
3571
|
+
}
|
|
3572
|
+
function layeredFilterNeedsValue(operator) {
|
|
3573
|
+
return operator !== "is_empty" && operator !== "is_not_empty";
|
|
3574
|
+
}
|
|
3575
|
+
function isCompleteLayeredFilterRule(rule) {
|
|
3576
|
+
if (!layeredFilterNeedsValue(rule.operator)) return true;
|
|
3577
|
+
if (rule.value.trim() === "") return false;
|
|
3578
|
+
return rule.operator !== "between" || Boolean(rule.valueTo?.trim());
|
|
3579
|
+
}
|
|
3580
|
+
function completeLayeredFilterRules(rules) {
|
|
3581
|
+
return (rules ?? []).filter(isCompleteLayeredFilterRule);
|
|
3582
|
+
}
|
|
3583
|
+
function isLayeredFilterOperator(value) {
|
|
3584
|
+
return LAYERED_FILTER_OPERATORS.some((operator) => operator === value);
|
|
3585
|
+
}
|
|
3586
|
+
function normalizedText(value) {
|
|
3587
|
+
if (value === null || value === void 0) return "";
|
|
3588
|
+
return String(value).trim().toLocaleLowerCase();
|
|
3589
|
+
}
|
|
3590
|
+
function words(value) {
|
|
3591
|
+
return value.split(/[^\p{L}\p{N}]+/u).filter(Boolean);
|
|
3592
|
+
}
|
|
3593
|
+
function layeredFilterMatchesValue(value, rule) {
|
|
3594
|
+
const actual = normalizedText(value);
|
|
3595
|
+
const expected = rule.value.trim().toLocaleLowerCase();
|
|
3596
|
+
const expectedTo = rule.valueTo?.trim().toLocaleLowerCase() ?? "";
|
|
3597
|
+
switch (rule.operator) {
|
|
3598
|
+
case "contains":
|
|
3599
|
+
return actual.includes(expected);
|
|
3600
|
+
case "not_contains":
|
|
3601
|
+
return !actual.includes(expected);
|
|
3602
|
+
case "equals":
|
|
3603
|
+
return actual === expected;
|
|
3604
|
+
case "not_equals":
|
|
3605
|
+
return actual !== expected;
|
|
3606
|
+
case "starts_with":
|
|
3607
|
+
return actual.startsWith(expected);
|
|
3608
|
+
case "ends_with":
|
|
3609
|
+
return actual.endsWith(expected);
|
|
3610
|
+
case "word":
|
|
3611
|
+
return words(actual).includes(expected);
|
|
3612
|
+
case "not_word":
|
|
3613
|
+
return !words(actual).includes(expected);
|
|
3614
|
+
case "is_empty":
|
|
3615
|
+
return actual === "";
|
|
3616
|
+
case "is_not_empty":
|
|
3617
|
+
return actual !== "";
|
|
3618
|
+
case "greater_than":
|
|
3619
|
+
return Number(actual) > Number(expected);
|
|
3620
|
+
case "greater_or_equal":
|
|
3621
|
+
return Number(actual) >= Number(expected);
|
|
3622
|
+
case "less_than":
|
|
3623
|
+
return Number(actual) < Number(expected);
|
|
3624
|
+
case "less_or_equal":
|
|
3625
|
+
return Number(actual) <= Number(expected);
|
|
3626
|
+
case "between": {
|
|
3627
|
+
const numeric = Number(actual);
|
|
3628
|
+
return numeric >= Number(expected) && numeric <= Number(expectedTo);
|
|
3629
|
+
}
|
|
3630
|
+
}
|
|
3631
|
+
}
|
|
3632
|
+
function layeredFilterRuleSummary(rule, fields) {
|
|
3633
|
+
const field = fields.find((candidate) => candidate.id === rule.field);
|
|
3634
|
+
const fieldLabel = field?.label ?? rule.field;
|
|
3635
|
+
const operator = LAYERED_FILTER_OPERATOR_LABELS[rule.operator];
|
|
3636
|
+
if (!layeredFilterNeedsValue(rule.operator))
|
|
3637
|
+
return `${fieldLabel} ${operator}`;
|
|
3638
|
+
const selectedLabel = field?.kind === "select" ? field.options.find((option) => option.value === rule.value)?.label : void 0;
|
|
3639
|
+
const value = selectedLabel ?? rule.value;
|
|
3640
|
+
return rule.operator === "between" ? `${fieldLabel} ${operator} ${value} and ${rule.valueTo ?? ""}` : `${fieldLabel} ${operator} ${value}`;
|
|
3641
|
+
}
|
|
3642
|
+
|
|
3643
|
+
// src/data-table/filter-engine.ts
|
|
3644
|
+
var SELECT_EMPTY_VALUE = "__empty__";
|
|
3645
|
+
var SELECT_NOT_EMPTY_VALUE = "__not_empty__";
|
|
3646
|
+
function columnId(col) {
|
|
3647
|
+
if (col.id) return col.id;
|
|
3648
|
+
if (col.accessorKey) return String(col.accessorKey);
|
|
3649
|
+
throw new Error("MatrxDataTable column requires `id` or `accessorKey`");
|
|
3650
|
+
}
|
|
3651
|
+
function getCellValue(row, col) {
|
|
3652
|
+
if (col.accessorFn) return col.accessorFn(row);
|
|
3653
|
+
if (col.accessorKey) {
|
|
3654
|
+
return row[col.accessorKey];
|
|
3655
|
+
}
|
|
3656
|
+
return void 0;
|
|
3657
|
+
}
|
|
3658
|
+
function getFilterValue(row, col) {
|
|
3659
|
+
return col.filterValue ? col.filterValue(row) : getCellValue(row, col);
|
|
3660
|
+
}
|
|
3661
|
+
function getSortValue(row, col) {
|
|
3662
|
+
return col.sortValue ? col.sortValue(row) : getCellValue(row, col);
|
|
3663
|
+
}
|
|
3664
|
+
function stringifyCellValue(value) {
|
|
3665
|
+
if (value == null) return "";
|
|
3666
|
+
if (typeof value === "string") return value;
|
|
3667
|
+
if (typeof value === "number" || typeof value === "boolean") {
|
|
3668
|
+
return String(value);
|
|
3669
|
+
}
|
|
3670
|
+
if (value instanceof Date) return value.toISOString();
|
|
3671
|
+
try {
|
|
3672
|
+
return JSON.stringify(value);
|
|
3673
|
+
} catch {
|
|
3674
|
+
return String(value);
|
|
3675
|
+
}
|
|
3676
|
+
}
|
|
3677
|
+
function tableSearchWords(value) {
|
|
3678
|
+
return value.toLocaleLowerCase().split(/[^\p{L}\p{N}]+/u).filter(Boolean);
|
|
3679
|
+
}
|
|
3680
|
+
function matchesTableSearch(searchableText, query, mode = "contains") {
|
|
3681
|
+
const normalizedQuery = query.trim().toLocaleLowerCase();
|
|
3682
|
+
if (!normalizedQuery) return true;
|
|
3683
|
+
if (mode === "contains") {
|
|
3684
|
+
return searchableText.toLocaleLowerCase().includes(normalizedQuery);
|
|
3685
|
+
}
|
|
3686
|
+
const actualWords = new Set(tableSearchWords(searchableText));
|
|
3687
|
+
const expectedWords = tableSearchWords(normalizedQuery);
|
|
3688
|
+
return expectedWords.length > 0 && expectedWords.every((word) => actualWords.has(word));
|
|
3689
|
+
}
|
|
3690
|
+
function compareValues(a, b) {
|
|
3691
|
+
if (a == null && b == null) return 0;
|
|
3692
|
+
if (a == null) return -1;
|
|
3693
|
+
if (b == null) return 1;
|
|
3694
|
+
if (typeof a === "number" && typeof b === "number") return a - b;
|
|
3695
|
+
if (typeof a === "boolean" && typeof b === "boolean") {
|
|
3696
|
+
return Number(a) - Number(b);
|
|
3697
|
+
}
|
|
3698
|
+
return stringifyCellValue(a).localeCompare(stringifyCellValue(b), void 0, {
|
|
3699
|
+
numeric: true,
|
|
3700
|
+
sensitivity: "base"
|
|
3701
|
+
});
|
|
3702
|
+
}
|
|
3703
|
+
function passesColumnFilter(value, filter) {
|
|
3704
|
+
const matches = (() => {
|
|
3705
|
+
switch (filter.kind) {
|
|
3706
|
+
case "text": {
|
|
3707
|
+
const s = stringifyCellValue(value);
|
|
3708
|
+
if (filter.mode === "null") return value == null;
|
|
3709
|
+
if (filter.mode === "not_null") return value != null;
|
|
3710
|
+
if (filter.mode === "empty") return s.trim() === "";
|
|
3711
|
+
if (filter.mode === "not_empty") return s.trim() !== "";
|
|
3712
|
+
const q = filter.value.trim().toLowerCase();
|
|
3713
|
+
if (!q) return true;
|
|
3714
|
+
return s.toLowerCase().includes(q);
|
|
3715
|
+
}
|
|
3716
|
+
case "select": {
|
|
3717
|
+
const selected = filter.values ?? (filter.value && filter.value !== "__all__" ? [filter.value] : []);
|
|
3718
|
+
if (selected.length === 0) return true;
|
|
3719
|
+
const s = stringifyCellValue(value);
|
|
3720
|
+
return selected.some(
|
|
3721
|
+
(v) => v === SELECT_EMPTY_VALUE ? s === "" : v === SELECT_NOT_EMPTY_VALUE ? s !== "" : s === v
|
|
3722
|
+
);
|
|
3723
|
+
}
|
|
3724
|
+
case "boolean": {
|
|
3725
|
+
return Boolean(value) === filter.value;
|
|
3726
|
+
}
|
|
3727
|
+
case "number": {
|
|
3728
|
+
const n = typeof value === "number" ? value : Number(stringifyCellValue(value).replace(/[^0-9.-]/g, ""));
|
|
3729
|
+
if (Number.isNaN(n)) return false;
|
|
3730
|
+
if (filter.min !== void 0 && n < filter.min) return false;
|
|
3731
|
+
if (filter.max !== void 0 && n > filter.max) return false;
|
|
3732
|
+
return true;
|
|
3733
|
+
}
|
|
3734
|
+
}
|
|
3735
|
+
})();
|
|
3736
|
+
return filter.negated ? !matches : matches;
|
|
3854
3737
|
}
|
|
3855
|
-
|
|
3856
|
-
|
|
3857
|
-
|
|
3858
|
-
|
|
3859
|
-
const
|
|
3860
|
-
|
|
3861
|
-
|
|
3862
|
-
|
|
3863
|
-
|
|
3864
|
-
|
|
3865
|
-
|
|
3866
|
-
|
|
3867
|
-
|
|
3868
|
-
|
|
3869
|
-
|
|
3870
|
-
|
|
3871
|
-
|
|
3872
|
-
|
|
3873
|
-
|
|
3874
|
-
|
|
3875
|
-
|
|
3876
|
-
|
|
3877
|
-
|
|
3878
|
-
|
|
3879
|
-
|
|
3880
|
-
|
|
3738
|
+
function filterAndSortRows(rows, columns, columnFilters, sort, globalSearch, anyOf, layeredFilters, globalSearchMode = "contains", searchText) {
|
|
3739
|
+
const colById = new Map(columns.map((c) => [columnId(c), c]));
|
|
3740
|
+
const q = globalSearch.trim().toLowerCase();
|
|
3741
|
+
const anyQ = anyOf?.query.trim().toLowerCase() ?? "";
|
|
3742
|
+
const activeLayeredFilters = completeLayeredFilterRules(layeredFilters);
|
|
3743
|
+
let result = rows.filter((row) => {
|
|
3744
|
+
for (const [id, filter] of Object.entries(columnFilters)) {
|
|
3745
|
+
if (!filter) continue;
|
|
3746
|
+
const col = colById.get(id);
|
|
3747
|
+
if (!col || col.filter === false) continue;
|
|
3748
|
+
if (!passesColumnFilter(getFilterValue(row, col), filter)) return false;
|
|
3749
|
+
}
|
|
3750
|
+
for (const rule of activeLayeredFilters) {
|
|
3751
|
+
const col = colById.get(rule.field);
|
|
3752
|
+
if (!col || !layeredFilterMatchesValue(getFilterValue(row, col), rule)) {
|
|
3753
|
+
return false;
|
|
3754
|
+
}
|
|
3755
|
+
}
|
|
3756
|
+
if (anyQ && anyOf) {
|
|
3757
|
+
const hit = anyOf.columnIds.some((id) => {
|
|
3758
|
+
const col = colById.get(id);
|
|
3759
|
+
if (!col) return false;
|
|
3760
|
+
return stringifyCellValue(getFilterValue(row, col)).toLowerCase().includes(anyQ);
|
|
3761
|
+
});
|
|
3762
|
+
if (!hit) return false;
|
|
3763
|
+
}
|
|
3764
|
+
if (!q) return true;
|
|
3765
|
+
const searchableValues = columns.filter(
|
|
3766
|
+
(col) => col.filter !== false || Boolean(col.accessorKey || col.accessorFn)
|
|
3767
|
+
).map((col) => stringifyCellValue(getFilterValue(row, col)));
|
|
3768
|
+
const additionalSearchText = searchText?.(row);
|
|
3769
|
+
if (additionalSearchText) searchableValues.push(additionalSearchText);
|
|
3770
|
+
if (globalSearchMode === "contains") {
|
|
3771
|
+
return searchableValues.some(
|
|
3772
|
+
(value) => matchesTableSearch(value, q, "contains")
|
|
3773
|
+
);
|
|
3774
|
+
}
|
|
3775
|
+
return matchesTableSearch(searchableValues.join(" "), q, "whole_words");
|
|
3776
|
+
});
|
|
3777
|
+
if (sort) {
|
|
3778
|
+
const col = colById.get(sort.id);
|
|
3779
|
+
if (col && col.sortable !== false) {
|
|
3780
|
+
const dir = sort.direction === "asc" ? 1 : -1;
|
|
3781
|
+
result = [...result].sort((a, b) => {
|
|
3782
|
+
const va = getSortValue(a, col);
|
|
3783
|
+
const vb = getSortValue(b, col);
|
|
3784
|
+
const ea = va == null || stringifyCellValue(va) === "";
|
|
3785
|
+
const eb = vb == null || stringifyCellValue(vb) === "";
|
|
3786
|
+
if (ea !== eb) return ea ? 1 : -1;
|
|
3787
|
+
return compareValues(va, vb) * dir;
|
|
3788
|
+
});
|
|
3789
|
+
}
|
|
3790
|
+
}
|
|
3791
|
+
return result;
|
|
3881
3792
|
}
|
|
3882
|
-
|
|
3883
|
-
|
|
3884
|
-
|
|
3885
|
-
|
|
3886
|
-
|
|
3887
|
-
|
|
3888
|
-
|
|
3889
|
-
|
|
3793
|
+
function countActiveColumnFilters(filters) {
|
|
3794
|
+
let n = 0;
|
|
3795
|
+
for (const f of Object.values(filters)) {
|
|
3796
|
+
if (!f) continue;
|
|
3797
|
+
switch (f.kind) {
|
|
3798
|
+
case "text":
|
|
3799
|
+
if (f.value.trim() || f.mode && f.mode !== "contains") n += 1;
|
|
3800
|
+
break;
|
|
3801
|
+
case "select":
|
|
3802
|
+
if (f.values ? f.values.length > 0 : f.value && f.value !== "__all__")
|
|
3803
|
+
n += 1;
|
|
3804
|
+
break;
|
|
3805
|
+
case "boolean":
|
|
3806
|
+
n += 1;
|
|
3807
|
+
break;
|
|
3808
|
+
case "number":
|
|
3809
|
+
if (f.min !== void 0 || f.max !== void 0) n += 1;
|
|
3810
|
+
break;
|
|
3811
|
+
}
|
|
3812
|
+
}
|
|
3813
|
+
return n;
|
|
3890
3814
|
}
|
|
3891
|
-
function
|
|
3892
|
-
|
|
3815
|
+
function isColumnFilterActive(filter) {
|
|
3816
|
+
if (!filter) return false;
|
|
3817
|
+
switch (filter.kind) {
|
|
3818
|
+
case "text":
|
|
3819
|
+
return filter.value.trim().length > 0 || filter.mode !== void 0 && filter.mode !== "contains";
|
|
3820
|
+
case "select":
|
|
3821
|
+
return filter.values ? filter.values.length > 0 : Boolean(filter.value) && filter.value !== "__all__";
|
|
3822
|
+
case "boolean":
|
|
3823
|
+
return true;
|
|
3824
|
+
case "number":
|
|
3825
|
+
return filter.min !== void 0 || filter.max !== void 0;
|
|
3826
|
+
}
|
|
3827
|
+
}
|
|
3828
|
+
function applyRowEdits(row, edits) {
|
|
3829
|
+
if (!edits || Object.keys(edits).length === 0) return row;
|
|
3830
|
+
return { ...row, ...edits };
|
|
3893
3831
|
}
|
|
3894
|
-
|
|
3895
|
-
// src/data-table/CopySubset.tsx
|
|
3896
|
-
var import_react4 = require("react");
|
|
3897
|
-
var import_clipboard = require("@ai-matrx/kit/clipboard");
|
|
3898
|
-
init_filter_engine();
|
|
3899
3832
|
|
|
3900
3833
|
// src/data-table/tableCopy.ts
|
|
3901
3834
|
var import_content_transfer3 = require("@ai-matrx/kit/content-transfer");
|
|
3902
|
-
init_filter_engine();
|
|
3903
3835
|
function projectDefaultTableCopyRow(row, columns) {
|
|
3904
3836
|
const record = /* @__PURE__ */ Object.create(null);
|
|
3905
3837
|
for (const column of columns) {
|
|
@@ -4488,7 +4420,6 @@ var CommandShortcut = ({
|
|
|
4488
4420
|
CommandShortcut.displayName = "CommandShortcut";
|
|
4489
4421
|
|
|
4490
4422
|
// src/data-table/ColumnHeaderCell.tsx
|
|
4491
|
-
init_filter_engine();
|
|
4492
4423
|
var import_jsx_runtime27 = require("react/jsx-runtime");
|
|
4493
4424
|
var HeaderButton = (0, import_react7.forwardRef)(({ dragDescription, "aria-describedby": tooltipDescription, ...props }, ref) => {
|
|
4494
4425
|
const descriptions = [tooltipDescription, dragDescription].filter((value) => Boolean(value)).join(" ");
|
|
@@ -5132,7 +5063,6 @@ function parseOptionalNumber(raw) {
|
|
|
5132
5063
|
// src/data-table/ColumnManager.tsx
|
|
5133
5064
|
var import_react8 = require("react");
|
|
5134
5065
|
var import_core2 = require("@dnd-kit/core");
|
|
5135
|
-
init_filter_engine();
|
|
5136
5066
|
var import_jsx_runtime28 = require("react/jsx-runtime");
|
|
5137
5067
|
function ColumnManager({
|
|
5138
5068
|
open,
|
|
@@ -5812,7 +5742,6 @@ function DirtySavePill({
|
|
|
5812
5742
|
|
|
5813
5743
|
// src/data-table/EditableTableCell.tsx
|
|
5814
5744
|
var import_react11 = require("react");
|
|
5815
|
-
init_filter_engine();
|
|
5816
5745
|
var import_jsx_runtime33 = require("react/jsx-runtime");
|
|
5817
5746
|
function CellEditShell({
|
|
5818
5747
|
href,
|
|
@@ -6328,7 +6257,6 @@ function resetToolbarFacets(facets) {
|
|
|
6328
6257
|
|
|
6329
6258
|
// src/data-table/LayeredFilterBuilder.tsx
|
|
6330
6259
|
var import_react12 = require("react");
|
|
6331
|
-
init_layered_filters();
|
|
6332
6260
|
var import_jsx_runtime35 = require("react/jsx-runtime");
|
|
6333
6261
|
function moveRule(rules, from, to) {
|
|
6334
6262
|
if (from === to || to < 0 || to >= rules.length) return [...rules];
|
|
@@ -6696,12 +6624,7 @@ function LayeredRuleRow({
|
|
|
6696
6624
|
);
|
|
6697
6625
|
}
|
|
6698
6626
|
|
|
6699
|
-
// src/data-table/MatrxDataTable.tsx
|
|
6700
|
-
init_layered_filters();
|
|
6701
|
-
init_filter_engine();
|
|
6702
|
-
|
|
6703
6627
|
// src/data-table/infer-filter.ts
|
|
6704
|
-
init_filter_engine();
|
|
6705
6628
|
var SELECT_CARDINALITY_CAP = 24;
|
|
6706
6629
|
function resolveFilterKind(col, sampleRows) {
|
|
6707
6630
|
if (col.filter === false) return null;
|
|
@@ -6796,24 +6719,6 @@ var import_jsx_runtime36 = require("react/jsx-runtime");
|
|
|
6796
6719
|
function hasSameRowReferences(previous, next) {
|
|
6797
6720
|
return previous.length === next.length && previous.every((row, index) => row === next[index]);
|
|
6798
6721
|
}
|
|
6799
|
-
function forwardUnboundedVerticalWheel(event) {
|
|
6800
|
-
const tableScroller = event.currentTarget;
|
|
6801
|
-
const isVerticalGesture = !event.shiftKey && Math.abs(event.deltaY) > Math.abs(event.deltaX);
|
|
6802
|
-
const tableOwnsVerticalScroll = tableScroller.scrollHeight > tableScroller.clientHeight + 1;
|
|
6803
|
-
if (!isVerticalGesture || tableOwnsVerticalScroll || event.deltaY === 0) return;
|
|
6804
|
-
let ancestor = tableScroller.parentElement;
|
|
6805
|
-
while (ancestor) {
|
|
6806
|
-
const overflowY = window.getComputedStyle(ancestor).overflowY;
|
|
6807
|
-
const canScroll = (overflowY === "auto" || overflowY === "scroll") && ancestor.scrollHeight > ancestor.clientHeight + 1;
|
|
6808
|
-
if (canScroll) {
|
|
6809
|
-
const scale = event.deltaMode === WheelEvent.DOM_DELTA_LINE ? 16 : event.deltaMode === WheelEvent.DOM_DELTA_PAGE ? ancestor.clientHeight : 1;
|
|
6810
|
-
event.preventDefault();
|
|
6811
|
-
ancestor.scrollTop += event.deltaY * scale;
|
|
6812
|
-
return;
|
|
6813
|
-
}
|
|
6814
|
-
ancestor = ancestor.parentElement;
|
|
6815
|
-
}
|
|
6816
|
-
}
|
|
6817
6722
|
function TableRowCopyControl({
|
|
6818
6723
|
copy,
|
|
6819
6724
|
row,
|
|
@@ -7874,6 +7779,11 @@ function MatrxDataTableCore({
|
|
|
7874
7779
|
id: tableDndContextId,
|
|
7875
7780
|
sensors: hierarchySensors,
|
|
7876
7781
|
collisionDetection: import_core3.pointerWithin,
|
|
7782
|
+
accessibility: {
|
|
7783
|
+
screenReaderInstructions: {
|
|
7784
|
+
draggable: "Drag with a pointer. To reorder columns with a keyboard, open Columns and use Move earlier or Move later."
|
|
7785
|
+
}
|
|
7786
|
+
},
|
|
7877
7787
|
measuring: { droppable: { strategy: import_core3.MeasuringStrategy.Always } },
|
|
7878
7788
|
onDragStart: (event) => {
|
|
7879
7789
|
const kind = event.active.data.current?.matrxDragKind;
|
|
@@ -8135,37 +8045,14 @@ function MatrxDataTableCore({
|
|
|
8135
8045
|
],
|
|
8136
8046
|
...effectiveCopy.aiCustom ? { aiCustom: effectiveCopy.aiCustom(processed, data) } : {},
|
|
8137
8047
|
export: {
|
|
8138
|
-
items:
|
|
8139
|
-
|
|
8140
|
-
|
|
8141
|
-
|
|
8142
|
-
|
|
8143
|
-
|
|
8144
|
-
)
|
|
8145
|
-
|
|
8146
|
-
id: "csv",
|
|
8147
|
-
label: "CSV (current view)",
|
|
8148
|
-
build: () => ({
|
|
8149
|
-
content: rowsToCsvFromColumns(processed, effectiveCopyColumns),
|
|
8150
|
-
extension: "csv",
|
|
8151
|
-
mime: "text/csv"
|
|
8152
|
-
})
|
|
8153
|
-
},
|
|
8154
|
-
{
|
|
8155
|
-
id: "xlsx",
|
|
8156
|
-
label: "Excel (.xlsx)",
|
|
8157
|
-
onSelect: async () => {
|
|
8158
|
-
const { downloadTableAsXlsx: downloadTableAsXlsx2 } = await Promise.resolve().then(() => (init_tableXlsx(), tableXlsx_exports));
|
|
8159
|
-
downloadTableAsXlsx2({
|
|
8160
|
-
rows: processed,
|
|
8161
|
-
columns: effectiveCopyColumns,
|
|
8162
|
-
label: effectiveCopy.listLabel ?? effectiveCopy.label
|
|
8163
|
-
});
|
|
8164
|
-
}
|
|
8165
|
-
}
|
|
8166
|
-
],
|
|
8167
|
-
sheetRows: () => copy === void 0 ? processed.map((row) => projectDefaultTableCopyRow(row, declaredVisibleCopyColumns)) : rowsToRecordsFromColumns(processed, effectiveCopyColumns),
|
|
8168
|
-
...copy === void 0 ? { sheetColumns: () => declaredVisibleCopyColumns.map((column) => ({ id: columnId(column), label: column.label ?? (typeof column.header === "string" ? column.header : columnId(column)) })) } : {}
|
|
8048
|
+
items: [],
|
|
8049
|
+
sheetRows: () => processed.map(
|
|
8050
|
+
(row) => projectDefaultTableCopyRow(row, declaredVisibleCopyColumns)
|
|
8051
|
+
),
|
|
8052
|
+
sheetColumns: () => declaredVisibleCopyColumns.map((column) => ({
|
|
8053
|
+
id: columnId(column),
|
|
8054
|
+
label: column.label ?? (typeof column.header === "string" ? column.header : columnId(column))
|
|
8055
|
+
}))
|
|
8169
8056
|
}
|
|
8170
8057
|
}
|
|
8171
8058
|
) : null,
|
|
@@ -8239,40 +8126,14 @@ function MatrxDataTableCore({
|
|
|
8239
8126
|
"selected"
|
|
8240
8127
|
),
|
|
8241
8128
|
export: {
|
|
8242
|
-
items:
|
|
8243
|
-
|
|
8244
|
-
|
|
8245
|
-
|
|
8246
|
-
|
|
8247
|
-
|
|
8248
|
-
)
|
|
8249
|
-
|
|
8250
|
-
id: "csv",
|
|
8251
|
-
label: "CSV (selected rows)",
|
|
8252
|
-
build: () => ({
|
|
8253
|
-
content: rowsToCsvFromColumns(
|
|
8254
|
-
selectedRows,
|
|
8255
|
-
effectiveCopyColumns
|
|
8256
|
-
),
|
|
8257
|
-
extension: "csv",
|
|
8258
|
-
mime: "text/csv"
|
|
8259
|
-
})
|
|
8260
|
-
},
|
|
8261
|
-
{
|
|
8262
|
-
id: "xlsx",
|
|
8263
|
-
label: "Excel (.xlsx)",
|
|
8264
|
-
onSelect: async () => {
|
|
8265
|
-
const { downloadTableAsXlsx: downloadTableAsXlsx2 } = await Promise.resolve().then(() => (init_tableXlsx(), tableXlsx_exports));
|
|
8266
|
-
downloadTableAsXlsx2({
|
|
8267
|
-
rows: selectedRows,
|
|
8268
|
-
columns: effectiveCopyColumns,
|
|
8269
|
-
label: `${effectiveCopy.listLabel ?? effectiveCopy.label} selected`
|
|
8270
|
-
});
|
|
8271
|
-
}
|
|
8272
|
-
}
|
|
8273
|
-
],
|
|
8274
|
-
sheetRows: () => copy === void 0 ? selectedRows.map((row) => projectDefaultTableCopyRow(row, declaredVisibleCopyColumns)) : rowsToRecordsFromColumns(selectedRows, effectiveCopyColumns),
|
|
8275
|
-
...copy === void 0 ? { sheetColumns: () => declaredVisibleCopyColumns.map((column) => ({ id: columnId(column), label: column.label ?? (typeof column.header === "string" ? column.header : columnId(column)) })) } : {}
|
|
8129
|
+
items: [],
|
|
8130
|
+
sheetRows: () => selectedRows.map(
|
|
8131
|
+
(row) => projectDefaultTableCopyRow(row, declaredVisibleCopyColumns)
|
|
8132
|
+
),
|
|
8133
|
+
sheetColumns: () => declaredVisibleCopyColumns.map((column) => ({
|
|
8134
|
+
id: columnId(column),
|
|
8135
|
+
label: column.label ?? (typeof column.header === "string" ? column.header : columnId(column))
|
|
8136
|
+
}))
|
|
8276
8137
|
}
|
|
8277
8138
|
}
|
|
8278
8139
|
) : null,
|
|
@@ -8388,7 +8249,6 @@ function MatrxDataTableCore({
|
|
|
8388
8249
|
ref: scrollRef,
|
|
8389
8250
|
"data-matrx-table-scroll": true,
|
|
8390
8251
|
onScroll: updateScrollHint,
|
|
8391
|
-
onWheel: forwardUnboundedVerticalWheel,
|
|
8392
8252
|
"aria-busy": isLoading || isFetching,
|
|
8393
8253
|
...appendQuery === null ? {} : { style: { containerType: "inline-size" } },
|
|
8394
8254
|
className: cn(
|
|
@@ -9361,6 +9221,39 @@ function resolveStringTitle(title, fallback) {
|
|
|
9361
9221
|
return fallback;
|
|
9362
9222
|
}
|
|
9363
9223
|
|
|
9364
|
-
// src/data-table/
|
|
9365
|
-
|
|
9224
|
+
// src/data-table/tableXlsx.ts
|
|
9225
|
+
var XLSX = __toESM(require("xlsx"), 1);
|
|
9226
|
+
function downloadTableAsXlsx({
|
|
9227
|
+
rows,
|
|
9228
|
+
columns,
|
|
9229
|
+
label
|
|
9230
|
+
}) {
|
|
9231
|
+
const visibleColumns = columns.filter(
|
|
9232
|
+
(column) => column.filter !== false || column.accessorKey
|
|
9233
|
+
);
|
|
9234
|
+
const headers = visibleColumns.map(
|
|
9235
|
+
(column) => typeof column.header === "string" ? column.header : columnId(column)
|
|
9236
|
+
);
|
|
9237
|
+
const values = rows.map(
|
|
9238
|
+
(row) => visibleColumns.map(
|
|
9239
|
+
(column) => stringifyCellValue(getCellValue(row, column))
|
|
9240
|
+
)
|
|
9241
|
+
);
|
|
9242
|
+
const worksheet = XLSX.utils.aoa_to_sheet([headers, ...values]);
|
|
9243
|
+
const workbook = XLSX.utils.book_new();
|
|
9244
|
+
const sheetName = label.replace(/[\\/?*[\]:]/g, " ").trim().slice(0, 31) || "Data";
|
|
9245
|
+
XLSX.utils.book_append_sheet(workbook, worksheet, sheetName);
|
|
9246
|
+
const bytes = XLSX.write(workbook, {
|
|
9247
|
+
type: "array",
|
|
9248
|
+
bookType: "xlsx",
|
|
9249
|
+
compression: true
|
|
9250
|
+
});
|
|
9251
|
+
const blob = new Blob([bytes], { type: "application/vnd.openxmlformats-officedocument.spreadsheetml.sheet" });
|
|
9252
|
+
const url = URL.createObjectURL(blob);
|
|
9253
|
+
const anchor = document.createElement("a");
|
|
9254
|
+
anchor.href = url;
|
|
9255
|
+
anchor.download = `${label.toLowerCase().replace(/[^a-z0-9]+/g, "-") || "table"}.xlsx`;
|
|
9256
|
+
anchor.click();
|
|
9257
|
+
URL.revokeObjectURL(url);
|
|
9258
|
+
}
|
|
9366
9259
|
//# sourceMappingURL=index.cjs.map
|