@oscarpalmer/tabela 0.13.0 → 0.14.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/{body.component.mjs → body.component.js} +3 -6
- package/dist/components/{column.component.mjs → column.component.js} +5 -8
- package/dist/components/{footer.component.mjs → footer.component.js} +4 -7
- package/dist/components/group.component.js +28 -0
- package/dist/components/{header.component.mjs → header.component.js} +3 -6
- package/dist/components/{row.component.mjs → row.component.js} +7 -11
- package/dist/helpers/{dom.helpers.mjs → dom.helpers.js} +9 -13
- package/dist/helpers/{misc.helpers.mjs → misc.helpers.js} +1 -3
- package/dist/helpers/style.helper.js +6 -0
- package/dist/{index.mjs → index.js} +1 -3
- package/dist/managers/{column.manager.mjs → column.manager.js} +1 -6
- package/dist/managers/data.manager.js +181 -0
- package/dist/managers/{event.manager.mjs → event.manager.js} +8 -9
- package/dist/managers/{filter.manager.mjs → filter.manager.js} +14 -23
- package/dist/managers/group.manager.js +46 -0
- package/dist/managers/{navigation.manager.mjs → navigation.manager.js} +24 -27
- package/dist/managers/{render.manager.mjs → render.manager.js} +26 -35
- package/dist/managers/{row.manager.mjs → row.manager.js} +11 -18
- package/dist/managers/{selection.manager.mjs → selection.manager.js} +28 -32
- package/dist/managers/{sort.manager.mjs → sort.manager.js} +9 -12
- package/dist/models/body.model.js +0 -0
- package/dist/models/column.model.js +0 -0
- package/dist/models/data.model.js +0 -0
- package/dist/models/filter.model.js +0 -0
- package/dist/models/footer.model.js +0 -0
- package/dist/models/group.model.js +0 -0
- package/dist/models/header.model.js +0 -0
- package/dist/models/render.model.js +0 -0
- package/dist/models/selection.model.js +0 -0
- package/dist/models/sort.model.js +0 -0
- package/dist/models/tabela.model.js +0 -0
- package/dist/models/tabela.options.js +0 -0
- package/dist/{tabela.full.mjs → tabela.full.js} +860 -1049
- package/dist/tabela.js +105 -0
- package/package.json +1 -1
- package/src/components/body.component.ts +10 -7
- package/src/components/column.component.ts +19 -15
- package/src/components/footer.component.ts +7 -10
- package/src/components/group.component.ts +34 -12
- package/src/components/header.component.ts +6 -5
- package/src/components/row.component.ts +27 -19
- package/src/helpers/dom.helpers.ts +18 -22
- package/src/helpers/misc.helpers.ts +5 -0
- package/src/managers/data.manager.ts +80 -77
- package/src/managers/event.manager.ts +21 -10
- package/src/managers/filter.manager.ts +34 -21
- package/src/managers/group.manager.ts +18 -9
- package/src/managers/navigation.manager.ts +46 -49
- package/src/managers/render.manager.ts +34 -21
- package/src/managers/row.manager.ts +1 -1
- package/src/managers/selection.manager.ts +37 -35
- package/src/managers/sort.manager.ts +47 -34
- package/src/managers/style.manager.ts +40 -25
- package/src/models/column.model.ts +2 -6
- package/src/models/data.model.ts +7 -8
- package/src/models/dom.model.ts +33 -0
- package/src/models/event.model.ts +7 -0
- package/src/models/filter.model.ts +20 -0
- package/src/models/group.model.ts +4 -0
- package/src/models/sort.model.ts +4 -0
- package/src/models/style.model.ts +32 -20
- package/src/models/tabela.model.ts +1 -0
- package/src/tabela.ts +20 -22
- package/dist/body.component-_VDOpJhV.d.mts +0 -10
- package/dist/body.model-2iwsovAV.d.mts +0 -7
- package/dist/column.component-Bx46r3JI.d.mts +0 -16
- package/dist/column.model-D-aw4EU4.d.mts +0 -16
- package/dist/components/body.component.d.mts +0 -2
- package/dist/components/column.component.d.mts +0 -2
- package/dist/components/footer.component.d.mts +0 -2
- package/dist/components/group.component.d.mts +0 -2
- package/dist/components/group.component.mjs +0 -51
- package/dist/components/header.component.d.mts +0 -2
- package/dist/components/row.component.d.mts +0 -2
- package/dist/filter.model-7ukJrtil.d.mts +0 -16
- package/dist/footer.component-Curiab8j.d.mts +0 -12
- package/dist/footer.model-DhqoS6ds.d.mts +0 -8
- package/dist/group.component-Cq1YYbfJ.d.mts +0 -285
- package/dist/group.model-BsKFwHbt.d.mts +0 -10
- package/dist/header.component-BjjlpZIg.d.mts +0 -12
- package/dist/header.model-DN_KzUCV.d.mts +0 -7
- package/dist/helpers/dom.helpers.d.mts +0 -12
- package/dist/helpers/misc.helpers.d.mts +0 -6
- package/dist/helpers/style.helper.d.mts +0 -6
- package/dist/helpers/style.helper.mjs +0 -8
- package/dist/index.d.mts +0 -7
- package/dist/managers/column.manager.d.mts +0 -2
- package/dist/managers/data.manager.d.mts +0 -2
- package/dist/managers/data.manager.mjs +0 -222
- package/dist/managers/event.manager.d.mts +0 -2
- package/dist/managers/filter.manager.d.mts +0 -2
- package/dist/managers/group.manager.d.mts +0 -2
- package/dist/managers/group.manager.mjs +0 -73
- package/dist/managers/navigation.manager.d.mts +0 -2
- package/dist/managers/render.manager.d.mts +0 -2
- package/dist/managers/row.manager.d.mts +0 -2
- package/dist/managers/selection.manager.d.mts +0 -2
- package/dist/managers/sort.manager.d.mts +0 -2
- package/dist/managers/style.manager.d.mts +0 -2
- package/dist/managers/style.manager.mjs +0 -149
- package/dist/models/body.model.d.mts +0 -2
- package/dist/models/body.model.mjs +0 -1
- package/dist/models/column.model.d.mts +0 -2
- package/dist/models/column.model.mjs +0 -1
- package/dist/models/data.model.d.mts +0 -2
- package/dist/models/data.model.mjs +0 -1
- package/dist/models/filter.model.d.mts +0 -2
- package/dist/models/filter.model.mjs +0 -1
- package/dist/models/footer.model.d.mts +0 -2
- package/dist/models/footer.model.mjs +0 -1
- package/dist/models/group.model.d.mts +0 -2
- package/dist/models/group.model.mjs +0 -1
- package/dist/models/header.model.d.mts +0 -2
- package/dist/models/header.model.mjs +0 -1
- package/dist/models/render.model.d.mts +0 -2
- package/dist/models/render.model.mjs +0 -1
- package/dist/models/selection.model.d.mts +0 -2
- package/dist/models/selection.model.mjs +0 -1
- package/dist/models/sort.model.d.mts +0 -2
- package/dist/models/sort.model.mjs +0 -1
- package/dist/models/style.model.d.mts +0 -23
- package/dist/models/style.model.mjs +0 -23
- package/dist/models/tabela.model.d.mts +0 -2
- package/dist/models/tabela.model.mjs +0 -1
- package/dist/models/tabela.options.d.mts +0 -2
- package/dist/models/tabela.options.mjs +0 -1
- package/dist/selection.model-rwQe9fco.d.mts +0 -12
- package/dist/sort.model-CauImaLu.d.mts +0 -15
- package/dist/tabela.d.mts +0 -21
- package/dist/tabela.mjs +0 -126
- package/dist/tabela.options-RkZvfptB.d.mts +0 -14
|
@@ -5,36 +5,38 @@ import {isPlainObject} from '@oscarpalmer/atoms/is';
|
|
|
5
5
|
import type {Key, PlainObject} from '@oscarpalmer/atoms/models';
|
|
6
6
|
import {delay} from '@oscarpalmer/atoms/promise/delay';
|
|
7
7
|
import {getValue} from '@oscarpalmer/atoms/value/handle';
|
|
8
|
+
import type {ColumnComponent} from '../components/column.component';
|
|
8
9
|
import {GroupComponent, updateGroup} from '../components/group.component';
|
|
9
|
-
import type {
|
|
10
|
+
import type {DataState, DataValue, TabelaData} from '../models/data.model';
|
|
11
|
+
import {SORT_ASCENDING} from '../models/sort.model';
|
|
10
12
|
import type {State} from '../models/tabela.model';
|
|
11
13
|
import {sortWithGroups} from './sort.manager';
|
|
12
|
-
import
|
|
14
|
+
import {isGroupKey} from '../helpers/misc.helpers';
|
|
13
15
|
|
|
14
16
|
export class DataManager {
|
|
15
|
-
handlers =
|
|
17
|
+
handlers: TabelaData = {
|
|
16
18
|
add: data => void this.add(data, true),
|
|
17
|
-
clear: () =>
|
|
19
|
+
clear: () => this.clear(),
|
|
18
20
|
get: active => this.get(active),
|
|
19
21
|
remove: items => void this.remove(items, true),
|
|
20
|
-
synchronize: (data, remove) => void this.synchronize(data, remove),
|
|
21
|
-
update: data => void this.update(data),
|
|
22
|
-
}
|
|
22
|
+
synchronize: (data, remove) => void this.synchronize(data, remove === true),
|
|
23
|
+
update: data => void this.update(data, true),
|
|
24
|
+
};
|
|
23
25
|
|
|
24
26
|
state: DataState;
|
|
25
27
|
|
|
26
|
-
get
|
|
27
|
-
return this.state.
|
|
28
|
+
get keys(): Key[] {
|
|
29
|
+
return this.state.keys.active ?? this.state.keys.original;
|
|
28
30
|
}
|
|
29
31
|
|
|
30
32
|
get size(): number {
|
|
31
|
-
return this.
|
|
33
|
+
return this.keys.length;
|
|
32
34
|
}
|
|
33
35
|
|
|
34
36
|
constructor(state: State) {
|
|
35
37
|
this.state = {
|
|
36
38
|
...state,
|
|
37
|
-
|
|
39
|
+
keys: {
|
|
38
40
|
original: [],
|
|
39
41
|
},
|
|
40
42
|
values: {
|
|
@@ -53,6 +55,8 @@ export class DataManager {
|
|
|
53
55
|
let groupColumn: ColumnComponent | undefined;
|
|
54
56
|
let {length} = data;
|
|
55
57
|
|
|
58
|
+
let added = 0;
|
|
59
|
+
|
|
56
60
|
for (let index = 0; index < length; index += 1) {
|
|
57
61
|
const item = data[index];
|
|
58
62
|
const key = getValue(item, state.key) as Key;
|
|
@@ -66,23 +70,25 @@ export class DataManager {
|
|
|
66
70
|
state.values.array.push(item);
|
|
67
71
|
state.values.mapped.set(key, item);
|
|
68
72
|
|
|
73
|
+
added += 1;
|
|
74
|
+
|
|
69
75
|
if (!state.managers.group.enabled) {
|
|
70
76
|
continue;
|
|
71
77
|
}
|
|
72
78
|
|
|
73
|
-
const groupValue = getValue(item, state.managers.group.field) as
|
|
79
|
+
const groupValue = getValue(item, state.managers.group.field) as Key;
|
|
74
80
|
|
|
75
|
-
let group = state.managers.group.
|
|
81
|
+
let group = state.managers.group.getForValue(groupValue);
|
|
76
82
|
|
|
77
83
|
if (group == null) {
|
|
78
84
|
groupColumn ??= state.managers.column.get(state.managers.group.field);
|
|
79
85
|
|
|
80
86
|
group = new GroupComponent(
|
|
81
|
-
`${groupColumn?.options.
|
|
87
|
+
`${groupColumn?.options.label ?? state.managers.group.field}: ${groupValue}`,
|
|
82
88
|
groupValue,
|
|
83
89
|
);
|
|
84
90
|
|
|
85
|
-
state.values.array.push(group);
|
|
91
|
+
state.values.array.push(group.key);
|
|
86
92
|
state.managers.group.add(group);
|
|
87
93
|
}
|
|
88
94
|
|
|
@@ -101,9 +107,9 @@ export class DataManager {
|
|
|
101
107
|
updateGroup(state, groups[index]);
|
|
102
108
|
}
|
|
103
109
|
|
|
104
|
-
|
|
105
|
-
|
|
106
|
-
|
|
110
|
+
await this.update(updates, added === 0);
|
|
111
|
+
|
|
112
|
+
if (added > 0 && render) {
|
|
107
113
|
this.render();
|
|
108
114
|
}
|
|
109
115
|
}
|
|
@@ -119,8 +125,8 @@ export class DataManager {
|
|
|
119
125
|
|
|
120
126
|
state.values.mapped.clear();
|
|
121
127
|
|
|
122
|
-
state.
|
|
123
|
-
state.
|
|
128
|
+
state.keys.active = undefined;
|
|
129
|
+
state.keys.original.length = 0;
|
|
124
130
|
state.values.array.length = 0;
|
|
125
131
|
|
|
126
132
|
this.handlers = undefined as never;
|
|
@@ -132,29 +138,23 @@ export class DataManager {
|
|
|
132
138
|
|
|
133
139
|
return (active ?? false)
|
|
134
140
|
? select(
|
|
135
|
-
state.
|
|
136
|
-
key => !(key
|
|
141
|
+
state.keys.active ?? [],
|
|
142
|
+
key => !isGroupKey(key),
|
|
137
143
|
key => state.values.mapped.get(key as Key)!,
|
|
138
144
|
)
|
|
139
|
-
: (state.values.array.filter(item => !(item
|
|
145
|
+
: (state.values.array.filter(item => !isGroupKey(item)) as PlainObject[]);
|
|
140
146
|
}
|
|
141
147
|
|
|
142
|
-
getIndex(item:
|
|
143
|
-
|
|
144
|
-
return this.items.indexOf(item);
|
|
145
|
-
}
|
|
146
|
-
|
|
147
|
-
return this.items.findIndex(value =>
|
|
148
|
-
value instanceof GroupComponent ? value.key === item : value === item,
|
|
149
|
-
);
|
|
148
|
+
getIndex(item: Key): number {
|
|
149
|
+
return this.keys.indexOf(item);
|
|
150
150
|
}
|
|
151
151
|
|
|
152
152
|
async remove(items: Array<Key | PlainObject>, render: boolean): Promise<void> {
|
|
153
153
|
const {state} = this;
|
|
154
154
|
|
|
155
|
-
const keys = items
|
|
156
|
-
value => (isPlainObject(value) ? getValue(value, state.key) : value) as Key
|
|
157
|
-
|
|
155
|
+
const keys = items
|
|
156
|
+
.map(value => (isPlainObject(value) ? getValue(value, state.key) : value) as Key)
|
|
157
|
+
.filter(key => !isGroupKey(key));
|
|
158
158
|
|
|
159
159
|
const {length} = keys;
|
|
160
160
|
|
|
@@ -163,12 +163,12 @@ export class DataManager {
|
|
|
163
163
|
}
|
|
164
164
|
}
|
|
165
165
|
|
|
166
|
-
async removeItems(
|
|
166
|
+
async removeItems(keys: Key[], clear: boolean, render: boolean): Promise<void> {
|
|
167
167
|
const {state} = this;
|
|
168
168
|
|
|
169
169
|
if (clear) {
|
|
170
|
-
state.
|
|
171
|
-
state.
|
|
170
|
+
state.keys.active = undefined;
|
|
171
|
+
state.keys.original = [];
|
|
172
172
|
state.values.array = [];
|
|
173
173
|
|
|
174
174
|
state.values.mapped.clear();
|
|
@@ -184,34 +184,34 @@ export class DataManager {
|
|
|
184
184
|
|
|
185
185
|
const groups: GroupComponent[] = [];
|
|
186
186
|
|
|
187
|
-
const chunked = chunk(
|
|
187
|
+
const chunked = chunk(keys);
|
|
188
188
|
const chunkedLength = chunked.length;
|
|
189
189
|
|
|
190
190
|
for (let chunkedIndex = 0; chunkedIndex < chunkedLength; chunkedIndex += 1) {
|
|
191
191
|
const chunk = chunked[chunkedIndex];
|
|
192
192
|
const chunkLength = chunk.length;
|
|
193
193
|
|
|
194
|
-
for (let
|
|
195
|
-
const
|
|
196
|
-
const dataIndex = state.
|
|
194
|
+
for (let keyIndex = 0; keyIndex < chunkLength; keyIndex += 1) {
|
|
195
|
+
const key = chunk[keyIndex];
|
|
196
|
+
const dataIndex = state.keys.original.indexOf(key);
|
|
197
197
|
|
|
198
198
|
let dataValue: PlainObject | undefined;
|
|
199
199
|
|
|
200
200
|
[dataValue] = state.values.array.splice(dataIndex, 1) as PlainObject[];
|
|
201
201
|
|
|
202
|
-
state.
|
|
203
|
-
state.managers.row.remove(
|
|
204
|
-
state.values.mapped.delete(
|
|
202
|
+
state.keys.original.splice(dataIndex, 1);
|
|
203
|
+
state.managers.row.remove(key as never);
|
|
204
|
+
state.values.mapped.delete(key as Key);
|
|
205
205
|
|
|
206
|
-
if (!state.managers.group.enabled ||
|
|
206
|
+
if (!state.managers.group.enabled || isGroupKey(key)) {
|
|
207
207
|
continue;
|
|
208
208
|
}
|
|
209
209
|
|
|
210
|
-
state.managers.group.collapsed.delete(
|
|
210
|
+
state.managers.group.collapsed.delete(key as never);
|
|
211
211
|
|
|
212
|
-
const
|
|
212
|
+
const groupValue = getValue(dataValue, state.managers.group.field) as unknown;
|
|
213
213
|
|
|
214
|
-
const group = state.managers.group.
|
|
214
|
+
const group = state.managers.group.getForValue(groupValue);
|
|
215
215
|
|
|
216
216
|
if (group == null) {
|
|
217
217
|
continue;
|
|
@@ -231,16 +231,16 @@ export class DataManager {
|
|
|
231
231
|
groups.splice(groupIndex, 1);
|
|
232
232
|
}
|
|
233
233
|
|
|
234
|
-
groupIndex = state.values.array.indexOf(group);
|
|
234
|
+
groupIndex = state.values.array.indexOf(group.key);
|
|
235
235
|
|
|
236
236
|
if (groupIndex > -1) {
|
|
237
|
-
state.
|
|
237
|
+
state.keys.original.splice(groupIndex, 1);
|
|
238
238
|
state.values.array.splice(groupIndex, 1);
|
|
239
239
|
}
|
|
240
240
|
|
|
241
241
|
state.managers.group.remove(group);
|
|
242
242
|
|
|
243
|
-
if (
|
|
243
|
+
if (keys.length >= 10_000) {
|
|
244
244
|
await delay(25);
|
|
245
245
|
}
|
|
246
246
|
}
|
|
@@ -263,25 +263,25 @@ export class DataManager {
|
|
|
263
263
|
if (state.managers.group.enabled) {
|
|
264
264
|
sortWithGroups(state, state.values.array, [
|
|
265
265
|
{
|
|
266
|
-
direction:
|
|
266
|
+
direction: SORT_ASCENDING,
|
|
267
267
|
key: state.key,
|
|
268
268
|
},
|
|
269
269
|
]);
|
|
270
270
|
} else {
|
|
271
271
|
sort(state.values.array as PlainObject[], [
|
|
272
272
|
{
|
|
273
|
-
direction:
|
|
273
|
+
direction: SORT_ASCENDING,
|
|
274
274
|
key: state.key,
|
|
275
275
|
},
|
|
276
276
|
]);
|
|
277
277
|
}
|
|
278
278
|
|
|
279
|
-
state.
|
|
280
|
-
item
|
|
279
|
+
state.keys.original = state.values.array.map(item =>
|
|
280
|
+
typeof item === 'string' ? item : (getValue(item, state.key) as Key),
|
|
281
281
|
);
|
|
282
282
|
|
|
283
283
|
state.values.mapped = toMap(
|
|
284
|
-
state.values.array.filter(item => !(item
|
|
284
|
+
state.values.array.filter(item => !isGroupKey(item)) as PlainObject[],
|
|
285
285
|
item => getValue(item, state.key) as Key,
|
|
286
286
|
);
|
|
287
287
|
|
|
@@ -297,7 +297,7 @@ export class DataManager {
|
|
|
297
297
|
set(data: PlainObject[]): void {
|
|
298
298
|
const {state} = this;
|
|
299
299
|
|
|
300
|
-
const array:
|
|
300
|
+
const array: DataValue[] = data.slice();
|
|
301
301
|
|
|
302
302
|
if (state.managers.group.enabled) {
|
|
303
303
|
const column = state.managers.column.get(state.managers.group.field);
|
|
@@ -316,7 +316,7 @@ export class DataManager {
|
|
|
316
316
|
const [value, items] = entries[index];
|
|
317
317
|
|
|
318
318
|
const group = new GroupComponent(
|
|
319
|
-
`${column?.options.
|
|
319
|
+
`${column?.options.label ?? state.managers.group.field}: ${value}`,
|
|
320
320
|
value,
|
|
321
321
|
);
|
|
322
322
|
|
|
@@ -324,7 +324,7 @@ export class DataManager {
|
|
|
324
324
|
|
|
325
325
|
groups.push(group);
|
|
326
326
|
|
|
327
|
-
array.push(group);
|
|
327
|
+
array.push(group.key);
|
|
328
328
|
}
|
|
329
329
|
|
|
330
330
|
state.managers.group.set(groups);
|
|
@@ -335,10 +335,10 @@ export class DataManager {
|
|
|
335
335
|
this.render();
|
|
336
336
|
}
|
|
337
337
|
|
|
338
|
-
async synchronize(data: PlainObject[], remove
|
|
338
|
+
async synchronize(data: PlainObject[], remove: boolean): Promise<void> {
|
|
339
339
|
const {state} = this;
|
|
340
340
|
|
|
341
|
-
const
|
|
341
|
+
const added: PlainObject[] = [];
|
|
342
342
|
const updated: PlainObject[] = [];
|
|
343
343
|
|
|
344
344
|
const keys = new Set<Key>([]);
|
|
@@ -352,7 +352,7 @@ export class DataManager {
|
|
|
352
352
|
if (state.values.mapped.has(key)) {
|
|
353
353
|
updated.push(object);
|
|
354
354
|
} else {
|
|
355
|
-
|
|
355
|
+
added.push(object);
|
|
356
356
|
}
|
|
357
357
|
|
|
358
358
|
keys.add(key);
|
|
@@ -362,9 +362,9 @@ export class DataManager {
|
|
|
362
362
|
return;
|
|
363
363
|
}
|
|
364
364
|
|
|
365
|
-
if (remove
|
|
366
|
-
const toRemove = state.
|
|
367
|
-
key => !(key
|
|
365
|
+
if (remove) {
|
|
366
|
+
const toRemove = state.keys.original.filter(
|
|
367
|
+
key => !isGroupKey(key) && !keys.has(key),
|
|
368
368
|
) as Key[];
|
|
369
369
|
|
|
370
370
|
if (toRemove.length > 0) {
|
|
@@ -372,31 +372,34 @@ export class DataManager {
|
|
|
372
372
|
}
|
|
373
373
|
}
|
|
374
374
|
|
|
375
|
-
await this.update(updated);
|
|
375
|
+
await this.update(updated, added.length === 0);
|
|
376
376
|
|
|
377
|
-
|
|
378
|
-
await this.add(add, false);
|
|
379
|
-
}
|
|
377
|
+
await this.add(added, false);
|
|
380
378
|
|
|
381
|
-
if (
|
|
379
|
+
if (added.length > 0 || remove) {
|
|
382
380
|
this.render();
|
|
383
381
|
}
|
|
384
382
|
}
|
|
385
383
|
|
|
386
|
-
async update(data: PlainObject[]): Promise<void> {
|
|
384
|
+
async update(data: PlainObject[], render: boolean): Promise<void> {
|
|
387
385
|
const {state} = this;
|
|
388
386
|
|
|
389
387
|
const {length} = data;
|
|
390
388
|
|
|
391
|
-
for (let
|
|
392
|
-
const
|
|
389
|
+
for (let dataIndex = 0; dataIndex < length; dataIndex += 1) {
|
|
390
|
+
const dataItem = data[dataIndex];
|
|
393
391
|
|
|
394
|
-
const key = getValue(
|
|
395
|
-
|
|
392
|
+
const key = getValue(dataItem, state.key) as Key;
|
|
393
|
+
|
|
394
|
+
const keyIndex = state.keys.original.indexOf(key);
|
|
395
|
+
|
|
396
|
+
if (keyIndex === -1) {
|
|
397
|
+
continue;
|
|
398
|
+
}
|
|
396
399
|
|
|
397
|
-
|
|
398
|
-
state.values.mapped.set(key, {...value, ...object} as PlainObject);
|
|
400
|
+
Object.assign(state.values.array[keyIndex], dataItem);
|
|
399
401
|
|
|
402
|
+
if (render) {
|
|
400
403
|
state.managers.row.update(key);
|
|
401
404
|
}
|
|
402
405
|
}
|
|
@@ -1,6 +1,13 @@
|
|
|
1
1
|
import {on} from '@oscarpalmer/toretto/event';
|
|
2
2
|
import {findAncestor} from '@oscarpalmer/toretto/find';
|
|
3
3
|
import type {State} from '../models/tabela.model';
|
|
4
|
+
import {
|
|
5
|
+
ATTRIBUTE_DATA_EVENT,
|
|
6
|
+
ATTRIBUTE_DATA_FIELD,
|
|
7
|
+
ATTRIBUTE_DATA_SORT_DIRECTION,
|
|
8
|
+
} from '../models/dom.model';
|
|
9
|
+
import {CSS_TABLE} from '../models/style.model';
|
|
10
|
+
import {EVENT_GROUP, EVENT_HEADING, EVENT_ROW} from '../models/event.model';
|
|
4
11
|
|
|
5
12
|
export class EventManager {
|
|
6
13
|
constructor(public state: State) {
|
|
@@ -14,8 +21,8 @@ export class EventManager {
|
|
|
14
21
|
}
|
|
15
22
|
|
|
16
23
|
onSort(event: MouseEvent, target: HTMLElement): void {
|
|
17
|
-
const direction = target.getAttribute(
|
|
18
|
-
const field = target.getAttribute(
|
|
24
|
+
const direction = target.getAttribute(ATTRIBUTE_DATA_SORT_DIRECTION);
|
|
25
|
+
const field = target.getAttribute(ATTRIBUTE_DATA_FIELD);
|
|
19
26
|
|
|
20
27
|
if (field != null) {
|
|
21
28
|
this.state.managers.sort.toggle(event, field, direction);
|
|
@@ -24,8 +31,8 @@ export class EventManager {
|
|
|
24
31
|
}
|
|
25
32
|
|
|
26
33
|
function onClick(event: MouseEvent): void {
|
|
27
|
-
const target = findAncestor(event,
|
|
28
|
-
const table = findAncestor(event,
|
|
34
|
+
const target = findAncestor(event, eventAttribute);
|
|
35
|
+
const table = findAncestor(event, tableClassName);
|
|
29
36
|
|
|
30
37
|
if (!(target instanceof HTMLElement) || !(table instanceof HTMLElement)) {
|
|
31
38
|
return;
|
|
@@ -37,18 +44,18 @@ function onClick(event: MouseEvent): void {
|
|
|
37
44
|
return;
|
|
38
45
|
}
|
|
39
46
|
|
|
40
|
-
const type = target?.getAttribute(
|
|
47
|
+
const type = target?.getAttribute(ATTRIBUTE_DATA_EVENT);
|
|
41
48
|
|
|
42
49
|
switch (type) {
|
|
43
|
-
case
|
|
50
|
+
case EVENT_GROUP:
|
|
44
51
|
manager.state.managers.group.handle(target);
|
|
45
52
|
break;
|
|
46
53
|
|
|
47
|
-
case
|
|
54
|
+
case EVENT_HEADING:
|
|
48
55
|
manager.onSort(event, target);
|
|
49
56
|
break;
|
|
50
57
|
|
|
51
|
-
case
|
|
58
|
+
case EVENT_ROW:
|
|
52
59
|
manager.state.managers.selection.handle(event, target);
|
|
53
60
|
break;
|
|
54
61
|
|
|
@@ -58,8 +65,8 @@ function onClick(event: MouseEvent): void {
|
|
|
58
65
|
}
|
|
59
66
|
|
|
60
67
|
function onKeydown(event: KeyboardEvent): void {
|
|
61
|
-
const target = findAncestor(event,
|
|
62
|
-
const table = findAncestor(event,
|
|
68
|
+
const target = findAncestor(event, eventAttribute);
|
|
69
|
+
const table = findAncestor(event, tableClassName);
|
|
63
70
|
|
|
64
71
|
if (!(target instanceof HTMLElement) || !(table instanceof HTMLElement)) {
|
|
65
72
|
return;
|
|
@@ -82,7 +89,11 @@ function onKeydown(event: KeyboardEvent): void {
|
|
|
82
89
|
manager.state.managers.navigation.handle(event);
|
|
83
90
|
}
|
|
84
91
|
|
|
92
|
+
const eventAttribute = `[${ATTRIBUTE_DATA_EVENT}]`;
|
|
93
|
+
|
|
85
94
|
const mapped = new WeakMap<HTMLElement, EventManager>();
|
|
86
95
|
|
|
96
|
+
const tableClassName = `.${CSS_TABLE}`;
|
|
97
|
+
|
|
87
98
|
on(document, 'click', onClick);
|
|
88
99
|
on(document, 'keydown', onKeydown, {passive: false});
|
|
@@ -1,19 +1,32 @@
|
|
|
1
|
+
import type {Key} from '@oscarpalmer/atoms/models';
|
|
1
2
|
import {getNumber} from '@oscarpalmer/atoms/number';
|
|
2
3
|
import {getString} from '@oscarpalmer/atoms/string';
|
|
3
4
|
import {endsWith, includes, startsWith} from '@oscarpalmer/atoms/string/match';
|
|
4
5
|
import {equal} from '@oscarpalmer/atoms/value/equal';
|
|
5
|
-
import {
|
|
6
|
-
import
|
|
7
|
-
|
|
6
|
+
import {isGroupKey} from '../helpers/misc.helpers';
|
|
7
|
+
import {
|
|
8
|
+
FILTER_CONTAINS,
|
|
9
|
+
FILTER_ENDS_WITH,
|
|
10
|
+
FILTER_EQUALS,
|
|
11
|
+
FILTER_GREATER_THAN,
|
|
12
|
+
FILTER_GREATER_THAN_OR_EQUAL,
|
|
13
|
+
FILTER_LESS_THAN,
|
|
14
|
+
FILTER_LESS_THAN_OR_EQUAL,
|
|
15
|
+
FILTER_NOT_CONTAINS,
|
|
16
|
+
FILTER_NOT_EQUALS,
|
|
17
|
+
FILTER_STARTS_WITH,
|
|
18
|
+
type TabelaFilter,
|
|
19
|
+
type TabelaFilterItem,
|
|
20
|
+
} from '../models/filter.model';
|
|
8
21
|
import type {State} from '../models/tabela.model';
|
|
9
22
|
|
|
10
23
|
export class FilterManager {
|
|
11
|
-
handlers =
|
|
24
|
+
handlers: TabelaFilter = {
|
|
12
25
|
add: item => this.add(item),
|
|
13
26
|
clear: () => this.clear(),
|
|
14
27
|
remove: value => this.remove(value),
|
|
15
28
|
set: items => this.set(items),
|
|
16
|
-
}
|
|
29
|
+
};
|
|
17
30
|
|
|
18
31
|
items: Record<string, TabelaFilterItem[]> = {};
|
|
19
32
|
|
|
@@ -52,15 +65,15 @@ export class FilterManager {
|
|
|
52
65
|
filter(): void {
|
|
53
66
|
const {state} = this;
|
|
54
67
|
|
|
55
|
-
const filtered:
|
|
68
|
+
const filtered: Key[] = [];
|
|
56
69
|
const filters = Object.entries(this.items);
|
|
57
70
|
|
|
58
|
-
const itemsLength = state.managers.data.state.
|
|
71
|
+
const itemsLength = state.managers.data.state.keys.original.length;
|
|
59
72
|
|
|
60
73
|
rowLoop: for (let itemIndex = 0; itemIndex < itemsLength; itemIndex += 1) {
|
|
61
|
-
const item = state.managers.data.state.
|
|
74
|
+
const item = state.managers.data.state.keys.original[itemIndex];
|
|
62
75
|
|
|
63
|
-
if (item
|
|
76
|
+
if (isGroupKey(item)) {
|
|
64
77
|
filtered.push(item);
|
|
65
78
|
|
|
66
79
|
continue;
|
|
@@ -91,7 +104,7 @@ export class FilterManager {
|
|
|
91
104
|
filtered.push(item);
|
|
92
105
|
}
|
|
93
106
|
|
|
94
|
-
state.managers.data.state.
|
|
107
|
+
state.managers.data.state.keys.active = filtered;
|
|
95
108
|
|
|
96
109
|
if (state.managers.sort.items.length > 0) {
|
|
97
110
|
state.managers.sort.sort();
|
|
@@ -156,17 +169,17 @@ export class FilterManager {
|
|
|
156
169
|
}
|
|
157
170
|
}
|
|
158
171
|
|
|
159
|
-
const comparators: Record<
|
|
160
|
-
|
|
161
|
-
|
|
162
|
-
|
|
163
|
-
|
|
164
|
-
|
|
165
|
-
|
|
166
|
-
|
|
167
|
-
|
|
168
|
-
|
|
169
|
-
|
|
172
|
+
const comparators: Record<string, (row: unknown, filter: unknown) => boolean> = {
|
|
173
|
+
[FILTER_CONTAINS]: (row, filter) => includes(getString(row), getString(filter), true),
|
|
174
|
+
[FILTER_ENDS_WITH]: (row, filter) => endsWith(getString(row), getString(filter), true),
|
|
175
|
+
[FILTER_EQUALS]: (row, filter) => equalizer(row, filter),
|
|
176
|
+
[FILTER_GREATER_THAN]: (row, filter) => getNumber(row) > getNumber(filter),
|
|
177
|
+
[FILTER_GREATER_THAN_OR_EQUAL]: (row, filter) => getNumber(row) >= getNumber(filter),
|
|
178
|
+
[FILTER_LESS_THAN]: (row, filter) => getNumber(row) < getNumber(filter),
|
|
179
|
+
[FILTER_LESS_THAN_OR_EQUAL]: (row, filter) => getNumber(row) <= getNumber(filter),
|
|
180
|
+
[FILTER_NOT_CONTAINS]: (row, filter) => !includes(getString(row), getString(filter), true),
|
|
181
|
+
[FILTER_NOT_EQUALS]: (row, filter) => !equalizer(row, filter),
|
|
182
|
+
[FILTER_STARTS_WITH]: (row, filter) => startsWith(getString(row), getString(filter), true),
|
|
170
183
|
};
|
|
171
184
|
|
|
172
185
|
const equalizer = equal.initialize({
|
|
@@ -1,4 +1,5 @@
|
|
|
1
1
|
import {sort} from '@oscarpalmer/atoms/array';
|
|
2
|
+
import {toMap} from '@oscarpalmer/atoms/array/to-map';
|
|
2
3
|
import {toRecord} from '@oscarpalmer/atoms/array/to-record';
|
|
3
4
|
import {isNullableOrWhitespace} from '@oscarpalmer/atoms/is';
|
|
4
5
|
import type {Key, Simplify} from '@oscarpalmer/atoms/models';
|
|
@@ -14,7 +15,7 @@ export class GroupManager {
|
|
|
14
15
|
|
|
15
16
|
field!: string;
|
|
16
17
|
|
|
17
|
-
handlers =
|
|
18
|
+
handlers: TabelaGroup = {
|
|
18
19
|
set: (group?: string) => {
|
|
19
20
|
if (group === this.field) {
|
|
20
21
|
return;
|
|
@@ -25,10 +26,12 @@ export class GroupManager {
|
|
|
25
26
|
|
|
26
27
|
this.state.managers.data.set(this.state.managers.data.get());
|
|
27
28
|
},
|
|
28
|
-
}
|
|
29
|
+
};
|
|
29
30
|
|
|
30
31
|
items: GroupComponent[] = [];
|
|
31
32
|
|
|
33
|
+
mapped = new Map<string, GroupComponent>();
|
|
34
|
+
|
|
32
35
|
order: Record<never, number> = {};
|
|
33
36
|
|
|
34
37
|
constructor(public state: State) {
|
|
@@ -67,15 +70,19 @@ export class GroupManager {
|
|
|
67
70
|
this.state = undefined as never;
|
|
68
71
|
}
|
|
69
72
|
|
|
70
|
-
|
|
73
|
+
getForKey(key: string): GroupComponent | undefined {
|
|
74
|
+
return this.mapped.get(key);
|
|
75
|
+
}
|
|
76
|
+
|
|
77
|
+
getForValue(value: unknown): GroupComponent | undefined {
|
|
71
78
|
const asString = getString(value);
|
|
72
79
|
|
|
73
80
|
return this.items.find(item => item.value.stringified === asString);
|
|
74
81
|
}
|
|
75
82
|
|
|
76
83
|
handle(button: HTMLElement): void {
|
|
77
|
-
const
|
|
78
|
-
const group = this.
|
|
84
|
+
const key = button.dataset.key?.replace(`${this.state.prefix}_`, '');
|
|
85
|
+
const group = this.getForKey(key ?? '');
|
|
79
86
|
|
|
80
87
|
if (group == null) {
|
|
81
88
|
return;
|
|
@@ -87,15 +94,15 @@ export class GroupManager {
|
|
|
87
94
|
|
|
88
95
|
const index = items.indexOf(group);
|
|
89
96
|
|
|
90
|
-
let first = state.managers.data.state.
|
|
97
|
+
let first = state.managers.data.state.keys.original.indexOf(group.key) + 1;
|
|
91
98
|
|
|
92
99
|
const last =
|
|
93
100
|
items[index + 1] == null
|
|
94
|
-
? state.managers.data.state.
|
|
95
|
-
: state.managers.data.state.
|
|
101
|
+
? state.managers.data.state.keys.original.length - 1
|
|
102
|
+
: state.managers.data.state.keys.original.indexOf(items[index + 1].key) - 1;
|
|
96
103
|
|
|
97
104
|
for (; first <= last; first += 1) {
|
|
98
|
-
const key = state.managers.data.state.
|
|
105
|
+
const key = state.managers.data.state.keys.original[first] as Key;
|
|
99
106
|
|
|
100
107
|
if (group.expanded) {
|
|
101
108
|
collapsed.delete(key);
|
|
@@ -122,6 +129,8 @@ export class GroupManager {
|
|
|
122
129
|
set(items: GroupComponent[]) {
|
|
123
130
|
this.items = sort(items, item => item.label);
|
|
124
131
|
|
|
132
|
+
this.mapped = toMap(items, group => group.key);
|
|
133
|
+
|
|
125
134
|
this.order = toRecord(
|
|
126
135
|
items as Simplify<GroupComponent>[],
|
|
127
136
|
group => group.value.stringified,
|