@lavalogic/scoria 0.20.0 → 0.21.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/Components/Table/Body/Rows/Columns/TableRowSelectionCheckbox.svelte +32 -31
- package/dist/Components/Table/Body/Rows/TableRow.svelte +1 -1
- package/dist/Components/Table/Body/TableBody.svelte +16 -14
- package/dist/Components/Table/Headers/HighlightAllHeader.svelte +13 -36
- package/dist/Components/Table/Headers/SelectAllHeader.svelte +9 -19
- package/dist/Components/Table/Table.svelte +15 -25
- package/dist/Components/Table/Types/Columns/ColumnPinningState.d.ts +2 -2
- package/dist/Components/Table/Types/Context/ITable.d.ts +1 -1
- package/dist/Components/Table/Types/Context/RowModel.d.ts +1 -1
- package/dist/Components/Table/Types/Context/TableContext.svelte.d.ts +39 -30
- package/dist/Components/Table/Types/Context/TableContext.svelte.js +600 -307
- package/dist/Components/Table/Types/Context/TableInitOptions.d.ts +1 -1
- package/dist/Components/Table/Types/Focus/TableFocusDetails.svelte.js +5 -22
- package/dist/Helpers/Helpers.svelte.d.ts +7 -7
- package/dist/Helpers/Helpers.svelte.js +119 -38
- package/package.json +12 -13
|
@@ -1,7 +1,7 @@
|
|
|
1
1
|
import { browser, dev } from '$app/environment';
|
|
2
|
-
import { asyncAll, asyncForEach, asyncMap,
|
|
2
|
+
import { asyncAll, asyncForEach, asyncMap, devCatch, getCanvasContext, } from '../../../../Helpers/Helpers.svelte.js';
|
|
3
3
|
import { tick, untrack } from 'svelte';
|
|
4
|
-
import { SvelteMap
|
|
4
|
+
import { SvelteMap } from 'svelte/reactivity';
|
|
5
5
|
import { ColumnType } from '../Columns/ColumnType.js';
|
|
6
6
|
import { AccessorDef } from '../Columns/Definitions/Accessors/AccessorDef.svelte.js';
|
|
7
7
|
import { CheckboxDef } from '../Columns/Definitions/Accessors/CheckboxDef.svelte.js';
|
|
@@ -69,16 +69,17 @@ export class TableContext {
|
|
|
69
69
|
// this.dataRepo.forceRefresh = this.forceVisibilityUpdate;
|
|
70
70
|
$effect(() => {
|
|
71
71
|
void this.currentPageData;
|
|
72
|
-
void this.selectedItems;
|
|
73
|
-
|
|
74
|
-
untrack(async () => {
|
|
75
|
-
await this.currentPageData;
|
|
72
|
+
// void this.selectedItems;
|
|
73
|
+
untrack(() => {
|
|
76
74
|
if (this.paginationRepo?.paginationState.pageIndex != undefined) {
|
|
77
|
-
|
|
78
|
-
|
|
79
|
-
|
|
75
|
+
this.updateSelectedItems()
|
|
76
|
+
.then(() => {
|
|
77
|
+
this.resetHighlightedRows();
|
|
78
|
+
})
|
|
79
|
+
.catch(devCatch);
|
|
80
|
+
// this.recalculateAllSelectedInCurrentPage();
|
|
80
81
|
}
|
|
81
|
-
})
|
|
82
|
+
});
|
|
82
83
|
});
|
|
83
84
|
let filteredIndicesAbortController = null;
|
|
84
85
|
$effect(() => {
|
|
@@ -100,7 +101,7 @@ export class TableContext {
|
|
|
100
101
|
});
|
|
101
102
|
}
|
|
102
103
|
else {
|
|
103
|
-
await asyncSleep(300);
|
|
104
|
+
// await asyncSleep(300);
|
|
104
105
|
const filtered = [];
|
|
105
106
|
for (let index = 0; index < data.length; ++index) {
|
|
106
107
|
if (currentController.signal.aborted) {
|
|
@@ -134,7 +135,182 @@ export class TableContext {
|
|
|
134
135
|
}
|
|
135
136
|
this._filteredIndices = filtered;
|
|
136
137
|
}
|
|
137
|
-
})().catch(
|
|
138
|
+
})().catch((e) => {
|
|
139
|
+
devCatch(e);
|
|
140
|
+
});
|
|
141
|
+
});
|
|
142
|
+
let lastIncrement = Number.MIN_SAFE_INTEGER;
|
|
143
|
+
$effect(() => {
|
|
144
|
+
void this.dataRepo.data.length;
|
|
145
|
+
void this.selectedItems;
|
|
146
|
+
void this.paginationRepo?.pageStartIndex;
|
|
147
|
+
const invalidValues = this._invalidValues;
|
|
148
|
+
const allSelectedInCurrentPage = [...this.selectedItems.keys()];
|
|
149
|
+
const currentIncrement = ++lastIncrement;
|
|
150
|
+
void this.allSelectedInCurrentPage;
|
|
151
|
+
const isUpToDate = lastIncrement === currentIncrement;
|
|
152
|
+
if (isUpToDate) {
|
|
153
|
+
this.hasInvalidSelectedItems = allSelectedInCurrentPage.some((key) => {
|
|
154
|
+
return invalidValues.has(key);
|
|
155
|
+
});
|
|
156
|
+
}
|
|
157
|
+
else {
|
|
158
|
+
if (dev) {
|
|
159
|
+
console.log('skipping recalculation due to stale data');
|
|
160
|
+
}
|
|
161
|
+
}
|
|
162
|
+
});
|
|
163
|
+
let latest_pageColData = 0;
|
|
164
|
+
$effect(() => {
|
|
165
|
+
const current = (latest_pageColData = latest_pageColData + 1);
|
|
166
|
+
if (!this.focusStart || !this.focusEnd) {
|
|
167
|
+
// eslint-disable-next-line svelte/prefer-svelte-reactivity
|
|
168
|
+
this._focusedRowIndices = new Set();
|
|
169
|
+
// eslint-disable-next-line svelte/prefer-svelte-reactivity
|
|
170
|
+
this._focusedColumnIds = new Set();
|
|
171
|
+
return;
|
|
172
|
+
}
|
|
173
|
+
const { row: startRowIndexId, column: startColumnIndex } = this.focusStart;
|
|
174
|
+
const { row: endRowIndexId, column: endColumnIndex } = this.focusEnd;
|
|
175
|
+
const model = this.sortedRowModel;
|
|
176
|
+
if (current === latest_pageColData) {
|
|
177
|
+
const startRowIndex = model.rows.findIndex((row) => row.visibleIndex === startRowIndexId);
|
|
178
|
+
const endRowIndex = model.rows.findIndex((row) => row.visibleIndex === endRowIndexId);
|
|
179
|
+
if (startRowIndex == -1 || endRowIndex == -1) {
|
|
180
|
+
// eslint-disable-next-line svelte/prefer-svelte-reactivity
|
|
181
|
+
this._focusedRowIndices = new Set();
|
|
182
|
+
// eslint-disable-next-line svelte/prefer-svelte-reactivity
|
|
183
|
+
this._focusedColumnIds = new Set();
|
|
184
|
+
return;
|
|
185
|
+
}
|
|
186
|
+
const minRowIndex = Math.min(startRowIndex, endRowIndex);
|
|
187
|
+
const maxRowIndex = Math.max(startRowIndex, endRowIndex);
|
|
188
|
+
const minColumnIndex = Math.min(startColumnIndex, endColumnIndex);
|
|
189
|
+
const maxColumnIndex = Math.max(startColumnIndex, endColumnIndex);
|
|
190
|
+
// eslint-disable-next-line svelte/prefer-svelte-reactivity
|
|
191
|
+
const affectedColumns = new Set();
|
|
192
|
+
const visibility = this.columnVisibility;
|
|
193
|
+
this.columnDefs
|
|
194
|
+
.filter((it) => 'index' in it &&
|
|
195
|
+
visibility[it.id] !== false &&
|
|
196
|
+
// TODO handle pinning behaviour
|
|
197
|
+
// !columnPinning.left?.includes(it.id) &&
|
|
198
|
+
// !columnPinning.right?.includes(it.id) &&
|
|
199
|
+
// (!('columnType' in it) || it.columnType === undefined || it.columnType === 'Accessor') &&
|
|
200
|
+
it.index >= minColumnIndex &&
|
|
201
|
+
it.index <= maxColumnIndex)
|
|
202
|
+
.forEach((it) => affectedColumns.add(it.id));
|
|
203
|
+
// eslint-disable-next-line svelte/prefer-svelte-reactivity
|
|
204
|
+
const indices = new Set();
|
|
205
|
+
for (let i = minRowIndex; i <= maxRowIndex; i++) {
|
|
206
|
+
indices.add(parseInt(model.rows[i].id));
|
|
207
|
+
}
|
|
208
|
+
this._focusedRowIndices = indices;
|
|
209
|
+
this._focusedColumnIds = affectedColumns;
|
|
210
|
+
}
|
|
211
|
+
});
|
|
212
|
+
let latest_paginationRowModel = 0;
|
|
213
|
+
$effect(() => {
|
|
214
|
+
const current = (latest_paginationRowModel = latest_paginationRowModel + 1);
|
|
215
|
+
const rows = this.rowsPromise;
|
|
216
|
+
if (current === latest_paginationRowModel) {
|
|
217
|
+
// eslint-disable-next-line svelte/prefer-svelte-reactivity
|
|
218
|
+
const rowsById = $derived(new Map(rows.map((it, index) => [index.toString(), it])));
|
|
219
|
+
this._paginationRowModel = {
|
|
220
|
+
rows,
|
|
221
|
+
get rowsById() {
|
|
222
|
+
return rowsById;
|
|
223
|
+
}, //FIXME should this be by sorted id or by original id?
|
|
224
|
+
};
|
|
225
|
+
}
|
|
226
|
+
});
|
|
227
|
+
let latest_sortedRowModel = 0;
|
|
228
|
+
$effect(() => {
|
|
229
|
+
void this.originalRowIndices;
|
|
230
|
+
void this.sortedData;
|
|
231
|
+
// if (!$effect.tracking()) {
|
|
232
|
+
// throw new Error(`filtered indices are not in a tracking context`);
|
|
233
|
+
// }
|
|
234
|
+
const current = (latest_sortedRowModel = latest_sortedRowModel + 1);
|
|
235
|
+
const sd = this.sortedData;
|
|
236
|
+
const ori = this.originalRowIndices;
|
|
237
|
+
if (current !== latest_sortedRowModel || !ori.size) {
|
|
238
|
+
return;
|
|
239
|
+
}
|
|
240
|
+
Promise.resolve(asyncMap(sd, (item, index) => {
|
|
241
|
+
const rawKey = this._cachedKey(item);
|
|
242
|
+
const finish = (key) => {
|
|
243
|
+
const originalIndex = ori.get(key);
|
|
244
|
+
const unsortedIndex = originalIndex ?? index;
|
|
245
|
+
if (current !== latest_sortedRowModel) {
|
|
246
|
+
throw new Error(`stale data`);
|
|
247
|
+
}
|
|
248
|
+
if (originalIndex == null) {
|
|
249
|
+
throw new Error(`Sorted Data not found in Original Row Indices: original index ${originalIndex}, index ${index}`);
|
|
250
|
+
}
|
|
251
|
+
return this.createRow(item, index, unsortedIndex);
|
|
252
|
+
};
|
|
253
|
+
if (rawKey instanceof Promise) {
|
|
254
|
+
return rawKey.then(finish);
|
|
255
|
+
}
|
|
256
|
+
return finish(rawKey);
|
|
257
|
+
}))
|
|
258
|
+
.then((rows) => {
|
|
259
|
+
if (current !== latest_sortedRowModel) {
|
|
260
|
+
return;
|
|
261
|
+
}
|
|
262
|
+
// eslint-disable-next-line svelte/prefer-svelte-reactivity
|
|
263
|
+
const rowsById = new Map(rows.map((it, index) => [index.toString(), it])); //FIXME should this be by sorted id or by original id?
|
|
264
|
+
this._sortedRowModel = {
|
|
265
|
+
get rows() {
|
|
266
|
+
return rows;
|
|
267
|
+
},
|
|
268
|
+
get rowsById() {
|
|
269
|
+
return rowsById;
|
|
270
|
+
},
|
|
271
|
+
};
|
|
272
|
+
})
|
|
273
|
+
.catch(devCatch);
|
|
274
|
+
});
|
|
275
|
+
let latest_originalRowIndices = 0;
|
|
276
|
+
$effect(() => {
|
|
277
|
+
const dataRepo = this.dataRepo;
|
|
278
|
+
const current = (latest_originalRowIndices = latest_originalRowIndices + 1);
|
|
279
|
+
Promise.resolve(asyncMap(dataRepo.data, (item, index) => {
|
|
280
|
+
const raw = this._cachedKey(item);
|
|
281
|
+
if (raw instanceof Promise) {
|
|
282
|
+
return raw.then((key) => [key, index]);
|
|
283
|
+
}
|
|
284
|
+
return [raw, index];
|
|
285
|
+
}))
|
|
286
|
+
.then((mapped) => {
|
|
287
|
+
if (current === latest_originalRowIndices) {
|
|
288
|
+
// eslint-disable-next-line svelte/prefer-svelte-reactivity
|
|
289
|
+
this._originalRowIndices = new Map(mapped);
|
|
290
|
+
}
|
|
291
|
+
})
|
|
292
|
+
.catch(devCatch);
|
|
293
|
+
});
|
|
294
|
+
$effect(() => {
|
|
295
|
+
if (this.highlightedItems.size === 0) {
|
|
296
|
+
this._allHighlighted = false;
|
|
297
|
+
return;
|
|
298
|
+
}
|
|
299
|
+
const pageStartIndex = this.paginationRepo ? this.paginationRepo.pageStartIndex : 0;
|
|
300
|
+
const pageEndIndexExclusive = this.paginationRepo
|
|
301
|
+
? Math.min(this.paginationRepo.pageEndIndexExclusive, this.sortedData.length)
|
|
302
|
+
: this.sortedData.length;
|
|
303
|
+
const allHighlightedResult = this._areAllHighlighted(pageStartIndex, pageEndIndexExclusive);
|
|
304
|
+
if (allHighlightedResult instanceof Promise) {
|
|
305
|
+
allHighlightedResult
|
|
306
|
+
.then((flag) => {
|
|
307
|
+
this._allHighlighted = flag;
|
|
308
|
+
})
|
|
309
|
+
.catch(devCatch);
|
|
310
|
+
}
|
|
311
|
+
else {
|
|
312
|
+
this._allHighlighted = allHighlightedResult;
|
|
313
|
+
}
|
|
138
314
|
});
|
|
139
315
|
if (defaultColumnDefs.remoteFilters) {
|
|
140
316
|
this.remoteFilters = defaultColumnDefs.remoteFilters;
|
|
@@ -251,11 +427,23 @@ export class TableContext {
|
|
|
251
427
|
this._remoteFilters = v;
|
|
252
428
|
}
|
|
253
429
|
_showSelectedOnly = $state(false);
|
|
430
|
+
_pageBeforeSelectedOnly = undefined;
|
|
254
431
|
get showSelectedOnly() {
|
|
255
432
|
return this._showSelectedOnly;
|
|
256
433
|
}
|
|
257
434
|
set showSelectedOnly(v) {
|
|
435
|
+
if (v === this._showSelectedOnly) {
|
|
436
|
+
return;
|
|
437
|
+
}
|
|
258
438
|
this._showSelectedOnly = v;
|
|
439
|
+
if (v) {
|
|
440
|
+
this._pageBeforeSelectedOnly = (this.paginationRepo?.paginationState.pageIndex ?? 0) + 1;
|
|
441
|
+
this.paginationRepo?.setPage(1);
|
|
442
|
+
}
|
|
443
|
+
else if (this._pageBeforeSelectedOnly != null) {
|
|
444
|
+
this.paginationRepo?.setPage(this._pageBeforeSelectedOnly);
|
|
445
|
+
this._pageBeforeSelectedOnly = undefined;
|
|
446
|
+
}
|
|
259
447
|
}
|
|
260
448
|
dateFilter = $derived(this.paginationRepo?.dateFilter);
|
|
261
449
|
numberFilter = $derived(this.paginationRepo?.numberFilter);
|
|
@@ -298,52 +486,20 @@ export class TableContext {
|
|
|
298
486
|
set selectedPreset(v) {
|
|
299
487
|
this._selectedPreset = v;
|
|
300
488
|
}
|
|
301
|
-
|
|
302
|
-
|
|
303
|
-
|
|
304
|
-
|
|
305
|
-
|
|
306
|
-
const { row: endRowIndexId, column: endColumnIndex } = this.focusEnd;
|
|
307
|
-
const model = await this.sortedRowModel;
|
|
308
|
-
const startRowIndex = model.rows.findIndex((row) => row.visibleIndex === startRowIndexId);
|
|
309
|
-
const endRowIndex = model.rows.findIndex((row) => row.visibleIndex === endRowIndexId);
|
|
310
|
-
if (startRowIndex == -1 || endRowIndex == -1) {
|
|
311
|
-
return { indices: new SvelteSet(), affectedColumns: new SvelteSet() };
|
|
312
|
-
}
|
|
313
|
-
const minRowIndex = Math.min(startRowIndex, endRowIndex);
|
|
314
|
-
const maxRowIndex = Math.max(startRowIndex, endRowIndex);
|
|
315
|
-
const minColumnIndex = Math.min(startColumnIndex, endColumnIndex);
|
|
316
|
-
const maxColumnIndex = Math.max(startColumnIndex, endColumnIndex);
|
|
317
|
-
const affectedColumns = new SvelteSet();
|
|
318
|
-
const visibility = this.columnVisibility;
|
|
319
|
-
this.columnDefs
|
|
320
|
-
.filter((it) => 'index' in it &&
|
|
321
|
-
visibility[it.id] !== false &&
|
|
322
|
-
// TODO handle pinning behaviour
|
|
323
|
-
// !columnPinning.left?.includes(it.id) &&
|
|
324
|
-
// !columnPinning.right?.includes(it.id) &&
|
|
325
|
-
// (!('columnType' in it) || it.columnType === undefined || it.columnType === 'Accessor') &&
|
|
326
|
-
it.index >= minColumnIndex &&
|
|
327
|
-
it.index <= maxColumnIndex)
|
|
328
|
-
.forEach((it) => affectedColumns.add(it.id));
|
|
329
|
-
const indices = new SvelteSet();
|
|
330
|
-
for (let i = minRowIndex; i <= maxRowIndex; i++) {
|
|
331
|
-
indices.add(parseInt(model.rows[i].id));
|
|
332
|
-
}
|
|
333
|
-
return { indices, affectedColumns };
|
|
334
|
-
});
|
|
335
|
-
focusedRowIndices = $derived.by(async () => {
|
|
336
|
-
void this._pageColData;
|
|
337
|
-
return (await this._pageColData).indices;
|
|
338
|
-
});
|
|
489
|
+
// eslint-disable-next-line svelte/prefer-svelte-reactivity
|
|
490
|
+
_focusedRowIndices = $state(new Set());
|
|
491
|
+
get focusedRowIndices() {
|
|
492
|
+
return this._focusedRowIndices;
|
|
493
|
+
}
|
|
339
494
|
_highlightedItems = $state(new SvelteMap());
|
|
340
495
|
get highlightedItems() {
|
|
341
496
|
return this._highlightedItems;
|
|
342
497
|
}
|
|
343
|
-
|
|
344
|
-
|
|
345
|
-
|
|
346
|
-
|
|
498
|
+
// eslint-disable-next-line svelte/prefer-svelte-reactivity
|
|
499
|
+
_focusedColumnIds = $state(new Set());
|
|
500
|
+
get focusedColumnIds() {
|
|
501
|
+
return this._focusedColumnIds;
|
|
502
|
+
}
|
|
347
503
|
_isMousingDown = $state(false);
|
|
348
504
|
get isMousingDown() {
|
|
349
505
|
return this._isMousingDown;
|
|
@@ -442,64 +598,113 @@ export class TableContext {
|
|
|
442
598
|
set openModalCoordinates(v) {
|
|
443
599
|
this._openModalCoordinates = v;
|
|
444
600
|
}
|
|
445
|
-
|
|
601
|
+
_allSelectedAsync = $state(false);
|
|
602
|
+
_allSelectedInCurrentPage = $derived.by(() => {
|
|
603
|
+
void this.columnDefs;
|
|
446
604
|
if (this.selectedItems.size === 0) {
|
|
447
|
-
return
|
|
605
|
+
return false;
|
|
448
606
|
}
|
|
449
|
-
|
|
450
|
-
void this.columnDefs;
|
|
451
|
-
const sortedData = await this.sortedData;
|
|
607
|
+
const sortedData = this.sortedData;
|
|
452
608
|
const pageStartIndex = this.paginationRepo ? this.paginationRepo.pageStartIndex : 0;
|
|
453
609
|
const pageEndIndexExclusive = this.paginationRepo
|
|
454
610
|
? Math.min(this.paginationRepo.pageEndIndexExclusive, sortedData.length)
|
|
455
611
|
: sortedData.length;
|
|
456
612
|
const selectableMethod = this.columnDefs.find((it) => it instanceof RowSelectionDef)?.isSelectable;
|
|
457
|
-
|
|
613
|
+
const result = this.allSelectedBySelectableMethod(pageStartIndex, pageEndIndexExclusive, selectableMethod);
|
|
614
|
+
if (result instanceof Promise) {
|
|
615
|
+
result
|
|
616
|
+
.then((flag) => {
|
|
617
|
+
this._allSelectedAsync = flag;
|
|
618
|
+
})
|
|
619
|
+
.catch(devCatch);
|
|
620
|
+
return this._allSelectedAsync;
|
|
621
|
+
}
|
|
622
|
+
return result;
|
|
458
623
|
});
|
|
459
624
|
get allSelectedInCurrentPage() {
|
|
460
625
|
return this._allSelectedInCurrentPage;
|
|
461
626
|
}
|
|
462
|
-
|
|
463
|
-
const sortedData =
|
|
627
|
+
allSelectedBySelectableMethod(pageStartIndex, pageEndIndexExclusive, selectableMethod) {
|
|
628
|
+
const sortedData = this.sortedData;
|
|
629
|
+
const emptyPromise = new Promise(() => { });
|
|
464
630
|
if (selectableMethod) {
|
|
465
|
-
|
|
466
|
-
|
|
467
|
-
|
|
468
|
-
|
|
469
|
-
|
|
631
|
+
const pending = [];
|
|
632
|
+
for (let i = pageStartIndex; i < pageEndIndexExclusive; i++) {
|
|
633
|
+
const item = sortedData[i];
|
|
634
|
+
const relIdx = i - pageStartIndex;
|
|
635
|
+
const raw = this._cachedKey(item);
|
|
636
|
+
const checkUnselected = (key) => {
|
|
637
|
+
const selectable = selectableMethod(item, relIdx);
|
|
638
|
+
if (selectable instanceof Promise) {
|
|
639
|
+
return selectable.then((s) => s && !this.selectedItems.has(key));
|
|
640
|
+
}
|
|
641
|
+
return selectable && !this.selectedItems.has(key);
|
|
642
|
+
};
|
|
643
|
+
const r = raw instanceof Promise ? raw.then(checkUnselected) : checkUnselected(raw);
|
|
644
|
+
if (r === true) {
|
|
645
|
+
return false;
|
|
646
|
+
}
|
|
647
|
+
if (r instanceof Promise) {
|
|
648
|
+
pending.push(r);
|
|
470
649
|
}
|
|
471
650
|
}
|
|
651
|
+
if (pending.length === 0) {
|
|
652
|
+
return true;
|
|
653
|
+
}
|
|
654
|
+
return Promise.race([
|
|
655
|
+
Promise.race(pending.map(async (p) => ((await p) ? false : emptyPromise))),
|
|
656
|
+
Promise.all(pending).then((results) => {
|
|
657
|
+
return !results.some(Boolean);
|
|
658
|
+
}),
|
|
659
|
+
]);
|
|
472
660
|
}
|
|
473
661
|
else {
|
|
474
|
-
|
|
475
|
-
|
|
476
|
-
|
|
477
|
-
|
|
662
|
+
const pending = [];
|
|
663
|
+
for (let i = pageStartIndex; i < pageEndIndexExclusive; i++) {
|
|
664
|
+
const raw = this._cachedKey(sortedData[i]);
|
|
665
|
+
if (raw instanceof Promise) {
|
|
666
|
+
pending.push(raw.then((key) => !this.selectedItems.has(key)));
|
|
667
|
+
}
|
|
668
|
+
else if (!this.selectedItems.has(raw)) {
|
|
669
|
+
return false;
|
|
478
670
|
}
|
|
479
671
|
}
|
|
672
|
+
if (pending.length === 0) {
|
|
673
|
+
return true;
|
|
674
|
+
}
|
|
675
|
+
return Promise.race([
|
|
676
|
+
Promise.race(pending.map(async (p) => ((await p) ? false : emptyPromise))),
|
|
677
|
+
Promise.all(pending).then((results) => !results.some(Boolean)),
|
|
678
|
+
]);
|
|
480
679
|
}
|
|
481
|
-
return Promise.resolve(true);
|
|
482
680
|
}
|
|
483
|
-
|
|
484
|
-
const sortedData =
|
|
681
|
+
_areAllHighlighted(pageStartIndex, pageEndIndexExclusive) {
|
|
682
|
+
const sortedData = this.sortedData;
|
|
485
683
|
for (let index = pageStartIndex; index < pageEndIndexExclusive; index++) {
|
|
486
684
|
const item = sortedData[index];
|
|
487
|
-
|
|
488
|
-
|
|
685
|
+
const raw = this._cachedKey(item);
|
|
686
|
+
if (raw instanceof Promise) {
|
|
687
|
+
return raw.then(async (key) => {
|
|
688
|
+
if (!this.highlightedItems.has(key)) {
|
|
689
|
+
return false;
|
|
690
|
+
}
|
|
691
|
+
for (let j = index + 1; j < pageEndIndexExclusive; j++) {
|
|
692
|
+
const r = this._cachedKey(sortedData[j]);
|
|
693
|
+
const k = r instanceof Promise ? await r : r;
|
|
694
|
+
if (!this.highlightedItems.has(k)) {
|
|
695
|
+
return false;
|
|
696
|
+
}
|
|
697
|
+
}
|
|
698
|
+
return true;
|
|
699
|
+
});
|
|
700
|
+
}
|
|
701
|
+
if (!this.highlightedItems.has(raw)) {
|
|
702
|
+
return false;
|
|
489
703
|
}
|
|
490
704
|
}
|
|
491
|
-
return
|
|
705
|
+
return true;
|
|
492
706
|
}
|
|
493
|
-
_allHighlighted = $
|
|
494
|
-
if (this.highlightedItems.size === 0) {
|
|
495
|
-
return Promise.resolve(false);
|
|
496
|
-
}
|
|
497
|
-
const pageStartIndex = this.paginationRepo ? this.paginationRepo.pageStartIndex : 0;
|
|
498
|
-
const pageEndIndexExclusive = this.paginationRepo
|
|
499
|
-
? Math.min(this.paginationRepo.pageEndIndexExclusive, (await this.sortedData).length)
|
|
500
|
-
: (await this.sortedData).length;
|
|
501
|
-
return await this._areAllHighlighted(pageStartIndex, pageEndIndexExclusive);
|
|
502
|
-
});
|
|
707
|
+
_allHighlighted = $state(false);
|
|
503
708
|
get allHighlighted() {
|
|
504
709
|
return this._allHighlighted;
|
|
505
710
|
}
|
|
@@ -527,7 +732,8 @@ export class TableContext {
|
|
|
527
732
|
this._hasInvalidSelectedItems = v;
|
|
528
733
|
}
|
|
529
734
|
// FIXME decide
|
|
530
|
-
|
|
735
|
+
// eslint-disable-next-line svelte/prefer-svelte-reactivity
|
|
736
|
+
columnDefsById = $derived(new Map(this.columnDefs.map((it) => [it.id, it])));
|
|
531
737
|
getSortingFn = (id, desc) => {
|
|
532
738
|
if (this.dataRepo.data.length == 0) {
|
|
533
739
|
return undefined;
|
|
@@ -560,11 +766,14 @@ export class TableContext {
|
|
|
560
766
|
get filteredIndices() {
|
|
561
767
|
return this._filteredIndices;
|
|
562
768
|
}
|
|
563
|
-
filteredData = $derived.by(
|
|
769
|
+
filteredData = $derived.by(() => {
|
|
564
770
|
void this.dataRepo.data;
|
|
565
771
|
void this.filteredIndices;
|
|
566
772
|
void this.showSelectedOnly;
|
|
567
|
-
|
|
773
|
+
// selectedItems is intentionally NOT read here unconditionally — doing so would
|
|
774
|
+
// invalidate filteredData → sortedData → currentPageData → entire row model on
|
|
775
|
+
// every single toggle. The selectedItems.values() reads inside the showSelectedOnly
|
|
776
|
+
// branches below are sufficient to track reactivity when it actually matters.
|
|
568
777
|
if (this.paginationRepo?.paginationType == PaginationType.Local) {
|
|
569
778
|
const data = this.showSelectedOnly
|
|
570
779
|
? // FIXME this will show the selected items by order of insertion to the selectedItems map.
|
|
@@ -580,7 +789,7 @@ export class TableContext {
|
|
|
580
789
|
return this.showSelectedOnly ? [...this.selectedItems.values()] : this.dataRepo.data;
|
|
581
790
|
});
|
|
582
791
|
sortedDataAbortController = null;
|
|
583
|
-
sortedData = $derived.by(
|
|
792
|
+
sortedData = $derived.by(() => {
|
|
584
793
|
// if (!$effect.tracking()) {
|
|
585
794
|
// throw new Error(`sorted data is not in a tracking context`);
|
|
586
795
|
// }
|
|
@@ -592,7 +801,7 @@ export class TableContext {
|
|
|
592
801
|
console.log('sorted data');
|
|
593
802
|
}
|
|
594
803
|
if (this.paginationRepo?.paginationType == PaginationType.Local) {
|
|
595
|
-
const data =
|
|
804
|
+
const data = this.filteredData;
|
|
596
805
|
if (currentController.signal.aborted) {
|
|
597
806
|
return [];
|
|
598
807
|
}
|
|
@@ -629,83 +838,51 @@ export class TableContext {
|
|
|
629
838
|
}
|
|
630
839
|
return this.filteredData;
|
|
631
840
|
});
|
|
632
|
-
|
|
633
|
-
|
|
634
|
-
|
|
635
|
-
|
|
636
|
-
|
|
637
|
-
// }
|
|
638
|
-
const sd = await this.sortedData;
|
|
639
|
-
const ori = await this.originalRowIndices;
|
|
640
|
-
const rows = await asyncMap(sd, async (item, index) => {
|
|
641
|
-
const originalIndex = ori.get(await this.selectionExtractor(item));
|
|
642
|
-
const unsortedIndex = originalIndex ?? index;
|
|
643
|
-
if (originalIndex == null) {
|
|
644
|
-
throw new Error(`Sorted Data not found in Original Row Indices: original index ${originalIndex}, index ${index}`);
|
|
645
|
-
}
|
|
646
|
-
return this.createRow(item, index, unsortedIndex);
|
|
647
|
-
});
|
|
648
|
-
const rowsById = $derived(new SvelteMap(rows.map((it, index) => [index.toString(), it]))); //FIXME should this be by sorted id or by original id?
|
|
649
|
-
return {
|
|
650
|
-
get rows() {
|
|
651
|
-
return rows;
|
|
652
|
-
},
|
|
653
|
-
get rowsById() {
|
|
654
|
-
return rowsById;
|
|
655
|
-
},
|
|
656
|
-
};
|
|
657
|
-
});
|
|
841
|
+
// eslint-disable-next-line svelte/prefer-svelte-reactivity
|
|
842
|
+
_sortedRowModel = $state({ rows: [], rowsById: new Map() });
|
|
843
|
+
get sortedRowModel() {
|
|
844
|
+
return this._sortedRowModel;
|
|
845
|
+
}
|
|
658
846
|
CurrentPageDataAbortController = null;
|
|
659
|
-
currentPageData = $derived.by(
|
|
660
|
-
// void this.originalRowIndices;
|
|
847
|
+
currentPageData = $derived.by(() => {
|
|
661
848
|
void this.sortedData;
|
|
662
|
-
void this.dataRepo.pageStartIndex;
|
|
663
|
-
void this.dataRepo.pageEndIndexExclusive;
|
|
664
849
|
// if (!$effect.tracking()) {
|
|
665
850
|
// throw new Error(`Current Page Data is not in a tracking context`);
|
|
666
851
|
// }
|
|
667
852
|
this.CurrentPageDataAbortController?.abort();
|
|
668
853
|
const currentController = (this.CurrentPageDataAbortController = new AbortController());
|
|
669
|
-
const sd =
|
|
854
|
+
const sd = this.sortedData;
|
|
670
855
|
if (currentController.signal.aborted) {
|
|
671
856
|
return [];
|
|
672
857
|
}
|
|
673
|
-
|
|
858
|
+
// When showing selected only, bypass pagination and return all filtered rows at once.
|
|
859
|
+
// Only track page indices when we will actually paginate, to avoid unnecessary re-runs
|
|
860
|
+
// while the user is in show-selected-only mode.
|
|
861
|
+
if (this.dataRepo.paginationType != PaginationType.Local || this.showSelectedOnly) {
|
|
674
862
|
return sd;
|
|
675
863
|
}
|
|
864
|
+
void this.dataRepo.pageStartIndex;
|
|
865
|
+
void this.dataRepo.pageEndIndexExclusive;
|
|
676
866
|
// eslint-disable-next-line @typescript-eslint/no-unnecessary-condition
|
|
677
867
|
if (currentController.signal.aborted) {
|
|
678
868
|
return [];
|
|
679
869
|
}
|
|
680
870
|
return sd.slice(this.dataRepo.pageStartIndex, this.dataRepo.pageEndIndexExclusive);
|
|
681
871
|
});
|
|
682
|
-
//
|
|
683
|
-
|
|
684
|
-
|
|
685
|
-
|
|
686
|
-
|
|
687
|
-
|
|
688
|
-
return new SvelteMap(awaited);
|
|
689
|
-
});
|
|
690
|
-
rowsPromiseAbortController = null;
|
|
691
|
-
rowsPromise = $derived.by(async () => {
|
|
872
|
+
// eslint-disable-next-line svelte/prefer-svelte-reactivity
|
|
873
|
+
_originalRowIndices = $state(new Map());
|
|
874
|
+
get originalRowIndices() {
|
|
875
|
+
return this._originalRowIndices;
|
|
876
|
+
}
|
|
877
|
+
rowsPromise = $derived.by(() => {
|
|
692
878
|
// void this.originalRowIndices;
|
|
693
879
|
void this.currentPageData;
|
|
694
880
|
// void this.columnDefsById;
|
|
695
881
|
void this.columnVisibility;
|
|
696
882
|
void this.paginationRepo?.sorting;
|
|
697
883
|
void this.columnPinning;
|
|
698
|
-
this.
|
|
699
|
-
const
|
|
700
|
-
const currentPageData = await this.currentPageData;
|
|
701
|
-
if (currentController.signal.aborted) {
|
|
702
|
-
return [];
|
|
703
|
-
}
|
|
704
|
-
const indices = await this.originalRowIndices;
|
|
705
|
-
// eslint-disable-next-line @typescript-eslint/no-unnecessary-condition
|
|
706
|
-
if (currentController.signal.aborted) {
|
|
707
|
-
return [];
|
|
708
|
-
}
|
|
884
|
+
const currentPageData = this.currentPageData;
|
|
885
|
+
const indices = this.originalRowIndices;
|
|
709
886
|
return currentPageData.map((item, index) => {
|
|
710
887
|
const unsortedIndex = indices.get(item) ?? index;
|
|
711
888
|
const getValue = $derived.by(() => {
|
|
@@ -819,16 +996,68 @@ export class TableContext {
|
|
|
819
996
|
return row;
|
|
820
997
|
});
|
|
821
998
|
});
|
|
822
|
-
|
|
823
|
-
|
|
824
|
-
|
|
825
|
-
|
|
826
|
-
rows,
|
|
827
|
-
rowsById: new SvelteMap(rows.map((it, index) => [index.toString(), it])), //FIXME should this be by sorted id or by original id?
|
|
828
|
-
};
|
|
999
|
+
_paginationRowModel = $state({
|
|
1000
|
+
rows: [],
|
|
1001
|
+
// eslint-disable-next-line svelte/prefer-svelte-reactivity
|
|
1002
|
+
rowsById: new Map(),
|
|
829
1003
|
});
|
|
1004
|
+
get paginationRowModel() {
|
|
1005
|
+
return this._paginationRowModel;
|
|
1006
|
+
}
|
|
830
1007
|
// #endregion
|
|
831
1008
|
// #region public methods
|
|
1009
|
+
// Key extraction cache — avoids re-calling selectionExtractor for the same item object.
|
|
1010
|
+
// Only onEditCell explicitly invalidates the cache (when the item is mutated in-place).
|
|
1011
|
+
_keyCache = new WeakMap();
|
|
1012
|
+
_cachedKey(item) {
|
|
1013
|
+
const cached = this._keyCache.get(item);
|
|
1014
|
+
if (cached !== undefined) {
|
|
1015
|
+
return cached;
|
|
1016
|
+
}
|
|
1017
|
+
const raw = this.selectionExtractor(item);
|
|
1018
|
+
if (raw instanceof Promise) {
|
|
1019
|
+
return raw.then((key) => {
|
|
1020
|
+
this._keyCache.set(item, key);
|
|
1021
|
+
return key;
|
|
1022
|
+
});
|
|
1023
|
+
}
|
|
1024
|
+
this._keyCache.set(item, raw);
|
|
1025
|
+
return raw;
|
|
1026
|
+
}
|
|
1027
|
+
// Pending selection changes — buffered and flushed as a single SvelteMap reassignment
|
|
1028
|
+
// to avoid per-toggle reactive cascades.
|
|
1029
|
+
// eslint-disable-next-line svelte/prefer-svelte-reactivity
|
|
1030
|
+
_pendingSelectionChanges = new Map();
|
|
1031
|
+
_flushScheduled = false;
|
|
1032
|
+
_flushPendingSelectionChanges() {
|
|
1033
|
+
if (this._pendingSelectionChanges.size === 0) {
|
|
1034
|
+
return;
|
|
1035
|
+
}
|
|
1036
|
+
// Mutate in place to preserve SvelteMap's per-key reactive tracking.
|
|
1037
|
+
// Replacing _selectedItems with a cloned map would invalidate every .has()/.get()
|
|
1038
|
+
// subscriber across all visible rows, not just the changed keys.
|
|
1039
|
+
for (const [key, item] of this._pendingSelectionChanges) {
|
|
1040
|
+
if (item === null) {
|
|
1041
|
+
this.selectedItems.delete(key);
|
|
1042
|
+
}
|
|
1043
|
+
else {
|
|
1044
|
+
this.selectedItems.set(key, item);
|
|
1045
|
+
}
|
|
1046
|
+
}
|
|
1047
|
+
this._pendingSelectionChanges.clear();
|
|
1048
|
+
this._flushScheduled = false;
|
|
1049
|
+
}
|
|
1050
|
+
_schedulePendingFlush() {
|
|
1051
|
+
if (this._flushScheduled) {
|
|
1052
|
+
return;
|
|
1053
|
+
}
|
|
1054
|
+
this._flushScheduled = true;
|
|
1055
|
+
tick()
|
|
1056
|
+
.then(() => {
|
|
1057
|
+
this._flushPendingSelectionChanges();
|
|
1058
|
+
})
|
|
1059
|
+
.catch(devCatch);
|
|
1060
|
+
}
|
|
832
1061
|
selectionContains = async (item) => {
|
|
833
1062
|
void item;
|
|
834
1063
|
void this.isSelectable;
|
|
@@ -839,174 +1068,226 @@ export class TableContext {
|
|
|
839
1068
|
if (!this.isSelectable) {
|
|
840
1069
|
return true;
|
|
841
1070
|
}
|
|
842
|
-
const
|
|
1071
|
+
const rawIdentity = this._cachedKey(item);
|
|
1072
|
+
const identity = rawIdentity instanceof Promise ? await rawIdentity : rawIdentity;
|
|
843
1073
|
const has = this.selectedItems.has(identity);
|
|
844
1074
|
return has;
|
|
845
1075
|
};
|
|
846
|
-
addInvalidValue =
|
|
847
|
-
|
|
1076
|
+
addInvalidValue = (item) => {
|
|
1077
|
+
const raw = this._cachedKey(item);
|
|
1078
|
+
if (raw instanceof Promise) {
|
|
1079
|
+
return raw.then((key) => {
|
|
1080
|
+
this.invalidValues.set(key, item);
|
|
1081
|
+
});
|
|
1082
|
+
}
|
|
1083
|
+
this.invalidValues.set(raw, item);
|
|
848
1084
|
};
|
|
849
|
-
removeInvalidValue =
|
|
850
|
-
|
|
1085
|
+
removeInvalidValue = (item) => {
|
|
1086
|
+
const raw = this._cachedKey(item);
|
|
1087
|
+
if (raw instanceof Promise) {
|
|
1088
|
+
return raw.then((key) => {
|
|
1089
|
+
this.invalidValues.delete(key);
|
|
1090
|
+
});
|
|
1091
|
+
}
|
|
1092
|
+
this.invalidValues.delete(raw);
|
|
851
1093
|
};
|
|
852
1094
|
setOpenModalCoordinates = (coordinates) => {
|
|
853
1095
|
this.openModalCoordinates = coordinates ? { ...coordinates } : null;
|
|
854
1096
|
};
|
|
855
|
-
toggleHighlightedRow =
|
|
856
|
-
const
|
|
857
|
-
if (
|
|
858
|
-
|
|
1097
|
+
toggleHighlightedRow = (item) => {
|
|
1098
|
+
const raw = this._cachedKey(item);
|
|
1099
|
+
if (raw instanceof Promise) {
|
|
1100
|
+
return raw.then((key) => {
|
|
1101
|
+
if (this.highlightedItems.has(key)) {
|
|
1102
|
+
this.highlightedItems.delete(key);
|
|
1103
|
+
}
|
|
1104
|
+
else {
|
|
1105
|
+
this.highlightedItems.set(key, item);
|
|
1106
|
+
}
|
|
1107
|
+
});
|
|
1108
|
+
}
|
|
1109
|
+
if (this.highlightedItems.has(raw)) {
|
|
1110
|
+
this.highlightedItems.delete(raw);
|
|
859
1111
|
}
|
|
860
1112
|
else {
|
|
861
|
-
this.highlightedItems.set(
|
|
1113
|
+
this.highlightedItems.set(raw, item);
|
|
862
1114
|
}
|
|
863
1115
|
};
|
|
864
1116
|
resetHighlightedRows = () => {
|
|
865
1117
|
this.highlightedItems.clear();
|
|
866
1118
|
};
|
|
867
|
-
toggleSelected =
|
|
868
|
-
const
|
|
869
|
-
if (
|
|
870
|
-
|
|
871
|
-
|
|
872
|
-
|
|
873
|
-
|
|
1119
|
+
toggleSelected = (item) => {
|
|
1120
|
+
const raw = this._cachedKey(item);
|
|
1121
|
+
if (raw instanceof Promise) {
|
|
1122
|
+
return raw.then((key) => {
|
|
1123
|
+
const pendingValue = this._pendingSelectionChanges.get(key);
|
|
1124
|
+
const isSelected = pendingValue !== undefined ? pendingValue !== null : this.selectedItems.has(key);
|
|
1125
|
+
this._pendingSelectionChanges.set(key, isSelected ? null : item);
|
|
1126
|
+
this._schedulePendingFlush();
|
|
1127
|
+
});
|
|
874
1128
|
}
|
|
1129
|
+
const pendingValue = this._pendingSelectionChanges.get(raw);
|
|
1130
|
+
const isSelected = pendingValue !== undefined ? pendingValue !== null : this.selectedItems.has(raw);
|
|
1131
|
+
this._pendingSelectionChanges.set(raw, isSelected ? null : item);
|
|
1132
|
+
this._schedulePendingFlush();
|
|
875
1133
|
};
|
|
876
|
-
setSelected =
|
|
877
|
-
const
|
|
878
|
-
if (
|
|
879
|
-
|
|
880
|
-
|
|
881
|
-
|
|
882
|
-
|
|
1134
|
+
setSelected = (item, selected) => {
|
|
1135
|
+
const raw = this._cachedKey(item);
|
|
1136
|
+
if (raw instanceof Promise) {
|
|
1137
|
+
return raw.then((key) => {
|
|
1138
|
+
this._pendingSelectionChanges.set(key, selected ? item : null);
|
|
1139
|
+
this._schedulePendingFlush();
|
|
1140
|
+
});
|
|
883
1141
|
}
|
|
1142
|
+
this._pendingSelectionChanges.set(raw, selected ? item : null);
|
|
1143
|
+
this._schedulePendingFlush();
|
|
884
1144
|
};
|
|
885
1145
|
setSelectionMap = (set) => {
|
|
886
1146
|
this._selectedItems = set;
|
|
887
1147
|
};
|
|
888
1148
|
updateSelectedItems = async () => {
|
|
1149
|
+
if (this.selectedItems.size === 0) {
|
|
1150
|
+
return;
|
|
1151
|
+
}
|
|
889
1152
|
const pageStartIndex = this.paginationRepo ? this.paginationRepo.pageStartIndex : 0;
|
|
890
|
-
const sortedData =
|
|
1153
|
+
const sortedData = this.sortedData;
|
|
891
1154
|
const pageEndIndexExclusive = this.paginationRepo
|
|
892
1155
|
? Math.min(this.paginationRepo.pageEndIndexExclusive, sortedData.length)
|
|
893
1156
|
: sortedData.length;
|
|
894
|
-
|
|
895
|
-
|
|
896
|
-
|
|
897
|
-
|
|
898
|
-
|
|
899
|
-
|
|
1157
|
+
// Build key → item map for the current page (O(page_size) extractions)
|
|
1158
|
+
// eslint-disable-next-line svelte/prefer-svelte-reactivity
|
|
1159
|
+
const pageKeyMap = new Map();
|
|
1160
|
+
const pending = [];
|
|
1161
|
+
for (let i = pageStartIndex; i < pageEndIndexExclusive; i++) {
|
|
1162
|
+
const item = sortedData[i];
|
|
1163
|
+
const raw = this._cachedKey(item);
|
|
1164
|
+
if (raw instanceof Promise) {
|
|
1165
|
+
pending.push(raw.then((key) => {
|
|
1166
|
+
pageKeyMap.set(key, item);
|
|
1167
|
+
}));
|
|
900
1168
|
}
|
|
901
|
-
|
|
902
|
-
|
|
903
|
-
for (let index = pageStartIndex; index < pageEndIndexExclusive; index++) {
|
|
904
|
-
const item = sortedData[index];
|
|
905
|
-
if (await selectableMethod(item, index)) {
|
|
906
|
-
await updateSelectedItem(item);
|
|
907
|
-
}
|
|
1169
|
+
else {
|
|
1170
|
+
pageKeyMap.set(raw, item);
|
|
908
1171
|
}
|
|
909
1172
|
}
|
|
910
|
-
|
|
911
|
-
|
|
912
|
-
const item = sortedData[index];
|
|
913
|
-
await updateSelectedItem(item);
|
|
914
|
-
}
|
|
1173
|
+
if (pending.length > 0) {
|
|
1174
|
+
await Promise.all(pending);
|
|
915
1175
|
}
|
|
916
|
-
|
|
917
|
-
resetSelectedItems = () => {
|
|
1176
|
+
// Update only selected items that appear on this page (O(selected_size))
|
|
918
1177
|
for (const key of this.selectedItems.keys()) {
|
|
919
|
-
|
|
1178
|
+
const newItem = pageKeyMap.get(key);
|
|
1179
|
+
if (newItem !== undefined) {
|
|
1180
|
+
this.selectedItems.set(key, newItem);
|
|
1181
|
+
}
|
|
920
1182
|
}
|
|
921
|
-
this.recalculateAllSelectedInCurrentPage();
|
|
922
1183
|
};
|
|
923
|
-
|
|
924
|
-
|
|
925
|
-
const invalidValues = this._invalidValues;
|
|
926
|
-
const allSelectedInCurrentPage = [...this.selectedItems.keys()];
|
|
927
|
-
const currentIncrement = ++this.lastIncrement;
|
|
928
|
-
this.allSelectedInCurrentPage
|
|
929
|
-
.then(() => {
|
|
930
|
-
if (this.lastIncrement == currentIncrement) {
|
|
931
|
-
this.hasInvalidSelectedItems = allSelectedInCurrentPage.some((key) => {
|
|
932
|
-
return invalidValues.has(key);
|
|
933
|
-
});
|
|
934
|
-
}
|
|
935
|
-
else {
|
|
936
|
-
if (dev) {
|
|
937
|
-
console.log('skipping recalculation due to stale data');
|
|
938
|
-
}
|
|
939
|
-
}
|
|
940
|
-
})
|
|
941
|
-
.catch(devCatch);
|
|
1184
|
+
resetSelectedItems = () => {
|
|
1185
|
+
this._selectedItems = new SvelteMap();
|
|
942
1186
|
};
|
|
943
1187
|
selectAllInCurrentPage = async () => {
|
|
944
1188
|
void this.paginationRepo?.pageStartIndex;
|
|
945
|
-
const sortedData =
|
|
946
|
-
|
|
947
|
-
|
|
948
|
-
|
|
949
|
-
|
|
950
|
-
|
|
951
|
-
|
|
952
|
-
|
|
953
|
-
|
|
1189
|
+
const sortedData = this.sortedData;
|
|
1190
|
+
const pageStartIndex = this.paginationRepo ? this.paginationRepo.pageStartIndex : 0;
|
|
1191
|
+
const pageEndIndexExclusive = this.paginationRepo
|
|
1192
|
+
? Math.min(this.paginationRepo.pageEndIndexExclusive, sortedData.length)
|
|
1193
|
+
: sortedData.length;
|
|
1194
|
+
// Will be doing one full reassignment to this.selectedItems to avoid svelteMap redraws
|
|
1195
|
+
const cloned = new SvelteMap(this.selectedItems);
|
|
1196
|
+
const pending = [];
|
|
1197
|
+
if (this.allSelectedInCurrentPage) {
|
|
1198
|
+
for (let i = pageStartIndex; i < pageEndIndexExclusive; i++) {
|
|
1199
|
+
const raw = this._cachedKey(sortedData[i]);
|
|
1200
|
+
if (raw instanceof Promise) {
|
|
1201
|
+
pending.push(raw.then((key) => {
|
|
1202
|
+
cloned.delete(key);
|
|
1203
|
+
}));
|
|
1204
|
+
}
|
|
1205
|
+
else {
|
|
1206
|
+
cloned.delete(raw);
|
|
1207
|
+
}
|
|
954
1208
|
}
|
|
955
1209
|
}
|
|
956
1210
|
else {
|
|
957
|
-
// this.resetSelectedItems();
|
|
958
|
-
// const selectedItems = new SvelteSet<number>();
|
|
959
|
-
const pageStartIndex = this.paginationRepo ? this.paginationRepo.pageStartIndex : 0;
|
|
960
|
-
const pageEndIndexExclusive = this.paginationRepo
|
|
961
|
-
? Math.min(this.paginationRepo.pageEndIndexExclusive, sortedData.length)
|
|
962
|
-
: sortedData.length;
|
|
963
1211
|
const selectableMethod = this.columnDefs.find((it) => it instanceof RowSelectionDef)?.isSelectable;
|
|
964
1212
|
if (selectableMethod) {
|
|
965
|
-
for (let
|
|
966
|
-
const item = sortedData[
|
|
967
|
-
|
|
968
|
-
|
|
1213
|
+
for (let i = pageStartIndex; i < pageEndIndexExclusive; i++) {
|
|
1214
|
+
const item = sortedData[i];
|
|
1215
|
+
const relIdx = i - pageStartIndex;
|
|
1216
|
+
const s = selectableMethod(item, relIdx);
|
|
1217
|
+
const doSet = (ok) => {
|
|
1218
|
+
if (!ok) {
|
|
1219
|
+
return;
|
|
1220
|
+
}
|
|
1221
|
+
const raw = this._cachedKey(item);
|
|
1222
|
+
if (raw instanceof Promise) {
|
|
1223
|
+
return raw.then((key) => {
|
|
1224
|
+
cloned.set(key, item);
|
|
1225
|
+
});
|
|
1226
|
+
}
|
|
1227
|
+
cloned.set(raw, item);
|
|
1228
|
+
};
|
|
1229
|
+
const r = s instanceof Promise ? s.then(doSet) : doSet(s);
|
|
1230
|
+
if (r instanceof Promise) {
|
|
1231
|
+
pending.push(r);
|
|
969
1232
|
}
|
|
970
1233
|
}
|
|
971
1234
|
}
|
|
972
1235
|
else {
|
|
973
|
-
for (let
|
|
974
|
-
const item = sortedData[
|
|
975
|
-
|
|
1236
|
+
for (let i = pageStartIndex; i < pageEndIndexExclusive; i++) {
|
|
1237
|
+
const item = sortedData[i];
|
|
1238
|
+
const raw = this._cachedKey(item);
|
|
1239
|
+
if (raw instanceof Promise) {
|
|
1240
|
+
pending.push(raw.then((key) => {
|
|
1241
|
+
cloned.set(key, item);
|
|
1242
|
+
}));
|
|
1243
|
+
}
|
|
1244
|
+
else {
|
|
1245
|
+
cloned.set(raw, item);
|
|
1246
|
+
}
|
|
976
1247
|
}
|
|
977
1248
|
}
|
|
978
1249
|
}
|
|
1250
|
+
if (pending.length > 0) {
|
|
1251
|
+
await Promise.all(pending);
|
|
1252
|
+
}
|
|
1253
|
+
this._selectedItems = cloned;
|
|
979
1254
|
};
|
|
980
1255
|
onHighlightAll = () => {
|
|
981
|
-
this.allHighlighted
|
|
982
|
-
.
|
|
983
|
-
|
|
984
|
-
|
|
985
|
-
|
|
986
|
-
|
|
987
|
-
|
|
988
|
-
|
|
989
|
-
|
|
990
|
-
|
|
1256
|
+
if (this.allHighlighted) {
|
|
1257
|
+
this.highlightedItems.clear();
|
|
1258
|
+
return Promise.resolve();
|
|
1259
|
+
}
|
|
1260
|
+
else {
|
|
1261
|
+
const items = this.currentPageData;
|
|
1262
|
+
return asyncForEach(items, (item) => {
|
|
1263
|
+
const raw = this._cachedKey(item);
|
|
1264
|
+
if (raw instanceof Promise) {
|
|
1265
|
+
return raw.then((key) => {
|
|
1266
|
+
this.highlightedItems.set(key, item);
|
|
991
1267
|
});
|
|
992
|
-
}
|
|
993
|
-
|
|
994
|
-
|
|
995
|
-
|
|
1268
|
+
}
|
|
1269
|
+
this.highlightedItems.set(raw, item);
|
|
1270
|
+
return;
|
|
1271
|
+
});
|
|
1272
|
+
}
|
|
996
1273
|
};
|
|
997
1274
|
onEditCell = async (item, coords, value) => {
|
|
998
|
-
const
|
|
1275
|
+
const rawOldKey = this._cachedKey(item);
|
|
1276
|
+
const oldKey = rawOldKey instanceof Promise ? await rawOldKey : rawOldKey;
|
|
999
1277
|
const wasSelected = this.selectedItems.has(oldKey);
|
|
1000
1278
|
if (wasSelected) {
|
|
1001
1279
|
this.selectedItems.delete(oldKey);
|
|
1002
1280
|
}
|
|
1281
|
+
// Invalidate cache — _onEditCell may mutate the item's key field in-place
|
|
1282
|
+
this._keyCache.delete(item);
|
|
1003
1283
|
await this._onEditCell?.(item, coords, value);
|
|
1004
1284
|
if (wasSelected && this.isSelectable) {
|
|
1005
|
-
const
|
|
1285
|
+
const rawNewKey = this._cachedKey(item);
|
|
1286
|
+
const newKey = rawNewKey instanceof Promise ? await rawNewKey : rawNewKey;
|
|
1006
1287
|
if (newKey) {
|
|
1007
1288
|
this.selectedItems.set(newKey, item);
|
|
1008
1289
|
}
|
|
1009
|
-
this.recalculateAllSelectedInCurrentPage();
|
|
1290
|
+
// this.recalculateAllSelectedInCurrentPage();
|
|
1010
1291
|
}
|
|
1011
1292
|
};
|
|
1012
1293
|
handleTdKeydown = (e) => {
|
|
@@ -1031,7 +1312,7 @@ export class TableContext {
|
|
|
1031
1312
|
this.tabBackward();
|
|
1032
1313
|
}
|
|
1033
1314
|
else {
|
|
1034
|
-
this.tabForward()
|
|
1315
|
+
this.tabForward();
|
|
1035
1316
|
}
|
|
1036
1317
|
}
|
|
1037
1318
|
if (e.target.tagName === 'INPUT' &&
|
|
@@ -1058,20 +1339,20 @@ export class TableContext {
|
|
|
1058
1339
|
if (!this.allowCopy) {
|
|
1059
1340
|
return;
|
|
1060
1341
|
}
|
|
1061
|
-
|
|
1342
|
+
this.focusToTop();
|
|
1062
1343
|
}
|
|
1063
1344
|
else {
|
|
1064
|
-
|
|
1345
|
+
this.moveToTop();
|
|
1065
1346
|
}
|
|
1066
1347
|
}
|
|
1067
1348
|
else if (e.getModifierState('Shift')) {
|
|
1068
1349
|
if (!this.allowCopy) {
|
|
1069
1350
|
return;
|
|
1070
1351
|
}
|
|
1071
|
-
|
|
1352
|
+
this.moveFocusUp();
|
|
1072
1353
|
}
|
|
1073
1354
|
else {
|
|
1074
|
-
|
|
1355
|
+
this.setFocusUp();
|
|
1075
1356
|
}
|
|
1076
1357
|
return;
|
|
1077
1358
|
}
|
|
@@ -1082,20 +1363,20 @@ export class TableContext {
|
|
|
1082
1363
|
if (!this.allowCopy) {
|
|
1083
1364
|
return;
|
|
1084
1365
|
}
|
|
1085
|
-
|
|
1366
|
+
this.focusToBottom();
|
|
1086
1367
|
}
|
|
1087
1368
|
else {
|
|
1088
|
-
|
|
1369
|
+
this.moveToBottom();
|
|
1089
1370
|
}
|
|
1090
1371
|
}
|
|
1091
1372
|
else if (e.getModifierState('Shift')) {
|
|
1092
1373
|
if (!this.allowCopy) {
|
|
1093
1374
|
return;
|
|
1094
1375
|
}
|
|
1095
|
-
|
|
1376
|
+
this.moveFocusDown();
|
|
1096
1377
|
}
|
|
1097
1378
|
else {
|
|
1098
|
-
|
|
1379
|
+
this.setFocusDown();
|
|
1099
1380
|
}
|
|
1100
1381
|
return;
|
|
1101
1382
|
}
|
|
@@ -1157,9 +1438,9 @@ export class TableContext {
|
|
|
1157
1438
|
case 'a': {
|
|
1158
1439
|
if (e.ctrlKey) {
|
|
1159
1440
|
e.preventDefault();
|
|
1160
|
-
|
|
1441
|
+
this.moveToTop();
|
|
1161
1442
|
this.moveToStart();
|
|
1162
|
-
|
|
1443
|
+
this.focusToBottom();
|
|
1163
1444
|
this.focusToEnd();
|
|
1164
1445
|
}
|
|
1165
1446
|
break;
|
|
@@ -1253,7 +1534,7 @@ export class TableContext {
|
|
|
1253
1534
|
if (!colId) {
|
|
1254
1535
|
return;
|
|
1255
1536
|
}
|
|
1256
|
-
const currentPageContents =
|
|
1537
|
+
const currentPageContents = this.currentPageData;
|
|
1257
1538
|
const ctx = getCanvasContext();
|
|
1258
1539
|
let maxWidth = 0;
|
|
1259
1540
|
if (columnDef.accessorFn) {
|
|
@@ -1332,7 +1613,7 @@ export class TableContext {
|
|
|
1332
1613
|
// this.forceVisibilityUpdate();
|
|
1333
1614
|
};
|
|
1334
1615
|
copyHighlightedRowsToClipboard = async () => {
|
|
1335
|
-
//
|
|
1616
|
+
// NOTE: False Positive. Clipboard does not exist in http environments
|
|
1336
1617
|
// eslint-disable-next-line @typescript-eslint/no-unnecessary-condition
|
|
1337
1618
|
if (!navigator.clipboard) {
|
|
1338
1619
|
alert('cannot copy in an insecure connection');
|
|
@@ -1341,7 +1622,7 @@ export class TableContext {
|
|
|
1341
1622
|
return this._performRowCopy(await this.getHighlightedRowData());
|
|
1342
1623
|
};
|
|
1343
1624
|
copyDataToClipboard = async () => {
|
|
1344
|
-
//
|
|
1625
|
+
// NOTE: False Positive. Clipboard does not exist in http environments
|
|
1345
1626
|
// eslint-disable-next-line @typescript-eslint/no-unnecessary-condition
|
|
1346
1627
|
if (!navigator.clipboard) {
|
|
1347
1628
|
alert('cannot copy in an insecure connection');
|
|
@@ -1352,7 +1633,8 @@ export class TableContext {
|
|
|
1352
1633
|
_performRowCopy = async ({ items, indicesByItem, focusedElementData, affectedColumns, }) => {
|
|
1353
1634
|
const focusedColumnIds = affectedColumns.map((it) => encapsulate(typeof it.header === 'string' ? it.header : it.id));
|
|
1354
1635
|
const value = await (async () => {
|
|
1355
|
-
|
|
1636
|
+
// eslint-disable-next-line svelte/prefer-svelte-reactivity
|
|
1637
|
+
const selectColumns = new Map();
|
|
1356
1638
|
for (let i = affectedColumns.length - 1; i > -1; i--) {
|
|
1357
1639
|
const columnDef = affectedColumns[i];
|
|
1358
1640
|
if (columnDef instanceof SelectDef) {
|
|
@@ -1426,41 +1708,41 @@ export class TableContext {
|
|
|
1426
1708
|
this.focusStart = null;
|
|
1427
1709
|
this.focusEnd = null;
|
|
1428
1710
|
};
|
|
1429
|
-
focusToTop =
|
|
1711
|
+
focusToTop = () => {
|
|
1430
1712
|
if (!this.allowCopy) {
|
|
1431
1713
|
return;
|
|
1432
1714
|
}
|
|
1433
|
-
|
|
1715
|
+
this._moveFocusEndRow(-Infinity);
|
|
1434
1716
|
};
|
|
1435
1717
|
focusToBottom = () => {
|
|
1436
1718
|
if (!this.allowCopy) {
|
|
1437
1719
|
return;
|
|
1438
1720
|
}
|
|
1439
|
-
|
|
1721
|
+
this._moveFocusEndRow(Infinity);
|
|
1440
1722
|
};
|
|
1441
|
-
moveToBottom =
|
|
1442
|
-
|
|
1723
|
+
moveToBottom = () => {
|
|
1724
|
+
this._moveFocusRow(Infinity);
|
|
1443
1725
|
};
|
|
1444
|
-
moveToTop =
|
|
1445
|
-
|
|
1726
|
+
moveToTop = () => {
|
|
1727
|
+
this._moveFocusRow(-Infinity);
|
|
1446
1728
|
};
|
|
1447
|
-
moveFocusUp =
|
|
1729
|
+
moveFocusUp = () => {
|
|
1448
1730
|
if (!this.allowCopy) {
|
|
1449
1731
|
return;
|
|
1450
1732
|
}
|
|
1451
|
-
|
|
1733
|
+
this._moveFocusEndRow(-1);
|
|
1452
1734
|
};
|
|
1453
|
-
setFocusUp =
|
|
1454
|
-
|
|
1735
|
+
setFocusUp = () => {
|
|
1736
|
+
this._moveFocusRow(-1);
|
|
1455
1737
|
};
|
|
1456
|
-
tabForward =
|
|
1738
|
+
tabForward = () => {
|
|
1457
1739
|
if (!this.allowCopy) {
|
|
1458
1740
|
return;
|
|
1459
1741
|
}
|
|
1460
1742
|
const defs = this.columnDefs;
|
|
1461
1743
|
const visibility = this.columnVisibility;
|
|
1462
1744
|
const indexBounds = defs.length;
|
|
1463
|
-
const rowBounds =
|
|
1745
|
+
const rowBounds = this.sortedData.length;
|
|
1464
1746
|
if (!this.focusStart || !rowBounds) {
|
|
1465
1747
|
return;
|
|
1466
1748
|
}
|
|
@@ -1582,14 +1864,14 @@ export class TableContext {
|
|
|
1582
1864
|
}
|
|
1583
1865
|
//otherwise return without doing anything
|
|
1584
1866
|
};
|
|
1585
|
-
moveFocusDown =
|
|
1867
|
+
moveFocusDown = () => {
|
|
1586
1868
|
if (!this.allowCopy) {
|
|
1587
1869
|
return;
|
|
1588
1870
|
}
|
|
1589
|
-
|
|
1871
|
+
this._moveFocusEndRow(1);
|
|
1590
1872
|
};
|
|
1591
|
-
setFocusDown =
|
|
1592
|
-
|
|
1873
|
+
setFocusDown = () => {
|
|
1874
|
+
this._moveFocusRow(1);
|
|
1593
1875
|
};
|
|
1594
1876
|
moveFocusLeft = () => {
|
|
1595
1877
|
if (!this.allowCopy) {
|
|
@@ -1856,7 +2138,7 @@ export class TableContext {
|
|
|
1856
2138
|
};
|
|
1857
2139
|
localStorage.setItem(`${this.userId}-${this.tableName}-settings`, JSON.stringify(settingsObject));
|
|
1858
2140
|
}
|
|
1859
|
-
|
|
2141
|
+
_moveFocusEndRow(offset) {
|
|
1860
2142
|
if (!this.allowCopy) {
|
|
1861
2143
|
return;
|
|
1862
2144
|
}
|
|
@@ -1868,21 +2150,23 @@ export class TableContext {
|
|
|
1868
2150
|
// throw new Error(`_moveFocusEndRow is not in a tracking context.`);
|
|
1869
2151
|
// }
|
|
1870
2152
|
const focusEnd = this.focusEnd;
|
|
1871
|
-
const
|
|
2153
|
+
const prm = this.paginationRowModel;
|
|
2154
|
+
const rows = prm.rows;
|
|
1872
2155
|
const endRowIndex = rows.findIndex((row) => row.visibleIndex === focusEnd.row);
|
|
1873
2156
|
this.focusEnd = {
|
|
1874
2157
|
...this.focusEnd,
|
|
1875
2158
|
row: rows[Math.max(Math.min(endRowIndex + offset, rows.length - 1), 0)].visibleIndex,
|
|
1876
2159
|
};
|
|
1877
2160
|
}
|
|
1878
|
-
|
|
2161
|
+
_moveFocusRow(offset) {
|
|
1879
2162
|
if (!this.focusStart) {
|
|
1880
2163
|
console.warn('no focusStart found');
|
|
1881
2164
|
return;
|
|
1882
2165
|
}
|
|
1883
2166
|
const focusStart = this.focusStart;
|
|
1884
|
-
const newEndRowIndex =
|
|
1885
|
-
const
|
|
2167
|
+
const newEndRowIndex = (() => {
|
|
2168
|
+
const prm = this.paginationRowModel;
|
|
2169
|
+
const rows = prm.rows;
|
|
1886
2170
|
const endRowIndex = rows.findIndex((row) => row.visibleIndex === focusStart.row);
|
|
1887
2171
|
return rows[Math.max(Math.min(endRowIndex + offset, rows.length - 1), 0)].visibleIndex;
|
|
1888
2172
|
})();
|
|
@@ -1890,9 +2174,10 @@ export class TableContext {
|
|
|
1890
2174
|
}
|
|
1891
2175
|
async getHighlightedRowData() {
|
|
1892
2176
|
const affectedColumns = this.columnDefs.filter(this.columnDefReturnsTextValue);
|
|
1893
|
-
|
|
2177
|
+
// eslint-disable-next-line svelte/prefer-svelte-reactivity
|
|
2178
|
+
const indices = new Map();
|
|
1894
2179
|
const selectedRows = [...this.highlightedItems.values()];
|
|
1895
|
-
const sortedData =
|
|
2180
|
+
const sortedData = this.sortedData;
|
|
1896
2181
|
for (const item of selectedRows) {
|
|
1897
2182
|
const rowIndex = sortedData.indexOf(item);
|
|
1898
2183
|
if (rowIndex == -1) {
|
|
@@ -1906,7 +2191,8 @@ export class TableContext {
|
|
|
1906
2191
|
const rowLength = selectedRows.length;
|
|
1907
2192
|
for (let rowIndex = 0; rowIndex < rowLength; rowIndex++) {
|
|
1908
2193
|
const item = selectedRows[rowIndex];
|
|
1909
|
-
const
|
|
2194
|
+
const rawKey = this._cachedKey(item);
|
|
2195
|
+
const key = rawKey instanceof Promise ? await rawKey : rawKey;
|
|
1910
2196
|
selectedCells[rowIndex] = [];
|
|
1911
2197
|
const targetRow = selectedCells[rowIndex];
|
|
1912
2198
|
const colLength = affectedColumns.length;
|
|
@@ -1949,10 +2235,10 @@ export class TableContext {
|
|
|
1949
2235
|
const { row: startRowIndexId, column: startColumnIndex } = this.focusStart;
|
|
1950
2236
|
const { row: endRowIndexId, column: endColumnIndex } = this.focusEnd;
|
|
1951
2237
|
// const model = this._currentPageData;
|
|
1952
|
-
const model =
|
|
2238
|
+
const model = this.paginationRowModel;
|
|
1953
2239
|
const startRowIndex = model.rows.findIndex((row) => row.visibleIndex === startRowIndexId);
|
|
1954
2240
|
const endRowIndex = model.rows.findIndex((row) => row.visibleIndex === endRowIndexId);
|
|
1955
|
-
if (!
|
|
2241
|
+
if (!this.currentPageData.length || startRowIndex == -1 || endRowIndex == -1) {
|
|
1956
2242
|
throw new Error(`copy was missing one of the two indices. First: ${startRowIndex}, second: ${endRowIndex}`);
|
|
1957
2243
|
}
|
|
1958
2244
|
const minRowIndex = Math.min(startRowIndex, endRowIndex);
|
|
@@ -1965,7 +2251,8 @@ export class TableContext {
|
|
|
1965
2251
|
this.columnDefReturnsTextValue(it));
|
|
1966
2252
|
});
|
|
1967
2253
|
const selectedRows = [];
|
|
1968
|
-
|
|
2254
|
+
// eslint-disable-next-line svelte/prefer-svelte-reactivity
|
|
2255
|
+
const indices = new Map();
|
|
1969
2256
|
for (let i = minRowIndex; i <= maxRowIndex; i++) {
|
|
1970
2257
|
const row = model.rows[i];
|
|
1971
2258
|
const item = row.original;
|
|
@@ -1976,10 +2263,11 @@ export class TableContext {
|
|
|
1976
2263
|
// TODO somewhere between here and the ending of the copy functionality, we end up with issues where instead of it using the accessor fn, it tries to pick up the select option, and ends up using the value ("1", etc)
|
|
1977
2264
|
const selectedCells = [];
|
|
1978
2265
|
const rowLength = selectedRows.length;
|
|
1979
|
-
const sortedData =
|
|
2266
|
+
const sortedData = this.sortedData;
|
|
1980
2267
|
for (let rowIndex = 0; rowIndex < rowLength; rowIndex++) {
|
|
1981
2268
|
const item = selectedRows[rowIndex];
|
|
1982
|
-
const
|
|
2269
|
+
const rawKey = this._cachedKey(item);
|
|
2270
|
+
const key = rawKey instanceof Promise ? await rawKey : rawKey;
|
|
1983
2271
|
selectedCells[rowIndex] = [];
|
|
1984
2272
|
const targetRow = selectedCells[rowIndex];
|
|
1985
2273
|
const colLength = affectedColumns.length;
|
|
@@ -2019,7 +2307,8 @@ export class TableContext {
|
|
|
2019
2307
|
}
|
|
2020
2308
|
return {
|
|
2021
2309
|
items: [],
|
|
2022
|
-
|
|
2310
|
+
// eslint-disable-next-line svelte/prefer-svelte-reactivity
|
|
2311
|
+
indicesByItem: new Map(),
|
|
2023
2312
|
focusedElementData: [],
|
|
2024
2313
|
affectedColumns: [],
|
|
2025
2314
|
};
|
|
@@ -2049,7 +2338,8 @@ export class TableContext {
|
|
|
2049
2338
|
return allDefs;
|
|
2050
2339
|
};
|
|
2051
2340
|
assertNoDuplicateIds() {
|
|
2052
|
-
|
|
2341
|
+
// eslint-disable-next-line svelte/prefer-svelte-reactivity
|
|
2342
|
+
const foundIds = new Set();
|
|
2053
2343
|
this.defaultColumnDefs.defs.forEach((def) => {
|
|
2054
2344
|
if (foundIds.has(def.id)) {
|
|
2055
2345
|
throw new Error(`Duplicate Column Definition ID ${def.id} in table ${this.tableName}`);
|
|
@@ -2223,13 +2513,15 @@ export class TableContext {
|
|
|
2223
2513
|
}
|
|
2224
2514
|
_setNewPinningState() {
|
|
2225
2515
|
this.columnPinning = {
|
|
2226
|
-
|
|
2516
|
+
// eslint-disable-next-line svelte/prefer-svelte-reactivity
|
|
2517
|
+
left: new Map(this.columnPinning.left &&
|
|
2227
2518
|
this.columnDefs
|
|
2228
2519
|
.filter((col) => {
|
|
2229
2520
|
return this.columnPinning.left?.has(col.id);
|
|
2230
2521
|
})
|
|
2231
2522
|
.map((col, index) => [col.id, index])),
|
|
2232
|
-
|
|
2523
|
+
// eslint-disable-next-line svelte/prefer-svelte-reactivity
|
|
2524
|
+
right: new Map(this.columnPinning.right &&
|
|
2233
2525
|
this.columnDefs
|
|
2234
2526
|
.filter((col) => this.columnPinning.right?.has(col.id))
|
|
2235
2527
|
.map((col, index) => [col.id, index])),
|
|
@@ -2308,7 +2600,8 @@ function areDefsEquivalent(newColumnDefs, oldColumnDefs) {
|
|
|
2308
2600
|
});
|
|
2309
2601
|
}
|
|
2310
2602
|
function columnDefsToMap(defs) {
|
|
2311
|
-
|
|
2603
|
+
// eslint-disable-next-line svelte/prefer-svelte-reactivity
|
|
2604
|
+
const map = new Map();
|
|
2312
2605
|
defs.forEach((def) => {
|
|
2313
2606
|
map.set(def.id, def);
|
|
2314
2607
|
});
|