@proyecto-viviana/solid-stately 0.2.3 → 0.2.7
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/LICENSE +21 -0
- package/dist/autocomplete/createAutocompleteState.d.ts +2 -1
- package/dist/checkbox/createCheckboxGroupState.d.ts +10 -1
- package/dist/collections/types.d.ts +11 -0
- package/dist/color/getColorChannels.d.ts +20 -0
- package/dist/data/createAsyncList.d.ts +111 -0
- package/dist/data/createListData.d.ts +65 -0
- package/dist/data/createTreeData.d.ts +61 -0
- package/dist/data/index.d.ts +3 -0
- package/dist/datepicker/index.d.ts +10 -0
- package/dist/grid/types.d.ts +5 -1
- package/dist/index.d.ts +6 -1
- package/dist/index.js +3737 -2697
- package/dist/index.js.map +1 -7
- package/dist/menu/index.d.ts +8 -0
- package/dist/radio/createRadioGroupState.d.ts +10 -1
- package/dist/select/createSelectState.d.ts +17 -0
- package/dist/selection/index.d.ts +11 -0
- package/dist/toast/createToastState.d.ts +7 -1
- package/dist/toggle/createToggleGroupState.d.ts +45 -0
- package/dist/toggle/index.d.ts +1 -0
- package/dist/tree/TreeCollection.d.ts +3 -2
- package/package.json +6 -5
- package/src/autocomplete/createAutocompleteState.ts +10 -11
- package/src/calendar/createDateFieldState.ts +24 -1
- package/src/checkbox/createCheckboxGroupState.ts +42 -6
- package/src/collections/ListCollection.ts +152 -146
- package/src/collections/createListState.ts +266 -264
- package/src/collections/createMenuState.ts +106 -106
- package/src/collections/createSelectionState.ts +336 -336
- package/src/collections/index.ts +46 -46
- package/src/collections/types.ts +181 -169
- package/src/color/Color.ts +951 -951
- package/src/color/createColorAreaState.ts +293 -293
- package/src/color/createColorFieldState.ts +292 -292
- package/src/color/createColorSliderState.ts +241 -241
- package/src/color/createColorWheelState.ts +211 -211
- package/src/color/getColorChannels.ts +34 -0
- package/src/color/index.ts +47 -47
- package/src/color/types.ts +127 -127
- package/src/combobox/createComboBoxState.ts +703 -703
- package/src/combobox/index.ts +13 -13
- package/src/data/createAsyncList.ts +377 -0
- package/src/data/createListData.ts +298 -0
- package/src/data/createTreeData.ts +433 -0
- package/src/data/index.ts +25 -0
- package/src/datepicker/index.ts +36 -0
- package/src/disclosure/createDisclosureState.ts +4 -4
- package/src/dnd/createDragState.ts +153 -153
- package/src/dnd/createDraggableCollectionState.ts +165 -165
- package/src/dnd/createDropState.ts +212 -212
- package/src/dnd/createDroppableCollectionState.ts +357 -357
- package/src/dnd/index.ts +76 -76
- package/src/dnd/types.ts +317 -317
- package/src/form/createFormValidationState.ts +389 -389
- package/src/form/index.ts +15 -15
- package/src/grid/types.ts +5 -0
- package/src/index.ts +49 -0
- package/src/menu/index.ts +19 -0
- package/src/numberfield/createNumberFieldState.ts +427 -383
- package/src/numberfield/index.ts +5 -5
- package/src/overlays/createOverlayTriggerState.ts +67 -67
- package/src/overlays/index.ts +5 -5
- package/src/radio/createRadioGroupState.ts +44 -6
- package/src/searchfield/createSearchFieldState.ts +62 -62
- package/src/searchfield/index.ts +5 -5
- package/src/select/createSelectState.ts +290 -181
- package/src/select/index.ts +5 -5
- package/src/selection/index.ts +28 -0
- package/src/slider/createSliderState.ts +211 -211
- package/src/slider/index.ts +6 -6
- package/src/tabs/createTabListState.ts +37 -11
- package/src/toast/createToastState.d.ts +6 -1
- package/src/toast/createToastState.ts +8 -1
- package/src/toggle/createToggleGroupState.ts +127 -0
- package/src/toggle/index.ts +6 -0
- package/src/tooltip/createTooltipTriggerState.ts +183 -183
- package/src/tooltip/index.ts +6 -6
- package/src/tree/TreeCollection.ts +208 -175
- package/src/tree/createTreeState.ts +392 -392
- package/src/tree/index.ts +13 -13
- package/src/tree/types.ts +174 -174
|
@@ -0,0 +1,433 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* createTreeData - SolidJS port of React Spectrum's useTreeData
|
|
3
|
+
*
|
|
4
|
+
* Manages state for an immutable tree data structure, and provides
|
|
5
|
+
* convenience methods to update the data over time.
|
|
6
|
+
*/
|
|
7
|
+
|
|
8
|
+
import { createSignal } from 'solid-js';
|
|
9
|
+
|
|
10
|
+
export type Key = string | number;
|
|
11
|
+
export type Selection = 'all' | Set<Key>;
|
|
12
|
+
|
|
13
|
+
export interface TreeNode<T> {
|
|
14
|
+
/** A unique key for the tree node. */
|
|
15
|
+
key: Key;
|
|
16
|
+
/** The key of the parent node. */
|
|
17
|
+
parentKey: Key | null;
|
|
18
|
+
/** The value object for the tree node. */
|
|
19
|
+
value: T;
|
|
20
|
+
/** The children of this node. */
|
|
21
|
+
children: TreeNode<T>[] | null;
|
|
22
|
+
}
|
|
23
|
+
|
|
24
|
+
export interface TreeOptions<T> {
|
|
25
|
+
/** Initial items in the tree. */
|
|
26
|
+
initialItems?: T[];
|
|
27
|
+
/** The keys for the initially selected items. */
|
|
28
|
+
initialSelectedKeys?: 'all' | Iterable<Key>;
|
|
29
|
+
/** A function that returns a unique key for an item object. */
|
|
30
|
+
getKey?: (item: T) => Key;
|
|
31
|
+
/** A function that returns the children of an item object. */
|
|
32
|
+
getChildren?: (item: T) => T[];
|
|
33
|
+
}
|
|
34
|
+
|
|
35
|
+
export interface TreeData<T> {
|
|
36
|
+
/** The root items in the tree. */
|
|
37
|
+
readonly items: TreeNode<T>[];
|
|
38
|
+
/** The keys of the currently selected items in the tree. */
|
|
39
|
+
readonly selectedKeys: Selection;
|
|
40
|
+
/** Sets the selected keys. */
|
|
41
|
+
setSelectedKeys(keys: Selection): void;
|
|
42
|
+
/** Gets an item from the tree by key. */
|
|
43
|
+
getItem(key: Key): TreeNode<T> | undefined;
|
|
44
|
+
/** Inserts items into the tree. */
|
|
45
|
+
insert(parentKey: Key | null, index: number, ...values: T[]): void;
|
|
46
|
+
/** Inserts items before a given key. */
|
|
47
|
+
insertBefore(key: Key, ...values: T[]): void;
|
|
48
|
+
/** Inserts items after a given key. */
|
|
49
|
+
insertAfter(key: Key, ...values: T[]): void;
|
|
50
|
+
/** Appends items to a parent node. */
|
|
51
|
+
append(parentKey: Key | null, ...values: T[]): void;
|
|
52
|
+
/** Prepends items to a parent node. */
|
|
53
|
+
prepend(parentKey: Key | null, ...values: T[]): void;
|
|
54
|
+
/** Removes items from the tree by their keys. */
|
|
55
|
+
remove(...keys: Key[]): void;
|
|
56
|
+
/** Removes all items from the tree that are currently in the set of selected items. */
|
|
57
|
+
removeSelectedItems(): void;
|
|
58
|
+
/** Moves an item to a new parent. */
|
|
59
|
+
move(key: Key, toParentKey: Key | null, index: number): void;
|
|
60
|
+
/** Updates an item in the tree. */
|
|
61
|
+
update(key: Key, newValue: T): void;
|
|
62
|
+
}
|
|
63
|
+
|
|
64
|
+
interface TreeDataState<T> {
|
|
65
|
+
items: TreeNode<T>[];
|
|
66
|
+
nodeMap: Map<Key, TreeNode<T>>;
|
|
67
|
+
}
|
|
68
|
+
|
|
69
|
+
/**
|
|
70
|
+
* Manages state for an immutable tree data structure, and provides
|
|
71
|
+
* convenience methods to update the data over time.
|
|
72
|
+
*/
|
|
73
|
+
export function createTreeData<T>(options: TreeOptions<T>): TreeData<T> {
|
|
74
|
+
const {
|
|
75
|
+
initialItems = [],
|
|
76
|
+
initialSelectedKeys,
|
|
77
|
+
getKey = (item: any) => item.id ?? item.key,
|
|
78
|
+
getChildren = (item: any) => item.children ?? [],
|
|
79
|
+
} = options;
|
|
80
|
+
|
|
81
|
+
// Build initial tree
|
|
82
|
+
const initialTree = buildTree(initialItems, new Map(), null, getKey, getChildren);
|
|
83
|
+
|
|
84
|
+
const [treeState, setTreeState] = createSignal<TreeDataState<T>>(initialTree);
|
|
85
|
+
const [selectedKeys, setSelectedKeys] = createSignal<Selection>(
|
|
86
|
+
initialSelectedKeys === 'all' ? 'all' : new Set(initialSelectedKeys || [])
|
|
87
|
+
);
|
|
88
|
+
|
|
89
|
+
function updateTree(
|
|
90
|
+
items: TreeNode<T>[],
|
|
91
|
+
key: Key | null,
|
|
92
|
+
update: (node: TreeNode<T>) => TreeNode<T> | null,
|
|
93
|
+
originalMap: Map<Key, TreeNode<T>>,
|
|
94
|
+
): TreeDataState<T> {
|
|
95
|
+
let node = key != null ? originalMap.get(key) : null;
|
|
96
|
+
if (key != null && !node) return { items, nodeMap: originalMap };
|
|
97
|
+
|
|
98
|
+
const newMap = new Map(originalMap);
|
|
99
|
+
|
|
100
|
+
if (node) {
|
|
101
|
+
const updated = update(node);
|
|
102
|
+
if (!updated) {
|
|
103
|
+
// Delete node
|
|
104
|
+
deleteNode(node, newMap);
|
|
105
|
+
if (node.parentKey != null) {
|
|
106
|
+
return updateTree(items, node.parentKey, parent => ({
|
|
107
|
+
...parent,
|
|
108
|
+
children: parent.children!.filter(c => c.key !== key),
|
|
109
|
+
}), newMap);
|
|
110
|
+
}
|
|
111
|
+
return { items: items.filter(i => i.key !== key), nodeMap: newMap };
|
|
112
|
+
}
|
|
113
|
+
|
|
114
|
+
newMap.set(key!, updated);
|
|
115
|
+
if (updated.children) {
|
|
116
|
+
for (const child of updated.children) {
|
|
117
|
+
addNode(child, newMap);
|
|
118
|
+
}
|
|
119
|
+
}
|
|
120
|
+
|
|
121
|
+
if (node.parentKey != null) {
|
|
122
|
+
return updateTree(items, node.parentKey, parent => ({
|
|
123
|
+
...parent,
|
|
124
|
+
children: parent.children!.map(c => c.key === key ? updated : c),
|
|
125
|
+
}), newMap);
|
|
126
|
+
}
|
|
127
|
+
|
|
128
|
+
return { items: items.map(i => i.key === key ? updated : i), nodeMap: newMap };
|
|
129
|
+
}
|
|
130
|
+
|
|
131
|
+
return { items, nodeMap: newMap };
|
|
132
|
+
}
|
|
133
|
+
|
|
134
|
+
return {
|
|
135
|
+
get items() { return treeState().items; },
|
|
136
|
+
get selectedKeys() { return selectedKeys(); },
|
|
137
|
+
|
|
138
|
+
setSelectedKeys(keys: Selection) {
|
|
139
|
+
setSelectedKeys(keys);
|
|
140
|
+
},
|
|
141
|
+
|
|
142
|
+
getItem(key: Key) {
|
|
143
|
+
return treeState().nodeMap.get(key);
|
|
144
|
+
},
|
|
145
|
+
|
|
146
|
+
insert(parentKey: Key | null, index: number, ...values: T[]) {
|
|
147
|
+
setTreeState(state => {
|
|
148
|
+
const { items, nodeMap } = state;
|
|
149
|
+
const newMap = new Map(nodeMap);
|
|
150
|
+
const newNodes = values.map(v => {
|
|
151
|
+
const tree = buildTree([v], newMap, parentKey, getKey, getChildren);
|
|
152
|
+
return tree.items[0];
|
|
153
|
+
});
|
|
154
|
+
|
|
155
|
+
if (parentKey == null) {
|
|
156
|
+
return {
|
|
157
|
+
items: [...items.slice(0, index), ...newNodes, ...items.slice(index)],
|
|
158
|
+
nodeMap: newMap,
|
|
159
|
+
};
|
|
160
|
+
}
|
|
161
|
+
|
|
162
|
+
return updateTree(items, parentKey, parent => ({
|
|
163
|
+
...parent,
|
|
164
|
+
children: [
|
|
165
|
+
...(parent.children || []).slice(0, index),
|
|
166
|
+
...newNodes,
|
|
167
|
+
...(parent.children || []).slice(index),
|
|
168
|
+
],
|
|
169
|
+
}), newMap);
|
|
170
|
+
});
|
|
171
|
+
},
|
|
172
|
+
|
|
173
|
+
insertBefore(key: Key, ...values: T[]) {
|
|
174
|
+
setTreeState(state => {
|
|
175
|
+
const { items, nodeMap } = state;
|
|
176
|
+
const node = nodeMap.get(key);
|
|
177
|
+
if (!node) return state;
|
|
178
|
+
|
|
179
|
+
const parent = node.parentKey != null ? nodeMap.get(node.parentKey) : null;
|
|
180
|
+
const siblings = parent?.children ?? items;
|
|
181
|
+
const index = siblings.findIndex(n => n.key === key);
|
|
182
|
+
if (index === -1) return state;
|
|
183
|
+
|
|
184
|
+
const newMap = new Map(nodeMap);
|
|
185
|
+
const newNodes = values.map(v => {
|
|
186
|
+
const tree = buildTree([v], newMap, node.parentKey, getKey, getChildren);
|
|
187
|
+
return tree.items[0];
|
|
188
|
+
});
|
|
189
|
+
|
|
190
|
+
if (node.parentKey == null) {
|
|
191
|
+
return {
|
|
192
|
+
items: [...items.slice(0, index), ...newNodes, ...items.slice(index)],
|
|
193
|
+
nodeMap: newMap,
|
|
194
|
+
};
|
|
195
|
+
}
|
|
196
|
+
|
|
197
|
+
return updateTree(items, node.parentKey, p => ({
|
|
198
|
+
...p,
|
|
199
|
+
children: [
|
|
200
|
+
...p.children!.slice(0, index),
|
|
201
|
+
...newNodes,
|
|
202
|
+
...p.children!.slice(index),
|
|
203
|
+
],
|
|
204
|
+
}), newMap);
|
|
205
|
+
});
|
|
206
|
+
},
|
|
207
|
+
|
|
208
|
+
insertAfter(key: Key, ...values: T[]) {
|
|
209
|
+
setTreeState(state => {
|
|
210
|
+
const { items, nodeMap } = state;
|
|
211
|
+
const node = nodeMap.get(key);
|
|
212
|
+
if (!node) return state;
|
|
213
|
+
|
|
214
|
+
const parent = node.parentKey != null ? nodeMap.get(node.parentKey) : null;
|
|
215
|
+
const siblings = parent?.children ?? items;
|
|
216
|
+
const index = siblings.findIndex(n => n.key === key);
|
|
217
|
+
if (index === -1) return state;
|
|
218
|
+
|
|
219
|
+
const newMap = new Map(nodeMap);
|
|
220
|
+
const newNodes = values.map(v => {
|
|
221
|
+
const tree = buildTree([v], newMap, node.parentKey, getKey, getChildren);
|
|
222
|
+
return tree.items[0];
|
|
223
|
+
});
|
|
224
|
+
|
|
225
|
+
if (node.parentKey == null) {
|
|
226
|
+
return {
|
|
227
|
+
items: [...items.slice(0, index + 1), ...newNodes, ...items.slice(index + 1)],
|
|
228
|
+
nodeMap: newMap,
|
|
229
|
+
};
|
|
230
|
+
}
|
|
231
|
+
|
|
232
|
+
return updateTree(items, node.parentKey, p => ({
|
|
233
|
+
...p,
|
|
234
|
+
children: [
|
|
235
|
+
...p.children!.slice(0, index + 1),
|
|
236
|
+
...newNodes,
|
|
237
|
+
...p.children!.slice(index + 1),
|
|
238
|
+
],
|
|
239
|
+
}), newMap);
|
|
240
|
+
});
|
|
241
|
+
},
|
|
242
|
+
|
|
243
|
+
append(parentKey: Key | null, ...values: T[]) {
|
|
244
|
+
setTreeState(state => {
|
|
245
|
+
const { items, nodeMap } = state;
|
|
246
|
+
const newMap = new Map(nodeMap);
|
|
247
|
+
const newNodes = values.map(v => {
|
|
248
|
+
const tree = buildTree([v], newMap, parentKey, getKey, getChildren);
|
|
249
|
+
return tree.items[0];
|
|
250
|
+
});
|
|
251
|
+
|
|
252
|
+
if (parentKey == null) {
|
|
253
|
+
return { items: [...items, ...newNodes], nodeMap: newMap };
|
|
254
|
+
}
|
|
255
|
+
|
|
256
|
+
return updateTree(items, parentKey, parent => ({
|
|
257
|
+
...parent,
|
|
258
|
+
children: [...(parent.children || []), ...newNodes],
|
|
259
|
+
}), newMap);
|
|
260
|
+
});
|
|
261
|
+
},
|
|
262
|
+
|
|
263
|
+
prepend(parentKey: Key | null, ...values: T[]) {
|
|
264
|
+
setTreeState(state => {
|
|
265
|
+
const { items, nodeMap } = state;
|
|
266
|
+
const newMap = new Map(nodeMap);
|
|
267
|
+
const newNodes = values.map(v => {
|
|
268
|
+
const tree = buildTree([v], newMap, parentKey, getKey, getChildren);
|
|
269
|
+
return tree.items[0];
|
|
270
|
+
});
|
|
271
|
+
|
|
272
|
+
if (parentKey == null) {
|
|
273
|
+
return { items: [...newNodes, ...items], nodeMap: newMap };
|
|
274
|
+
}
|
|
275
|
+
|
|
276
|
+
return updateTree(items, parentKey, parent => ({
|
|
277
|
+
...parent,
|
|
278
|
+
children: [...newNodes, ...(parent.children || [])],
|
|
279
|
+
}), newMap);
|
|
280
|
+
});
|
|
281
|
+
},
|
|
282
|
+
|
|
283
|
+
remove(...keys: Key[]) {
|
|
284
|
+
setTreeState(state => {
|
|
285
|
+
let { items, nodeMap } = state;
|
|
286
|
+
let newMap = new Map(nodeMap);
|
|
287
|
+
let newItems = items;
|
|
288
|
+
|
|
289
|
+
for (const key of keys) {
|
|
290
|
+
const result = updateTree(newItems, key, () => null, newMap);
|
|
291
|
+
newItems = result.items;
|
|
292
|
+
newMap = result.nodeMap;
|
|
293
|
+
}
|
|
294
|
+
|
|
295
|
+
return { items: newItems, nodeMap: newMap };
|
|
296
|
+
});
|
|
297
|
+
|
|
298
|
+
setSelectedKeys(sel => {
|
|
299
|
+
if (sel === 'all') return sel;
|
|
300
|
+
const newSel = new Set(sel);
|
|
301
|
+
for (const key of keys) {
|
|
302
|
+
newSel.delete(key);
|
|
303
|
+
}
|
|
304
|
+
return newSel;
|
|
305
|
+
});
|
|
306
|
+
},
|
|
307
|
+
|
|
308
|
+
removeSelectedItems() {
|
|
309
|
+
const sel = selectedKeys();
|
|
310
|
+
if (sel === 'all') {
|
|
311
|
+
setTreeState({ items: [], nodeMap: new Map() });
|
|
312
|
+
setSelectedKeys(new Set<Key>());
|
|
313
|
+
return;
|
|
314
|
+
}
|
|
315
|
+
|
|
316
|
+
const keysToRemove = [...sel];
|
|
317
|
+
setTreeState(state => {
|
|
318
|
+
let { items, nodeMap } = state;
|
|
319
|
+
let newMap = new Map(nodeMap);
|
|
320
|
+
let newItems = items;
|
|
321
|
+
for (const key of keysToRemove) {
|
|
322
|
+
const result = updateTree(newItems, key, () => null, newMap);
|
|
323
|
+
newItems = result.items;
|
|
324
|
+
newMap = result.nodeMap;
|
|
325
|
+
}
|
|
326
|
+
return { items: newItems, nodeMap: newMap };
|
|
327
|
+
});
|
|
328
|
+
setSelectedKeys(new Set<Key>());
|
|
329
|
+
},
|
|
330
|
+
|
|
331
|
+
move(key: Key, toParentKey: Key | null, index: number) {
|
|
332
|
+
setTreeState(state => {
|
|
333
|
+
const { items, nodeMap } = state;
|
|
334
|
+
const node = nodeMap.get(key);
|
|
335
|
+
if (!node) return state;
|
|
336
|
+
|
|
337
|
+
// Remove the node
|
|
338
|
+
let newMap = new Map(nodeMap);
|
|
339
|
+
const removeResult = updateTree(items, key, () => null, newMap);
|
|
340
|
+
let newItems = removeResult.items;
|
|
341
|
+
newMap = removeResult.nodeMap;
|
|
342
|
+
|
|
343
|
+
// Re-add it at the target
|
|
344
|
+
const movedNode: TreeNode<T> = { ...node, parentKey: toParentKey };
|
|
345
|
+
addNode(movedNode, newMap);
|
|
346
|
+
|
|
347
|
+
if (toParentKey == null) {
|
|
348
|
+
return {
|
|
349
|
+
items: [...newItems.slice(0, index), movedNode, ...newItems.slice(index)],
|
|
350
|
+
nodeMap: newMap,
|
|
351
|
+
};
|
|
352
|
+
}
|
|
353
|
+
|
|
354
|
+
return updateTree(newItems, toParentKey, parent => ({
|
|
355
|
+
...parent,
|
|
356
|
+
children: [
|
|
357
|
+
...(parent.children || []).slice(0, index),
|
|
358
|
+
movedNode,
|
|
359
|
+
...(parent.children || []).slice(index),
|
|
360
|
+
],
|
|
361
|
+
}), newMap);
|
|
362
|
+
});
|
|
363
|
+
},
|
|
364
|
+
|
|
365
|
+
update(key: Key, newValue: T) {
|
|
366
|
+
setTreeState(state => {
|
|
367
|
+
const { items, nodeMap } = state;
|
|
368
|
+
const newMap = new Map(nodeMap);
|
|
369
|
+
|
|
370
|
+
return updateTree(items, key, oldNode => {
|
|
371
|
+
const node: TreeNode<T> = {
|
|
372
|
+
key: oldNode.key,
|
|
373
|
+
parentKey: oldNode.parentKey,
|
|
374
|
+
value: newValue,
|
|
375
|
+
children: null,
|
|
376
|
+
};
|
|
377
|
+
const tree = buildTree(getChildren(newValue), newMap, node.key, getKey, getChildren);
|
|
378
|
+
node.children = tree.items;
|
|
379
|
+
return node;
|
|
380
|
+
}, newMap);
|
|
381
|
+
});
|
|
382
|
+
},
|
|
383
|
+
};
|
|
384
|
+
}
|
|
385
|
+
|
|
386
|
+
function buildTree<T>(
|
|
387
|
+
items: T[],
|
|
388
|
+
nodeMap: Map<Key, TreeNode<T>>,
|
|
389
|
+
parentKey: Key | null,
|
|
390
|
+
getKey: (item: T) => Key,
|
|
391
|
+
getChildren: (item: T) => T[],
|
|
392
|
+
): TreeDataState<T> {
|
|
393
|
+
const nodes: TreeNode<T>[] = [];
|
|
394
|
+
|
|
395
|
+
for (const item of items) {
|
|
396
|
+
const key = getKey(item);
|
|
397
|
+
const children = getChildren(item);
|
|
398
|
+
|
|
399
|
+
const childTree = children.length > 0
|
|
400
|
+
? buildTree(children, nodeMap, key, getKey, getChildren)
|
|
401
|
+
: { items: [], nodeMap };
|
|
402
|
+
|
|
403
|
+
const node: TreeNode<T> = {
|
|
404
|
+
key,
|
|
405
|
+
parentKey,
|
|
406
|
+
value: item,
|
|
407
|
+
children: childTree.items.length > 0 ? childTree.items : null,
|
|
408
|
+
};
|
|
409
|
+
|
|
410
|
+
nodeMap.set(key, node);
|
|
411
|
+
nodes.push(node);
|
|
412
|
+
}
|
|
413
|
+
|
|
414
|
+
return { items: nodes, nodeMap };
|
|
415
|
+
}
|
|
416
|
+
|
|
417
|
+
function addNode<T>(node: TreeNode<T>, map: Map<Key, TreeNode<T>>): void {
|
|
418
|
+
map.set(node.key, node);
|
|
419
|
+
if (node.children) {
|
|
420
|
+
for (const child of node.children) {
|
|
421
|
+
addNode(child, map);
|
|
422
|
+
}
|
|
423
|
+
}
|
|
424
|
+
}
|
|
425
|
+
|
|
426
|
+
function deleteNode<T>(node: TreeNode<T>, map: Map<Key, TreeNode<T>>): void {
|
|
427
|
+
map.delete(node.key);
|
|
428
|
+
if (node.children) {
|
|
429
|
+
for (const child of node.children) {
|
|
430
|
+
deleteNode(child, map);
|
|
431
|
+
}
|
|
432
|
+
}
|
|
433
|
+
}
|
|
@@ -0,0 +1,25 @@
|
|
|
1
|
+
export {
|
|
2
|
+
createListData,
|
|
3
|
+
type ListOptions,
|
|
4
|
+
type ListData,
|
|
5
|
+
type Key as ListDataKey,
|
|
6
|
+
type Selection as ListDataSelection,
|
|
7
|
+
} from './createListData';
|
|
8
|
+
|
|
9
|
+
export {
|
|
10
|
+
createTreeData,
|
|
11
|
+
type TreeOptions,
|
|
12
|
+
type TreeData,
|
|
13
|
+
type TreeNode as TreeDataNode,
|
|
14
|
+
} from './createTreeData';
|
|
15
|
+
|
|
16
|
+
export {
|
|
17
|
+
createAsyncList,
|
|
18
|
+
type AsyncListOptions,
|
|
19
|
+
type AsyncListData,
|
|
20
|
+
type AsyncListLoadFunction,
|
|
21
|
+
type AsyncListLoadOptions,
|
|
22
|
+
type AsyncListStateUpdate,
|
|
23
|
+
type SortDescriptor,
|
|
24
|
+
type LoadingState,
|
|
25
|
+
} from './createAsyncList';
|
|
@@ -0,0 +1,36 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* Datepicker compatibility surface.
|
|
3
|
+
*
|
|
4
|
+
* This is a module-compat shim that maps React Stately datepicker hook names
|
|
5
|
+
* to existing Solid stately primitives.
|
|
6
|
+
*/
|
|
7
|
+
|
|
8
|
+
export {
|
|
9
|
+
createDateFieldState,
|
|
10
|
+
createTimeFieldState,
|
|
11
|
+
createRangeCalendarState,
|
|
12
|
+
type DateFieldStateProps as DateFieldStateOptions,
|
|
13
|
+
type DateFieldState,
|
|
14
|
+
type DateSegment,
|
|
15
|
+
type DateSegmentType as SegmentType,
|
|
16
|
+
type TimeFieldStateProps as TimeFieldStateOptions,
|
|
17
|
+
type TimeFieldState,
|
|
18
|
+
type TimeSegment,
|
|
19
|
+
type TimeSegmentType,
|
|
20
|
+
type RangeCalendarStateProps as DateRangePickerStateOptions,
|
|
21
|
+
type RangeCalendarState as DateRangePickerState,
|
|
22
|
+
} from '../calendar';
|
|
23
|
+
|
|
24
|
+
export {
|
|
25
|
+
createOverlayTriggerState,
|
|
26
|
+
type OverlayTriggerProps as DatePickerStateOptions,
|
|
27
|
+
type OverlayTriggerState as DatePickerState,
|
|
28
|
+
} from '../overlays';
|
|
29
|
+
|
|
30
|
+
export {
|
|
31
|
+
createDateFieldState as useDateFieldState,
|
|
32
|
+
createTimeFieldState as useTimeFieldState,
|
|
33
|
+
createRangeCalendarState as useDateRangePickerState,
|
|
34
|
+
} from '../calendar';
|
|
35
|
+
|
|
36
|
+
export { createOverlayTriggerState as useDatePickerState } from '../overlays';
|
|
@@ -3,7 +3,7 @@
|
|
|
3
3
|
* Based on @react-stately/disclosure useDisclosureState and useDisclosureGroupState
|
|
4
4
|
*/
|
|
5
5
|
|
|
6
|
-
import { createSignal, createEffect, type Accessor } from 'solid-js';
|
|
6
|
+
import { createSignal, createEffect, createMemo, type Accessor } from 'solid-js';
|
|
7
7
|
import { access, type MaybeAccessor } from '../utils';
|
|
8
8
|
|
|
9
9
|
// ============================================
|
|
@@ -121,11 +121,11 @@ export function createDisclosureGroupState(
|
|
|
121
121
|
new Set(propsAccessor().defaultExpandedKeys ?? [])
|
|
122
122
|
);
|
|
123
123
|
|
|
124
|
-
// Determine expanded keys (controlled vs uncontrolled)
|
|
125
|
-
const expandedKeys: Accessor<Set<Key>> = () => {
|
|
124
|
+
// Determine expanded keys (controlled vs uncontrolled, memoized)
|
|
125
|
+
const expandedKeys: Accessor<Set<Key>> = createMemo(() => {
|
|
126
126
|
const p = propsAccessor();
|
|
127
127
|
return p.expandedKeys !== undefined ? new Set(p.expandedKeys) : internalKeys();
|
|
128
|
-
};
|
|
128
|
+
});
|
|
129
129
|
|
|
130
130
|
const setExpandedKeys = (keys: Set<Key>) => {
|
|
131
131
|
const p = propsAccessor();
|