@kitlangton/knobs 0.2.0 → 0.3.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/README.md +135 -17
- package/dist/dev/{chunk-gezhc24g.js → chunk-7xgkerd2.js} +14 -5
- package/dist/dev/{chunk-5cr85vv6.js → chunk-jx1ktap3.js} +7843 -7933
- package/dist/dev/{chunk-693jd1gj.js → chunk-pmkvb9ep.js} +1544 -160
- package/dist/dev/{chunk-4km87zfx.js → chunk-v8ssbcbk.js} +18 -7
- package/dist/dev/index.js +187 -31
- package/dist/index.js +197 -33
- package/dist/panel.js +20260 -18462
- package/dist/types/core/keys.d.ts +2 -0
- package/dist/types/core/remote.d.ts +2 -0
- package/dist/types/core/schema.d.ts +5 -0
- package/dist/types/core/store.d.ts +29 -2
- package/dist/types/core/unlock.d.ts +77 -0
- package/dist/types/index.d.ts +1 -0
- package/dist/types/panel/attach.d.ts +2 -0
- package/dist/types/panel/crumbs.d.ts +19 -0
- package/dist/types/panel/editors.d.ts +9 -0
- package/dist/types/panel/feel.d.ts +103 -0
- package/dist/types/panel/give.d.ts +34 -1
- package/dist/types/panel/gpu/color.d.ts +4 -4
- package/dist/types/panel/gpu/renderer.d.ts +32 -0
- package/dist/types/panel/gpu/shader.wgsl.d.ts +1 -1
- package/dist/types/panel/index.d.ts +2 -1
- package/dist/types/panel/inspector.d.ts +1 -1
- package/dist/types/panel/lens.d.ts +113 -0
- package/dist/types/panel/motion.d.ts +2 -0
- package/dist/types/panel/page-hints.d.ts +2 -1
- package/dist/types/panel/prefs.d.ts +2 -2
- package/dist/types/panel/presence.d.ts +20 -0
- package/dist/types/panel/scope.d.ts +29 -0
- package/dist/types/panel/slider.d.ts +21 -4
- package/dist/types/panel/tab-transition.d.ts +15 -0
- package/dist/types/panel/tabs.d.ts +1 -1
- package/dist/types/panel/toggle.d.ts +27 -0
- package/dist/types/ui/look.d.ts +1 -1
- package/dist/types/ui/scrollbar.d.ts +12 -0
- package/dist/types/ui/split-model.d.ts +4 -3
- package/dist/types/ui/split.d.ts +8 -6
- package/dist/ui-react.js +232 -132
- package/dist/ui-solid.js +232 -132
- package/dist/ui.js +285 -174
- package/package.json +1 -1
|
@@ -1,12 +1,13 @@
|
|
|
1
1
|
import {
|
|
2
2
|
__preload
|
|
3
|
-
} from "./chunk-
|
|
3
|
+
} from "./chunk-7xgkerd2.js";
|
|
4
4
|
import {
|
|
5
5
|
iconSvg,
|
|
6
6
|
readSession,
|
|
7
7
|
writeSession,
|
|
8
|
-
injectStyles
|
|
9
|
-
|
|
8
|
+
injectStyles,
|
|
9
|
+
toggleLayer
|
|
10
|
+
} from "./chunk-pmkvb9ep.js";
|
|
10
11
|
|
|
11
12
|
// src/panel/attach.ts
|
|
12
13
|
function attach(controls, element, options = {}) {
|
|
@@ -32,11 +33,11 @@ function attach(controls, element, options = {}) {
|
|
|
32
33
|
let addedTabIndex = !element.hasAttribute("tabindex") && !element.matches("a[href],button,input,select,textarea");
|
|
33
34
|
if (addedTabIndex)
|
|
34
35
|
element.tabIndex = 0;
|
|
35
|
-
let hovered = element.matches(":hover"), disposed = !1, loading = !1, panel, leaving, revealed = () => reveal !== "shortcut" || knobsMode(win), position = () => {
|
|
36
|
+
let hovered = element.matches(":hover"), disposed = !1, loading = !1, panel, leaving, toggledOn = !0, revealed = () => reveal !== "shortcut" || knobsMode(win), position = () => {
|
|
36
37
|
let box = element.getBoundingClientRect();
|
|
37
38
|
chip.style.left = `${Math.max(4, Math.min(win.innerWidth - chip.offsetWidth - 4, box.right - chip.offsetWidth - 6))}px`, chip.style.top = `${Math.max(4, box.top + 6)}px`;
|
|
38
39
|
}, update = () => {
|
|
39
|
-
let shown = controls.enabled && revealed() && !panel && (reveal === "always" || hovered || element.contains(doc.activeElement) || doc.activeElement === chip);
|
|
40
|
+
let shown = controls.enabled && toggledOn && revealed() && !panel && (reveal === "always" || hovered || element.contains(doc.activeElement) || doc.activeElement === chip);
|
|
40
41
|
if (shown)
|
|
41
42
|
position();
|
|
42
43
|
if (setShown(shown), !controls.enabled)
|
|
@@ -82,7 +83,7 @@ function attach(controls, element, options = {}) {
|
|
|
82
83
|
return;
|
|
83
84
|
loading = !0;
|
|
84
85
|
try {
|
|
85
|
-
let { createPanel } = await (__preload("
|
|
86
|
+
let { createPanel } = await (__preload("jx1ktap3"), import("./chunk-jx1ktap3.js"));
|
|
86
87
|
if (disposed || !controls.enabled || panel)
|
|
87
88
|
return;
|
|
88
89
|
if (panel = createPanel(controls, element, close, { restored, chip }), remember)
|
|
@@ -105,9 +106,19 @@ function attach(controls, element, options = {}) {
|
|
|
105
106
|
update();
|
|
106
107
|
}, offShortcut = reveal === "shortcut" ? listenForShortcut(win, shortcut, controls.theme) : void 0;
|
|
107
108
|
win.addEventListener(MODE_EVENT, onMode);
|
|
109
|
+
let toggled = controls.toggleKey ? toggleLayer(doc).register({
|
|
110
|
+
id: controls.id,
|
|
111
|
+
key: controls.toggleKey,
|
|
112
|
+
storage: () => controls.storage,
|
|
113
|
+
root: chip,
|
|
114
|
+
show: (shown) => {
|
|
115
|
+
toggledOn = shown, update();
|
|
116
|
+
}
|
|
117
|
+
}) : void 0;
|
|
118
|
+
toggledOn = toggled?.shown ?? !0;
|
|
108
119
|
let unsubscribe = controls.subscribe(update);
|
|
109
120
|
return update(), () => {
|
|
110
|
-
disposed = !0, unsubscribe(), panel?.dispose(), leaving?.dispose(), observer.disconnect(), offShortcut?.(), win.removeEventListener(MODE_EVENT, onMode), win.removeEventListener("scroll", position, !0), win.removeEventListener("resize", position);
|
|
121
|
+
disposed = !0, toggled?.dispose(), unsubscribe(), panel?.dispose(), leaving?.dispose(), observer.disconnect(), offShortcut?.(), win.removeEventListener(MODE_EVENT, onMode), win.removeEventListener("scroll", position, !0), win.removeEventListener("resize", position);
|
|
111
122
|
for (let node of [element, chip])
|
|
112
123
|
node.removeEventListener("pointerenter", enter), node.removeEventListener("pointerleave", leave), node.removeEventListener("focusin", update), node.removeEventListener("focusout", focusOut);
|
|
113
124
|
if (chip.remove(), addedTabIndex && element.getAttribute("tabindex") === "0")
|
package/dist/dev/index.js
CHANGED
|
@@ -15,6 +15,7 @@ import {
|
|
|
15
15
|
matchesCombo2,
|
|
16
16
|
comboParts2,
|
|
17
17
|
comboLabel2,
|
|
18
|
+
isTypingTarget,
|
|
18
19
|
sampleGradient2,
|
|
19
20
|
gradientCss2,
|
|
20
21
|
sampleCurve2,
|
|
@@ -72,8 +73,8 @@ import {
|
|
|
72
73
|
browserStorage,
|
|
73
74
|
urlFlag2,
|
|
74
75
|
storageKey
|
|
75
|
-
} from "./chunk-
|
|
76
|
-
__chunks(import.meta.url,["
|
|
76
|
+
} from "./chunk-7xgkerd2.js";
|
|
77
|
+
__chunks(import.meta.url,["8qt6yygv","jx1ktap3","v8ssbcbk","7xgkerd2","pmkvb9ep"],[["./index.js",3],["./chunk-jx1ktap3.js",3,4],["./chunk-v8ssbcbk.js",3,4],["./chunk-7xgkerd2.js"],["./chunk-pmkvb9ep.js",3]],0);
|
|
77
78
|
// src/core/random.ts
|
|
78
79
|
var lattice = (min, max, step, r) => min + Math.floor(r * (Math.floor((max - min) / step + 0.000000001) + 1)) * step, between = (min, max, r) => min + (max - min) * r;
|
|
79
80
|
function pick(field, random) {
|
|
@@ -337,6 +338,143 @@ function mutateValues(schema, current, keys = valueKeys(schema), random = Math.r
|
|
|
337
338
|
return out;
|
|
338
339
|
}
|
|
339
340
|
|
|
341
|
+
// src/core/unlock.ts
|
|
342
|
+
var KONAMI = Object.freeze([
|
|
343
|
+
"ArrowUp",
|
|
344
|
+
"ArrowUp",
|
|
345
|
+
"ArrowDown",
|
|
346
|
+
"ArrowDown",
|
|
347
|
+
"ArrowLeft",
|
|
348
|
+
"ArrowRight",
|
|
349
|
+
"ArrowLeft",
|
|
350
|
+
"ArrowRight",
|
|
351
|
+
"b",
|
|
352
|
+
"a"
|
|
353
|
+
]), GATE = Symbol.for("knobs.unlock.v1"), gate = () => {
|
|
354
|
+
let holder = globalThis;
|
|
355
|
+
return holder[GATE] ??= { unlocked: !1, listeners: /* @__PURE__ */ new Set };
|
|
356
|
+
}, isUnlocked = () => globalThis[GATE]?.unlocked ?? !1;
|
|
357
|
+
function onUnlock(listener) {
|
|
358
|
+
let listeners = gate().listeners;
|
|
359
|
+
return listeners.add(listener), () => void listeners.delete(listener);
|
|
360
|
+
}
|
|
361
|
+
var UNLOCK_KEY = "knobs:unlocked";
|
|
362
|
+
function sequenceKeys(sequence) {
|
|
363
|
+
return typeof sequence === "string" ? [...sequence] : [...sequence];
|
|
364
|
+
}
|
|
365
|
+
var fold = (key) => key.length === 1 ? key.toLowerCase() : key;
|
|
366
|
+
function sequenceMatcher(sequence, gap = 1500) {
|
|
367
|
+
let want = sequenceKeys(sequence).map(fold), typed = [], last = -1 / 0;
|
|
368
|
+
return (key, at) => {
|
|
369
|
+
if (!want.length)
|
|
370
|
+
return !1;
|
|
371
|
+
if (at - last > gap)
|
|
372
|
+
typed = [];
|
|
373
|
+
if (last = at, typed.push(fold(key)), typed.length > want.length)
|
|
374
|
+
typed.shift();
|
|
375
|
+
if (typed.length === want.length && typed.every((k, i) => k === want[i]))
|
|
376
|
+
return typed = [], !0;
|
|
377
|
+
return !1;
|
|
378
|
+
};
|
|
379
|
+
}
|
|
380
|
+
function queryUnlock(search, name) {
|
|
381
|
+
let params = new URLSearchParams(search);
|
|
382
|
+
if (!params.has(name))
|
|
383
|
+
return;
|
|
384
|
+
return !["off", "0", "false", "lock", "no"].includes((params.get(name) ?? "").toLowerCase());
|
|
385
|
+
}
|
|
386
|
+
function resolveUnlock(input) {
|
|
387
|
+
let unlocked = input.query ?? (input.persist && input.stored);
|
|
388
|
+
return { unlocked, remember: input.persist && input.query !== void 0 ? unlocked : void 0 };
|
|
389
|
+
}
|
|
390
|
+
function inCorner(x, y, width, height, corner, size = 48) {
|
|
391
|
+
let left = corner.endsWith("left") ? x <= size : x >= width - size, top = corner.startsWith("top") ? y <= size : y >= height - size;
|
|
392
|
+
return left && top;
|
|
393
|
+
}
|
|
394
|
+
function tapCounter(count = 3, within = 500) {
|
|
395
|
+
let taps = 0, last = -1 / 0;
|
|
396
|
+
return (at) => {
|
|
397
|
+
if (taps = at - last <= within ? taps + 1 : 1, last = at, taps < count)
|
|
398
|
+
return !1;
|
|
399
|
+
return taps = 0, !0;
|
|
400
|
+
};
|
|
401
|
+
}
|
|
402
|
+
var readStored = () => {
|
|
403
|
+
try {
|
|
404
|
+
return globalThis.localStorage?.getItem(UNLOCK_KEY) === "1";
|
|
405
|
+
} catch {
|
|
406
|
+
return !1;
|
|
407
|
+
}
|
|
408
|
+
}, writeStored = (on) => {
|
|
409
|
+
try {
|
|
410
|
+
if (on)
|
|
411
|
+
globalThis.localStorage?.setItem(UNLOCK_KEY, "1");
|
|
412
|
+
else
|
|
413
|
+
globalThis.localStorage?.removeItem(UNLOCK_KEY);
|
|
414
|
+
} catch {}
|
|
415
|
+
};
|
|
416
|
+
function unlock(options) {
|
|
417
|
+
let g = gate();
|
|
418
|
+
g.panel = options.panel;
|
|
419
|
+
let persist = options.persist !== !1, query = options.query === void 0 ? "knobs" : options.query, sequence = options.sequence === void 0 ? "knobs" : options.sequence, corner = options.corner === void 0 ? "top-right" : options.corner, win = typeof window > "u" ? void 0 : window, announce = (text) => {
|
|
420
|
+
(g.module ? Promise.resolve(g.module) : g.panel?.())?.then((m) => {
|
|
421
|
+
if (g.module = m, g.unlocked === (text === "knobs unlocked"))
|
|
422
|
+
m.status?.(text);
|
|
423
|
+
}).catch(() => {});
|
|
424
|
+
}, set = (on, say) => {
|
|
425
|
+
if (persist)
|
|
426
|
+
writeStored(on);
|
|
427
|
+
if (g.unlocked === on)
|
|
428
|
+
return;
|
|
429
|
+
g.unlocked = on;
|
|
430
|
+
for (let listener of [...g.listeners])
|
|
431
|
+
listener();
|
|
432
|
+
if (say)
|
|
433
|
+
announce(on ? "knobs unlocked" : "knobs locked");
|
|
434
|
+
}, start = resolveUnlock({
|
|
435
|
+
query: query && win ? queryUnlock(win.location.search, query) : void 0,
|
|
436
|
+
stored: persist && readStored(),
|
|
437
|
+
persist
|
|
438
|
+
});
|
|
439
|
+
if (start.remember !== void 0)
|
|
440
|
+
writeStored(start.remember);
|
|
441
|
+
set(start.unlocked || g.unlocked, !1);
|
|
442
|
+
let offs = [];
|
|
443
|
+
if (win && sequence !== !1 && sequenceKeys(sequence).length) {
|
|
444
|
+
let typed = sequenceMatcher(sequence), onKey = (event) => {
|
|
445
|
+
if (event.ctrlKey || event.metaKey || event.altKey || event.isComposing || event.repeat)
|
|
446
|
+
return;
|
|
447
|
+
if (event.key === "Shift" || event.key === "CapsLock" || isTypingTarget(event.target))
|
|
448
|
+
return;
|
|
449
|
+
if (typed(event.key, event.timeStamp || performance.now()))
|
|
450
|
+
set(!g.unlocked, !0);
|
|
451
|
+
};
|
|
452
|
+
win.addEventListener("keydown", onKey, !0), offs.push(() => win.removeEventListener("keydown", onKey, !0));
|
|
453
|
+
}
|
|
454
|
+
if (win && corner) {
|
|
455
|
+
let tapped = tapCounter(), onTap = (event) => {
|
|
456
|
+
if (!event.isPrimary)
|
|
457
|
+
return;
|
|
458
|
+
if (!inCorner(event.clientX, event.clientY, win.innerWidth, win.innerHeight, corner))
|
|
459
|
+
return void (tapped = tapCounter());
|
|
460
|
+
if (tapped(event.timeStamp || performance.now()))
|
|
461
|
+
set(!g.unlocked, !0);
|
|
462
|
+
};
|
|
463
|
+
win.addEventListener("pointerdown", onTap, { capture: !0, passive: !0 }), offs.push(() => win.removeEventListener("pointerdown", onTap, !0));
|
|
464
|
+
}
|
|
465
|
+
return {
|
|
466
|
+
get unlocked() {
|
|
467
|
+
return g.unlocked;
|
|
468
|
+
},
|
|
469
|
+
unlock: () => set(!0, !0),
|
|
470
|
+
lock: () => set(!1, !0),
|
|
471
|
+
dispose() {
|
|
472
|
+
for (let off of offs.splice(0))
|
|
473
|
+
off();
|
|
474
|
+
}
|
|
475
|
+
};
|
|
476
|
+
}
|
|
477
|
+
|
|
340
478
|
// src/core/variants.ts
|
|
341
479
|
function createVariants(schema, id, key, storage, get, set, notify, enabled) {
|
|
342
480
|
let ready = !1, list = Object.freeze([]);
|
|
@@ -451,7 +589,7 @@ function sameField(a, b) {
|
|
|
451
589
|
function defineControls(id, input, options = {}) {
|
|
452
590
|
if (!id.trim())
|
|
453
591
|
throw Error("Controls need a stable, nonempty id.");
|
|
454
|
-
let schema = Object.freeze({ ...input }), locked = normalize(schema, {}), actions = Object.freeze([...options.actions ?? []]), theme = options.theme ?? "dark", density = options.density ?? "default", renderer = options.renderer ?? "auto", enabled = () => typeof options.enabled === "function" ? options.enabled() : options.enabled ?? (Boolean(options.ship) || typeof location < "u" && ["localhost", "127.0.0.1", "[::1]"].includes(location.hostname)), storage = () => options.storage === void 0 ? browserStorage() : options.storage, persistMode = options.persist ?? "all", valueStorage = () => persistMode === "all" ? storage() : null, variantStorage = () => persistMode === "none" ? null : storage(), draw = options.random ?? Math.random, hostHistory = options.history, unsubscribeHistory, listeners = /* @__PURE__ */ new Set, refreshes = 0, notify = () => {
|
|
592
|
+
let schema = Object.freeze({ ...input }), locked = normalize(schema, {}), actions = Object.freeze([...options.actions ?? []]), theme = options.theme ?? "dark", density = options.density ?? "default", renderer = options.renderer ?? "auto", enabled = () => typeof options.enabled === "function" ? options.enabled() : options.enabled ?? (Boolean(options.ship) || isUnlocked() || typeof location < "u" && ["localhost", "127.0.0.1", "[::1]"].includes(location.hostname)), storage = () => options.storage === void 0 ? browserStorage() : options.storage, persistMode = options.persist ?? "all", valueStorage = () => persistMode === "all" ? storage() : null, variantStorage = () => persistMode === "none" ? null : storage(), draw = options.random ?? Math.random, hostHistory = options.history, unsubscribeHistory, unsubscribeUnlock, listeners = /* @__PURE__ */ new Set, refreshes = 0, notify = () => {
|
|
455
593
|
for (let cb of [...listeners])
|
|
456
594
|
cb();
|
|
457
595
|
}, mixed = /* @__PURE__ */ new Set, current = locked, read = !1, error = null, locks = /* @__PURE__ */ new Set, bindings = /* @__PURE__ */ new Map, comparing = null, landing = !1, echo = Math.max(0, options.echo ?? 0), grabbed = /* @__PURE__ */ new Set, changedAt = /* @__PURE__ */ new Map, sent = /* @__PURE__ */ new Map, pending = /* @__PURE__ */ new Map, echoTimer, now = () => typeof performance < "u" ? performance.now() : Date.now(), isHeld = (key) => grabbed.has(key) || echo > 0 && now() - (changedAt.get(key) ?? -1 / 0) < echo, NO_BASE = Object.freeze({ preset: null, groups: Object.freeze({}) }), base = NO_BASE, past = [], future = [], HISTORY = 100, stateKey = storageKey(id, "state"), buildPresets = () => Object.freeze(Object.fromEntries([
|
|
@@ -869,6 +1007,36 @@ function defineControls(id, input, options = {}) {
|
|
|
869
1007
|
for (let key of Object.keys(patch))
|
|
870
1008
|
options.onReset?.({ key });
|
|
871
1009
|
}
|
|
1010
|
+
function live(load, make, unmake) {
|
|
1011
|
+
let disposed = !1, loading = !1, handle, sync = () => {
|
|
1012
|
+
if (disposed)
|
|
1013
|
+
return;
|
|
1014
|
+
if (!enabled()) {
|
|
1015
|
+
if (handle !== void 0)
|
|
1016
|
+
unmake(handle);
|
|
1017
|
+
handle = void 0;
|
|
1018
|
+
return;
|
|
1019
|
+
}
|
|
1020
|
+
if (handle !== void 0 || loading)
|
|
1021
|
+
return;
|
|
1022
|
+
let pending = load();
|
|
1023
|
+
if (!pending)
|
|
1024
|
+
return;
|
|
1025
|
+
loading = !0, pending.then((module) => {
|
|
1026
|
+
if (loading = !1, !disposed && enabled() && handle === void 0)
|
|
1027
|
+
handle = make(module);
|
|
1028
|
+
}).catch((cause) => {
|
|
1029
|
+
loading = !1, error = String(cause), notify();
|
|
1030
|
+
});
|
|
1031
|
+
};
|
|
1032
|
+
sync();
|
|
1033
|
+
let off = onUnlock(sync);
|
|
1034
|
+
return () => {
|
|
1035
|
+
if (disposed = !0, off(), handle !== void 0)
|
|
1036
|
+
unmake(handle);
|
|
1037
|
+
handle = void 0;
|
|
1038
|
+
};
|
|
1039
|
+
}
|
|
872
1040
|
let controls = {
|
|
873
1041
|
id,
|
|
874
1042
|
get schema() {
|
|
@@ -888,9 +1056,10 @@ function defineControls(id, input, options = {}) {
|
|
|
888
1056
|
marks: options.marks !== !1,
|
|
889
1057
|
chip: Object.freeze({
|
|
890
1058
|
...options.chip,
|
|
891
|
-
reveal: options.chip?.reveal ?? (devBuild() ? "hover" : "shortcut"),
|
|
1059
|
+
reveal: options.chip?.reveal ?? (devBuild() || !options.ship ? "hover" : "shortcut"),
|
|
892
1060
|
shortcut: options.chip?.shortcut ?? "Alt+Shift+D"
|
|
893
1061
|
}),
|
|
1062
|
+
toggleKey: options.toggleKey ?? (options.ship ? !1 : "`"),
|
|
894
1063
|
groupPresetDisplay: options.groupPresetDisplay ?? "auto",
|
|
895
1064
|
groupLabel: (group) => options.groupLabels?.[group] ?? fieldLabels().group.get(group),
|
|
896
1065
|
sectionLabel: (section) => options.sectionLabels?.[section] ?? fieldLabels().section.get(section),
|
|
@@ -985,9 +1154,10 @@ function defineControls(id, input, options = {}) {
|
|
|
985
1154
|
subscribe(cb) {
|
|
986
1155
|
if (listeners.add(cb), hostHistory?.subscribe && !unsubscribeHistory)
|
|
987
1156
|
unsubscribeHistory = hostHistory.subscribe(notify);
|
|
988
|
-
return () => {
|
|
989
|
-
if (listeners.delete(cb),
|
|
990
|
-
|
|
1157
|
+
return unsubscribeUnlock ??= onUnlock(notify), () => {
|
|
1158
|
+
if (listeners.delete(cb), listeners.size)
|
|
1159
|
+
return;
|
|
1160
|
+
unsubscribeHistory?.(), unsubscribeHistory = void 0, unsubscribeUnlock?.(), unsubscribeUnlock = void 0;
|
|
991
1161
|
};
|
|
992
1162
|
},
|
|
993
1163
|
reset(keys) {
|
|
@@ -1205,32 +1375,15 @@ function defineControls(id, input, options = {}) {
|
|
|
1205
1375
|
code: (format, values) => formatCode(values ?? get(), format),
|
|
1206
1376
|
variants,
|
|
1207
1377
|
attach(element, chip) {
|
|
1208
|
-
let load = options.ship ? () => options.ship().then((m) => m.attach) : () => (__preload("
|
|
1209
|
-
|
|
1210
|
-
return () => {};
|
|
1211
|
-
let disposed = !1, detach;
|
|
1212
|
-
return load().then((attach) => {
|
|
1213
|
-
if (!disposed && enabled())
|
|
1214
|
-
detach = attach(controls, element, chip);
|
|
1215
|
-
}).catch((cause) => {
|
|
1216
|
-
error = String(cause), notify();
|
|
1217
|
-
}), () => {
|
|
1218
|
-
disposed = !0, detach?.();
|
|
1219
|
-
};
|
|
1378
|
+
let load = options.ship ? () => options.ship().then((m) => m.attach) : () => (__preload("v8ssbcbk"), import("./chunk-v8ssbcbk.js")).then((m) => m.attach);
|
|
1379
|
+
return live(load, (attach) => attach(controls, element, chip), (detach) => detach());
|
|
1220
1380
|
},
|
|
1221
1381
|
mount(container, mountOptions) {
|
|
1222
|
-
let load = options.ship ? () => options.ship().then((m) => m.mountPanel) : () => (__preload("
|
|
1223
|
-
|
|
1224
|
-
|
|
1225
|
-
|
|
1226
|
-
|
|
1227
|
-
if (!disposed && enabled())
|
|
1228
|
-
panel = mountPanel(controls, container, mountOptions), mountOptions?.onReady?.(panel);
|
|
1229
|
-
}).catch((cause) => {
|
|
1230
|
-
error = String(cause), notify();
|
|
1231
|
-
}), () => {
|
|
1232
|
-
disposed = !0, panel?.dispose();
|
|
1233
|
-
};
|
|
1382
|
+
let load = options.ship ? () => options.ship().then((m) => m.mountPanel) : () => (__preload("jx1ktap3"), import("./chunk-jx1ktap3.js")).then((m) => m.mountPanel);
|
|
1383
|
+
return live(load, (mountPanel) => {
|
|
1384
|
+
let panel = mountPanel(controls, container, mountOptions);
|
|
1385
|
+
return mountOptions?.onReady?.(panel), panel;
|
|
1386
|
+
}, (panel) => panel.dispose());
|
|
1234
1387
|
}
|
|
1235
1388
|
};
|
|
1236
1389
|
return Object.freeze(controls);
|
|
@@ -1510,6 +1663,7 @@ function createRemoteControls(id, descriptors, options = {}) {
|
|
|
1510
1663
|
}, controls = defineControls(id, fromDescriptors(frozenDescriptors), {
|
|
1511
1664
|
enabled: options.enabled ?? !0,
|
|
1512
1665
|
ship: options.ship,
|
|
1666
|
+
toggleKey: options.toggleKey,
|
|
1513
1667
|
echo: options.echo ?? ECHO_MS,
|
|
1514
1668
|
storage: options.storage ?? null,
|
|
1515
1669
|
persist: options.persist,
|
|
@@ -1603,6 +1757,7 @@ export {
|
|
|
1603
1757
|
AROUND,
|
|
1604
1758
|
CURVE_SHAPES2 as CURVE_SHAPES,
|
|
1605
1759
|
EASINGS2 as EASINGS,
|
|
1760
|
+
KONAMI,
|
|
1606
1761
|
SPRING2 as SPRING,
|
|
1607
1762
|
action2 as action,
|
|
1608
1763
|
actionShortcut2 as actionShortcut,
|
|
@@ -1652,6 +1807,7 @@ export {
|
|
|
1652
1807
|
toggle2 as toggle,
|
|
1653
1808
|
toolbar2 as toolbar,
|
|
1654
1809
|
toolbarShortcut2 as toolbarShortcut,
|
|
1810
|
+
unlock,
|
|
1655
1811
|
urlFlag2 as urlFlag,
|
|
1656
1812
|
vec22 as vec2,
|
|
1657
1813
|
vec32 as vec3,
|
package/dist/index.js
CHANGED
|
@@ -221,6 +221,17 @@ function comboParts(combo, apple = isApple()) {
|
|
|
221
221
|
function comboLabel(combo, apple = isApple()) {
|
|
222
222
|
return comboParts(combo, apple).join(apple ? "" : "+");
|
|
223
223
|
}
|
|
224
|
+
function isTypingTarget(target) {
|
|
225
|
+
let el = target;
|
|
226
|
+
if (!el || typeof el.tagName !== "string")
|
|
227
|
+
return !1;
|
|
228
|
+
let tag = el.tagName;
|
|
229
|
+
if (tag === "SELECT" || el.isContentEditable)
|
|
230
|
+
return !0;
|
|
231
|
+
if (tag === "TEXTAREA")
|
|
232
|
+
return !el.readOnly;
|
|
233
|
+
return tag === "INPUT" && !el.readOnly && !["range", "checkbox", "radio", "button", "submit", "reset", "color"].includes(el.type);
|
|
234
|
+
}
|
|
224
235
|
|
|
225
236
|
// src/core/ramp.ts
|
|
226
237
|
var MAX_STOPS = 32, MAX_POINTS = 64, GRADIENT_SAMPLES = 64;
|
|
@@ -475,11 +486,9 @@ function withMeta(base, meta) {
|
|
|
475
486
|
return checkShortcut(meta?.shortcut), Object.freeze({ ...base, ...pickMeta(meta) });
|
|
476
487
|
}
|
|
477
488
|
function knob(value, options) {
|
|
478
|
-
|
|
479
|
-
if (![value, options.min, options.max, step].every(Number.isFinite) || options.max < options.min || step <= 0)
|
|
489
|
+
if (!Number.isFinite(value))
|
|
480
490
|
throw Error("A knob needs finite bounds and a positive step.");
|
|
481
|
-
|
|
482
|
-
throw Error("A knob's decimals must be a whole number.");
|
|
491
|
+
let step = bounds(options, "A knob");
|
|
483
492
|
checkShortcut(options.shortcut);
|
|
484
493
|
let field = { ...options, kind: "knob", value, step };
|
|
485
494
|
return Object.freeze({ ...field, value: normalizeField(field, value) });
|
|
@@ -1328,6 +1337,143 @@ function urlFlag(name) {
|
|
|
1328
1337
|
}
|
|
1329
1338
|
var storageKey = (id, part) => `knobs:${encodeURIComponent(id)}:${part}:v1`;
|
|
1330
1339
|
|
|
1340
|
+
// src/core/unlock.ts
|
|
1341
|
+
var KONAMI = Object.freeze([
|
|
1342
|
+
"ArrowUp",
|
|
1343
|
+
"ArrowUp",
|
|
1344
|
+
"ArrowDown",
|
|
1345
|
+
"ArrowDown",
|
|
1346
|
+
"ArrowLeft",
|
|
1347
|
+
"ArrowRight",
|
|
1348
|
+
"ArrowLeft",
|
|
1349
|
+
"ArrowRight",
|
|
1350
|
+
"b",
|
|
1351
|
+
"a"
|
|
1352
|
+
]), GATE = Symbol.for("knobs.unlock.v1"), gate = () => {
|
|
1353
|
+
let holder = globalThis;
|
|
1354
|
+
return holder[GATE] ??= { unlocked: !1, listeners: /* @__PURE__ */ new Set };
|
|
1355
|
+
}, isUnlocked = () => globalThis[GATE]?.unlocked ?? !1, unlockedPanel = () => isUnlocked() ? gate().panel : void 0;
|
|
1356
|
+
function onUnlock(listener) {
|
|
1357
|
+
let listeners = gate().listeners;
|
|
1358
|
+
return listeners.add(listener), () => void listeners.delete(listener);
|
|
1359
|
+
}
|
|
1360
|
+
var UNLOCK_KEY = "knobs:unlocked";
|
|
1361
|
+
function sequenceKeys(sequence) {
|
|
1362
|
+
return typeof sequence === "string" ? [...sequence] : [...sequence];
|
|
1363
|
+
}
|
|
1364
|
+
var fold = (key) => key.length === 1 ? key.toLowerCase() : key;
|
|
1365
|
+
function sequenceMatcher(sequence, gap = 1500) {
|
|
1366
|
+
let want = sequenceKeys(sequence).map(fold), typed = [], last = -1 / 0;
|
|
1367
|
+
return (key, at) => {
|
|
1368
|
+
if (!want.length)
|
|
1369
|
+
return !1;
|
|
1370
|
+
if (at - last > gap)
|
|
1371
|
+
typed = [];
|
|
1372
|
+
if (last = at, typed.push(fold(key)), typed.length > want.length)
|
|
1373
|
+
typed.shift();
|
|
1374
|
+
if (typed.length === want.length && typed.every((k, i) => k === want[i]))
|
|
1375
|
+
return typed = [], !0;
|
|
1376
|
+
return !1;
|
|
1377
|
+
};
|
|
1378
|
+
}
|
|
1379
|
+
function queryUnlock(search, name) {
|
|
1380
|
+
let params = new URLSearchParams(search);
|
|
1381
|
+
if (!params.has(name))
|
|
1382
|
+
return;
|
|
1383
|
+
return !["off", "0", "false", "lock", "no"].includes((params.get(name) ?? "").toLowerCase());
|
|
1384
|
+
}
|
|
1385
|
+
function resolveUnlock(input) {
|
|
1386
|
+
let unlocked = input.query ?? (input.persist && input.stored);
|
|
1387
|
+
return { unlocked, remember: input.persist && input.query !== void 0 ? unlocked : void 0 };
|
|
1388
|
+
}
|
|
1389
|
+
function inCorner(x, y, width, height, corner, size = 48) {
|
|
1390
|
+
let left = corner.endsWith("left") ? x <= size : x >= width - size, top = corner.startsWith("top") ? y <= size : y >= height - size;
|
|
1391
|
+
return left && top;
|
|
1392
|
+
}
|
|
1393
|
+
function tapCounter(count = 3, within = 500) {
|
|
1394
|
+
let taps = 0, last = -1 / 0;
|
|
1395
|
+
return (at) => {
|
|
1396
|
+
if (taps = at - last <= within ? taps + 1 : 1, last = at, taps < count)
|
|
1397
|
+
return !1;
|
|
1398
|
+
return taps = 0, !0;
|
|
1399
|
+
};
|
|
1400
|
+
}
|
|
1401
|
+
var readStored = () => {
|
|
1402
|
+
try {
|
|
1403
|
+
return globalThis.localStorage?.getItem(UNLOCK_KEY) === "1";
|
|
1404
|
+
} catch {
|
|
1405
|
+
return !1;
|
|
1406
|
+
}
|
|
1407
|
+
}, writeStored = (on) => {
|
|
1408
|
+
try {
|
|
1409
|
+
if (on)
|
|
1410
|
+
globalThis.localStorage?.setItem(UNLOCK_KEY, "1");
|
|
1411
|
+
else
|
|
1412
|
+
globalThis.localStorage?.removeItem(UNLOCK_KEY);
|
|
1413
|
+
} catch {}
|
|
1414
|
+
};
|
|
1415
|
+
function unlock(options) {
|
|
1416
|
+
let g = gate();
|
|
1417
|
+
g.panel = options.panel;
|
|
1418
|
+
let persist = options.persist !== !1, query = options.query === void 0 ? "knobs" : options.query, sequence = options.sequence === void 0 ? "knobs" : options.sequence, corner = options.corner === void 0 ? "top-right" : options.corner, win = typeof window > "u" ? void 0 : window, announce = (text) => {
|
|
1419
|
+
(g.module ? Promise.resolve(g.module) : g.panel?.())?.then((m) => {
|
|
1420
|
+
if (g.module = m, g.unlocked === (text === "knobs unlocked"))
|
|
1421
|
+
m.status?.(text);
|
|
1422
|
+
}).catch(() => {});
|
|
1423
|
+
}, set = (on, say) => {
|
|
1424
|
+
if (persist)
|
|
1425
|
+
writeStored(on);
|
|
1426
|
+
if (g.unlocked === on)
|
|
1427
|
+
return;
|
|
1428
|
+
g.unlocked = on;
|
|
1429
|
+
for (let listener of [...g.listeners])
|
|
1430
|
+
listener();
|
|
1431
|
+
if (say)
|
|
1432
|
+
announce(on ? "knobs unlocked" : "knobs locked");
|
|
1433
|
+
}, start = resolveUnlock({
|
|
1434
|
+
query: query && win ? queryUnlock(win.location.search, query) : void 0,
|
|
1435
|
+
stored: persist && readStored(),
|
|
1436
|
+
persist
|
|
1437
|
+
});
|
|
1438
|
+
if (start.remember !== void 0)
|
|
1439
|
+
writeStored(start.remember);
|
|
1440
|
+
set(start.unlocked || g.unlocked, !1);
|
|
1441
|
+
let offs = [];
|
|
1442
|
+
if (win && sequence !== !1 && sequenceKeys(sequence).length) {
|
|
1443
|
+
let typed = sequenceMatcher(sequence), onKey = (event) => {
|
|
1444
|
+
if (event.ctrlKey || event.metaKey || event.altKey || event.isComposing || event.repeat)
|
|
1445
|
+
return;
|
|
1446
|
+
if (event.key === "Shift" || event.key === "CapsLock" || isTypingTarget(event.target))
|
|
1447
|
+
return;
|
|
1448
|
+
if (typed(event.key, event.timeStamp || performance.now()))
|
|
1449
|
+
set(!g.unlocked, !0);
|
|
1450
|
+
};
|
|
1451
|
+
win.addEventListener("keydown", onKey, !0), offs.push(() => win.removeEventListener("keydown", onKey, !0));
|
|
1452
|
+
}
|
|
1453
|
+
if (win && corner) {
|
|
1454
|
+
let tapped = tapCounter(), onTap = (event) => {
|
|
1455
|
+
if (!event.isPrimary)
|
|
1456
|
+
return;
|
|
1457
|
+
if (!inCorner(event.clientX, event.clientY, win.innerWidth, win.innerHeight, corner))
|
|
1458
|
+
return void (tapped = tapCounter());
|
|
1459
|
+
if (tapped(event.timeStamp || performance.now()))
|
|
1460
|
+
set(!g.unlocked, !0);
|
|
1461
|
+
};
|
|
1462
|
+
win.addEventListener("pointerdown", onTap, { capture: !0, passive: !0 }), offs.push(() => win.removeEventListener("pointerdown", onTap, !0));
|
|
1463
|
+
}
|
|
1464
|
+
return {
|
|
1465
|
+
get unlocked() {
|
|
1466
|
+
return g.unlocked;
|
|
1467
|
+
},
|
|
1468
|
+
unlock: () => set(!0, !0),
|
|
1469
|
+
lock: () => set(!1, !0),
|
|
1470
|
+
dispose() {
|
|
1471
|
+
for (let off of offs.splice(0))
|
|
1472
|
+
off();
|
|
1473
|
+
}
|
|
1474
|
+
};
|
|
1475
|
+
}
|
|
1476
|
+
|
|
1331
1477
|
// src/core/variants.ts
|
|
1332
1478
|
function createVariants(schema, id, key, storage, get, set, notify, enabled) {
|
|
1333
1479
|
let ready = !1, list = Object.freeze([]);
|
|
@@ -1442,7 +1588,7 @@ function sameField(a, b) {
|
|
|
1442
1588
|
function defineControls(id, input, options = {}) {
|
|
1443
1589
|
if (!id.trim())
|
|
1444
1590
|
throw Error("Controls need a stable, nonempty id.");
|
|
1445
|
-
let schema = Object.freeze({ ...input }), locked = normalize(schema, {}), actions = Object.freeze([...options.actions ?? []]), theme = options.theme ?? "dark", density = options.density ?? "default", renderer = options.renderer ?? "auto", enabled = () => Boolean(options.ship) && (typeof options.enabled === "function" ? options.enabled() : options.enabled ?? (Boolean(options.ship) || typeof location < "u" && ["localhost", "127.0.0.1", "[::1]"].includes(location.hostname))), storage = () => options.storage === void 0 ? browserStorage() : options.storage, persistMode = options.persist ?? "all", valueStorage = () => persistMode === "all" ? storage() : null, variantStorage = () => persistMode === "none" ? null : storage(), draw = options.random ?? Math.random, hostHistory = options.history, unsubscribeHistory, listeners = /* @__PURE__ */ new Set, refreshes = 0, notify = () => {
|
|
1591
|
+
let schema = Object.freeze({ ...input }), locked = normalize(schema, {}), actions = Object.freeze([...options.actions ?? []]), theme = options.theme ?? "dark", density = options.density ?? "default", renderer = options.renderer ?? "auto", enabled = () => (Boolean(options.ship) || isUnlocked()) && (typeof options.enabled === "function" ? options.enabled() : options.enabled ?? (Boolean(options.ship) || isUnlocked() || typeof location < "u" && ["localhost", "127.0.0.1", "[::1]"].includes(location.hostname))), storage = () => options.storage === void 0 ? browserStorage() : options.storage, persistMode = options.persist ?? "all", valueStorage = () => persistMode === "all" ? storage() : null, variantStorage = () => persistMode === "none" ? null : storage(), draw = options.random ?? Math.random, hostHistory = options.history, unsubscribeHistory, unsubscribeUnlock, listeners = /* @__PURE__ */ new Set, refreshes = 0, notify = () => {
|
|
1446
1592
|
for (let cb of [...listeners])
|
|
1447
1593
|
cb();
|
|
1448
1594
|
}, mixed = /* @__PURE__ */ new Set, current = locked, read = !1, error = null, locks = /* @__PURE__ */ new Set, bindings = /* @__PURE__ */ new Map, comparing = null, landing = !1, echo = Math.max(0, options.echo ?? 0), grabbed = /* @__PURE__ */ new Set, changedAt = /* @__PURE__ */ new Map, sent = /* @__PURE__ */ new Map, pending = /* @__PURE__ */ new Map, echoTimer, now = () => typeof performance < "u" ? performance.now() : Date.now(), isHeld = (key) => grabbed.has(key) || echo > 0 && now() - (changedAt.get(key) ?? -1 / 0) < echo, NO_BASE = Object.freeze({ preset: null, groups: Object.freeze({}) }), base = NO_BASE, past = [], future = [], HISTORY = 100, stateKey = storageKey(id, "state"), buildPresets = () => Object.freeze(Object.fromEntries([
|
|
@@ -1860,6 +2006,36 @@ function defineControls(id, input, options = {}) {
|
|
|
1860
2006
|
for (let key of Object.keys(patch))
|
|
1861
2007
|
options.onReset?.({ key });
|
|
1862
2008
|
}
|
|
2009
|
+
function live(load, make, unmake) {
|
|
2010
|
+
let disposed = !1, loading = !1, handle, sync = () => {
|
|
2011
|
+
if (disposed)
|
|
2012
|
+
return;
|
|
2013
|
+
if (!enabled()) {
|
|
2014
|
+
if (handle !== void 0)
|
|
2015
|
+
unmake(handle);
|
|
2016
|
+
handle = void 0;
|
|
2017
|
+
return;
|
|
2018
|
+
}
|
|
2019
|
+
if (handle !== void 0 || loading)
|
|
2020
|
+
return;
|
|
2021
|
+
let pending = load();
|
|
2022
|
+
if (!pending)
|
|
2023
|
+
return;
|
|
2024
|
+
loading = !0, pending.then((module) => {
|
|
2025
|
+
if (loading = !1, !disposed && enabled() && handle === void 0)
|
|
2026
|
+
handle = make(module);
|
|
2027
|
+
}).catch((cause) => {
|
|
2028
|
+
loading = !1, error = String(cause), notify();
|
|
2029
|
+
});
|
|
2030
|
+
};
|
|
2031
|
+
sync();
|
|
2032
|
+
let off = onUnlock(sync);
|
|
2033
|
+
return () => {
|
|
2034
|
+
if (disposed = !0, off(), handle !== void 0)
|
|
2035
|
+
unmake(handle);
|
|
2036
|
+
handle = void 0;
|
|
2037
|
+
};
|
|
2038
|
+
}
|
|
1863
2039
|
let controls = {
|
|
1864
2040
|
id,
|
|
1865
2041
|
get schema() {
|
|
@@ -1879,9 +2055,10 @@ function defineControls(id, input, options = {}) {
|
|
|
1879
2055
|
marks: options.marks !== !1,
|
|
1880
2056
|
chip: Object.freeze({
|
|
1881
2057
|
...options.chip,
|
|
1882
|
-
reveal: options.chip?.reveal ?? (devBuild() ? "hover" : "shortcut"),
|
|
2058
|
+
reveal: options.chip?.reveal ?? (devBuild() || !options.ship ? "hover" : "shortcut"),
|
|
1883
2059
|
shortcut: options.chip?.shortcut ?? "Alt+Shift+D"
|
|
1884
2060
|
}),
|
|
2061
|
+
toggleKey: options.toggleKey ?? (options.ship ? !1 : "`"),
|
|
1885
2062
|
groupPresetDisplay: options.groupPresetDisplay ?? "auto",
|
|
1886
2063
|
groupLabel: (group) => options.groupLabels?.[group] ?? fieldLabels().group.get(group),
|
|
1887
2064
|
sectionLabel: (section) => options.sectionLabels?.[section] ?? fieldLabels().section.get(section),
|
|
@@ -1976,9 +2153,10 @@ function defineControls(id, input, options = {}) {
|
|
|
1976
2153
|
subscribe(cb) {
|
|
1977
2154
|
if (listeners.add(cb), hostHistory?.subscribe && !unsubscribeHistory)
|
|
1978
2155
|
unsubscribeHistory = hostHistory.subscribe(notify);
|
|
1979
|
-
return () => {
|
|
1980
|
-
if (listeners.delete(cb),
|
|
1981
|
-
|
|
2156
|
+
return unsubscribeUnlock ??= onUnlock(notify), () => {
|
|
2157
|
+
if (listeners.delete(cb), listeners.size)
|
|
2158
|
+
return;
|
|
2159
|
+
unsubscribeHistory?.(), unsubscribeHistory = void 0, unsubscribeUnlock?.(), unsubscribeUnlock = void 0;
|
|
1982
2160
|
};
|
|
1983
2161
|
},
|
|
1984
2162
|
reset(keys) {
|
|
@@ -2196,32 +2374,15 @@ function defineControls(id, input, options = {}) {
|
|
|
2196
2374
|
code: (format, values) => formatCode(values ?? get(), format),
|
|
2197
2375
|
variants,
|
|
2198
2376
|
attach(element, chip) {
|
|
2199
|
-
let load = options.ship ? () => options.ship().then((m) => m.attach) :
|
|
2200
|
-
|
|
2201
|
-
return () => {};
|
|
2202
|
-
let disposed = !1, detach;
|
|
2203
|
-
return load().then((attach) => {
|
|
2204
|
-
if (!disposed && enabled())
|
|
2205
|
-
detach = attach(controls, element, chip);
|
|
2206
|
-
}).catch((cause) => {
|
|
2207
|
-
error = String(cause), notify();
|
|
2208
|
-
}), () => {
|
|
2209
|
-
disposed = !0, detach?.();
|
|
2210
|
-
};
|
|
2377
|
+
let load = options.ship ? () => options.ship().then((m) => m.attach) : () => unlockedPanel()?.().then((m) => m.attach);
|
|
2378
|
+
return live(load, (attach) => attach(controls, element, chip), (detach) => detach());
|
|
2211
2379
|
},
|
|
2212
2380
|
mount(container, mountOptions) {
|
|
2213
|
-
let load = options.ship ? () => options.ship().then((m) => m.mountPanel) :
|
|
2214
|
-
|
|
2215
|
-
|
|
2216
|
-
|
|
2217
|
-
|
|
2218
|
-
if (!disposed && enabled())
|
|
2219
|
-
panel = mountPanel(controls, container, mountOptions), mountOptions?.onReady?.(panel);
|
|
2220
|
-
}).catch((cause) => {
|
|
2221
|
-
error = String(cause), notify();
|
|
2222
|
-
}), () => {
|
|
2223
|
-
disposed = !0, panel?.dispose();
|
|
2224
|
-
};
|
|
2381
|
+
let load = options.ship ? () => options.ship().then((m) => m.mountPanel) : () => unlockedPanel()?.().then((m) => m.mountPanel);
|
|
2382
|
+
return live(load, (mountPanel) => {
|
|
2383
|
+
let panel = mountPanel(controls, container, mountOptions);
|
|
2384
|
+
return mountOptions?.onReady?.(panel), panel;
|
|
2385
|
+
}, (panel) => panel.dispose());
|
|
2225
2386
|
}
|
|
2226
2387
|
};
|
|
2227
2388
|
return Object.freeze(controls);
|
|
@@ -2501,6 +2662,7 @@ function createRemoteControls(id, descriptors, options = {}) {
|
|
|
2501
2662
|
}, controls = defineControls(id, fromDescriptors(frozenDescriptors), {
|
|
2502
2663
|
enabled: options.enabled ?? !0,
|
|
2503
2664
|
ship: options.ship,
|
|
2665
|
+
toggleKey: options.toggleKey,
|
|
2504
2666
|
echo: options.echo ?? ECHO_MS,
|
|
2505
2667
|
storage: options.storage ?? null,
|
|
2506
2668
|
persist: options.persist,
|
|
@@ -2594,6 +2756,7 @@ export {
|
|
|
2594
2756
|
AROUND,
|
|
2595
2757
|
CURVE_SHAPES,
|
|
2596
2758
|
EASINGS,
|
|
2759
|
+
KONAMI,
|
|
2597
2760
|
SPRING,
|
|
2598
2761
|
action,
|
|
2599
2762
|
actionShortcut,
|
|
@@ -2643,6 +2806,7 @@ export {
|
|
|
2643
2806
|
toggle,
|
|
2644
2807
|
toolbar,
|
|
2645
2808
|
toolbarShortcut,
|
|
2809
|
+
unlock,
|
|
2646
2810
|
urlFlag,
|
|
2647
2811
|
vec2,
|
|
2648
2812
|
vec3,
|