@oscarpalmer/abydon 0.12.0 → 0.13.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/abydon.full.js +1247 -0
- package/dist/fragment.js +60 -0
- package/dist/helpers/dom.js +28 -0
- package/dist/helpers/index.js +11 -0
- package/dist/index.js +6 -911
- package/dist/node/attribute/index.js +34 -0
- package/dist/node/attribute/value.js +58 -0
- package/dist/node/event.js +32 -0
- package/dist/node/index.js +52 -0
- package/dist/node/value.js +93 -0
- package/dist/parse.js +21 -0
- package/package.json +41 -28
- package/src/fragment.ts +13 -14
- package/src/helpers/dom.ts +2 -1
- package/src/helpers/index.ts +0 -9
- package/src/index.ts +11 -2
- package/src/models.ts +6 -8
- package/src/node/attribute/index.ts +4 -3
- package/src/node/attribute/value.ts +8 -15
- package/src/node/event.ts +1 -1
- package/src/node/index.ts +4 -3
- package/src/node/value.ts +6 -7
- package/src/{html.ts → parse.ts} +5 -14
- package/types/fragment.d.cts +27 -0
- package/types/helpers/dom.d.cts +7 -0
- package/types/helpers/index.d.cts +29 -0
- package/types/helpers/index.d.ts +0 -3
- package/types/index.d.cts +278 -2
- package/types/index.d.ts +4 -2
- package/types/models.d.cts +107 -0
- package/types/models.d.ts +6 -7
- package/types/node/attribute/index.d.cts +109 -0
- package/types/node/attribute/index.d.ts +2 -1
- package/types/node/attribute/value.d.cts +109 -0
- package/types/node/attribute/value.d.ts +2 -1
- package/types/node/event.d.cts +7 -0
- package/types/node/event.d.ts +1 -1
- package/types/node/index.d.cts +108 -0
- package/types/node/value.d.cts +108 -0
- package/types/node/value.d.ts +2 -2
- package/types/parse.d.cts +108 -0
- package/types/parse.d.ts +2 -0
- package/dist/fragment.mjs +0 -75
- package/dist/helpers/dom.mjs +0 -44
- package/dist/helpers/index.mjs +0 -25
- package/dist/html.mjs +0 -36
- package/dist/index.mjs +0 -6
- package/dist/node/attribute/index.mjs +0 -40
- package/dist/node/attribute/value.mjs +0 -89
- package/dist/node/event.mjs +0 -38
- package/dist/node/index.mjs +0 -60
- package/dist/node/value.mjs +0 -123
- package/types/html.d.ts +0 -4
- /package/dist/{models.mjs → models.js} +0 -0
|
@@ -0,0 +1,1247 @@
|
|
|
1
|
+
function isArray(value) {
|
|
2
|
+
return isMora(value, arrayName);
|
|
3
|
+
}
|
|
4
|
+
function isComputed(value) {
|
|
5
|
+
return isMora(value, computedName);
|
|
6
|
+
}
|
|
7
|
+
function isEffect(value) {
|
|
8
|
+
return isMora(value, effectName);
|
|
9
|
+
}
|
|
10
|
+
function isMora(value, name) {
|
|
11
|
+
return typeof value === "object" && value != null && "$mora" in value && (typeof name === "string" ? value.$mora === name : name.has(value.$mora));
|
|
12
|
+
}
|
|
13
|
+
function isReactive(value) {
|
|
14
|
+
return isMora(value, reactiveNames);
|
|
15
|
+
}
|
|
16
|
+
function isSignal(value) {
|
|
17
|
+
return isMora(value, signalName);
|
|
18
|
+
}
|
|
19
|
+
const arrayName = "array";
|
|
20
|
+
const computedName = "computed";
|
|
21
|
+
const effectName = "effect";
|
|
22
|
+
const signalName = "signal";
|
|
23
|
+
const storeName = "store";
|
|
24
|
+
const reactiveNames = /* @__PURE__ */ new Set([arrayName, computedName, signalName, storeName]);
|
|
25
|
+
|
|
26
|
+
class Effect {
|
|
27
|
+
constructor(callback) {
|
|
28
|
+
Object.defineProperty(this, "$mora", {
|
|
29
|
+
value: effectName
|
|
30
|
+
});
|
|
31
|
+
this.state = {
|
|
32
|
+
callback
|
|
33
|
+
};
|
|
34
|
+
runEffect(this);
|
|
35
|
+
}
|
|
36
|
+
}
|
|
37
|
+
function runEffect(effect2) {
|
|
38
|
+
const previousEffect = activeEffect;
|
|
39
|
+
activeEffect = effect2;
|
|
40
|
+
try {
|
|
41
|
+
effect2.state.callback();
|
|
42
|
+
} finally {
|
|
43
|
+
activeEffect = previousEffect;
|
|
44
|
+
}
|
|
45
|
+
}
|
|
46
|
+
function effect(callback) {
|
|
47
|
+
return new Effect(callback);
|
|
48
|
+
}
|
|
49
|
+
let activeEffect;
|
|
50
|
+
|
|
51
|
+
function flushHandlers() {
|
|
52
|
+
while (batchDepth === 0 && batchedHandlers.size > 0) {
|
|
53
|
+
const handlers = [...batchedHandlers];
|
|
54
|
+
batchedHandlers.clear();
|
|
55
|
+
for (const handler of handlers) {
|
|
56
|
+
if (isEffect(handler)) {
|
|
57
|
+
runEffect(handler);
|
|
58
|
+
} else {
|
|
59
|
+
handler.callback(handler.state.value);
|
|
60
|
+
}
|
|
61
|
+
}
|
|
62
|
+
}
|
|
63
|
+
}
|
|
64
|
+
function startBatch() {
|
|
65
|
+
batchDepth += 1;
|
|
66
|
+
}
|
|
67
|
+
function stopBatch() {
|
|
68
|
+
if (batchDepth > 0) {
|
|
69
|
+
batchDepth -= 1;
|
|
70
|
+
}
|
|
71
|
+
flushHandlers();
|
|
72
|
+
}
|
|
73
|
+
const batchedHandlers = /* @__PURE__ */ new Set();
|
|
74
|
+
let batchDepth = 0;
|
|
75
|
+
|
|
76
|
+
class Subscription {
|
|
77
|
+
constructor(state, callback) {
|
|
78
|
+
this.state = state;
|
|
79
|
+
this.callback = callback;
|
|
80
|
+
callback(state.value);
|
|
81
|
+
}
|
|
82
|
+
}
|
|
83
|
+
function noop() {
|
|
84
|
+
}
|
|
85
|
+
function subscribe(state, callback) {
|
|
86
|
+
if (typeof callback !== "function" || state.subscriptions.has(callback)) {
|
|
87
|
+
return noop;
|
|
88
|
+
}
|
|
89
|
+
state.subscriptions.set(callback, new Subscription(state, callback));
|
|
90
|
+
return () => {
|
|
91
|
+
unsubscribe(state, callback);
|
|
92
|
+
};
|
|
93
|
+
}
|
|
94
|
+
function unsubscribe(state, callback) {
|
|
95
|
+
const subscription = state.subscriptions.get(callback);
|
|
96
|
+
state.subscriptions.delete(callback);
|
|
97
|
+
if (subscription != null) {
|
|
98
|
+
subscription.callback = noop;
|
|
99
|
+
subscription.state = void 0;
|
|
100
|
+
}
|
|
101
|
+
}
|
|
102
|
+
|
|
103
|
+
var __defProp$1 = Object.defineProperty;
|
|
104
|
+
var __defNormalProp$1 = (obj, key, value) => key in obj ? __defProp$1(obj, key, { enumerable: true, configurable: true, writable: true, value }) : obj[key] = value;
|
|
105
|
+
var __publicField$1 = (obj, key, value) => __defNormalProp$1(obj, key + "" , value);
|
|
106
|
+
class Reactive {
|
|
107
|
+
constructor(name, value, options) {
|
|
108
|
+
__publicField$1(this, "state", {
|
|
109
|
+
computeds: /* @__PURE__ */ new Set(),
|
|
110
|
+
effects: /* @__PURE__ */ new Set(),
|
|
111
|
+
equal: Object.is,
|
|
112
|
+
subscriptions: /* @__PURE__ */ new Map(),
|
|
113
|
+
value: void 0
|
|
114
|
+
});
|
|
115
|
+
this.state.value = value;
|
|
116
|
+
if (typeof options === "object" && typeof options.equal === "function") {
|
|
117
|
+
this.state.equal = options.equal;
|
|
118
|
+
}
|
|
119
|
+
Object.defineProperty(this, "$mora", {
|
|
120
|
+
value: name
|
|
121
|
+
});
|
|
122
|
+
}
|
|
123
|
+
/**
|
|
124
|
+
* Get the value _(without reactivity)_
|
|
125
|
+
*/
|
|
126
|
+
peek() {
|
|
127
|
+
return this.state.value;
|
|
128
|
+
}
|
|
129
|
+
/**
|
|
130
|
+
* Subscribe to changes
|
|
131
|
+
*/
|
|
132
|
+
subscribe(callback) {
|
|
133
|
+
return subscribe(this.state, callback);
|
|
134
|
+
}
|
|
135
|
+
/**
|
|
136
|
+
* JSON representation of the value
|
|
137
|
+
*/
|
|
138
|
+
toJSON() {
|
|
139
|
+
return this.get();
|
|
140
|
+
}
|
|
141
|
+
/**
|
|
142
|
+
* String representation of the value
|
|
143
|
+
*/
|
|
144
|
+
toString() {
|
|
145
|
+
return String(this.get());
|
|
146
|
+
}
|
|
147
|
+
/**
|
|
148
|
+
* Unsubscribe from changes
|
|
149
|
+
*/
|
|
150
|
+
unsubscribe(callback) {
|
|
151
|
+
unsubscribe(this.state, callback);
|
|
152
|
+
}
|
|
153
|
+
}
|
|
154
|
+
|
|
155
|
+
var __defProp = Object.defineProperty;
|
|
156
|
+
var __defNormalProp = (obj, key, value) => key in obj ? __defProp(obj, key, { enumerable: true, configurable: true, writable: true, value }) : obj[key] = value;
|
|
157
|
+
var __publicField = (obj, key, value) => __defNormalProp(obj, key + "" , value);
|
|
158
|
+
let activeComputed;
|
|
159
|
+
class Computed extends Reactive {
|
|
160
|
+
constructor(callback, options) {
|
|
161
|
+
super(computedName, void 0, options);
|
|
162
|
+
__publicField(this, "effect", {
|
|
163
|
+
dirty: true,
|
|
164
|
+
instance: void 0
|
|
165
|
+
});
|
|
166
|
+
this.effect.instance = effect(() => {
|
|
167
|
+
if (this.effect.dirty) {
|
|
168
|
+
const previousComputed = activeComputed;
|
|
169
|
+
activeComputed = this;
|
|
170
|
+
const value = callback();
|
|
171
|
+
activeComputed = previousComputed;
|
|
172
|
+
if (!this.state.equal(this.state.value, value)) {
|
|
173
|
+
this.state.value = value;
|
|
174
|
+
for (const computed2 of this.state.computeds) {
|
|
175
|
+
computed2.effect.dirty = true;
|
|
176
|
+
}
|
|
177
|
+
for (const effect2 of this.state.effects) {
|
|
178
|
+
batchedHandlers.add(effect2);
|
|
179
|
+
}
|
|
180
|
+
for (const [, subscription] of this.state.subscriptions) {
|
|
181
|
+
subscription.callback(value);
|
|
182
|
+
}
|
|
183
|
+
}
|
|
184
|
+
this.effect.dirty = false;
|
|
185
|
+
}
|
|
186
|
+
});
|
|
187
|
+
}
|
|
188
|
+
/**
|
|
189
|
+
* @inheritdoc
|
|
190
|
+
*/
|
|
191
|
+
get() {
|
|
192
|
+
if (activeComputed != null && this !== activeComputed) {
|
|
193
|
+
this.state.computeds.add(activeComputed);
|
|
194
|
+
}
|
|
195
|
+
if (activeEffect != null && activeEffect !== this.effect.instance) {
|
|
196
|
+
this.state.effects.add(activeEffect);
|
|
197
|
+
}
|
|
198
|
+
if (this.effect.dirty && batchDepth === 0) {
|
|
199
|
+
runEffect(this.effect.instance);
|
|
200
|
+
}
|
|
201
|
+
return this.state.value;
|
|
202
|
+
}
|
|
203
|
+
}
|
|
204
|
+
function computed(callback, options) {
|
|
205
|
+
return new Computed(callback, options);
|
|
206
|
+
}
|
|
207
|
+
|
|
208
|
+
function emitValue(state) {
|
|
209
|
+
for (const computed of state.computeds) {
|
|
210
|
+
computed.effect.dirty = true;
|
|
211
|
+
}
|
|
212
|
+
for (const effect of state.effects) {
|
|
213
|
+
batchedHandlers.add(effect);
|
|
214
|
+
}
|
|
215
|
+
for (const [, subscription] of state.subscriptions) {
|
|
216
|
+
batchedHandlers.add(subscription);
|
|
217
|
+
}
|
|
218
|
+
if (batchDepth === 0) {
|
|
219
|
+
flushHandlers();
|
|
220
|
+
}
|
|
221
|
+
}
|
|
222
|
+
function equalArrays(state, first, second) {
|
|
223
|
+
let { length } = first;
|
|
224
|
+
if (length !== second.length) {
|
|
225
|
+
return false;
|
|
226
|
+
}
|
|
227
|
+
let offset = 0;
|
|
228
|
+
if (length >= 100) {
|
|
229
|
+
offset = Math.round(length / 10);
|
|
230
|
+
offset = offset > 25 ? 25 : offset;
|
|
231
|
+
for (let index = 0; index < offset; index += 1) {
|
|
232
|
+
if (!state.equal(first[index], second[index])) {
|
|
233
|
+
return false;
|
|
234
|
+
}
|
|
235
|
+
}
|
|
236
|
+
}
|
|
237
|
+
length -= offset;
|
|
238
|
+
for (let index = offset; index < length; index += 1) {
|
|
239
|
+
if (!state.equal(first[index], second[index])) {
|
|
240
|
+
return false;
|
|
241
|
+
}
|
|
242
|
+
}
|
|
243
|
+
return true;
|
|
244
|
+
}
|
|
245
|
+
function getValue$1(state) {
|
|
246
|
+
if (activeComputed != null) {
|
|
247
|
+
state.computeds.add(activeComputed);
|
|
248
|
+
}
|
|
249
|
+
if (activeEffect != null) {
|
|
250
|
+
state.effects.add(activeEffect);
|
|
251
|
+
}
|
|
252
|
+
return state.value;
|
|
253
|
+
}
|
|
254
|
+
|
|
255
|
+
function getReactiveValueInProxy(reactive, mapped, key, isArray) {
|
|
256
|
+
let item = mapped.get(key);
|
|
257
|
+
if (item == null) {
|
|
258
|
+
item = computed(() => {
|
|
259
|
+
const value = reactive.get();
|
|
260
|
+
return isArray ? value.at(key) : value[key];
|
|
261
|
+
});
|
|
262
|
+
mapped.set(key, item);
|
|
263
|
+
}
|
|
264
|
+
return item;
|
|
265
|
+
}
|
|
266
|
+
function setProxyValue(proxy, value) {
|
|
267
|
+
startBatch();
|
|
268
|
+
const proxyKeys = Object.keys(proxy);
|
|
269
|
+
const valueKeys = Object.keys(value);
|
|
270
|
+
let { length } = proxyKeys;
|
|
271
|
+
for (let index = 0; index < length; index += 1) {
|
|
272
|
+
const key = proxyKeys[index];
|
|
273
|
+
proxy[key] = valueKeys.includes(key) ? value[key] : void 0;
|
|
274
|
+
}
|
|
275
|
+
length = valueKeys.length;
|
|
276
|
+
for (let index = 0; index < length; index += 1) {
|
|
277
|
+
const key = valueKeys[index];
|
|
278
|
+
if (!proxyKeys.includes(key)) {
|
|
279
|
+
const keyedValue = value[key];
|
|
280
|
+
proxy[key] = keyedValue;
|
|
281
|
+
}
|
|
282
|
+
}
|
|
283
|
+
stopBatch();
|
|
284
|
+
}
|
|
285
|
+
function setValueInProxy(target, property, value, state, isArray, length) {
|
|
286
|
+
if (isArray) {
|
|
287
|
+
const isIndex = !Number.isNaN(Number(property));
|
|
288
|
+
const isLength = property === "length";
|
|
289
|
+
if (!isIndex && !isLength) {
|
|
290
|
+
return Reflect.set(target, property, value);
|
|
291
|
+
}
|
|
292
|
+
}
|
|
293
|
+
const previous = Reflect.get(target, property);
|
|
294
|
+
if (!state.equal(previous, value)) {
|
|
295
|
+
Reflect.set(target, property, value);
|
|
296
|
+
emitValue(state);
|
|
297
|
+
if (isArray) {
|
|
298
|
+
length == null ? void 0 : length.set(target.length);
|
|
299
|
+
}
|
|
300
|
+
}
|
|
301
|
+
return true;
|
|
302
|
+
}
|
|
303
|
+
|
|
304
|
+
class Signal extends Reactive {
|
|
305
|
+
constructor(value, options) {
|
|
306
|
+
super(signalName, value, options);
|
|
307
|
+
}
|
|
308
|
+
/**
|
|
309
|
+
* @inheritdoc
|
|
310
|
+
*/
|
|
311
|
+
get() {
|
|
312
|
+
return getValue$1(this.state);
|
|
313
|
+
}
|
|
314
|
+
/**
|
|
315
|
+
* Set the value
|
|
316
|
+
*/
|
|
317
|
+
set(value) {
|
|
318
|
+
if (!this.state.equal(this.state.value, value)) {
|
|
319
|
+
this.state.value = value;
|
|
320
|
+
emitValue(this.state);
|
|
321
|
+
}
|
|
322
|
+
}
|
|
323
|
+
/**
|
|
324
|
+
* Update the value _(based on the current value)_
|
|
325
|
+
*/
|
|
326
|
+
update(callback) {
|
|
327
|
+
this.set(callback(this.state.value));
|
|
328
|
+
}
|
|
329
|
+
}
|
|
330
|
+
function signal(value, options) {
|
|
331
|
+
return new Signal(value, options);
|
|
332
|
+
}
|
|
333
|
+
|
|
334
|
+
var __typeError$1 = (msg) => {
|
|
335
|
+
throw TypeError(msg);
|
|
336
|
+
};
|
|
337
|
+
var __accessCheck$1 = (obj, member, msg) => member.has(obj) || __typeError$1("Cannot " + msg);
|
|
338
|
+
var __privateGet$1 = (obj, member, getter) => (__accessCheck$1(obj, member, "read from private field"), getter ? getter.call(obj) : member.get(obj));
|
|
339
|
+
var __privateAdd$1 = (obj, member, value) => member.has(obj) ? __typeError$1("Cannot add the same private member more than once") : member instanceof WeakSet ? member.add(obj) : member.set(obj, value);
|
|
340
|
+
var _indiced, _size;
|
|
341
|
+
class ReactiveArray extends Reactive {
|
|
342
|
+
constructor(value, options) {
|
|
343
|
+
super(
|
|
344
|
+
arrayName,
|
|
345
|
+
new Proxy(value, {
|
|
346
|
+
get: (target, property) => updateMethods.has(property) ? updateArray(property, target, this.state, __privateGet$1(this, _size)) : Reflect.get(target, property),
|
|
347
|
+
set: (target, property, value2) => setValueInProxy(
|
|
348
|
+
target,
|
|
349
|
+
property,
|
|
350
|
+
value2,
|
|
351
|
+
this.state,
|
|
352
|
+
true,
|
|
353
|
+
__privateGet$1(this, _size)
|
|
354
|
+
)
|
|
355
|
+
}),
|
|
356
|
+
options
|
|
357
|
+
);
|
|
358
|
+
__privateAdd$1(this, _indiced, /* @__PURE__ */ new Map());
|
|
359
|
+
__privateAdd$1(this, _size, signal(0));
|
|
360
|
+
__privateGet$1(this, _size).set(value.length);
|
|
361
|
+
}
|
|
362
|
+
/**
|
|
363
|
+
* The length of the array
|
|
364
|
+
*/
|
|
365
|
+
get length() {
|
|
366
|
+
return __privateGet$1(this, _size).get();
|
|
367
|
+
}
|
|
368
|
+
/**
|
|
369
|
+
* Set the length of the array
|
|
370
|
+
*/
|
|
371
|
+
set length(value) {
|
|
372
|
+
if (typeof value === "number" && value >= 0 && value !== this.state.value.length) {
|
|
373
|
+
this.get().length = value;
|
|
374
|
+
}
|
|
375
|
+
}
|
|
376
|
+
/**
|
|
377
|
+
* Clear the array
|
|
378
|
+
*/
|
|
379
|
+
clear() {
|
|
380
|
+
this.length = 0;
|
|
381
|
+
}
|
|
382
|
+
get(first) {
|
|
383
|
+
if (typeof first === "number") {
|
|
384
|
+
return getReactiveValueInProxy(this, __privateGet$1(this, _indiced), first, true).get();
|
|
385
|
+
}
|
|
386
|
+
if (first === "length") {
|
|
387
|
+
return this.length;
|
|
388
|
+
}
|
|
389
|
+
return getValue$1(this.state);
|
|
390
|
+
}
|
|
391
|
+
/**
|
|
392
|
+
* Create a computed, filtered array
|
|
393
|
+
*/
|
|
394
|
+
filter(callback) {
|
|
395
|
+
return computed(() => this.get().filter(callback));
|
|
396
|
+
}
|
|
397
|
+
/**
|
|
398
|
+
* Create a computed, mapped array
|
|
399
|
+
*/
|
|
400
|
+
map(callback) {
|
|
401
|
+
return computed(() => this.get().map(callback));
|
|
402
|
+
}
|
|
403
|
+
peek(value) {
|
|
404
|
+
if (value === true) {
|
|
405
|
+
return __privateGet$1(this, _size).peek();
|
|
406
|
+
}
|
|
407
|
+
if (typeof value === "number") {
|
|
408
|
+
return this.state.value.at(value);
|
|
409
|
+
}
|
|
410
|
+
return [...this.state.value];
|
|
411
|
+
}
|
|
412
|
+
/**
|
|
413
|
+
* Remove and return the last item of the array
|
|
414
|
+
*/
|
|
415
|
+
pop() {
|
|
416
|
+
return this.state.value.pop();
|
|
417
|
+
}
|
|
418
|
+
/**
|
|
419
|
+
* Add items to the end of the array
|
|
420
|
+
*/
|
|
421
|
+
push(...items) {
|
|
422
|
+
return this.state.value.push(...items);
|
|
423
|
+
}
|
|
424
|
+
set(first, second) {
|
|
425
|
+
if (first == null || Array.isArray(first)) {
|
|
426
|
+
this.state.value.splice(0, this.state.value.length, ...first ?? []);
|
|
427
|
+
} else if (first === "length") {
|
|
428
|
+
this.length = second;
|
|
429
|
+
} else if (typeof first === "number") {
|
|
430
|
+
this.state.value[first] = second;
|
|
431
|
+
}
|
|
432
|
+
}
|
|
433
|
+
/**
|
|
434
|
+
* Remove and return the first item of the array
|
|
435
|
+
*/
|
|
436
|
+
shift() {
|
|
437
|
+
return this.state.value.shift();
|
|
438
|
+
}
|
|
439
|
+
/**
|
|
440
|
+
* Remove and return items from the array _(and optionally add new items)_
|
|
441
|
+
*/
|
|
442
|
+
splice(from, to, ...items) {
|
|
443
|
+
return this.state.value.splice(
|
|
444
|
+
from,
|
|
445
|
+
to ?? this.state.value.length,
|
|
446
|
+
...items
|
|
447
|
+
);
|
|
448
|
+
}
|
|
449
|
+
subscribe(first, second) {
|
|
450
|
+
if (typeof first === "number" && typeof second === "function") {
|
|
451
|
+
return getReactiveValueInProxy(
|
|
452
|
+
this,
|
|
453
|
+
__privateGet$1(this, _indiced),
|
|
454
|
+
first,
|
|
455
|
+
true
|
|
456
|
+
).subscribe(second);
|
|
457
|
+
}
|
|
458
|
+
return typeof first === "function" ? subscribe(this.state, first) : noop;
|
|
459
|
+
}
|
|
460
|
+
/**
|
|
461
|
+
* Add items to the beginning of the array
|
|
462
|
+
*/
|
|
463
|
+
unshift(...items) {
|
|
464
|
+
return this.state.value.unshift(...items);
|
|
465
|
+
}
|
|
466
|
+
/**
|
|
467
|
+
* Update the value _(based on the current value)_
|
|
468
|
+
*/
|
|
469
|
+
update(callback) {
|
|
470
|
+
const updated = callback(this.state.value);
|
|
471
|
+
if (updated == null || Array.isArray(updated)) {
|
|
472
|
+
this.set(updated);
|
|
473
|
+
}
|
|
474
|
+
}
|
|
475
|
+
}
|
|
476
|
+
_indiced = new WeakMap();
|
|
477
|
+
_size = new WeakMap();
|
|
478
|
+
function array(value, options) {
|
|
479
|
+
return new ReactiveArray(Array.isArray(value) ? value : [], options);
|
|
480
|
+
}
|
|
481
|
+
function updateArray(type, array2, state, length) {
|
|
482
|
+
const affectsLength = lengthAffectingMethods.has(type);
|
|
483
|
+
const previousArray = affectsLength ? [] : [...array2];
|
|
484
|
+
const previousLength = array2.length;
|
|
485
|
+
return (...args) => {
|
|
486
|
+
const result = array2[type](
|
|
487
|
+
...args
|
|
488
|
+
);
|
|
489
|
+
if (affectsLength ? array2.length !== previousLength : !equalArrays(state, previousArray, array2)) {
|
|
490
|
+
emitValue(state);
|
|
491
|
+
length.set(array2.length);
|
|
492
|
+
}
|
|
493
|
+
return result;
|
|
494
|
+
};
|
|
495
|
+
}
|
|
496
|
+
const lengthAffectingMethods = /* @__PURE__ */ new Set([
|
|
497
|
+
"pop",
|
|
498
|
+
"push",
|
|
499
|
+
"shift",
|
|
500
|
+
"unshift"
|
|
501
|
+
]);
|
|
502
|
+
const updateMethods = /* @__PURE__ */ new Set([
|
|
503
|
+
...lengthAffectingMethods,
|
|
504
|
+
"copyWithin",
|
|
505
|
+
"fill",
|
|
506
|
+
"reverse",
|
|
507
|
+
"sort",
|
|
508
|
+
"splice"
|
|
509
|
+
]);
|
|
510
|
+
|
|
511
|
+
function isKey(value) {
|
|
512
|
+
return typeof value === "number" || typeof value === "string";
|
|
513
|
+
}
|
|
514
|
+
function isPlainObject$1(value) {
|
|
515
|
+
if (value === null || typeof value !== "object") {
|
|
516
|
+
return false;
|
|
517
|
+
}
|
|
518
|
+
if (Symbol.toStringTag in value || Symbol.iterator in value) {
|
|
519
|
+
return false;
|
|
520
|
+
}
|
|
521
|
+
const prototype = Object.getPrototypeOf(value);
|
|
522
|
+
return prototype === null || prototype === Object.prototype || Object.getPrototypeOf(prototype) === null;
|
|
523
|
+
}
|
|
524
|
+
|
|
525
|
+
var __typeError = (msg) => {
|
|
526
|
+
throw TypeError(msg);
|
|
527
|
+
};
|
|
528
|
+
var __accessCheck = (obj, member, msg) => member.has(obj) || __typeError("Cannot " + msg);
|
|
529
|
+
var __privateGet = (obj, member, getter) => (__accessCheck(obj, member, "read from private field"), getter ? getter.call(obj) : member.get(obj));
|
|
530
|
+
var __privateAdd = (obj, member, value) => member.has(obj) ? __typeError("Cannot add the same private member more than once") : member instanceof WeakSet ? member.add(obj) : member.set(obj, value);
|
|
531
|
+
var _keyed;
|
|
532
|
+
class Store extends Reactive {
|
|
533
|
+
constructor(value, options) {
|
|
534
|
+
super(
|
|
535
|
+
storeName,
|
|
536
|
+
new Proxy(value, {
|
|
537
|
+
set: (target, property, value2) => setValueInProxy(target, property, value2, this.state, false)
|
|
538
|
+
}),
|
|
539
|
+
options
|
|
540
|
+
);
|
|
541
|
+
__privateAdd(this, _keyed, /* @__PURE__ */ new Map());
|
|
542
|
+
}
|
|
543
|
+
get(key) {
|
|
544
|
+
return isKey(key) ? getReactiveValueInProxy(this, __privateGet(this, _keyed), key, false).get() : getValue$1(this.state);
|
|
545
|
+
}
|
|
546
|
+
peek(key) {
|
|
547
|
+
return isKey(key) ? this.state.value[key] : { ...this.state.value };
|
|
548
|
+
}
|
|
549
|
+
set(first, second) {
|
|
550
|
+
if (isKey(first)) {
|
|
551
|
+
this.state.value[first] = second;
|
|
552
|
+
} else if (first == null || isPlainObject$1(first)) {
|
|
553
|
+
setProxyValue(this.state.value, first ?? {});
|
|
554
|
+
}
|
|
555
|
+
}
|
|
556
|
+
subscribe(first, second) {
|
|
557
|
+
if (isKey(first) && typeof second === "function") {
|
|
558
|
+
return getReactiveValueInProxy(this, __privateGet(this, _keyed), first, false).subscribe(
|
|
559
|
+
second
|
|
560
|
+
);
|
|
561
|
+
}
|
|
562
|
+
return typeof first === "function" ? subscribe(this.state, first) : noop;
|
|
563
|
+
}
|
|
564
|
+
/**
|
|
565
|
+
* Update the value _(based on the current value)_
|
|
566
|
+
*/
|
|
567
|
+
update(callback) {
|
|
568
|
+
const updated = callback({ ...this.state.value });
|
|
569
|
+
if (updated == null || isPlainObject$1(updated)) {
|
|
570
|
+
setProxyValue(this.state.value, updated ?? {});
|
|
571
|
+
}
|
|
572
|
+
}
|
|
573
|
+
}
|
|
574
|
+
_keyed = new WeakMap();
|
|
575
|
+
function store(value, options) {
|
|
576
|
+
return new Store(isPlainObject$1(value) ? value : {}, options);
|
|
577
|
+
}
|
|
578
|
+
|
|
579
|
+
function isChildNode(value) {
|
|
580
|
+
return value instanceof Node && childNodeTypes.has(value.nodeType);
|
|
581
|
+
}
|
|
582
|
+
function isHTMLOrSVGElement(value) {
|
|
583
|
+
return value instanceof HTMLElement || value instanceof SVGElement;
|
|
584
|
+
}
|
|
585
|
+
var childNodeTypes = new Set([
|
|
586
|
+
1,
|
|
587
|
+
3,
|
|
588
|
+
7,
|
|
589
|
+
8,
|
|
590
|
+
10
|
|
591
|
+
]);
|
|
592
|
+
|
|
593
|
+
function getString(value) {
|
|
594
|
+
if (typeof value === "string") return value;
|
|
595
|
+
if (value == null) return "";
|
|
596
|
+
if (typeof value !== "object") return String(value);
|
|
597
|
+
const asString = String(value.valueOf?.() ?? value);
|
|
598
|
+
return asString.startsWith("[object ") ? JSON.stringify(value) : asString;
|
|
599
|
+
}
|
|
600
|
+
|
|
601
|
+
function isPlainObject(value) {
|
|
602
|
+
if (value === null || typeof value !== "object") return false;
|
|
603
|
+
if (Symbol.toStringTag in value || Symbol.iterator in value) return false;
|
|
604
|
+
const prototype = Object.getPrototypeOf(value);
|
|
605
|
+
return prototype === null || prototype === Object.prototype || Object.getPrototypeOf(prototype) === null;
|
|
606
|
+
}
|
|
607
|
+
|
|
608
|
+
function isNullableOrWhitespace(value) {
|
|
609
|
+
return value == null || whiteSpaceExpression.test(getString(value));
|
|
610
|
+
}
|
|
611
|
+
var whiteSpaceExpression = /^\s*$/;
|
|
612
|
+
|
|
613
|
+
function isAttribute(value) {
|
|
614
|
+
return value instanceof Attr || isPlainObject(value) && typeof value.name === "string" && typeof value.value === "string";
|
|
615
|
+
}
|
|
616
|
+
function isBadAttribute(first, second) {
|
|
617
|
+
return validateAttribute((attribute) => attribute == null || onPrefix.test(attribute.name) || sourcePrefix.test(attribute.name) && valuePrefix.test(String(attribute.value)), first, second);
|
|
618
|
+
}
|
|
619
|
+
function isBooleanAttribute(value) {
|
|
620
|
+
return validateAttribute((attribute) => attribute != null && booleanAttributes.includes(attribute.name.toLowerCase()), value, "");
|
|
621
|
+
}
|
|
622
|
+
function isEmptyNonBooleanAttribute(first, second) {
|
|
623
|
+
return validateAttribute((attribute) => attribute != null && !booleanAttributes.includes(attribute.name) && String(attribute.value).trim().length === 0, first, second);
|
|
624
|
+
}
|
|
625
|
+
function isInvalidBooleanAttribute(first, second) {
|
|
626
|
+
return validateAttribute((attribute) => {
|
|
627
|
+
if (attribute == null) return true;
|
|
628
|
+
if (!booleanAttributes.includes(attribute.name)) return false;
|
|
629
|
+
const normalized = String(attribute.value).toLowerCase().trim();
|
|
630
|
+
return !(normalized.length === 0 || normalized === attribute.name);
|
|
631
|
+
}, first, second);
|
|
632
|
+
}
|
|
633
|
+
function isProperty(value) {
|
|
634
|
+
return isPlainObject(value) && typeof value.name === "string";
|
|
635
|
+
}
|
|
636
|
+
function setAttribute$1(element, first, second) {
|
|
637
|
+
updateValue(element, first, second, updateAttribute);
|
|
638
|
+
}
|
|
639
|
+
function updateAttribute(element, name, value) {
|
|
640
|
+
if (booleanAttributes.includes(name.toLowerCase())) updateProperty$1(element, name, value);
|
|
641
|
+
else if (value == null) element.removeAttribute(name);
|
|
642
|
+
else element.setAttribute(name, typeof value === "string" ? value : getString(value));
|
|
643
|
+
}
|
|
644
|
+
function updateProperty$1(element, name, value, validate) {
|
|
645
|
+
const actual = name;
|
|
646
|
+
if (actual === "hidden") element.hidden = value === "" || value === true;
|
|
647
|
+
else element[actual] = value === "" || typeof value === "string" && value.toLowerCase() === actual || value === true;
|
|
648
|
+
}
|
|
649
|
+
function updateValue(element, first, second, callback) {
|
|
650
|
+
if (!isHTMLOrSVGElement(element)) return;
|
|
651
|
+
if (isProperty(first)) callback(element, first.name, first.value);
|
|
652
|
+
else if (typeof first === "string") callback(element, first, second);
|
|
653
|
+
}
|
|
654
|
+
function validateAttribute(callback, first, second) {
|
|
655
|
+
let attribute;
|
|
656
|
+
if (isAttribute(first)) attribute = first;
|
|
657
|
+
else if (typeof first === "string" && typeof second === "string") attribute = {
|
|
658
|
+
name: first,
|
|
659
|
+
value: second
|
|
660
|
+
};
|
|
661
|
+
return callback(attribute);
|
|
662
|
+
}
|
|
663
|
+
const booleanAttributes = Object.freeze([
|
|
664
|
+
"async",
|
|
665
|
+
"autofocus",
|
|
666
|
+
"autoplay",
|
|
667
|
+
"checked",
|
|
668
|
+
"controls",
|
|
669
|
+
"default",
|
|
670
|
+
"defer",
|
|
671
|
+
"disabled",
|
|
672
|
+
"formnovalidate",
|
|
673
|
+
"hidden",
|
|
674
|
+
"inert",
|
|
675
|
+
"ismap",
|
|
676
|
+
"itemscope",
|
|
677
|
+
"loop",
|
|
678
|
+
"multiple",
|
|
679
|
+
"muted",
|
|
680
|
+
"nomodule",
|
|
681
|
+
"novalidate",
|
|
682
|
+
"open",
|
|
683
|
+
"playsinline",
|
|
684
|
+
"readonly",
|
|
685
|
+
"required",
|
|
686
|
+
"reversed",
|
|
687
|
+
"selected"
|
|
688
|
+
]);
|
|
689
|
+
var onPrefix = /^on/i;
|
|
690
|
+
var sourcePrefix = /^(href|src|xlink:href)$/i;
|
|
691
|
+
var valuePrefix = /(data:text\/html|javascript:)/i;
|
|
692
|
+
|
|
693
|
+
function getOptions$1(input) {
|
|
694
|
+
const options = isPlainObject(input) ? input : {};
|
|
695
|
+
options.sanitizeBooleanAttributes = typeof options.sanitizeBooleanAttributes === "boolean" ? options.sanitizeBooleanAttributes : true;
|
|
696
|
+
return options;
|
|
697
|
+
}
|
|
698
|
+
function sanitize(value, options) {
|
|
699
|
+
return sanitizeNodes(Array.isArray(value) ? value : [value], getOptions$1(options));
|
|
700
|
+
}
|
|
701
|
+
function sanitizeAttributes(element, attributes, options) {
|
|
702
|
+
const { length } = attributes;
|
|
703
|
+
for (let index = 0; index < length; index += 1) {
|
|
704
|
+
const attribute = attributes[index];
|
|
705
|
+
if (isBadAttribute(attribute) || isEmptyNonBooleanAttribute(attribute)) element.removeAttribute(attribute.name);
|
|
706
|
+
else if (options.sanitizeBooleanAttributes && isInvalidBooleanAttribute(attribute)) element.setAttribute(attribute.name, "");
|
|
707
|
+
}
|
|
708
|
+
}
|
|
709
|
+
function sanitizeNodes(nodes, options) {
|
|
710
|
+
const actual = nodes.filter((node) => node instanceof Node);
|
|
711
|
+
const { length } = nodes;
|
|
712
|
+
for (let index = 0; index < length; index += 1) {
|
|
713
|
+
const node = actual[index];
|
|
714
|
+
if (node instanceof Element) sanitizeAttributes(node, [...node.attributes], options);
|
|
715
|
+
if (node.hasChildNodes()) sanitizeNodes([...node.childNodes], options);
|
|
716
|
+
}
|
|
717
|
+
return nodes;
|
|
718
|
+
}
|
|
719
|
+
|
|
720
|
+
function createTemplate(html$1) {
|
|
721
|
+
const template = document.createElement("template");
|
|
722
|
+
template.innerHTML = html$1;
|
|
723
|
+
templates[html$1] = template;
|
|
724
|
+
return template;
|
|
725
|
+
}
|
|
726
|
+
function getTemplate(value) {
|
|
727
|
+
if (typeof value !== "string" || value.trim().length === 0) return;
|
|
728
|
+
if (value in templates) return templates[value];
|
|
729
|
+
let template;
|
|
730
|
+
if (idPattern.test(value)) template = document.querySelector(`#${value}`);
|
|
731
|
+
templates[value] = template instanceof HTMLTemplateElement ? template : createTemplate(value);
|
|
732
|
+
return templates[value];
|
|
733
|
+
}
|
|
734
|
+
function html$1(value, sanitization) {
|
|
735
|
+
if (typeof value !== "string" && !(value instanceof HTMLTemplateElement)) return [];
|
|
736
|
+
const options = sanitization == null || sanitization === true ? {} : isPlainObject(sanitization) ? { ...sanitization } : null;
|
|
737
|
+
const template = value instanceof HTMLTemplateElement ? value : getTemplate(value);
|
|
738
|
+
if (template == null) return [];
|
|
739
|
+
const cloned = template.content.cloneNode(true);
|
|
740
|
+
const scripts = cloned.querySelectorAll("script");
|
|
741
|
+
const { length } = scripts;
|
|
742
|
+
for (let index = 0; index < length; index += 1) scripts[index].remove();
|
|
743
|
+
cloned.normalize();
|
|
744
|
+
return options != null ? sanitize([...cloned.childNodes], options) : [...cloned.childNodes];
|
|
745
|
+
}
|
|
746
|
+
var idPattern = /^[a-z][\w-]*$/i;
|
|
747
|
+
var templates = {};
|
|
748
|
+
|
|
749
|
+
const controllers = new WeakMap();
|
|
750
|
+
const eventNamePattern = /^@([\w-]+)(?::([a-z:]+))?$/i;
|
|
751
|
+
const reason = 'Event removed as element was removed from document by Abydon';
|
|
752
|
+
function getController(element) {
|
|
753
|
+
let controller = controllers.get(element);
|
|
754
|
+
if (controller == null) {
|
|
755
|
+
controller = new AbortController();
|
|
756
|
+
controllers.set(element, controller);
|
|
757
|
+
}
|
|
758
|
+
return controller;
|
|
759
|
+
}
|
|
760
|
+
function getOptions(options) {
|
|
761
|
+
const parts = options.split(':');
|
|
762
|
+
return {
|
|
763
|
+
capture: parts.includes('c') || parts.includes('capture'),
|
|
764
|
+
once: parts.includes('o') || parts.includes('once'),
|
|
765
|
+
passive: !parts.includes('a') && !parts.includes('active'),
|
|
766
|
+
};
|
|
767
|
+
}
|
|
768
|
+
function mapEvent(element, name, value) {
|
|
769
|
+
element.removeAttribute(name);
|
|
770
|
+
const [, type, options] = eventNamePattern.exec(name) ?? [];
|
|
771
|
+
if (typeof value === 'function' && type != null) {
|
|
772
|
+
element.addEventListener(type, value, {
|
|
773
|
+
...getOptions(options ?? ''),
|
|
774
|
+
signal: getController(element).signal,
|
|
775
|
+
});
|
|
776
|
+
}
|
|
777
|
+
}
|
|
778
|
+
function removeEvents(element) {
|
|
779
|
+
controllers.get(element)?.abort(reason);
|
|
780
|
+
controllers.delete(element);
|
|
781
|
+
}
|
|
782
|
+
|
|
783
|
+
function compareArrays(first, second) {
|
|
784
|
+
const firstIsLarger = first.length > second.length;
|
|
785
|
+
const from = firstIsLarger ? first : second;
|
|
786
|
+
const to = firstIsLarger ? second : first;
|
|
787
|
+
if (!from
|
|
788
|
+
.filter(key => to.includes(key))
|
|
789
|
+
.every((key, index) => to[index] === key)) {
|
|
790
|
+
return 'dissimilar';
|
|
791
|
+
}
|
|
792
|
+
return firstIsLarger ? 'removed' : 'added';
|
|
793
|
+
}
|
|
794
|
+
function isFragment(value) {
|
|
795
|
+
return (typeof value === 'object' &&
|
|
796
|
+
value != null &&
|
|
797
|
+
'$fragment' in value &&
|
|
798
|
+
value.$fragment === true);
|
|
799
|
+
}
|
|
800
|
+
|
|
801
|
+
function createNodes(value) {
|
|
802
|
+
if (isFragment(value)) {
|
|
803
|
+
return value.get();
|
|
804
|
+
}
|
|
805
|
+
if (isChildNode(value)) {
|
|
806
|
+
return [value];
|
|
807
|
+
}
|
|
808
|
+
return [new Text(getString(value))];
|
|
809
|
+
}
|
|
810
|
+
function removeNodes(nodes) {
|
|
811
|
+
sanitiseNodes(nodes);
|
|
812
|
+
const { length } = nodes;
|
|
813
|
+
for (let index = 0; index < length; index += 1) {
|
|
814
|
+
nodes[index].remove();
|
|
815
|
+
}
|
|
816
|
+
}
|
|
817
|
+
function replaceNodes(from, to) {
|
|
818
|
+
from[0]?.replaceWith(...to);
|
|
819
|
+
const { length } = from;
|
|
820
|
+
for (let index = 1; index < length; index += 1) {
|
|
821
|
+
from[index].remove();
|
|
822
|
+
}
|
|
823
|
+
}
|
|
824
|
+
function sanitiseNodes(nodes) {
|
|
825
|
+
const { length } = nodes;
|
|
826
|
+
for (let index = 0; index < length; index += 1) {
|
|
827
|
+
const node = nodes[index];
|
|
828
|
+
if (isHTMLOrSVGElement(node)) {
|
|
829
|
+
removeEvents(node);
|
|
830
|
+
}
|
|
831
|
+
if (node.hasChildNodes()) {
|
|
832
|
+
sanitiseNodes([...node.childNodes]);
|
|
833
|
+
}
|
|
834
|
+
}
|
|
835
|
+
}
|
|
836
|
+
|
|
837
|
+
const classExpression = /^class\./;
|
|
838
|
+
const styleFullExpression = /^style\.([\w-]+)(?:\.([\w-]+))?$/;
|
|
839
|
+
const stylePrefixExpression = /^style\./;
|
|
840
|
+
function setAttribute(data, element, name, value) {
|
|
841
|
+
element.removeAttribute(name);
|
|
842
|
+
switch (true) {
|
|
843
|
+
case classExpression.test(name):
|
|
844
|
+
setClasses(data, element, name, value);
|
|
845
|
+
return;
|
|
846
|
+
case stylePrefixExpression.test(name):
|
|
847
|
+
setStyle(data, element, name, value);
|
|
848
|
+
return;
|
|
849
|
+
default:
|
|
850
|
+
setValue(data, element, name, value);
|
|
851
|
+
break;
|
|
852
|
+
}
|
|
853
|
+
}
|
|
854
|
+
function setClasses(data, element, name, value) {
|
|
855
|
+
function update(value) {
|
|
856
|
+
if (value === true) {
|
|
857
|
+
element.classList.add(...classes);
|
|
858
|
+
}
|
|
859
|
+
else {
|
|
860
|
+
element.classList.remove(...classes);
|
|
861
|
+
}
|
|
862
|
+
}
|
|
863
|
+
const classes = name.slice(6).split('.');
|
|
864
|
+
if (isReactive(value)) {
|
|
865
|
+
data.mora.subscribers.add(value.subscribe(update));
|
|
866
|
+
}
|
|
867
|
+
else {
|
|
868
|
+
update(value);
|
|
869
|
+
}
|
|
870
|
+
}
|
|
871
|
+
function setStyle(data, element, name, value) {
|
|
872
|
+
function update(value) {
|
|
873
|
+
if (value == null || value === false || (value === true && unit == null)) {
|
|
874
|
+
element.style.removeProperty(property);
|
|
875
|
+
}
|
|
876
|
+
else {
|
|
877
|
+
element.style.setProperty(property, value === true ? unit : getString(value));
|
|
878
|
+
}
|
|
879
|
+
}
|
|
880
|
+
const [, property, unit] = styleFullExpression.exec(name) ?? [];
|
|
881
|
+
if (property != null) {
|
|
882
|
+
if (isReactive(value)) {
|
|
883
|
+
data.mora.subscribers.add(value.subscribe(update));
|
|
884
|
+
}
|
|
885
|
+
else {
|
|
886
|
+
update(value);
|
|
887
|
+
}
|
|
888
|
+
}
|
|
889
|
+
}
|
|
890
|
+
function setValue(data, element, name, value) {
|
|
891
|
+
const callback = isBooleanAttribute(name) && name in element
|
|
892
|
+
? name === 'selected'
|
|
893
|
+
? updateSelected
|
|
894
|
+
: updateProperty
|
|
895
|
+
: setAttribute$1;
|
|
896
|
+
if (isReactive(value)) {
|
|
897
|
+
data.mora.subscribers.add(value.subscribe(next => {
|
|
898
|
+
callback(element, name, next);
|
|
899
|
+
}));
|
|
900
|
+
}
|
|
901
|
+
else {
|
|
902
|
+
callback(element, name, value);
|
|
903
|
+
}
|
|
904
|
+
}
|
|
905
|
+
function triggerSelectChange(select) {
|
|
906
|
+
if (select != null) {
|
|
907
|
+
select.dispatchEvent(new Event('change', { bubbles: true }));
|
|
908
|
+
}
|
|
909
|
+
}
|
|
910
|
+
function updateProperty(element, name, value) {
|
|
911
|
+
element[name] = value === true;
|
|
912
|
+
}
|
|
913
|
+
function updateSelected(element, name, value) {
|
|
914
|
+
const select = element.closest('select');
|
|
915
|
+
const options = [...(select?.options ?? [])];
|
|
916
|
+
if (select != null && options.includes(element)) {
|
|
917
|
+
triggerSelectChange(select);
|
|
918
|
+
}
|
|
919
|
+
updateProperty(element, name, value);
|
|
920
|
+
}
|
|
921
|
+
|
|
922
|
+
const commentExpression$1 = /^<!--abydon\.(\d+)-->$/;
|
|
923
|
+
function getValue(data, original) {
|
|
924
|
+
const matches = commentExpression$1.exec(original ?? '');
|
|
925
|
+
return matches == null ? original : data.values[+matches[1]];
|
|
926
|
+
}
|
|
927
|
+
function mapAttributes(data, element) {
|
|
928
|
+
const attributes = [...element.attributes];
|
|
929
|
+
const { length } = attributes;
|
|
930
|
+
for (let index = 0; index < length; index += 1) {
|
|
931
|
+
const { name, value } = attributes[index];
|
|
932
|
+
const actual = getValue(data, value);
|
|
933
|
+
if (name.startsWith('@')) {
|
|
934
|
+
mapEvent(element, name, actual);
|
|
935
|
+
}
|
|
936
|
+
else if (name.includes('.') ||
|
|
937
|
+
typeof value === 'function' ||
|
|
938
|
+
isReactive(actual)) {
|
|
939
|
+
mapValue$1(data, element, name, actual);
|
|
940
|
+
}
|
|
941
|
+
}
|
|
942
|
+
}
|
|
943
|
+
function mapValue$1(data, element, name, value) {
|
|
944
|
+
switch (true) {
|
|
945
|
+
case typeof value === 'function':
|
|
946
|
+
setComputedAttribute(data, element, name, value);
|
|
947
|
+
break;
|
|
948
|
+
default:
|
|
949
|
+
setAttribute(data, element, name, value);
|
|
950
|
+
break;
|
|
951
|
+
}
|
|
952
|
+
}
|
|
953
|
+
function setComputedAttribute(data, element, name, callback) {
|
|
954
|
+
const value = computed(callback);
|
|
955
|
+
data.mora.values.add(value);
|
|
956
|
+
setAttribute(data, element, name, value);
|
|
957
|
+
}
|
|
958
|
+
|
|
959
|
+
function removeFragments(fragments) {
|
|
960
|
+
if (fragments != null) {
|
|
961
|
+
const { length } = fragments;
|
|
962
|
+
for (let index = 0; index < length; index += 1) {
|
|
963
|
+
fragments[index].remove();
|
|
964
|
+
}
|
|
965
|
+
}
|
|
966
|
+
}
|
|
967
|
+
function setArray(fragments, nodes, comment, text, value) {
|
|
968
|
+
if (value.length === 0) {
|
|
969
|
+
return {
|
|
970
|
+
nodes: setText(fragments, nodes, comment, text, value),
|
|
971
|
+
};
|
|
972
|
+
}
|
|
973
|
+
let templates = value.filter(item => isFragment(item) && item.identifier != null);
|
|
974
|
+
const identifiers = templates.map(fragment => fragment.identifier);
|
|
975
|
+
const oldIdentifiers = fragments?.map(fragment => fragment.identifier) ?? [];
|
|
976
|
+
if (new Set(identifiers).size !== templates.length) {
|
|
977
|
+
templates = [];
|
|
978
|
+
}
|
|
979
|
+
const noTemplates = templates.length === 0;
|
|
980
|
+
if (noTemplates ||
|
|
981
|
+
nodes == null ||
|
|
982
|
+
oldIdentifiers.some(identifier => identifier == null)) {
|
|
983
|
+
return {
|
|
984
|
+
fragments: noTemplates ? undefined : templates,
|
|
985
|
+
nodes: setNodes(fragments, nodes, comment, text, noTemplates
|
|
986
|
+
? value.flatMap(item => createNodes(item))
|
|
987
|
+
: templates.flatMap(template => template.get())),
|
|
988
|
+
};
|
|
989
|
+
}
|
|
990
|
+
const next = templates.map(template => fragments?.find(fragment => fragment.identifier === template.identifier) ?? template);
|
|
991
|
+
const comparison = compareArrays(fragments ?? [], templates);
|
|
992
|
+
if (comparison !== 'removed') {
|
|
993
|
+
let position = nodes[0];
|
|
994
|
+
const before = comparison === 'added' &&
|
|
995
|
+
!oldIdentifiers.includes(templates[0].identifier);
|
|
996
|
+
const items = next.flatMap(fragment => fragment.get().flatMap(node => ({
|
|
997
|
+
identifier: fragment.identifier,
|
|
998
|
+
value: node,
|
|
999
|
+
})));
|
|
1000
|
+
const { length } = items;
|
|
1001
|
+
for (let index = 0; index < length; index += 1) {
|
|
1002
|
+
const item = items[index];
|
|
1003
|
+
if (comparison === 'dissimilar' ||
|
|
1004
|
+
!oldIdentifiers.includes(item.identifier)) {
|
|
1005
|
+
if (index === 0 && before) {
|
|
1006
|
+
position.before(item.value);
|
|
1007
|
+
}
|
|
1008
|
+
else {
|
|
1009
|
+
position.after(item.value);
|
|
1010
|
+
}
|
|
1011
|
+
}
|
|
1012
|
+
position = item.value;
|
|
1013
|
+
}
|
|
1014
|
+
}
|
|
1015
|
+
const toRemove = fragments?.filter(fragment => !identifiers.includes(fragment.identifier)) ?? [];
|
|
1016
|
+
const { length } = toRemove;
|
|
1017
|
+
for (let index = 0; index < length; index += 1) {
|
|
1018
|
+
toRemove[index].remove();
|
|
1019
|
+
}
|
|
1020
|
+
return {
|
|
1021
|
+
fragments: next,
|
|
1022
|
+
nodes: next.flatMap(fragment => fragment.get()),
|
|
1023
|
+
};
|
|
1024
|
+
}
|
|
1025
|
+
function setNodes(fragments, nodes, comment, text, next) {
|
|
1026
|
+
if (nodes == null) {
|
|
1027
|
+
if (comment.parentNode != null) {
|
|
1028
|
+
replaceNodes([comment], next);
|
|
1029
|
+
}
|
|
1030
|
+
else if (text.parentNode != null) {
|
|
1031
|
+
replaceNodes([text], next);
|
|
1032
|
+
}
|
|
1033
|
+
}
|
|
1034
|
+
else {
|
|
1035
|
+
replaceNodes(nodes, next);
|
|
1036
|
+
}
|
|
1037
|
+
removeFragments(fragments);
|
|
1038
|
+
return next;
|
|
1039
|
+
}
|
|
1040
|
+
function setReactiveValue(data, comment, reactive) {
|
|
1041
|
+
const item = data.items.find(item => item.nodes.includes(comment));
|
|
1042
|
+
const text = new Text();
|
|
1043
|
+
let fragments;
|
|
1044
|
+
let nodes;
|
|
1045
|
+
data.mora.subscribers.add(reactive.subscribe(value => {
|
|
1046
|
+
if (Array.isArray(value)) {
|
|
1047
|
+
const result = setArray(fragments, nodes, comment, text, value);
|
|
1048
|
+
fragments = typeof result === 'boolean' ? undefined : result?.fragments;
|
|
1049
|
+
nodes =
|
|
1050
|
+
typeof result === 'boolean'
|
|
1051
|
+
? result
|
|
1052
|
+
? [text]
|
|
1053
|
+
: undefined
|
|
1054
|
+
: result?.nodes;
|
|
1055
|
+
}
|
|
1056
|
+
else {
|
|
1057
|
+
const valueIsFragment = isFragment(value);
|
|
1058
|
+
fragments = valueIsFragment ? [value] : undefined;
|
|
1059
|
+
if (valueIsFragment || isChildNode(value)) {
|
|
1060
|
+
nodes = setNodes(fragments, nodes, comment, text, createNodes(value));
|
|
1061
|
+
}
|
|
1062
|
+
else {
|
|
1063
|
+
nodes = setText(fragments, nodes, comment, text, value);
|
|
1064
|
+
}
|
|
1065
|
+
}
|
|
1066
|
+
if (item != null) {
|
|
1067
|
+
item.fragments = fragments;
|
|
1068
|
+
item.nodes = [...(nodes ?? [comment])];
|
|
1069
|
+
}
|
|
1070
|
+
}));
|
|
1071
|
+
}
|
|
1072
|
+
function setText(fragments, nodes, comment, text, value) {
|
|
1073
|
+
const isNullable = isNullableOrWhitespace(value);
|
|
1074
|
+
text.textContent = isNullable ? '' : getString(value);
|
|
1075
|
+
let result = false;
|
|
1076
|
+
if (nodes != null) {
|
|
1077
|
+
replaceNodes(nodes, [isNullable ? comment : text]);
|
|
1078
|
+
result = !isNullable;
|
|
1079
|
+
}
|
|
1080
|
+
else if (isNullable && comment.parentNode == null) {
|
|
1081
|
+
text.replaceWith(comment);
|
|
1082
|
+
}
|
|
1083
|
+
else if (!isNullable && text.parentNode == null) {
|
|
1084
|
+
comment.replaceWith(text);
|
|
1085
|
+
result = true;
|
|
1086
|
+
}
|
|
1087
|
+
removeFragments(fragments);
|
|
1088
|
+
return result ? [text] : undefined;
|
|
1089
|
+
}
|
|
1090
|
+
|
|
1091
|
+
const commentExpression = /^abydon\.(\d+)$/;
|
|
1092
|
+
function mapNode(data, comment) {
|
|
1093
|
+
const matches = commentExpression.exec(comment.textContent ?? '');
|
|
1094
|
+
const value = matches == null ? null : data.values[+matches[1]];
|
|
1095
|
+
if (value != null) {
|
|
1096
|
+
mapValue(data, comment, value);
|
|
1097
|
+
}
|
|
1098
|
+
}
|
|
1099
|
+
function mapNodes(data, nodes) {
|
|
1100
|
+
const { length } = nodes;
|
|
1101
|
+
for (let index = 0; index < length; index += 1) {
|
|
1102
|
+
const node = nodes[index];
|
|
1103
|
+
if (node instanceof Comment) {
|
|
1104
|
+
mapNode(data, node);
|
|
1105
|
+
continue;
|
|
1106
|
+
}
|
|
1107
|
+
if (isHTMLOrSVGElement(node)) {
|
|
1108
|
+
mapAttributes(data, node);
|
|
1109
|
+
}
|
|
1110
|
+
if (node.hasChildNodes()) {
|
|
1111
|
+
mapNodes(data, [...node.childNodes]);
|
|
1112
|
+
}
|
|
1113
|
+
}
|
|
1114
|
+
}
|
|
1115
|
+
function mapValue(data, comment, value) {
|
|
1116
|
+
switch (true) {
|
|
1117
|
+
case typeof value === 'function':
|
|
1118
|
+
setComputedValue(data, comment, value);
|
|
1119
|
+
break;
|
|
1120
|
+
case isReactive(value):
|
|
1121
|
+
setReactiveValue(data, comment, value);
|
|
1122
|
+
break;
|
|
1123
|
+
default:
|
|
1124
|
+
replaceComment(data, comment, value);
|
|
1125
|
+
break;
|
|
1126
|
+
}
|
|
1127
|
+
}
|
|
1128
|
+
function replaceComment(data, comment, value) {
|
|
1129
|
+
const item = data.items.find(item => item.nodes.includes(comment));
|
|
1130
|
+
const nodes = createNodes(value);
|
|
1131
|
+
if (item != null) {
|
|
1132
|
+
item.fragments = isFragment(value) ? [value] : undefined;
|
|
1133
|
+
item.nodes = nodes;
|
|
1134
|
+
}
|
|
1135
|
+
comment.replaceWith(...nodes);
|
|
1136
|
+
}
|
|
1137
|
+
function setComputedValue(data, comment, callback) {
|
|
1138
|
+
const value = computed(callback);
|
|
1139
|
+
data.mora.values.add(value);
|
|
1140
|
+
setReactiveValue(data, comment, value);
|
|
1141
|
+
}
|
|
1142
|
+
|
|
1143
|
+
function handleExpression(data, prefix, expression) {
|
|
1144
|
+
if (Array.isArray(expression)) {
|
|
1145
|
+
const { length } = expression;
|
|
1146
|
+
let expressions = '';
|
|
1147
|
+
for (let index = 0; index < length; index += 1) {
|
|
1148
|
+
expressions += handleExpression(data, '', expression[index]);
|
|
1149
|
+
}
|
|
1150
|
+
return `${prefix}${expressions}`;
|
|
1151
|
+
}
|
|
1152
|
+
if (typeof expression === 'function' ||
|
|
1153
|
+
(typeof expression === 'object' && expression != null)) {
|
|
1154
|
+
const index = data.values.push(expression) - 1;
|
|
1155
|
+
return `${prefix}<!--abydon.${index}-->`;
|
|
1156
|
+
}
|
|
1157
|
+
return isNullableOrWhitespace(expression) ? prefix : `${prefix}${expression}`;
|
|
1158
|
+
}
|
|
1159
|
+
function parse(data) {
|
|
1160
|
+
const { length } = data.strings;
|
|
1161
|
+
let template = '';
|
|
1162
|
+
for (let index = 0; index < length; index += 1) {
|
|
1163
|
+
template += handleExpression(data, data.strings[index], data.expressions[index]);
|
|
1164
|
+
}
|
|
1165
|
+
return template;
|
|
1166
|
+
}
|
|
1167
|
+
|
|
1168
|
+
class Fragment {
|
|
1169
|
+
$fragment = true;
|
|
1170
|
+
data;
|
|
1171
|
+
get identifier() {
|
|
1172
|
+
return this.data.identifier;
|
|
1173
|
+
}
|
|
1174
|
+
constructor(strings, expressions) {
|
|
1175
|
+
this.data = {
|
|
1176
|
+
expressions,
|
|
1177
|
+
strings,
|
|
1178
|
+
items: [],
|
|
1179
|
+
mora: {
|
|
1180
|
+
subscribers: new Set(),
|
|
1181
|
+
values: new Set(),
|
|
1182
|
+
},
|
|
1183
|
+
values: [],
|
|
1184
|
+
};
|
|
1185
|
+
}
|
|
1186
|
+
/**
|
|
1187
|
+
* Appends the fragment to the given element
|
|
1188
|
+
*/
|
|
1189
|
+
appendTo(element) {
|
|
1190
|
+
element.append(...this.get());
|
|
1191
|
+
}
|
|
1192
|
+
/**
|
|
1193
|
+
* Gets a list of the fragment's nodes
|
|
1194
|
+
*/
|
|
1195
|
+
get() {
|
|
1196
|
+
if (this.data.items.length === 0) {
|
|
1197
|
+
const parsed = parse(this.data);
|
|
1198
|
+
const templated = html$1(parsed, {
|
|
1199
|
+
sanitizeBooleanAttributes: false,
|
|
1200
|
+
});
|
|
1201
|
+
this.data.items.splice(0, this.data.items.length, ...templated.map(node => ({
|
|
1202
|
+
nodes: [node],
|
|
1203
|
+
})));
|
|
1204
|
+
mapNodes(this.data, this.data.items.flatMap(item => item.fragments?.flatMap(fragment => fragment.get()) ?? item.nodes));
|
|
1205
|
+
}
|
|
1206
|
+
return [
|
|
1207
|
+
...this.data.items.flatMap(item => item.fragments?.flatMap(fragment => fragment.get()) ?? item.nodes),
|
|
1208
|
+
];
|
|
1209
|
+
}
|
|
1210
|
+
identify(identifier) {
|
|
1211
|
+
this.data.identifier = identifier;
|
|
1212
|
+
return this;
|
|
1213
|
+
}
|
|
1214
|
+
/**
|
|
1215
|
+
* Removes the fragment from the DOM
|
|
1216
|
+
*/
|
|
1217
|
+
remove() {
|
|
1218
|
+
removeFragment(this.data);
|
|
1219
|
+
}
|
|
1220
|
+
}
|
|
1221
|
+
function removeFragment(data) {
|
|
1222
|
+
removeMora(data);
|
|
1223
|
+
const { length } = data.items;
|
|
1224
|
+
for (let index = 0; index < length; index += 1) {
|
|
1225
|
+
const { fragments, nodes } = data.items[index];
|
|
1226
|
+
const { length } = fragments ?? [];
|
|
1227
|
+
for (let index = 0; index < length; index += 1) {
|
|
1228
|
+
fragments?.[index]?.remove();
|
|
1229
|
+
}
|
|
1230
|
+
removeNodes(nodes);
|
|
1231
|
+
}
|
|
1232
|
+
data.items.splice(0, length);
|
|
1233
|
+
}
|
|
1234
|
+
function removeMora(data) {
|
|
1235
|
+
const unsubscribers = [...data.mora.subscribers];
|
|
1236
|
+
data.mora.subscribers.clear();
|
|
1237
|
+
data.mora.values.clear();
|
|
1238
|
+
for (const unsubscribe of unsubscribers) {
|
|
1239
|
+
unsubscribe();
|
|
1240
|
+
}
|
|
1241
|
+
}
|
|
1242
|
+
|
|
1243
|
+
function html(strings, ...values) {
|
|
1244
|
+
return new Fragment(strings, values);
|
|
1245
|
+
}
|
|
1246
|
+
|
|
1247
|
+
export { array, computed, effect, html, isArray, isComputed, isEffect, isReactive, isSignal, signal, startBatch, stopBatch, store };
|