veles 0.0.1
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/README.md +304 -0
- package/dist/chunk-EVX3ZDYT.js +271 -0
- package/dist/chunk-EVX3ZDYT.js.map +1 -0
- package/dist/index.cjs +727 -0
- package/dist/index.cjs.map +1 -0
- package/dist/index.d.cts +63 -0
- package/dist/index.d.ts +63 -0
- package/dist/index.js +441 -0
- package/dist/index.js.map +1 -0
- package/dist/jsx-runtime-vDysOz5d.d.cts +250 -0
- package/dist/jsx-runtime-vDysOz5d.d.ts +250 -0
- package/dist/jsx-runtime.cjs +276 -0
- package/dist/jsx-runtime.cjs.map +1 -0
- package/dist/jsx-runtime.d.cts +1 -0
- package/dist/jsx-runtime.d.ts +1 -0
- package/dist/jsx-runtime.js +9 -0
- package/dist/jsx-runtime.js.map +1 -0
- package/package.json +53 -0
package/dist/index.cjs
ADDED
|
@@ -0,0 +1,727 @@
|
|
|
1
|
+
var __defProp = Object.defineProperty;
|
|
2
|
+
var __getOwnPropDesc = Object.getOwnPropertyDescriptor;
|
|
3
|
+
var __getOwnPropNames = Object.getOwnPropertyNames;
|
|
4
|
+
var __hasOwnProp = Object.prototype.hasOwnProperty;
|
|
5
|
+
var __export = (target, all) => {
|
|
6
|
+
for (var name in all)
|
|
7
|
+
__defProp(target, name, { get: all[name], enumerable: true });
|
|
8
|
+
};
|
|
9
|
+
var __copyProps = (to, from, except, desc) => {
|
|
10
|
+
if (from && typeof from === "object" || typeof from === "function") {
|
|
11
|
+
for (let key of __getOwnPropNames(from))
|
|
12
|
+
if (!__hasOwnProp.call(to, key) && key !== except)
|
|
13
|
+
__defProp(to, key, { get: () => from[key], enumerable: !(desc = __getOwnPropDesc(from, key)) || desc.enumerable });
|
|
14
|
+
}
|
|
15
|
+
return to;
|
|
16
|
+
};
|
|
17
|
+
var __toCommonJS = (mod) => __copyProps(__defProp({}, "__esModule", { value: true }), mod);
|
|
18
|
+
|
|
19
|
+
// src/index.ts
|
|
20
|
+
var src_exports = {};
|
|
21
|
+
__export(src_exports, {
|
|
22
|
+
Fragment: () => Fragment,
|
|
23
|
+
attachComponent: () => attachComponent,
|
|
24
|
+
combineState: () => combineState,
|
|
25
|
+
createElement: () => createElement,
|
|
26
|
+
createRef: () => createRef,
|
|
27
|
+
createState: () => createState,
|
|
28
|
+
onMount: () => onMount,
|
|
29
|
+
onUnmount: () => onUnmount
|
|
30
|
+
});
|
|
31
|
+
module.exports = __toCommonJS(src_exports);
|
|
32
|
+
|
|
33
|
+
// src/utils.ts
|
|
34
|
+
function getComponentVelesNode(component) {
|
|
35
|
+
const componentsTree = [];
|
|
36
|
+
if ("velesStringElement" in component) {
|
|
37
|
+
return {
|
|
38
|
+
velesElementNode: component,
|
|
39
|
+
componentsTree: []
|
|
40
|
+
};
|
|
41
|
+
}
|
|
42
|
+
let childNode = component;
|
|
43
|
+
while ("velesComponent" in childNode) {
|
|
44
|
+
componentsTree.push(childNode);
|
|
45
|
+
if ("velesStringElement" in childNode.tree) {
|
|
46
|
+
return {
|
|
47
|
+
velesElementNode: childNode.tree,
|
|
48
|
+
componentsTree
|
|
49
|
+
};
|
|
50
|
+
} else {
|
|
51
|
+
childNode = childNode.tree;
|
|
52
|
+
}
|
|
53
|
+
}
|
|
54
|
+
return { velesElementNode: childNode, componentsTree };
|
|
55
|
+
}
|
|
56
|
+
function identity(value1, value2) {
|
|
57
|
+
return value1 === value2;
|
|
58
|
+
}
|
|
59
|
+
|
|
60
|
+
// src/create-element/parse-children.ts
|
|
61
|
+
function parseChildren({
|
|
62
|
+
children,
|
|
63
|
+
htmlElement,
|
|
64
|
+
velesNode
|
|
65
|
+
}) {
|
|
66
|
+
const childComponents = [];
|
|
67
|
+
if (children === void 0 || children === null) {
|
|
68
|
+
return childComponents;
|
|
69
|
+
}
|
|
70
|
+
(Array.isArray(children) ? children : [children]).forEach(
|
|
71
|
+
(childComponent) => {
|
|
72
|
+
if (typeof childComponent === "string") {
|
|
73
|
+
const text = document.createTextNode(childComponent);
|
|
74
|
+
htmlElement.append(text);
|
|
75
|
+
} else if (typeof childComponent === "object" && childComponent && "velesNode" in childComponent && (childComponent == null ? void 0 : childComponent.velesNode)) {
|
|
76
|
+
if (childComponent.phantom) {
|
|
77
|
+
childComponent.childComponents.forEach((childComponentofPhantom) => {
|
|
78
|
+
if ("velesNode" in childComponentofPhantom) {
|
|
79
|
+
htmlElement.append(childComponentofPhantom.html);
|
|
80
|
+
childComponentofPhantom.parentVelesElement = velesNode;
|
|
81
|
+
} else {
|
|
82
|
+
const { componentsTree, velesElementNode } = getComponentVelesNode(childComponentofPhantom);
|
|
83
|
+
if (!velesElementNode) {
|
|
84
|
+
console.error("can't find HTML tree in a component chain");
|
|
85
|
+
} else {
|
|
86
|
+
htmlElement.append(velesElementNode.html);
|
|
87
|
+
componentsTree.forEach((component) => {
|
|
88
|
+
component._privateMethods._callMountHandlers();
|
|
89
|
+
});
|
|
90
|
+
velesElementNode.parentVelesElement = velesNode;
|
|
91
|
+
}
|
|
92
|
+
}
|
|
93
|
+
});
|
|
94
|
+
childComponent.parentVelesElement = velesNode;
|
|
95
|
+
childComponents.push(childComponent);
|
|
96
|
+
} else {
|
|
97
|
+
htmlElement.append(childComponent.html);
|
|
98
|
+
childComponent.parentVelesElement = velesNode;
|
|
99
|
+
childComponents.push(childComponent);
|
|
100
|
+
}
|
|
101
|
+
} else if (typeof childComponent === "object" && childComponent && "velesComponent" in childComponent && (childComponent == null ? void 0 : childComponent.velesComponent)) {
|
|
102
|
+
const { componentsTree, velesElementNode } = getComponentVelesNode(childComponent);
|
|
103
|
+
if (!velesElementNode) {
|
|
104
|
+
console.error("can't find HTML tree in a component chain");
|
|
105
|
+
} else {
|
|
106
|
+
if ("velesNode" in velesElementNode && velesElementNode.phantom) {
|
|
107
|
+
velesElementNode.childComponents.forEach(
|
|
108
|
+
(childComponentofPhantom) => {
|
|
109
|
+
if ("velesNode" in childComponentofPhantom) {
|
|
110
|
+
htmlElement.append(childComponentofPhantom.html);
|
|
111
|
+
childComponentofPhantom.parentVelesElement = velesNode;
|
|
112
|
+
} else {
|
|
113
|
+
const { componentsTree: componentsTree2, velesElementNode: velesElementNode2 } = getComponentVelesNode(childComponentofPhantom);
|
|
114
|
+
if (!velesElementNode2) {
|
|
115
|
+
console.error("can't find HTML tree in a component chain");
|
|
116
|
+
} else {
|
|
117
|
+
htmlElement.append(velesElementNode2.html);
|
|
118
|
+
setTimeout(() => {
|
|
119
|
+
componentsTree2.forEach((component) => {
|
|
120
|
+
component._privateMethods._callMountHandlers();
|
|
121
|
+
});
|
|
122
|
+
}, 0);
|
|
123
|
+
velesElementNode2.parentVelesElement = velesNode;
|
|
124
|
+
}
|
|
125
|
+
}
|
|
126
|
+
}
|
|
127
|
+
);
|
|
128
|
+
} else {
|
|
129
|
+
htmlElement.append(velesElementNode.html);
|
|
130
|
+
}
|
|
131
|
+
setTimeout(() => {
|
|
132
|
+
componentsTree.forEach((component) => {
|
|
133
|
+
component._privateMethods._callMountHandlers();
|
|
134
|
+
});
|
|
135
|
+
}, 0);
|
|
136
|
+
velesElementNode.parentVelesElement = velesNode;
|
|
137
|
+
childComponents.push(childComponent);
|
|
138
|
+
}
|
|
139
|
+
} else if (typeof childComponent === "object" && childComponent && "velesStringElement" in childComponent && (childComponent == null ? void 0 : childComponent.velesStringElement)) {
|
|
140
|
+
htmlElement.append(childComponent.html);
|
|
141
|
+
childComponent.parentVelesElement = velesNode;
|
|
142
|
+
childComponents.push(childComponent);
|
|
143
|
+
}
|
|
144
|
+
}
|
|
145
|
+
);
|
|
146
|
+
return childComponents;
|
|
147
|
+
}
|
|
148
|
+
|
|
149
|
+
// src/create-element/assign-attributes.ts
|
|
150
|
+
function assignAttributes({
|
|
151
|
+
props,
|
|
152
|
+
htmlElement,
|
|
153
|
+
velesNode
|
|
154
|
+
}) {
|
|
155
|
+
Object.entries(props).forEach(([key, value]) => {
|
|
156
|
+
const isFunction = typeof value === "function";
|
|
157
|
+
if (isFunction && value.velesAttribute === true) {
|
|
158
|
+
const attributeValue = value(htmlElement, key, velesNode);
|
|
159
|
+
htmlElement.setAttribute(key, attributeValue);
|
|
160
|
+
} else if (
|
|
161
|
+
// basically, any form of `on` handlers, like `onClick`, `onCopy`, etc
|
|
162
|
+
isFunction && key.length > 2 && key.startsWith("on")
|
|
163
|
+
) {
|
|
164
|
+
htmlElement.addEventListener(
|
|
165
|
+
key[2].toLocaleLowerCase() + key.slice(3),
|
|
166
|
+
value
|
|
167
|
+
);
|
|
168
|
+
} else {
|
|
169
|
+
htmlElement.setAttribute(key, value);
|
|
170
|
+
}
|
|
171
|
+
});
|
|
172
|
+
}
|
|
173
|
+
|
|
174
|
+
// src/hooks/lifecycle.ts
|
|
175
|
+
var contextStack = [];
|
|
176
|
+
var currentContext = null;
|
|
177
|
+
function addContext(newContext) {
|
|
178
|
+
contextStack.push(newContext);
|
|
179
|
+
currentContext = newContext;
|
|
180
|
+
}
|
|
181
|
+
function popContext() {
|
|
182
|
+
contextStack.pop();
|
|
183
|
+
currentContext = contextStack[contextStack.length - 1];
|
|
184
|
+
}
|
|
185
|
+
function onMount(cb) {
|
|
186
|
+
if (currentContext) {
|
|
187
|
+
currentContext.onMount(cb);
|
|
188
|
+
} else {
|
|
189
|
+
console.error("missing current context");
|
|
190
|
+
}
|
|
191
|
+
}
|
|
192
|
+
function onUnmount(cb) {
|
|
193
|
+
if (currentContext) {
|
|
194
|
+
currentContext.onUnmount(cb);
|
|
195
|
+
} else {
|
|
196
|
+
console.error("missing current context");
|
|
197
|
+
}
|
|
198
|
+
}
|
|
199
|
+
|
|
200
|
+
// src/create-element/parse-component.ts
|
|
201
|
+
function parseComponent({
|
|
202
|
+
element,
|
|
203
|
+
props
|
|
204
|
+
}) {
|
|
205
|
+
const componentUnmountCbs = [];
|
|
206
|
+
const componentMountCbs = [];
|
|
207
|
+
const componentAPI = {
|
|
208
|
+
onMount: (cb) => {
|
|
209
|
+
componentMountCbs.push(cb);
|
|
210
|
+
},
|
|
211
|
+
onUnmount: (cb) => {
|
|
212
|
+
componentUnmountCbs.push(cb);
|
|
213
|
+
}
|
|
214
|
+
};
|
|
215
|
+
addContext(componentAPI);
|
|
216
|
+
const _componentTree = element(props, componentAPI);
|
|
217
|
+
const componentTree = typeof _componentTree === "string" || !_componentTree ? {
|
|
218
|
+
velesStringElement: true,
|
|
219
|
+
html: document.createTextNode(
|
|
220
|
+
typeof _componentTree === "string" ? _componentTree : ""
|
|
221
|
+
)
|
|
222
|
+
} : _componentTree;
|
|
223
|
+
popContext();
|
|
224
|
+
const velesComponent = {
|
|
225
|
+
velesComponent: true,
|
|
226
|
+
tree: componentTree,
|
|
227
|
+
_privateMethods: {
|
|
228
|
+
_addUnmountHandler: (cb) => {
|
|
229
|
+
componentAPI.onUnmount(cb);
|
|
230
|
+
},
|
|
231
|
+
_callMountHandlers: () => {
|
|
232
|
+
componentMountCbs.forEach((cb) => cb());
|
|
233
|
+
},
|
|
234
|
+
_callUnmountHandlers: () => {
|
|
235
|
+
componentUnmountCbs.forEach((cb) => cb());
|
|
236
|
+
if ("_privateMethods" in velesComponent.tree) {
|
|
237
|
+
velesComponent.tree._privateMethods._callUnmountHandlers();
|
|
238
|
+
}
|
|
239
|
+
}
|
|
240
|
+
}
|
|
241
|
+
};
|
|
242
|
+
return velesComponent;
|
|
243
|
+
}
|
|
244
|
+
|
|
245
|
+
// src/create-element/create-element.ts
|
|
246
|
+
function createElement(element, props = {}) {
|
|
247
|
+
if (typeof element === "string") {
|
|
248
|
+
const { children, ref, phantom = false, ...otherProps } = props;
|
|
249
|
+
const newElement = document.createElement(element);
|
|
250
|
+
const velesNode = {};
|
|
251
|
+
if (ref == null ? void 0 : ref.velesRef) {
|
|
252
|
+
ref.current = newElement;
|
|
253
|
+
}
|
|
254
|
+
const childComponents = parseChildren({
|
|
255
|
+
children,
|
|
256
|
+
htmlElement: newElement,
|
|
257
|
+
velesNode
|
|
258
|
+
});
|
|
259
|
+
let unmountHandlers = [];
|
|
260
|
+
const callUnmountHandlers = () => {
|
|
261
|
+
unmountHandlers.forEach((cb) => cb());
|
|
262
|
+
unmountHandlers = [];
|
|
263
|
+
childComponents.forEach((childComponent) => {
|
|
264
|
+
childComponent._privateMethods._callUnmountHandlers();
|
|
265
|
+
});
|
|
266
|
+
};
|
|
267
|
+
velesNode.html = newElement;
|
|
268
|
+
velesNode.velesNode = true;
|
|
269
|
+
velesNode.childComponents = childComponents;
|
|
270
|
+
velesNode.phantom = phantom;
|
|
271
|
+
velesNode._privateMethods = {
|
|
272
|
+
_addUnmountHandler: (cb) => {
|
|
273
|
+
unmountHandlers.push(cb);
|
|
274
|
+
},
|
|
275
|
+
_callUnmountHandlers: callUnmountHandlers
|
|
276
|
+
};
|
|
277
|
+
assignAttributes({ props: otherProps, htmlElement: newElement, velesNode });
|
|
278
|
+
return velesNode;
|
|
279
|
+
} else if (typeof element === "function") {
|
|
280
|
+
return parseComponent({ element, props });
|
|
281
|
+
}
|
|
282
|
+
throw new Error(
|
|
283
|
+
"Veles createElement expects a valid DOM string or another component"
|
|
284
|
+
);
|
|
285
|
+
}
|
|
286
|
+
|
|
287
|
+
// src/attach-component.ts
|
|
288
|
+
function attachComponent({
|
|
289
|
+
htmlElement,
|
|
290
|
+
component
|
|
291
|
+
}) {
|
|
292
|
+
const wrappedApp = createElement("div", { children: [component] });
|
|
293
|
+
const { velesElementNode } = getComponentVelesNode(wrappedApp);
|
|
294
|
+
htmlElement.appendChild(velesElementNode.html);
|
|
295
|
+
return () => {
|
|
296
|
+
velesElementNode.html.remove();
|
|
297
|
+
};
|
|
298
|
+
}
|
|
299
|
+
|
|
300
|
+
// src/create-element/create-text-element.ts
|
|
301
|
+
function createTextElement(text) {
|
|
302
|
+
const unmountHandlers = [];
|
|
303
|
+
return {
|
|
304
|
+
velesStringElement: true,
|
|
305
|
+
// in case there is no text, we create an empty Text node, so we still can
|
|
306
|
+
// have a reference to it, replace it, call lifecycle methods, etc
|
|
307
|
+
html: document.createTextNode(text || ""),
|
|
308
|
+
_privateMethods: {
|
|
309
|
+
_addUnmountHandler: (cb) => {
|
|
310
|
+
unmountHandlers.push(cb);
|
|
311
|
+
},
|
|
312
|
+
_callUnmountHandlers: () => {
|
|
313
|
+
unmountHandlers.forEach((cb) => cb());
|
|
314
|
+
}
|
|
315
|
+
}
|
|
316
|
+
};
|
|
317
|
+
}
|
|
318
|
+
|
|
319
|
+
// src/hooks/create-state.ts
|
|
320
|
+
function createState(initialValue, subscribeCallback) {
|
|
321
|
+
let value = initialValue;
|
|
322
|
+
let previousValue = void 0;
|
|
323
|
+
let trackingEffects = [];
|
|
324
|
+
let trackingSelectorElements = [];
|
|
325
|
+
let trackingAttributes = [];
|
|
326
|
+
let trackingIterators = [];
|
|
327
|
+
const result = {
|
|
328
|
+
// supposed to be used at the component level
|
|
329
|
+
trackValue: (cb, options = {}) => {
|
|
330
|
+
result.trackValueSelector(void 0, cb, options);
|
|
331
|
+
},
|
|
332
|
+
trackValueSelector(selector, cb, options = {}) {
|
|
333
|
+
const trackedValue = selector ? selector(value) : value;
|
|
334
|
+
trackingEffects.push({
|
|
335
|
+
cb,
|
|
336
|
+
selector,
|
|
337
|
+
comparator: options.comparator,
|
|
338
|
+
selectedValue: trackedValue
|
|
339
|
+
});
|
|
340
|
+
if (!options.skipFirstCall) {
|
|
341
|
+
if (options.callOnMount) {
|
|
342
|
+
onMount(() => {
|
|
343
|
+
cb(trackedValue);
|
|
344
|
+
});
|
|
345
|
+
} else {
|
|
346
|
+
cb(trackedValue);
|
|
347
|
+
}
|
|
348
|
+
}
|
|
349
|
+
onUnmount(() => {
|
|
350
|
+
trackingEffects = trackingEffects.filter(
|
|
351
|
+
(trackingCallback) => trackingCallback.cb !== cb
|
|
352
|
+
);
|
|
353
|
+
});
|
|
354
|
+
},
|
|
355
|
+
useValue: (cb, comparator) => {
|
|
356
|
+
return result.useValueSelector(void 0, cb, comparator);
|
|
357
|
+
},
|
|
358
|
+
useValueSelector(selector, cb, comparator = identity) {
|
|
359
|
+
const selectedValue = selector ? selector(value) : value;
|
|
360
|
+
const returnedNode = cb(selectedValue);
|
|
361
|
+
const node = !returnedNode || typeof returnedNode === "string" ? createTextElement(returnedNode) : returnedNode;
|
|
362
|
+
trackingSelectorElements.push({
|
|
363
|
+
selector,
|
|
364
|
+
selectedValue,
|
|
365
|
+
cb,
|
|
366
|
+
node,
|
|
367
|
+
comparator
|
|
368
|
+
});
|
|
369
|
+
node._privateMethods._addUnmountHandler(() => {
|
|
370
|
+
trackingSelectorElements = trackingSelectorElements.filter(
|
|
371
|
+
(trackingSelectorElement) => trackingSelectorElement.cb !== cb
|
|
372
|
+
);
|
|
373
|
+
});
|
|
374
|
+
return node;
|
|
375
|
+
},
|
|
376
|
+
useValueIterator(options, cb) {
|
|
377
|
+
const children = [];
|
|
378
|
+
const elementsByKey = {};
|
|
379
|
+
const elements = options.selector ? options.selector(value) : value;
|
|
380
|
+
if (!Array.isArray(elements)) {
|
|
381
|
+
console.error("useValueIterator received non-array value");
|
|
382
|
+
return null;
|
|
383
|
+
}
|
|
384
|
+
elements.forEach((element, index) => {
|
|
385
|
+
let calculatedKey = "";
|
|
386
|
+
if (typeof options.key === "string" && typeof element === "object" && element !== null && options.key in element) {
|
|
387
|
+
calculatedKey = element[options.key];
|
|
388
|
+
} else if (typeof options.key === "function") {
|
|
389
|
+
calculatedKey = options.key({ element, index });
|
|
390
|
+
} else {
|
|
391
|
+
}
|
|
392
|
+
const elementState = createState(element);
|
|
393
|
+
if (!calculatedKey) {
|
|
394
|
+
return;
|
|
395
|
+
}
|
|
396
|
+
let node = cb({ elementState, index });
|
|
397
|
+
elementsByKey[calculatedKey] = {
|
|
398
|
+
node,
|
|
399
|
+
index,
|
|
400
|
+
elementState
|
|
401
|
+
};
|
|
402
|
+
children.push([node, calculatedKey, elementState]);
|
|
403
|
+
});
|
|
404
|
+
const trackingParams = {};
|
|
405
|
+
trackingIterators.push(trackingParams);
|
|
406
|
+
const wrapperComponent = createElement(() => {
|
|
407
|
+
onUnmount(() => {
|
|
408
|
+
trackingIterators = trackingIterators.filter(
|
|
409
|
+
(currentTrackingParams) => currentTrackingParams !== trackingParams
|
|
410
|
+
);
|
|
411
|
+
});
|
|
412
|
+
return createElement("div", {
|
|
413
|
+
phantom: true,
|
|
414
|
+
children: children.map((child) => child[0])
|
|
415
|
+
});
|
|
416
|
+
});
|
|
417
|
+
trackingParams.cb = cb;
|
|
418
|
+
trackingParams.key = options.key;
|
|
419
|
+
trackingParams.elementsByKey = elementsByKey;
|
|
420
|
+
trackingParams.renderedElements = children;
|
|
421
|
+
trackingParams.wrapperComponent = wrapperComponent;
|
|
422
|
+
if (options.selector) {
|
|
423
|
+
trackingParams.selector = options.selector;
|
|
424
|
+
}
|
|
425
|
+
return wrapperComponent;
|
|
426
|
+
},
|
|
427
|
+
useAttribute: (cb) => {
|
|
428
|
+
const attributeValue = cb(value);
|
|
429
|
+
const attributeHelper = (htmlElement, attributeName, node) => {
|
|
430
|
+
trackingAttributes.push({ cb, htmlElement, attributeName });
|
|
431
|
+
node._privateMethods._addUnmountHandler(() => {
|
|
432
|
+
trackingAttributes = trackingAttributes.filter(
|
|
433
|
+
(trackingAttribute) => trackingAttribute.cb !== cb
|
|
434
|
+
);
|
|
435
|
+
});
|
|
436
|
+
return attributeValue;
|
|
437
|
+
};
|
|
438
|
+
attributeHelper.velesAttribute = true;
|
|
439
|
+
return attributeHelper;
|
|
440
|
+
},
|
|
441
|
+
// useful for stuff like callbacks
|
|
442
|
+
getValue: () => {
|
|
443
|
+
return value;
|
|
444
|
+
},
|
|
445
|
+
getPreviousValue: () => {
|
|
446
|
+
return previousValue;
|
|
447
|
+
},
|
|
448
|
+
// set up new value only through the callback which
|
|
449
|
+
// gives the latest value to ensure no outdated data
|
|
450
|
+
// can be used for the state
|
|
451
|
+
setValue: (newValueCB) => {
|
|
452
|
+
const newValue = newValueCB(value);
|
|
453
|
+
if (newValue !== value) {
|
|
454
|
+
previousValue = value;
|
|
455
|
+
value = newValue;
|
|
456
|
+
result._triggerUpdates();
|
|
457
|
+
}
|
|
458
|
+
},
|
|
459
|
+
// TODO: remove it from this object completely
|
|
460
|
+
// and access it from closure
|
|
461
|
+
_triggerUpdates: () => {
|
|
462
|
+
trackingSelectorElements = trackingSelectorElements.map(
|
|
463
|
+
(selectorTrackingElement) => {
|
|
464
|
+
const { selectedValue, selector, cb, node, comparator } = selectorTrackingElement;
|
|
465
|
+
const newSelectedValue = selector ? selector(value) : value;
|
|
466
|
+
if (comparator(selectedValue, newSelectedValue)) {
|
|
467
|
+
return selectorTrackingElement;
|
|
468
|
+
}
|
|
469
|
+
const returnednewNode = cb(newSelectedValue);
|
|
470
|
+
const newNode = !returnednewNode || typeof returnednewNode === "string" ? createTextElement(returnednewNode) : returnednewNode;
|
|
471
|
+
const { velesElementNode: oldVelesElementNode } = getComponentVelesNode(node);
|
|
472
|
+
const { velesElementNode: newVelesElementNode } = getComponentVelesNode(newNode);
|
|
473
|
+
const parentVelesElement = oldVelesElementNode.parentVelesElement;
|
|
474
|
+
if (parentVelesElement) {
|
|
475
|
+
newVelesElementNode.parentVelesElement = parentVelesElement;
|
|
476
|
+
parentVelesElement.html.replaceChild(
|
|
477
|
+
newVelesElementNode.html,
|
|
478
|
+
oldVelesElementNode.html
|
|
479
|
+
);
|
|
480
|
+
parentVelesElement.childComponents = parentVelesElement.childComponents.map(
|
|
481
|
+
(childComponent) => childComponent === node ? newNode : node
|
|
482
|
+
);
|
|
483
|
+
node._privateMethods._callUnmountHandlers();
|
|
484
|
+
trackingSelectorElements.push({
|
|
485
|
+
selector,
|
|
486
|
+
selectedValue: newSelectedValue,
|
|
487
|
+
cb,
|
|
488
|
+
node: newNode,
|
|
489
|
+
comparator
|
|
490
|
+
});
|
|
491
|
+
newNode._privateMethods._addUnmountHandler(() => {
|
|
492
|
+
trackingSelectorElements = trackingSelectorElements.filter(
|
|
493
|
+
(trackingSelectorElement) => trackingSelectorElement.cb !== cb
|
|
494
|
+
);
|
|
495
|
+
});
|
|
496
|
+
} else {
|
|
497
|
+
console.log("parent node was not found");
|
|
498
|
+
}
|
|
499
|
+
return {
|
|
500
|
+
selectedValue: newSelectedValue,
|
|
501
|
+
selector,
|
|
502
|
+
cb,
|
|
503
|
+
node: newNode,
|
|
504
|
+
comparator
|
|
505
|
+
};
|
|
506
|
+
}
|
|
507
|
+
);
|
|
508
|
+
trackingAttributes.forEach(({ cb, htmlElement, attributeName }) => {
|
|
509
|
+
const newAttributeValue = cb(value);
|
|
510
|
+
htmlElement.setAttribute(attributeName, newAttributeValue);
|
|
511
|
+
});
|
|
512
|
+
trackingEffects.forEach((trackingEffect) => {
|
|
513
|
+
const { cb, selectedValue, selector, comparator } = trackingEffect;
|
|
514
|
+
const newSelectedValue = selector ? selector(value) : value;
|
|
515
|
+
if (comparator ? comparator(selectedValue, newSelectedValue) : selectedValue === newSelectedValue) {
|
|
516
|
+
return;
|
|
517
|
+
}
|
|
518
|
+
cb(newSelectedValue);
|
|
519
|
+
});
|
|
520
|
+
trackingIterators.forEach((trackingIterator) => {
|
|
521
|
+
const {
|
|
522
|
+
cb,
|
|
523
|
+
key,
|
|
524
|
+
renderedElements,
|
|
525
|
+
elementsByKey,
|
|
526
|
+
wrapperComponent,
|
|
527
|
+
selector
|
|
528
|
+
} = trackingIterator;
|
|
529
|
+
if (!wrapperComponent) {
|
|
530
|
+
console.error("there is no wrapper component for the iterator");
|
|
531
|
+
return;
|
|
532
|
+
}
|
|
533
|
+
const { velesElementNode: wrapperVelesElementNode } = getComponentVelesNode(wrapperComponent);
|
|
534
|
+
const parentVelesElement = wrapperVelesElementNode.parentVelesElement;
|
|
535
|
+
if (!parentVelesElement) {
|
|
536
|
+
console.error(
|
|
537
|
+
"there is no parent Veles node for the iterator wrapper"
|
|
538
|
+
);
|
|
539
|
+
return;
|
|
540
|
+
}
|
|
541
|
+
const elements = selector ? selector(value) : value;
|
|
542
|
+
if (Array.isArray(elements)) {
|
|
543
|
+
const newRenderedElements = [];
|
|
544
|
+
const newElementsByKey = {};
|
|
545
|
+
const renderedExistingElements = {};
|
|
546
|
+
elements.forEach((element, index) => {
|
|
547
|
+
let calculatedKey = "";
|
|
548
|
+
if (typeof key === "string" && typeof element === "object" && element !== null && key in element) {
|
|
549
|
+
calculatedKey = element[key];
|
|
550
|
+
} else if (typeof key === "function") {
|
|
551
|
+
calculatedKey = key({ element, index });
|
|
552
|
+
} else {
|
|
553
|
+
}
|
|
554
|
+
if (!calculatedKey) {
|
|
555
|
+
return;
|
|
556
|
+
}
|
|
557
|
+
const existingElement = elementsByKey[calculatedKey];
|
|
558
|
+
if (existingElement) {
|
|
559
|
+
renderedExistingElements[calculatedKey] = true;
|
|
560
|
+
const currentValue = existingElement.elementState.getValue();
|
|
561
|
+
if (currentValue !== element) {
|
|
562
|
+
existingElement.elementState.setValue(() => element);
|
|
563
|
+
}
|
|
564
|
+
newRenderedElements.push([
|
|
565
|
+
existingElement.node,
|
|
566
|
+
calculatedKey,
|
|
567
|
+
existingElement.elementState
|
|
568
|
+
]);
|
|
569
|
+
newElementsByKey[calculatedKey] = {
|
|
570
|
+
elementState: existingElement.elementState,
|
|
571
|
+
index,
|
|
572
|
+
node: existingElement.node
|
|
573
|
+
};
|
|
574
|
+
} else {
|
|
575
|
+
const elementState = createState(element);
|
|
576
|
+
const node = cb({ elementState, index });
|
|
577
|
+
newRenderedElements.push([node, calculatedKey, elementState]);
|
|
578
|
+
newElementsByKey[calculatedKey] = {
|
|
579
|
+
elementState,
|
|
580
|
+
index,
|
|
581
|
+
node
|
|
582
|
+
};
|
|
583
|
+
}
|
|
584
|
+
});
|
|
585
|
+
const positioningOffset = {};
|
|
586
|
+
let newElementsCount = 0;
|
|
587
|
+
let offset = 0;
|
|
588
|
+
let currentElement = null;
|
|
589
|
+
newRenderedElements.forEach((newRenderedElement, index) => {
|
|
590
|
+
var _a, _b, _c;
|
|
591
|
+
if (positioningOffset[index]) {
|
|
592
|
+
offset = offset + positioningOffset[index];
|
|
593
|
+
}
|
|
594
|
+
const [newNode, calculatedKey, newState] = newRenderedElement;
|
|
595
|
+
const existingElement = elementsByKey[calculatedKey];
|
|
596
|
+
if (existingElement) {
|
|
597
|
+
const { velesElementNode: existingElementNode } = getComponentVelesNode(existingElement.node);
|
|
598
|
+
if (existingElement.index + offset === index) {
|
|
599
|
+
currentElement = existingElementNode.html;
|
|
600
|
+
return;
|
|
601
|
+
}
|
|
602
|
+
if (existingElement.index + offset > index) {
|
|
603
|
+
if (currentElement) {
|
|
604
|
+
currentElement.after(existingElementNode.html);
|
|
605
|
+
positioningOffset[existingElement.index + 1] = -1;
|
|
606
|
+
} else {
|
|
607
|
+
const firstRenderedElement = (_a = renderedElements[0]) == null ? void 0 : _a[0];
|
|
608
|
+
if (firstRenderedElement) {
|
|
609
|
+
const { velesElementNode: firstRenderedVelesNode } = getComponentVelesNode(firstRenderedElement);
|
|
610
|
+
firstRenderedVelesNode.html.before(
|
|
611
|
+
existingElementNode.html
|
|
612
|
+
);
|
|
613
|
+
} else {
|
|
614
|
+
}
|
|
615
|
+
}
|
|
616
|
+
currentElement = existingElementNode.html;
|
|
617
|
+
offset = offset + 1;
|
|
618
|
+
} else {
|
|
619
|
+
if (currentElement) {
|
|
620
|
+
currentElement.after(existingElementNode.html);
|
|
621
|
+
positioningOffset[existingElement.index + 1] = 1;
|
|
622
|
+
} else {
|
|
623
|
+
const firstRenderedElement = (_b = renderedElements[0]) == null ? void 0 : _b[0];
|
|
624
|
+
if (firstRenderedElement) {
|
|
625
|
+
const { velesElementNode: firstRenderedVelesNode } = getComponentVelesNode(firstRenderedElement);
|
|
626
|
+
firstRenderedVelesNode.html.before(
|
|
627
|
+
existingElementNode.html
|
|
628
|
+
);
|
|
629
|
+
} else {
|
|
630
|
+
}
|
|
631
|
+
}
|
|
632
|
+
currentElement = existingElementNode.html;
|
|
633
|
+
offset = offset - 1;
|
|
634
|
+
}
|
|
635
|
+
} else {
|
|
636
|
+
const { velesElementNode: newNodeVelesElement } = getComponentVelesNode(newNode);
|
|
637
|
+
newNodeVelesElement.parentVelesElement = parentVelesElement;
|
|
638
|
+
if (currentElement) {
|
|
639
|
+
currentElement.after(newNodeVelesElement.html);
|
|
640
|
+
} else {
|
|
641
|
+
const firstRenderedElement = (_c = renderedElements[0]) == null ? void 0 : _c[0];
|
|
642
|
+
if (firstRenderedElement) {
|
|
643
|
+
const { velesElementNode: firstRenderedVelesNode } = getComponentVelesNode(firstRenderedElement);
|
|
644
|
+
firstRenderedVelesNode.html.before(newNodeVelesElement.html);
|
|
645
|
+
} else {
|
|
646
|
+
parentVelesElement.html.prepend(newNodeVelesElement.html);
|
|
647
|
+
}
|
|
648
|
+
}
|
|
649
|
+
offset = offset + 1;
|
|
650
|
+
currentElement = newNodeVelesElement.html;
|
|
651
|
+
newElementsCount = newElementsCount + 1;
|
|
652
|
+
}
|
|
653
|
+
});
|
|
654
|
+
if (renderedElements.length === newRenderedElements.length + newElementsCount) {
|
|
655
|
+
} else {
|
|
656
|
+
renderedElements.forEach(([oldNode, calculatedKey]) => {
|
|
657
|
+
if (renderedExistingElements[calculatedKey] === true) {
|
|
658
|
+
return;
|
|
659
|
+
} else {
|
|
660
|
+
const { velesElementNode: oldRenderedVelesNode } = getComponentVelesNode(oldNode);
|
|
661
|
+
oldRenderedVelesNode.html.remove();
|
|
662
|
+
oldNode._privateMethods._callUnmountHandlers();
|
|
663
|
+
if ("velesNode" in wrapperVelesElementNode) {
|
|
664
|
+
wrapperVelesElementNode.childComponents = wrapperVelesElementNode.childComponents.filter(
|
|
665
|
+
(childComponent) => childComponent !== oldNode
|
|
666
|
+
);
|
|
667
|
+
} else {
|
|
668
|
+
throw new Error("Wrapper iterator element is a string");
|
|
669
|
+
}
|
|
670
|
+
}
|
|
671
|
+
});
|
|
672
|
+
}
|
|
673
|
+
trackingIterator.renderedElements = newRenderedElements;
|
|
674
|
+
trackingIterator.elementsByKey = newElementsByKey;
|
|
675
|
+
}
|
|
676
|
+
});
|
|
677
|
+
}
|
|
678
|
+
};
|
|
679
|
+
if (subscribeCallback) {
|
|
680
|
+
const unsubscribe = subscribeCallback(result.setValue);
|
|
681
|
+
if (unsubscribe) {
|
|
682
|
+
onUnmount(unsubscribe);
|
|
683
|
+
}
|
|
684
|
+
}
|
|
685
|
+
return result;
|
|
686
|
+
}
|
|
687
|
+
|
|
688
|
+
// src/hooks/combine-state.ts
|
|
689
|
+
function combineState(...states) {
|
|
690
|
+
const initialValue = states.map((state) => state.getValue());
|
|
691
|
+
const combinedState = createState(initialValue);
|
|
692
|
+
states.forEach((state) => {
|
|
693
|
+
state.trackValue(() => {
|
|
694
|
+
const updatedValue = states.map((state2) => state2.getValue());
|
|
695
|
+
combinedState.setValue(() => updatedValue);
|
|
696
|
+
});
|
|
697
|
+
});
|
|
698
|
+
return combinedState;
|
|
699
|
+
}
|
|
700
|
+
|
|
701
|
+
// src/create-ref.ts
|
|
702
|
+
function createRef(initialRefValue = null) {
|
|
703
|
+
return {
|
|
704
|
+
velesRef: true,
|
|
705
|
+
current: initialRefValue
|
|
706
|
+
};
|
|
707
|
+
}
|
|
708
|
+
|
|
709
|
+
// src/fragment.ts
|
|
710
|
+
function Fragment({ children }) {
|
|
711
|
+
return createElement("div", {
|
|
712
|
+
phantom: true,
|
|
713
|
+
children
|
|
714
|
+
});
|
|
715
|
+
}
|
|
716
|
+
// Annotate the CommonJS export names for ESM import in node:
|
|
717
|
+
0 && (module.exports = {
|
|
718
|
+
Fragment,
|
|
719
|
+
attachComponent,
|
|
720
|
+
combineState,
|
|
721
|
+
createElement,
|
|
722
|
+
createRef,
|
|
723
|
+
createState,
|
|
724
|
+
onMount,
|
|
725
|
+
onUnmount
|
|
726
|
+
});
|
|
727
|
+
//# sourceMappingURL=index.cjs.map
|