@tint-ui/data-table 0.3.5

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.
Files changed (122) hide show
  1. package/LICENSE +21 -0
  2. package/README.md +9 -0
  3. package/adapters/boolean.d.ts +10 -0
  4. package/adapters/boolean.js +38 -0
  5. package/adapters/index.d.ts +6 -0
  6. package/adapters/index.js +18 -0
  7. package/adapters/number-format.d.ts +1 -0
  8. package/adapters/number-format.js +42 -0
  9. package/adapters/number.d.ts +12 -0
  10. package/adapters/number.js +51 -0
  11. package/adapters/text.d.ts +4 -0
  12. package/adapters/text.js +9 -0
  13. package/cell-adapter-type.d.ts +43 -0
  14. package/cell-adapter-type.js +306 -0
  15. package/cjs/adapters/boolean.js +43 -0
  16. package/cjs/adapters/index.js +21 -0
  17. package/cjs/adapters/number-format.js +46 -0
  18. package/cjs/adapters/number.js +56 -0
  19. package/cjs/adapters/text.js +13 -0
  20. package/cjs/cell-adapter-type.js +312 -0
  21. package/cjs/classes.js +27 -0
  22. package/cjs/context.js +14 -0
  23. package/cjs/data-table-content.js +105 -0
  24. package/cjs/data-table-pagination.js +38 -0
  25. package/cjs/data-table-text-filter.js +83 -0
  26. package/cjs/data-table-toolbar.js +103 -0
  27. package/cjs/data-table-views-options.js +137 -0
  28. package/cjs/data-table.js +63 -0
  29. package/cjs/filter-adapter-type.js +162 -0
  30. package/cjs/filter-adapters/index.js +10 -0
  31. package/cjs/filter-adapters/option.js +152 -0
  32. package/cjs/filter-adapters/use-option-filter.js +195 -0
  33. package/cjs/filter-classes.js +26 -0
  34. package/cjs/filter-fn.js +84 -0
  35. package/cjs/index.js +99 -0
  36. package/cjs/package.json +3 -0
  37. package/cjs/pagination-arrow.js +93 -0
  38. package/cjs/pagination-classes.js +20 -0
  39. package/cjs/pagination-number.js +66 -0
  40. package/cjs/pagination-size-options.js +48 -0
  41. package/cjs/row-button-menu.js +49 -0
  42. package/cjs/row-popover-menu.js +52 -0
  43. package/cjs/toolbar-classes.js +24 -0
  44. package/cjs/types.js +3 -0
  45. package/cjs/use-data-table.js +768 -0
  46. package/cjs/use-lexicon.js +155 -0
  47. package/cjs/use-row-menu.js +60 -0
  48. package/cjs/use-visibility-column.js +105 -0
  49. package/cjs/use-visibility-filter.js +149 -0
  50. package/cjs/utils.js +136 -0
  51. package/classes.d.ts +34 -0
  52. package/classes.js +23 -0
  53. package/context.d.ts +5 -0
  54. package/context.js +9 -0
  55. package/data-table-content.d.ts +9 -0
  56. package/data-table-content.js +98 -0
  57. package/data-table-pagination.d.ts +5 -0
  58. package/data-table-pagination.js +31 -0
  59. package/data-table-text-filter.d.ts +7 -0
  60. package/data-table-text-filter.js +76 -0
  61. package/data-table-toolbar.d.ts +5 -0
  62. package/data-table-toolbar.js +95 -0
  63. package/data-table-views-options.d.ts +2 -0
  64. package/data-table-views-options.js +133 -0
  65. package/data-table.d.ts +18 -0
  66. package/data-table.js +56 -0
  67. package/filter-adapter-type.d.ts +9 -0
  68. package/filter-adapter-type.js +155 -0
  69. package/filter-adapters/index.d.ts +5 -0
  70. package/filter-adapters/index.js +7 -0
  71. package/filter-adapters/option.d.ts +3 -0
  72. package/filter-adapters/option.js +147 -0
  73. package/filter-adapters/use-option-filter.d.ts +27 -0
  74. package/filter-adapters/use-option-filter.js +192 -0
  75. package/filter-classes.d.ts +32 -0
  76. package/filter-classes.js +22 -0
  77. package/filter-fn.d.ts +7 -0
  78. package/filter-fn.js +76 -0
  79. package/index.d.ts +16 -0
  80. package/index.js +16 -0
  81. package/package.json +97 -0
  82. package/pagination-arrow.d.ts +5 -0
  83. package/pagination-arrow.js +86 -0
  84. package/pagination-classes.d.ts +20 -0
  85. package/pagination-classes.js +16 -0
  86. package/pagination-number.d.ts +5 -0
  87. package/pagination-number.js +59 -0
  88. package/pagination-size-options.d.ts +3 -0
  89. package/pagination-size-options.js +44 -0
  90. package/row-button-menu.d.ts +5 -0
  91. package/row-button-menu.js +45 -0
  92. package/row-popover-menu.d.ts +5 -0
  93. package/row-popover-menu.js +48 -0
  94. package/styles-filter.css +1 -0
  95. package/styles-filter.module.css +64 -0
  96. package/styles-filter.module.scss +65 -0
  97. package/styles-pagination.css +1 -0
  98. package/styles-pagination.module.css +28 -0
  99. package/styles-pagination.module.scss +31 -0
  100. package/styles-toolbar.css +1 -0
  101. package/styles-toolbar.module.css +70 -0
  102. package/styles-toolbar.module.scss +67 -0
  103. package/styles.css +1 -0
  104. package/styles.json +8 -0
  105. package/styles.module.css +39 -0
  106. package/styles.module.scss +38 -0
  107. package/toolbar-classes.d.ts +26 -0
  108. package/toolbar-classes.js +20 -0
  109. package/types.d.ts +226 -0
  110. package/types.js +2 -0
  111. package/use-data-table.d.ts +3 -0
  112. package/use-data-table.js +768 -0
  113. package/use-lexicon.d.ts +12 -0
  114. package/use-lexicon.js +151 -0
  115. package/use-row-menu.d.ts +7 -0
  116. package/use-row-menu.js +58 -0
  117. package/use-visibility-column.d.ts +7 -0
  118. package/use-visibility-column.js +101 -0
  119. package/use-visibility-filter.d.ts +7 -0
  120. package/use-visibility-filter.js +145 -0
  121. package/utils.d.ts +14 -0
  122. package/utils.js +128 -0
@@ -0,0 +1,768 @@
1
+ "use strict";
2
+ "use client";
3
+
4
+ var _interopRequireDefault = require("@babel/runtime/helpers/interopRequireDefault").default;
5
+ var _interopRequireWildcard = require("@babel/runtime/helpers/interopRequireWildcard").default;
6
+ exports.__esModule = true;
7
+ exports.useDataTable = void 0;
8
+ var _objectWithoutPropertiesLoose2 = _interopRequireDefault(require("@babel/runtime/helpers/objectWithoutPropertiesLoose"));
9
+ var React = _interopRequireWildcard(require("react"));
10
+ var _reactTable = require("@tanstack/react-table");
11
+ var _errorMessage = require("@tint-ui/tools/error-message");
12
+ var _useVisibilityColumn = require("./use-visibility-column");
13
+ var _cellAdapterType = require("./cell-adapter-type");
14
+ var _useLexicon = require("./use-lexicon");
15
+ var _useVisibilityFilter = require("./use-visibility-filter");
16
+ var _filterFn = require("./filter-fn");
17
+ var _rowButtonMenu = require("./row-button-menu");
18
+ var _rowPopoverMenu = require("./row-popover-menu");
19
+ var _utils = require("./utils");
20
+ const _excluded = ["globalFilter"],
21
+ _excluded2 = ["columnFilters"],
22
+ _excluded3 = ["sorting"],
23
+ _excluded4 = ["pagination"];
24
+ const createHash = function (name, keyName, manual, cells) {
25
+ let hash = `${name}[${keyName},${manual ? "1" : "0"}]://`;
26
+ for (const cell of cells) {
27
+ hash += ":" + (cell.type || "text") + "/" + String(cell.name);
28
+ }
29
+ return hash;
30
+ };
31
+ const displayType = function (cell) {
32
+ const {
33
+ type = "text",
34
+ name,
35
+ config = {},
36
+ defaultSortDir = "asc",
37
+ label,
38
+ hidden = false,
39
+ required = false,
40
+ searchable = type === "text",
41
+ sortable = false,
42
+ invisible = false
43
+ } = cell;
44
+ let {
45
+ filter: inputFilter = null
46
+ } = cell;
47
+ const displayCell = {
48
+ type,
49
+ name,
50
+ config,
51
+ defaultSortDir,
52
+ label,
53
+ hidden,
54
+ invisible,
55
+ required,
56
+ searchable,
57
+ sortable,
58
+ filter: inputFilter != null
59
+ };
60
+ let filter = null;
61
+ let filterFn = undefined;
62
+ if (inputFilter != null) {
63
+ if (Array.isArray(inputFilter) || typeof inputFilter === "function") {
64
+ inputFilter = {
65
+ type: "option",
66
+ config: {
67
+ options: inputFilter
68
+ }
69
+ };
70
+ }
71
+ const {
72
+ type: adapterType = "option",
73
+ multiple = false,
74
+ config = {}
75
+ } = inputFilter;
76
+ let {
77
+ valueType
78
+ } = inputFilter;
79
+ if (!valueType) {
80
+ if (type === "boolean" || type === "number") {
81
+ valueType = type;
82
+ } else {
83
+ valueType = "string";
84
+ }
85
+ }
86
+ filter = {
87
+ name,
88
+ type: adapterType,
89
+ valueType: valueType,
90
+ multiple: multiple && type !== "boolean",
91
+ label: inputFilter.label || label,
92
+ hidden: typeof inputFilter.hidden === "boolean" ? inputFilter.hidden : hidden,
93
+ required: typeof inputFilter.required === "boolean" ? inputFilter.required : required,
94
+ config
95
+ };
96
+ switch (valueType) {
97
+ case "boolean":
98
+ filterFn = _filterFn.filterBoolean;
99
+ break;
100
+ case "number":
101
+ filterFn = multiple ? _filterFn.filterNumberMultiple : _filterFn.filterNumber;
102
+ break;
103
+ case "string":
104
+ filterFn = multiple ? _filterFn.filterStringMultiple : _filterFn.filterString;
105
+ break;
106
+ }
107
+ }
108
+ return {
109
+ cell: displayCell,
110
+ filter,
111
+ filterFn
112
+ };
113
+ };
114
+ const initialDataState = function (data, initialData) {
115
+ if (Array.isArray(initialData)) {
116
+ return initialData;
117
+ }
118
+ if (typeof data === "function") {
119
+ return [];
120
+ }
121
+ return Array.isArray(data) ? data : [];
122
+ };
123
+ const createFilterState = function (props, opts) {
124
+ const {
125
+ offset = 0,
126
+ filter,
127
+ sortBy,
128
+ sortDir,
129
+ filterText = ""
130
+ } = props;
131
+ const {
132
+ data,
133
+ manual,
134
+ pageSizeOptions,
135
+ hash
136
+ } = opts;
137
+ let {
138
+ total
139
+ } = props;
140
+ if (!manual) {
141
+ total = data.length;
142
+ }
143
+ let {
144
+ limit
145
+ } = props;
146
+ if (limit == null) {
147
+ limit = pageSizeOptions[0];
148
+ }
149
+ let pageIndex = 0;
150
+ if (offset > 0 && offset >= limit) {
151
+ pageIndex = (offset - offset % limit) / limit;
152
+ }
153
+ const columnFilters = [];
154
+ const pagination = {
155
+ pageIndex,
156
+ pageSize: limit
157
+ };
158
+ if (filter != null) {
159
+ applyFilter(columnFilters, filter);
160
+ }
161
+ const sorting = [];
162
+ if (sortBy != null) {
163
+ sorting.push({
164
+ id: sortBy,
165
+ desc: sortDir == null ? false : sortDir === "desc"
166
+ });
167
+ }
168
+ return {
169
+ hash,
170
+ error: null,
171
+ loading: false,
172
+ loadingTarget: null,
173
+ totalCount: total == null ? -1 : total,
174
+ pageCount: getPageCount(total, limit),
175
+ sorting,
176
+ globalFilter: filterText,
177
+ columnFilters,
178
+ pagination,
179
+ selected: [] // todo
180
+ };
181
+ };
182
+ const applyFilter = function (columnFilters, filter) {
183
+ for (const key in filter) {
184
+ const value = filter[key];
185
+ if (value != null) columnFilters.push({
186
+ id: key,
187
+ value
188
+ });
189
+ }
190
+ };
191
+ const defaultPageSize = 25;
192
+ const getPageCount = (total, limit) => {
193
+ return total == null ? -1 : total > limit ? Math.ceil(total / limit) : 1;
194
+ };
195
+ const useDataTable = function (props) {
196
+ const {
197
+ table,
198
+ header,
199
+ cacheable = true,
200
+ onRowClick,
201
+ toolbar: toolbarProp,
202
+ navbar: navbarProp
203
+ } = props;
204
+ const {
205
+ name,
206
+ keyName = "id",
207
+ cells: tableCells,
208
+ rowMenu: rowMenuProp = null,
209
+ storage = false,
210
+ ssr = true,
211
+ requiredFilterText = false
212
+ } = table;
213
+
214
+ // manual (dynamic) table or not
215
+ const refDataFn = React.useRef(null);
216
+ refDataFn.current = typeof props.data === "function" ? props.data : null;
217
+ const manual = refDataFn.current != null;
218
+ const hash = createHash(name, keyName, manual, tableCells);
219
+ const refHash = React.useRef(hash);
220
+ const [data, setData] = React.useState(() => initialDataState(props.data, props.initialData));
221
+ const toolbar = (0, _utils.getToolbarConfig)(toolbarProp);
222
+ const navbar = (0, _utils.getNavbarConfig)(navbarProp, props.limit || defaultPageSize);
223
+ const [state, setState] = React.useState(() => createFilterState(props, {
224
+ data,
225
+ pageSizeOptions: navbar.pageSizeOptions,
226
+ manual,
227
+ hash
228
+ }));
229
+
230
+ // read page size from state
231
+ navbar.pageSize = state.pagination.pageSize;
232
+ const {
233
+ onMount,
234
+ onReload,
235
+ onFilterReset,
236
+ onPageSizeChange,
237
+ onColumnFiltersChange,
238
+ onSortingChange,
239
+ onGlobalFilterChange,
240
+ onPaginationChange
241
+ } = React.useMemo(() => {
242
+ let mount = false;
243
+ let lazyId = null;
244
+ let waitTime = 0;
245
+ const clearTimeout = () => {
246
+ if (lazyId != null) {
247
+ window.clearTimeout(lazyId);
248
+ lazyId = null;
249
+ }
250
+ };
251
+ const compareHash = hash => {
252
+ return refHash.current === hash;
253
+ };
254
+ const query = (newState, loadingTarget = null) => {
255
+ const fn = refDataFn.current;
256
+ if (!fn || !mount) {
257
+ return false;
258
+ }
259
+ waitTime = 0;
260
+ const queryHash = refHash.current;
261
+ const asyncFn = async data => fn(data);
262
+ const {
263
+ pagination: {
264
+ pageIndex,
265
+ pageSize
266
+ },
267
+ sorting,
268
+ columnFilters,
269
+ globalFilter
270
+ } = newState;
271
+ const sort = sorting[0];
272
+ const data = {
273
+ filter: {},
274
+ filterText: globalFilter,
275
+ limit: pageSize,
276
+ offset: pageIndex > 0 ? pageIndex * pageSize : 0,
277
+ sortBy: sort == null ? null : sort.id,
278
+ sortDir: sort != null && sort.desc ? "desc" : "asc"
279
+ };
280
+ for (const filter of columnFilters) {
281
+ data.filter[filter.id] = filter.value;
282
+ }
283
+
284
+ // check loading status
285
+ setState(prev => {
286
+ if (prev.loading) {
287
+ return prev;
288
+ }
289
+ return Object.assign({}, prev, {
290
+ loading: true,
291
+ loadingTarget
292
+ });
293
+ });
294
+ asyncFn(data).then(result => {
295
+ if (!mount || !compareHash(queryHash)) {
296
+ return;
297
+ }
298
+ const {
299
+ data,
300
+ total,
301
+ filter,
302
+ sortBy,
303
+ sortDir,
304
+ filterText,
305
+ limit,
306
+ offset = 0
307
+ } = result;
308
+ setData(data);
309
+ setState(prev => {
310
+ const columnFilters = [];
311
+ if (filter != null) {
312
+ applyFilter(columnFilters, filter);
313
+ }
314
+ const pageSize = limit;
315
+ const pageIndex = offset >= pageSize ? (offset - offset % pageSize) / pageSize : 0;
316
+ return {
317
+ hash: prev.hash,
318
+ selected: [],
319
+ // todo find selected in new data
320
+ pagination: {
321
+ pageSize,
322
+ pageIndex
323
+ },
324
+ columnFilters,
325
+ globalFilter: typeof filterText === "string" ? filterText : "",
326
+ sorting: sortBy == null ? [] : [{
327
+ id: sortBy,
328
+ desc: sortDir == null ? false : sortDir === "desc"
329
+ }],
330
+ totalCount: total,
331
+ pageCount: getPageCount(total, pageSize),
332
+ loading: false,
333
+ loadingTarget: null,
334
+ error: null
335
+ };
336
+ });
337
+ }).catch(err => {
338
+ if (!mount || !compareHash(queryHash)) {
339
+ return;
340
+ }
341
+ setState(prev => Object.assign({}, prev, {
342
+ loading: false,
343
+ loadingTarget: null,
344
+ error: (0, _errorMessage.errorMessage)(err).message
345
+ }));
346
+ });
347
+ return true;
348
+ };
349
+ const force = (newState, lazy = false, loadingTarget = null) => {
350
+ const fn = refDataFn.current;
351
+ if (!fn) {
352
+ return false;
353
+ }
354
+ const queryHash = refHash.current;
355
+
356
+ // lazy, wait
357
+ if (lazy) {
358
+ const now = Date.now();
359
+ if (waitTime === 0 || now - waitTime < 2500) {
360
+ clearTimeout();
361
+ if (waitTime === 0) {
362
+ waitTime = now;
363
+ }
364
+ lazyId = window.setTimeout(() => {
365
+ if (compareHash(queryHash)) {
366
+ force(newState, false, loadingTarget);
367
+ }
368
+ }, 200);
369
+ return false;
370
+ }
371
+ }
372
+ return query(newState, loadingTarget);
373
+ };
374
+ return {
375
+ onMount() {
376
+ mount = true;
377
+ return () => {
378
+ mount = false;
379
+ };
380
+ },
381
+ onReload(reloadState) {
382
+ query(reloadState, "reload");
383
+ },
384
+ onFilterReset() {
385
+ if (!mount) {
386
+ return;
387
+ }
388
+ setState(prev => {
389
+ if (prev.loading) {
390
+ return prev;
391
+ }
392
+ const state = Object.assign({}, prev, {
393
+ columnFilters: [],
394
+ globalFilter: ""
395
+ });
396
+ if (force(state)) {
397
+ state.loading = true;
398
+ state.loadingTarget = "reset";
399
+ }
400
+ return state;
401
+ });
402
+ },
403
+ onPageSizeChange(pageSize) {
404
+ setState(prev => {
405
+ if (prev.loading || prev.pagination.pageSize === pageSize) {
406
+ return prev;
407
+ }
408
+ const state = Object.assign({}, prev, {
409
+ pagination: {
410
+ pageSize,
411
+ pageIndex: 0
412
+ }
413
+ });
414
+ if (force(state)) {
415
+ state.loading = true;
416
+ state.loadingTarget = "page-size";
417
+ }
418
+ return state;
419
+ });
420
+ },
421
+ onGlobalFilterChange(value) {
422
+ setState(prev => {
423
+ if (prev.loading) {
424
+ return prev;
425
+ }
426
+ const {
427
+ globalFilter
428
+ } = prev,
429
+ rest = (0, _objectWithoutPropertiesLoose2.default)(prev, _excluded);
430
+ if (typeof value === "function") {
431
+ value = value(globalFilter);
432
+ }
433
+ const state = Object.assign({}, rest, {
434
+ globalFilter: value == null ? "" : String(value)
435
+ });
436
+ if (force(state, true, "filter-text")) {
437
+ state.loading = true;
438
+ state.loadingTarget = "filter-text";
439
+ }
440
+ return state;
441
+ });
442
+ },
443
+ onColumnFiltersChange(value) {
444
+ setState(prev => {
445
+ if (prev.loading) {
446
+ return prev;
447
+ }
448
+ const {
449
+ columnFilters
450
+ } = prev,
451
+ rest = (0, _objectWithoutPropertiesLoose2.default)(prev, _excluded2);
452
+ if (typeof value === "function") {
453
+ value = value(columnFilters);
454
+ }
455
+ value = value.filter(({
456
+ value
457
+ }) => Array.isArray(value) ? value.length > 0 : value != null && value !== "");
458
+ const state = Object.assign({}, rest, {
459
+ columnFilters: value
460
+ });
461
+ if (force(state)) {
462
+ state.loading = true;
463
+ state.loadingTarget = "filter:" + (0, _utils.diffFilterId)(columnFilters, state.columnFilters);
464
+ }
465
+ return state;
466
+ });
467
+ },
468
+ onSortingChange(value) {
469
+ setState(prev => {
470
+ if (prev.loading) {
471
+ return prev;
472
+ }
473
+ const {
474
+ sorting
475
+ } = prev,
476
+ rest = (0, _objectWithoutPropertiesLoose2.default)(prev, _excluded3);
477
+ const state = Object.assign({}, rest, {
478
+ error: null,
479
+ sorting: typeof value === "function" ? value(sorting) : value,
480
+ loading: false
481
+ });
482
+ if (force(state)) {
483
+ state.loading = true;
484
+ const first = sorting[0];
485
+ if (first) {
486
+ state.loadingTarget = `sorting:${first.id}`;
487
+ }
488
+ }
489
+ return state;
490
+ });
491
+ },
492
+ onPaginationChange(value) {
493
+ setState(prev => {
494
+ if (prev.loading) {
495
+ return prev;
496
+ }
497
+ const {
498
+ pagination
499
+ } = prev,
500
+ rest = (0, _objectWithoutPropertiesLoose2.default)(prev, _excluded4);
501
+ const state = Object.assign({}, rest, {
502
+ pagination: typeof value === "function" ? value(pagination) : value,
503
+ error: null,
504
+ loading: false
505
+ });
506
+ if (force(state)) {
507
+ state.loading = true;
508
+ state.loadingTarget = "pagination:" + (state.pagination.pageIndex + 1);
509
+ }
510
+ return state;
511
+ });
512
+ }
513
+ };
514
+ }, [hash]);
515
+ React.useEffect(onMount, [onMount]);
516
+ const currentData = !cacheable && !manual && Array.isArray(props.data) ? props.data : null;
517
+ React.useEffect(() => {
518
+ if (currentData != null && data != currentData) {
519
+ setData(currentData);
520
+ }
521
+ }, [currentData, data]);
522
+ React.useEffect(() => {
523
+ let dataState = data;
524
+ let filterState = state;
525
+ if (refHash.current !== hash) {
526
+ refHash.current = hash;
527
+
528
+ // update data state
529
+ dataState = initialDataState(props.data, props.initialData);
530
+ setData(dataState);
531
+
532
+ // update filter state
533
+ filterState = createFilterState(props, {
534
+ data: dataState,
535
+ pageSizeOptions: navbar.pageSizeOptions,
536
+ manual,
537
+ hash
538
+ });
539
+ setState(filterState);
540
+ }
541
+
542
+ // load table if empty
543
+ if (manual && dataState.length === 0) {
544
+ onReload(filterState);
545
+ }
546
+ }, [hash]);
547
+ const {
548
+ cells,
549
+ filters,
550
+ columns,
551
+ dynamic,
552
+ filterText,
553
+ invisible
554
+ } = React.useMemo(() => {
555
+ const cells = [];
556
+ const columns = [];
557
+ const filters = [];
558
+ const invisible = {};
559
+ const dynamic = {
560
+ column: false,
561
+ sort: false,
562
+ filter: false,
563
+ filterText: false
564
+ };
565
+ let filterText = false;
566
+ for (const cell of tableCells) {
567
+ const {
568
+ cell: requiredCell,
569
+ filter,
570
+ filterFn
571
+ } = displayType(cell);
572
+ const {
573
+ name,
574
+ sortable,
575
+ defaultSortDir,
576
+ searchable,
577
+ required
578
+ } = requiredCell;
579
+ if (cell.invisible) {
580
+ invisible[cell.name] = true;
581
+ }
582
+ cells.push(requiredCell);
583
+ if (filter != null) {
584
+ filters.push(filter);
585
+ dynamic.filter = true;
586
+ }
587
+ if (sortable) {
588
+ dynamic.sort = true;
589
+ }
590
+ if (searchable) {
591
+ filterText = true;
592
+ if (!requiredFilterText) {
593
+ dynamic.filterText = true;
594
+ }
595
+ }
596
+ if (!required) {
597
+ dynamic.column = true;
598
+ }
599
+ columns.push({
600
+ accessorKey: name,
601
+ cell: info => (0, _cellAdapterType.renderDataTableCell)(info.getValue(), requiredCell, info.row.original),
602
+ header: () => cell.label,
603
+ footer: () => cell.label,
604
+ filterFn,
605
+ enableHiding: !required && !cell.invisible,
606
+ enableSorting: sortable,
607
+ sortDescFirst: defaultSortDir === "desc",
608
+ enableColumnFilter: filter != null,
609
+ enableGlobalFilter: searchable,
610
+ meta: {
611
+ _cell: requiredCell
612
+ }
613
+ });
614
+ }
615
+ let menu = [];
616
+ let mode = null;
617
+ let alignStart = false;
618
+ if (rowMenuProp != null) {
619
+ if (Array.isArray(rowMenuProp)) {
620
+ menu = rowMenuProp;
621
+ } else {
622
+ menu = rowMenuProp.menu;
623
+ if (rowMenuProp.mode) {
624
+ mode = rowMenuProp.mode;
625
+ }
626
+ if (rowMenuProp.align === "start") {
627
+ alignStart = true;
628
+ }
629
+ }
630
+ if (!mode) {
631
+ mode = menu.length > 4 ? "popover" : "button";
632
+ }
633
+ } else {
634
+ mode = "button";
635
+ }
636
+ if (menu.length > 0) {
637
+ const column = {
638
+ accessorKey: "__#menu",
639
+ cell: mode === "button" ? info => (0, _rowButtonMenu.rowButtonMenu)(info, menu) : info => (0, _rowPopoverMenu.rowPopoverMenu)(info, menu),
640
+ header: "",
641
+ footer: "",
642
+ enableHiding: false,
643
+ enableSorting: false,
644
+ enableColumnFilter: false,
645
+ enableGlobalFilter: false
646
+ };
647
+ alignStart ? columns.unshift(column) : columns.push(column);
648
+ }
649
+
650
+ // todo selectable mode...
651
+
652
+ return {
653
+ columns,
654
+ filters,
655
+ cells,
656
+ dynamic,
657
+ filterText,
658
+ invisible
659
+ };
660
+ }, [hash]);
661
+ const [columnVisibility, onColumnVisibilityChange] = (0, _useVisibilityColumn.useVisibilityColumn)(name, cells, {
662
+ storage,
663
+ ssr
664
+ });
665
+ const filterVisible = (0, _useVisibilityFilter.useVisibilityFilter)(name, filters, filterText, {
666
+ storage,
667
+ ssr,
668
+ requiredFilterText
669
+ });
670
+ const top = header === "top" || header === "both";
671
+ let bottom = header === "bottom" || header === "both";
672
+ if (data.length < 7 && top && bottom) {
673
+ bottom = false;
674
+ }
675
+ const {
676
+ loading
677
+ } = state;
678
+ const getRowClickHandler = React.useCallback(data => {
679
+ if (!onRowClick || loading) {
680
+ return undefined;
681
+ }
682
+ return event => {
683
+ const target = event.target;
684
+ if ("closest" in target && !target.closest("a[href],button,input,select,textarea,[role=button]")) {
685
+ onRowClick(data);
686
+ }
687
+ };
688
+ }, [onRowClick, loading]);
689
+ const {
690
+ pagination
691
+ } = state;
692
+ const tableCtx = (0, _reactTable.useReactTable)({
693
+ data,
694
+ columns,
695
+ pageCount: manual ? state.pageCount : undefined,
696
+ state: {
697
+ columnVisibility,
698
+ sorting: state.sorting,
699
+ globalFilter: state.globalFilter,
700
+ columnFilters: state.columnFilters,
701
+ pagination
702
+ },
703
+ getCoreRowModel: (0, _reactTable.getCoreRowModel)(),
704
+ getPaginationRowModel: (0, _reactTable.getPaginationRowModel)(),
705
+ getFilteredRowModel: (0, _reactTable.getFilteredRowModel)(),
706
+ getSortedRowModel: (0, _reactTable.getSortedRowModel)(),
707
+ globalFilterFn: "auto",
708
+ onColumnFiltersChange,
709
+ onGlobalFilterChange,
710
+ onColumnVisibilityChange,
711
+ onSortingChange,
712
+ onPaginationChange,
713
+ manualFiltering: manual,
714
+ manualSorting: manual,
715
+ manualPagination: manual
716
+ });
717
+
718
+ // lexicon page config
719
+ const limit = pagination.pageSize;
720
+ const offset = pagination.pageIndex * limit;
721
+ let totalCount = state.totalCount;
722
+ let size = data.length;
723
+ let pageCount = state.pageCount;
724
+ if (!manual) {
725
+ totalCount = data.length;
726
+ pageCount = tableCtx.getPageCount();
727
+ const end = offset + limit;
728
+ size = end > totalCount ? limit - end + totalCount : limit;
729
+ }
730
+ const lexicon = (0, _useLexicon.useLexicon)(props.lexicon || {}, {
731
+ limit,
732
+ offset,
733
+ pageNumber: pagination.pageIndex + 1,
734
+ pageCount,
735
+ total: totalCount,
736
+ size,
737
+ selected: state.selected.length
738
+ });
739
+ console.log("state.loadingTarget", state.loadingTarget);
740
+ return {
741
+ hash,
742
+ data,
743
+ cells,
744
+ filters,
745
+ dynamic,
746
+ totalCount,
747
+ lexicon,
748
+ getRowClickHandler,
749
+ filterVisible,
750
+ manual,
751
+ loading,
752
+ loadingTarget: state.loadingTarget,
753
+ header: {
754
+ top,
755
+ bottom
756
+ },
757
+ toolbar: Object.assign({}, toolbar, {
758
+ onFilterReset
759
+ }),
760
+ navbar: Object.assign({}, navbar, {
761
+ onPageSizeChange
762
+ }),
763
+ table: tableCtx,
764
+ error: state.error,
765
+ invisible
766
+ };
767
+ };
768
+ exports.useDataTable = useDataTable;