@unrulysystems/native-motion-core 0.1.0-alpha.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/CHANGELOG.md +9 -0
- package/LICENSE +21 -0
- package/README.md +48 -0
- package/dist/clock.cjs +71 -0
- package/dist/clock.d.cts +23 -0
- package/dist/clock.d.ts +23 -0
- package/dist/clock.js +66 -0
- package/dist/collect-reads.cjs +68 -0
- package/dist/collect-reads.d.cts +23 -0
- package/dist/collect-reads.d.ts +23 -0
- package/dist/collect-reads.js +62 -0
- package/dist/component/boundedArray.cjs +74 -0
- package/dist/component/boundedArray.d.cts +25 -0
- package/dist/component/boundedArray.d.ts +25 -0
- package/dist/component/boundedArray.js +68 -0
- package/dist/component/index.cjs +57 -0
- package/dist/component/index.d.cts +12 -0
- package/dist/component/index.d.ts +12 -0
- package/dist/component/index.js +22 -0
- package/dist/component/orchestration.cjs +129 -0
- package/dist/component/orchestration.d.cts +66 -0
- package/dist/component/orchestration.d.ts +66 -0
- package/dist/component/orchestration.js +124 -0
- package/dist/component/resolve.cjs +104 -0
- package/dist/component/resolve.d.cts +11 -0
- package/dist/component/resolve.d.ts +11 -0
- package/dist/component/resolve.js +97 -0
- package/dist/component/transition.cjs +352 -0
- package/dist/component/transition.d.cts +33 -0
- package/dist/component/transition.d.ts +33 -0
- package/dist/component/transition.js +339 -0
- package/dist/component/types.cjs +114 -0
- package/dist/component/types.d.cts +60 -0
- package/dist/component/types.d.ts +60 -0
- package/dist/component/types.js +111 -0
- package/dist/component/validate.cjs +1015 -0
- package/dist/component/validate.d.cts +37 -0
- package/dist/component/validate.d.ts +37 -0
- package/dist/component/validate.js +1002 -0
- package/dist/component/variants.cjs +333 -0
- package/dist/component/variants.d.cts +106 -0
- package/dist/component/variants.d.ts +106 -0
- package/dist/component/variants.js +321 -0
- package/dist/config/constants.cjs +41 -0
- package/dist/config/constants.d.cts +29 -0
- package/dist/config/constants.d.ts +29 -0
- package/dist/config/constants.js +38 -0
- package/dist/delay.cjs +72 -0
- package/dist/delay.d.cts +26 -0
- package/dist/delay.d.ts +26 -0
- package/dist/delay.js +70 -0
- package/dist/derived.cjs +143 -0
- package/dist/derived.d.cts +41 -0
- package/dist/derived.d.ts +41 -0
- package/dist/derived.js +139 -0
- package/dist/driver/index.cjs +22 -0
- package/dist/driver/index.d.cts +7 -0
- package/dist/driver/index.d.ts +7 -0
- package/dist/driver/index.js +14 -0
- package/dist/driver/keyframeTiming.cjs +130 -0
- package/dist/driver/keyframeTiming.d.cts +18 -0
- package/dist/driver/keyframeTiming.d.ts +18 -0
- package/dist/driver/keyframeTiming.js +124 -0
- package/dist/driver/keyframeTimingConfig.cjs +24 -0
- package/dist/driver/keyframeTimingConfig.d.cts +5 -0
- package/dist/driver/keyframeTimingConfig.d.ts +5 -0
- package/dist/driver/keyframeTimingConfig.js +22 -0
- package/dist/driver/prepare.cjs +459 -0
- package/dist/driver/prepare.d.cts +4 -0
- package/dist/driver/prepare.d.ts +4 -0
- package/dist/driver/prepare.js +454 -0
- package/dist/driver/reference.cjs +762 -0
- package/dist/driver/reference.d.cts +53 -0
- package/dist/driver/reference.d.ts +53 -0
- package/dist/driver/reference.js +757 -0
- package/dist/driver/step.cjs +55 -0
- package/dist/driver/step.d.cts +9 -0
- package/dist/driver/step.d.ts +9 -0
- package/dist/driver/step.js +52 -0
- package/dist/driver/tiers.cjs +40 -0
- package/dist/driver/tiers.d.cts +2 -0
- package/dist/driver/tiers.d.ts +2 -0
- package/dist/driver/tiers.js +37 -0
- package/dist/driver/types.cjs +9 -0
- package/dist/driver/types.d.cts +68 -0
- package/dist/driver/types.d.ts +68 -0
- package/dist/driver/types.js +8 -0
- package/dist/external-animation-ledger.cjs +1250 -0
- package/dist/external-animation-ledger.d.cts +416 -0
- package/dist/external-animation-ledger.d.ts +416 -0
- package/dist/external-animation-ledger.js +1243 -0
- package/dist/gesture/directionLock.cjs +25 -0
- package/dist/gesture/directionLock.d.cts +8 -0
- package/dist/gesture/directionLock.d.ts +8 -0
- package/dist/gesture/directionLock.js +21 -0
- package/dist/gesture/dragConfig.cjs +634 -0
- package/dist/gesture/dragConfig.d.cts +298 -0
- package/dist/gesture/dragConfig.d.ts +298 -0
- package/dist/gesture/dragConfig.js +624 -0
- package/dist/gesture/elastic.cjs +44 -0
- package/dist/gesture/elastic.d.cts +4 -0
- package/dist/gesture/elastic.d.ts +4 -0
- package/dist/gesture/elastic.js +39 -0
- package/dist/gesture/handoffSession.cjs +161 -0
- package/dist/gesture/handoffSession.d.cts +35 -0
- package/dist/gesture/handoffSession.d.ts +35 -0
- package/dist/gesture/handoffSession.js +158 -0
- package/dist/gesture/index.cjs +37 -0
- package/dist/gesture/index.d.cts +12 -0
- package/dist/gesture/index.d.ts +12 -0
- package/dist/gesture/index.js +11 -0
- package/dist/gesture/projection.cjs +95 -0
- package/dist/gesture/projection.d.cts +7 -0
- package/dist/gesture/projection.d.ts +7 -0
- package/dist/gesture/projection.js +87 -0
- package/dist/gesture/session.cjs +162 -0
- package/dist/gesture/session.d.cts +29 -0
- package/dist/gesture/session.d.ts +29 -0
- package/dist/gesture/session.js +158 -0
- package/dist/gesture/types.cjs +5 -0
- package/dist/gesture/types.d.cts +13 -0
- package/dist/gesture/types.d.ts +13 -0
- package/dist/gesture/types.js +4 -0
- package/dist/gesture/viewportConstraints.cjs +38 -0
- package/dist/gesture/viewportConstraints.d.cts +6 -0
- package/dist/gesture/viewportConstraints.d.ts +6 -0
- package/dist/gesture/viewportConstraints.js +34 -0
- package/dist/graph.cjs +226 -0
- package/dist/graph.d.cts +2 -0
- package/dist/graph.d.ts +2 -0
- package/dist/graph.js +223 -0
- package/dist/index.cjs +140 -0
- package/dist/index.d.cts +33 -0
- package/dist/index.d.ts +33 -0
- package/dist/index.js +70 -0
- package/dist/inertia.cjs +214 -0
- package/dist/inertia.d.cts +53 -0
- package/dist/inertia.d.ts +53 -0
- package/dist/inertia.js +212 -0
- package/dist/instant.cjs +66 -0
- package/dist/instant.d.cts +16 -0
- package/dist/instant.d.ts +16 -0
- package/dist/instant.js +63 -0
- package/dist/internal-driver.cjs +81 -0
- package/dist/internal-driver.d.cts +19 -0
- package/dist/internal-driver.d.ts +19 -0
- package/dist/internal-driver.js +35 -0
- package/dist/keyframes.cjs +191 -0
- package/dist/keyframes.d.cts +13 -0
- package/dist/keyframes.d.ts +13 -0
- package/dist/keyframes.js +188 -0
- package/dist/layout/commitDetector.cjs +67 -0
- package/dist/layout/commitDetector.d.cts +21 -0
- package/dist/layout/commitDetector.d.ts +21 -0
- package/dist/layout/commitDetector.js +64 -0
- package/dist/layout/compose.cjs +67 -0
- package/dist/layout/compose.d.cts +30 -0
- package/dist/layout/compose.d.ts +30 -0
- package/dist/layout/compose.js +65 -0
- package/dist/layout/constants.cjs +13 -0
- package/dist/layout/constants.d.cts +6 -0
- package/dist/layout/constants.d.ts +6 -0
- package/dist/layout/constants.js +10 -0
- package/dist/layout/identity.cjs +700 -0
- package/dist/layout/identity.d.cts +67 -0
- package/dist/layout/identity.d.ts +67 -0
- package/dist/layout/identity.js +698 -0
- package/dist/layout/index.cjs +36 -0
- package/dist/layout/index.d.cts +18 -0
- package/dist/layout/index.d.ts +18 -0
- package/dist/layout/index.js +13 -0
- package/dist/layout/measure.cjs +81 -0
- package/dist/layout/measure.d.cts +43 -0
- package/dist/layout/measure.d.ts +43 -0
- package/dist/layout/measure.js +78 -0
- package/dist/layout/projection.cjs +99 -0
- package/dist/layout/projection.d.cts +23 -0
- package/dist/layout/projection.d.ts +23 -0
- package/dist/layout/projection.js +97 -0
- package/dist/layout/scroll.cjs +27 -0
- package/dist/layout/scroll.d.cts +13 -0
- package/dist/layout/scroll.d.ts +13 -0
- package/dist/layout/scroll.js +24 -0
- package/dist/layout/session.cjs +207 -0
- package/dist/layout/session.d.cts +73 -0
- package/dist/layout/session.d.ts +73 -0
- package/dist/layout/session.js +205 -0
- package/dist/layout/tree.cjs +826 -0
- package/dist/layout/tree.d.cts +70 -0
- package/dist/layout/tree.d.ts +70 -0
- package/dist/layout/tree.js +823 -0
- package/dist/layout/types.cjs +36 -0
- package/dist/layout/types.d.cts +31 -0
- package/dist/layout/types.d.ts +31 -0
- package/dist/layout/types.js +35 -0
- package/dist/motion-arc.cjs +184 -0
- package/dist/motion-arc.d.cts +78 -0
- package/dist/motion-arc.d.ts +78 -0
- package/dist/motion-arc.js +183 -0
- package/dist/motion-mix.cjs +205 -0
- package/dist/motion-mix.d.cts +3 -0
- package/dist/motion-mix.d.ts +3 -0
- package/dist/motion-mix.js +202 -0
- package/dist/motion-value-driver-port.cjs +636 -0
- package/dist/motion-value-driver-port.d.cts +406 -0
- package/dist/motion-value-driver-port.d.ts +406 -0
- package/dist/motion-value-driver-port.js +627 -0
- package/dist/motion-value.cjs +189 -0
- package/dist/motion-value.d.cts +51 -0
- package/dist/motion-value.d.ts +51 -0
- package/dist/motion-value.js +185 -0
- package/dist/presence/controller.cjs +657 -0
- package/dist/presence/controller.d.cts +6 -0
- package/dist/presence/controller.d.ts +6 -0
- package/dist/presence/controller.js +652 -0
- package/dist/presence/index.cjs +19 -0
- package/dist/presence/index.d.cts +4 -0
- package/dist/presence/index.d.ts +4 -0
- package/dist/presence/index.js +12 -0
- package/dist/presence/machine.cjs +50 -0
- package/dist/presence/machine.d.cts +10 -0
- package/dist/presence/machine.d.ts +10 -0
- package/dist/presence/machine.js +46 -0
- package/dist/presence/types.cjs +6 -0
- package/dist/presence/types.d.cts +32 -0
- package/dist/presence/types.d.ts +32 -0
- package/dist/presence/types.js +5 -0
- package/dist/repeat.cjs +311 -0
- package/dist/repeat.d.cts +174 -0
- package/dist/repeat.d.ts +174 -0
- package/dist/repeat.js +300 -0
- package/dist/spring.cjs +128 -0
- package/dist/spring.d.cts +18 -0
- package/dist/spring.d.ts +18 -0
- package/dist/spring.js +125 -0
- package/dist/subscriptions.cjs +74 -0
- package/dist/subscriptions.d.cts +19 -0
- package/dist/subscriptions.d.ts +19 -0
- package/dist/subscriptions.js +69 -0
- package/dist/subset/index.cjs +23 -0
- package/dist/subset/index.d.cts +6 -0
- package/dist/subset/index.d.ts +6 -0
- package/dist/subset/index.js +13 -0
- package/dist/subset/normalize.cjs +90 -0
- package/dist/subset/normalize.d.cts +10 -0
- package/dist/subset/normalize.d.ts +10 -0
- package/dist/subset/normalize.js +85 -0
- package/dist/subset/registry.cjs +259 -0
- package/dist/subset/registry.d.cts +25 -0
- package/dist/subset/registry.d.ts +25 -0
- package/dist/subset/registry.js +256 -0
- package/dist/subset/resolve.cjs +98 -0
- package/dist/subset/resolve.d.cts +24 -0
- package/dist/subset/resolve.d.ts +24 -0
- package/dist/subset/resolve.js +90 -0
- package/dist/timing.cjs +206 -0
- package/dist/timing.d.cts +17 -0
- package/dist/timing.d.ts +17 -0
- package/dist/timing.js +201 -0
- package/dist/transformTemplate.cjs +219 -0
- package/dist/transformTemplate.d.cts +29 -0
- package/dist/transformTemplate.d.ts +29 -0
- package/dist/transformTemplate.js +215 -0
- package/dist/transition.cjs +231 -0
- package/dist/transition.d.cts +89 -0
- package/dist/transition.d.ts +89 -0
- package/dist/transition.js +223 -0
- package/dist/types.cjs +4 -0
- package/dist/types.d.cts +175 -0
- package/dist/types.d.ts +175 -0
- package/dist/types.js +3 -0
- package/dist/value-types/color.cjs +220 -0
- package/dist/value-types/color.d.cts +19 -0
- package/dist/value-types/color.d.ts +19 -0
- package/dist/value-types/color.js +218 -0
- package/dist/value-types/complex.cjs +160 -0
- package/dist/value-types/complex.d.cts +19 -0
- package/dist/value-types/complex.d.ts +19 -0
- package/dist/value-types/complex.js +155 -0
- package/dist/value-types/constants.cjs +15 -0
- package/dist/value-types/constants.d.cts +6 -0
- package/dist/value-types/constants.d.ts +6 -0
- package/dist/value-types/constants.js +12 -0
- package/dist/value-types/discrete.cjs +62 -0
- package/dist/value-types/discrete.d.cts +4 -0
- package/dist/value-types/discrete.d.ts +4 -0
- package/dist/value-types/discrete.js +56 -0
- package/dist/value-types/index.cjs +59 -0
- package/dist/value-types/index.d.cts +14 -0
- package/dist/value-types/index.d.ts +14 -0
- package/dist/value-types/index.js +24 -0
- package/dist/value-types/measure-resolve.cjs +325 -0
- package/dist/value-types/measure-resolve.d.cts +91 -0
- package/dist/value-types/measure-resolve.d.ts +91 -0
- package/dist/value-types/measure-resolve.js +313 -0
- package/dist/value-types/mix.cjs +90 -0
- package/dist/value-types/mix.d.cts +27 -0
- package/dist/value-types/mix.d.ts +27 -0
- package/dist/value-types/mix.js +85 -0
- package/dist/value-types/named-colors.cjs +61 -0
- package/dist/value-types/named-colors.d.cts +2 -0
- package/dist/value-types/named-colors.d.ts +2 -0
- package/dist/value-types/named-colors.js +58 -0
- package/dist/value-types/numeric.cjs +86 -0
- package/dist/value-types/numeric.d.cts +16 -0
- package/dist/value-types/numeric.d.ts +16 -0
- package/dist/value-types/numeric.js +79 -0
- package/dist/worklet-layout/config/constants.js +39 -0
- package/dist/worklet-layout/layout/constants.js +11 -0
- package/dist/worklet-layout/layout/identity.js +699 -0
- package/dist/worklet-layout/layout/projection.js +98 -0
- package/dist/worklet-layout/layout/session.js +206 -0
- package/dist/worklet-layout/layout/tree.js +824 -0
- package/dist/worklet-layout/layout/types.js +36 -0
- package/dist/worklet-layout/spring.js +125 -0
- package/dist/worklet-layout/timing.js +201 -0
- package/dist/worklet-layout/transition.js +223 -0
- package/dist/worklet-layout.cjs +47 -0
- package/dist/worklet-layout.d.cts +15 -0
- package/dist/worklet-layout.d.ts +15 -0
- package/dist/worklet-layout.js +28 -0
- package/dist/wrap.cjs +7 -0
- package/dist/wrap.d.cts +1 -0
- package/dist/wrap.d.ts +1 -0
- package/dist/wrap.js +4 -0
- package/package.json +45 -0
|
@@ -0,0 +1,205 @@
|
|
|
1
|
+
"use strict";
|
|
2
|
+
Object.defineProperty(exports, "__esModule", { value: true });
|
|
3
|
+
exports.motionMix = motionMix;
|
|
4
|
+
// The public Motion `mix` utility. Pin: motion-dom/src/utils/mix/{index,complex,immediate,number}
|
|
5
|
+
// and value/types/color. H1 (REQ-VALUETYPE-016): arm SELECTION is the pin's `getMixer`, dispatching
|
|
6
|
+
// on the ORIGIN alone, and the arms the pin owns outright — array, object, color object,
|
|
7
|
+
// CSS-variable token, and the non-mixable fallback — run the pin's own algorithms, output-reference
|
|
8
|
+
// reuse included. The remaining string arm still executes through core's ONE value seam
|
|
9
|
+
// (parseValue → mix → transformValue): its per-family laws are unchanged here, and its recorded
|
|
10
|
+
// divergences from the pin — REQ-VALUETYPE-004/007/008 value-seam strictness and
|
|
11
|
+
// REQ-VALUETYPE-005/006 color-syntax capability — stay owned by those requirements and by their own
|
|
12
|
+
// doctrine-census rows, never by this file. REQ-VALUETYPE-015's both-visible discrete pair is no
|
|
13
|
+
// longer among them: H3 closed it, and the seam publishes the pin's zero-slot constant.
|
|
14
|
+
//
|
|
15
|
+
// Exported publicly as `mix` by the PRODUCT entries only — the core-root `mix` name stays the
|
|
16
|
+
// SPEC-VALUE-TYPES typed seam.
|
|
17
|
+
const value_types_1 = require("./value-types/index.cjs");
|
|
18
|
+
const color_1 = require("./value-types/color.cjs");
|
|
19
|
+
// pin mix/number.ts: unclamped linear interpolation through raw JavaScript arithmetic — a
|
|
20
|
+
// non-numeric operand yields NaN, it does not refuse.
|
|
21
|
+
function mixNumber(from, to, progress) {
|
|
22
|
+
return from + (to - from) * progress;
|
|
23
|
+
}
|
|
24
|
+
function numberMixer(from, to) {
|
|
25
|
+
return (p) => mixNumber(from, to, p);
|
|
26
|
+
}
|
|
27
|
+
// pin mix/immediate.ts: the origin until progress passes zero, then the target.
|
|
28
|
+
function mixImmediate(from, to) {
|
|
29
|
+
return (p) => (p > 0 ? to : from);
|
|
30
|
+
}
|
|
31
|
+
// pin animation/utils/is-css-variable.ts, reproduced verbatim (prefix guard + comment-stripped
|
|
32
|
+
// single-variable pattern). Native has no CSS custom properties to resolve, so the pin's immediate
|
|
33
|
+
// arm IS the faithful behavior — a refusal here would be a stricter native policy.
|
|
34
|
+
const SINGLE_CSS_VARIABLE_RE = /var\(--(?:[\w-]+\s*|[\w-]+\s*,(?:\s*[^)(\s]|\s*\((?:[^)(]|\([^)(]*\))*\))+\s*)\)$/iu;
|
|
35
|
+
function isCssVariableToken(value) {
|
|
36
|
+
if (!value.startsWith('var(--'))
|
|
37
|
+
return false;
|
|
38
|
+
return SINGLE_CSS_VARIABLE_RE.test((value.split('/*')[0] ?? '').trim());
|
|
39
|
+
}
|
|
40
|
+
// pin value/types/utils/single-color-regex.ts, reproduced verbatim (flags included) — the pin's
|
|
41
|
+
// colour RECOGNIZER. Core's own `isColor` is deliberately WIDER (a named-colour table,
|
|
42
|
+
// whitespace-padded channels — `motion.color-syntax-capability`), so this replica exists to answer
|
|
43
|
+
// the one question `colorMixer`'s degrade path cannot answer with core's recognizer: which PIN arm
|
|
44
|
+
// would own the pair. The reproduced stringification fault depends on it (LOOP Decision 53), and
|
|
45
|
+
// the differential's boundary rows pin both sides.
|
|
46
|
+
const SINGLE_COLOR_REGEX = /^(?:#[\da-f]{3,8}|(?:rgb|hsl)a?\((?:-?[\d.]+%?[,\s]+){2}-?[\d.]+%?\s*(?:[,/]\s*)?(?:\b\d+(?:\.\d+)?|\.\d+)?%?\))$/iu;
|
|
47
|
+
// pin value/types/color/index.ts `color.test` for the OBJECT arm: an own `red` property is an RGBA
|
|
48
|
+
// record, an own `hue` property an HSLA record. `Object.hasOwn` is the modern spelling of the pin's
|
|
49
|
+
// `Object.prototype.hasOwnProperty.call` and answers identically.
|
|
50
|
+
function isColorObject(value) {
|
|
51
|
+
return Object.hasOwn(value, 'red') || Object.hasOwn(value, 'hue');
|
|
52
|
+
}
|
|
53
|
+
const NOT_A_COLOR = { kind: 'not-a-color' };
|
|
54
|
+
function asRgba(value) {
|
|
55
|
+
if (typeof value === 'string') {
|
|
56
|
+
if (!(0, color_1.isColor)(value))
|
|
57
|
+
return NOT_A_COLOR;
|
|
58
|
+
const verdict = (0, color_1.parseColorVerdict)(value);
|
|
59
|
+
return verdict.refusal === null
|
|
60
|
+
? { kind: 'rgba', value: verdict.parsed }
|
|
61
|
+
: { kind: 'unparseable', refusal: verdict.refusal };
|
|
62
|
+
}
|
|
63
|
+
if (typeof value !== 'object' || value === null)
|
|
64
|
+
return NOT_A_COLOR;
|
|
65
|
+
if (Object.hasOwn(value, 'red'))
|
|
66
|
+
return { kind: 'rgba', value: value };
|
|
67
|
+
if (Object.hasOwn(value, 'hue')) {
|
|
68
|
+
const hsla = value;
|
|
69
|
+
return {
|
|
70
|
+
kind: 'rgba',
|
|
71
|
+
value: (0, color_1.hslaToRgba)(hsla.hue, hsla.saturation, hsla.lightness, hsla.alpha),
|
|
72
|
+
};
|
|
73
|
+
}
|
|
74
|
+
return NOT_A_COLOR;
|
|
75
|
+
}
|
|
76
|
+
// The pin's factory-time stringification of the endpoint that failed `asRgba`, reproduced so the
|
|
77
|
+
// same TypeError escapes at the same moment (LOOP Decision 53). Which pin arm would own the pair
|
|
78
|
+
// decides which operation the pin would fault on:
|
|
79
|
+
// - a `singleColorRegex` string origin, or a colour RECORD (the pin's object branch sends
|
|
80
|
+
// red/hue records to `mixColor` too): `mixColor`'s `asRGBA` interpolates the endpoint into its
|
|
81
|
+
// `warning()` template literal BEFORE returning false — throwing on a `Symbol`, an object with
|
|
82
|
+
// no `toString`, or a throwing `toString`; a nullish target stringifies fine there.
|
|
83
|
+
// - any other string origin core recognizes (a named colour, whitespace-padded rgb — the pairs
|
|
84
|
+
// core's WIDER recognizer routes here): `mixComplex`'s `analyseComplexValue`
|
|
85
|
+
// (value/types/complex/index.ts:21-22) opens with `const originalValue = value.toString()` and
|
|
86
|
+
// immediately parses the result with `.replace(complexRegex, …)` — throwing on a nullish
|
|
87
|
+
// target, on a target with no `toString`, AND on a `toString` that returns a non-string
|
|
88
|
+
// (`originalValue.replace is not a function`); tolerating a `Symbol` (its `toString` returns
|
|
89
|
+
// a string).
|
|
90
|
+
// For every pair the pin tolerates the operation is inert and the caller's step stands. `from` is
|
|
91
|
+
// never the failing endpoint here: `getMixer` only routes origins `asRgba` resolves.
|
|
92
|
+
function pinStringification(from, to) {
|
|
93
|
+
if (typeof from === 'string' && !SINGLE_COLOR_REGEX.test(from)) {
|
|
94
|
+
return pinComplexStringification(to);
|
|
95
|
+
}
|
|
96
|
+
return `${to}`;
|
|
97
|
+
}
|
|
98
|
+
// pin value/types/complex/index.ts `analyseComplexValue`'s fault surface, operation for operation:
|
|
99
|
+
// `const originalValue = value.toString()` then `originalValue.replace(complexRegex, …)`. The
|
|
100
|
+
// parameter is NAMED `value` because V8 quotes the receiver's source text in the TypeError, so the
|
|
101
|
+
// pin's message escapes byte-identically only under the pin's own identifier (the precedent is
|
|
102
|
+
// `arrayMixer`'s `blendValue`). The parse that follows the replace is the pin's semantics, not
|
|
103
|
+
// its fault surface, and is not reproduced. One acknowledged tail: the pin's `tokenised.split(...)`
|
|
104
|
+
// on the replace RESULT can still throw there (a `toString` returning a non-primitive object with
|
|
105
|
+
// a hostile `replace`) and is not reproduced — a contract-breaking constructed input, recorded by
|
|
106
|
+
// the confirming review as a non-blocking minor.
|
|
107
|
+
function pinComplexStringification(value) {
|
|
108
|
+
const originalValue = value.toString();
|
|
109
|
+
return originalValue.replace(/$/, '');
|
|
110
|
+
}
|
|
111
|
+
function colorMixer(from, to) {
|
|
112
|
+
const fromColor = asRgba(from);
|
|
113
|
+
const toColor = asRgba(to);
|
|
114
|
+
if (fromColor.kind === 'unparseable')
|
|
115
|
+
throw new Error(fromColor.refusal);
|
|
116
|
+
if (toColor.kind === 'unparseable')
|
|
117
|
+
throw new Error(toColor.refusal);
|
|
118
|
+
if (fromColor.kind === 'not-a-color' || toColor.kind === 'not-a-color') {
|
|
119
|
+
pinStringification(from, to);
|
|
120
|
+
return mixImmediate(from, to);
|
|
121
|
+
}
|
|
122
|
+
const fromRgba = fromColor.value;
|
|
123
|
+
const toRgba = toColor.value;
|
|
124
|
+
return (p) => (0, color_1.transformColor)((0, color_1.mixColor)(fromRgba, toRgba, p));
|
|
125
|
+
}
|
|
126
|
+
// The one core value seam (SPEC-VALUE-TYPES §3) — the pin's `mixComplex` position in the dispatch
|
|
127
|
+
// table. A non-string target has no decomposition here, so it stays the seam's own loud
|
|
128
|
+
// cross-family refusal (REQ-VALUETYPE-008, `motion.value-seam-strictness`).
|
|
129
|
+
function seamMixer(from, to) {
|
|
130
|
+
if (typeof to !== 'string') {
|
|
131
|
+
throw new Error(`mix: cannot mix ${JSON.stringify(from)} with ${JSON.stringify(to)} — a value-seam origin ` +
|
|
132
|
+
'needs a string target of one value family (REQ-VALUETYPE-008)');
|
|
133
|
+
}
|
|
134
|
+
const fromTyped = (0, value_types_1.parseValue)(from);
|
|
135
|
+
const toTyped = (0, value_types_1.parseValue)(to);
|
|
136
|
+
return (p) => {
|
|
137
|
+
const committed = (0, value_types_1.transformValue)((0, value_types_1.mix)(fromTyped, toTyped, p));
|
|
138
|
+
return typeof committed === 'number' ? String(committed) : committed;
|
|
139
|
+
};
|
|
140
|
+
}
|
|
141
|
+
// pin mix/complex.ts `mixArray`: the ORIGIN governs length and arm choice, and ONE output array is
|
|
142
|
+
// mutated in place and handed back on every call.
|
|
143
|
+
function arrayMixer(from, to) {
|
|
144
|
+
const origin = from;
|
|
145
|
+
const target = to;
|
|
146
|
+
const output = [...origin];
|
|
147
|
+
const numValues = output.length;
|
|
148
|
+
// Named `blendValue` to match the pin's own local: `Array#map` SKIPS holes, so a sparse origin
|
|
149
|
+
// leaves a hole here and the call below raises the pin's `blendValue[i] is not a function`
|
|
150
|
+
// TypeError — byte-identical only if the identifier is. Guarding the hole instead would suppress
|
|
151
|
+
// a pin fault of exactly the class LOOP Decision 25 keeps.
|
|
152
|
+
const blendValue = origin.map((value, i) => getMixer(value)(value, target[i]));
|
|
153
|
+
return (p) => {
|
|
154
|
+
for (let i = 0; i < numValues; i++) {
|
|
155
|
+
output[i] = blendValue[i](p);
|
|
156
|
+
}
|
|
157
|
+
return output;
|
|
158
|
+
};
|
|
159
|
+
}
|
|
160
|
+
// pin mix/complex.ts `mixObject`: a UNION snapshot of both sides, only both-defined keys blended,
|
|
161
|
+
// and ONE output object mutated in place and handed back on every call. `for…in` and the direct
|
|
162
|
+
// `origin[key]` read are the pin's own operations — a null origin against a populated target
|
|
163
|
+
// raises the pin's `TypeError` here, which the fidelity presumption keeps rather than guarding.
|
|
164
|
+
function objectMixer(from, to) {
|
|
165
|
+
const origin = from;
|
|
166
|
+
const target = to;
|
|
167
|
+
const output = { ...origin, ...target };
|
|
168
|
+
const blendValue = {};
|
|
169
|
+
for (const key in output) {
|
|
170
|
+
if (origin[key] !== undefined && target[key] !== undefined) {
|
|
171
|
+
blendValue[key] = getMixer(origin[key])(origin[key], target[key]);
|
|
172
|
+
}
|
|
173
|
+
}
|
|
174
|
+
return (p) => {
|
|
175
|
+
for (const key in blendValue) {
|
|
176
|
+
output[key] = blendValue[key](p);
|
|
177
|
+
}
|
|
178
|
+
return output;
|
|
179
|
+
};
|
|
180
|
+
}
|
|
181
|
+
// pin mix/complex.ts `getMixer`, branch for branch. `typeof from === 'object'` deliberately
|
|
182
|
+
// includes `null`, exactly as the pin's does.
|
|
183
|
+
function getMixer(from) {
|
|
184
|
+
if (typeof from === 'number')
|
|
185
|
+
return numberMixer;
|
|
186
|
+
if (typeof from === 'string') {
|
|
187
|
+
if (isCssVariableToken(from))
|
|
188
|
+
return mixImmediate;
|
|
189
|
+
return (0, color_1.isColor)(from) ? colorMixer : seamMixer;
|
|
190
|
+
}
|
|
191
|
+
if (Array.isArray(from))
|
|
192
|
+
return arrayMixer;
|
|
193
|
+
if (typeof from === 'object') {
|
|
194
|
+
return from !== null && isColorObject(from) ? colorMixer : objectMixer;
|
|
195
|
+
}
|
|
196
|
+
return mixImmediate;
|
|
197
|
+
}
|
|
198
|
+
function motionMix(from, to, p) {
|
|
199
|
+
// pin mix/index.ts: the immediate form requires all THREE arguments to be numbers; otherwise the
|
|
200
|
+
// third is ignored and the factory is returned.
|
|
201
|
+
if (typeof from === 'number' && typeof to === 'number' && typeof p === 'number') {
|
|
202
|
+
return mixNumber(from, to, p);
|
|
203
|
+
}
|
|
204
|
+
return getMixer(from)(from, to);
|
|
205
|
+
}
|
|
@@ -0,0 +1,202 @@
|
|
|
1
|
+
// The public Motion `mix` utility. Pin: motion-dom/src/utils/mix/{index,complex,immediate,number}
|
|
2
|
+
// and value/types/color. H1 (REQ-VALUETYPE-016): arm SELECTION is the pin's `getMixer`, dispatching
|
|
3
|
+
// on the ORIGIN alone, and the arms the pin owns outright — array, object, color object,
|
|
4
|
+
// CSS-variable token, and the non-mixable fallback — run the pin's own algorithms, output-reference
|
|
5
|
+
// reuse included. The remaining string arm still executes through core's ONE value seam
|
|
6
|
+
// (parseValue → mix → transformValue): its per-family laws are unchanged here, and its recorded
|
|
7
|
+
// divergences from the pin — REQ-VALUETYPE-004/007/008 value-seam strictness and
|
|
8
|
+
// REQ-VALUETYPE-005/006 color-syntax capability — stay owned by those requirements and by their own
|
|
9
|
+
// doctrine-census rows, never by this file. REQ-VALUETYPE-015's both-visible discrete pair is no
|
|
10
|
+
// longer among them: H3 closed it, and the seam publishes the pin's zero-slot constant.
|
|
11
|
+
//
|
|
12
|
+
// Exported publicly as `mix` by the PRODUCT entries only — the core-root `mix` name stays the
|
|
13
|
+
// SPEC-VALUE-TYPES typed seam.
|
|
14
|
+
import { mix as mixTyped, parseValue, transformValue } from "./value-types/index.js";
|
|
15
|
+
import { hslaToRgba, isColor, mixColor, parseColorVerdict, transformColor, } from "./value-types/color.js";
|
|
16
|
+
// pin mix/number.ts: unclamped linear interpolation through raw JavaScript arithmetic — a
|
|
17
|
+
// non-numeric operand yields NaN, it does not refuse.
|
|
18
|
+
function mixNumber(from, to, progress) {
|
|
19
|
+
return from + (to - from) * progress;
|
|
20
|
+
}
|
|
21
|
+
function numberMixer(from, to) {
|
|
22
|
+
return (p) => mixNumber(from, to, p);
|
|
23
|
+
}
|
|
24
|
+
// pin mix/immediate.ts: the origin until progress passes zero, then the target.
|
|
25
|
+
function mixImmediate(from, to) {
|
|
26
|
+
return (p) => (p > 0 ? to : from);
|
|
27
|
+
}
|
|
28
|
+
// pin animation/utils/is-css-variable.ts, reproduced verbatim (prefix guard + comment-stripped
|
|
29
|
+
// single-variable pattern). Native has no CSS custom properties to resolve, so the pin's immediate
|
|
30
|
+
// arm IS the faithful behavior — a refusal here would be a stricter native policy.
|
|
31
|
+
const SINGLE_CSS_VARIABLE_RE = /var\(--(?:[\w-]+\s*|[\w-]+\s*,(?:\s*[^)(\s]|\s*\((?:[^)(]|\([^)(]*\))*\))+\s*)\)$/iu;
|
|
32
|
+
function isCssVariableToken(value) {
|
|
33
|
+
if (!value.startsWith('var(--'))
|
|
34
|
+
return false;
|
|
35
|
+
return SINGLE_CSS_VARIABLE_RE.test((value.split('/*')[0] ?? '').trim());
|
|
36
|
+
}
|
|
37
|
+
// pin value/types/utils/single-color-regex.ts, reproduced verbatim (flags included) — the pin's
|
|
38
|
+
// colour RECOGNIZER. Core's own `isColor` is deliberately WIDER (a named-colour table,
|
|
39
|
+
// whitespace-padded channels — `motion.color-syntax-capability`), so this replica exists to answer
|
|
40
|
+
// the one question `colorMixer`'s degrade path cannot answer with core's recognizer: which PIN arm
|
|
41
|
+
// would own the pair. The reproduced stringification fault depends on it (LOOP Decision 53), and
|
|
42
|
+
// the differential's boundary rows pin both sides.
|
|
43
|
+
const SINGLE_COLOR_REGEX = /^(?:#[\da-f]{3,8}|(?:rgb|hsl)a?\((?:-?[\d.]+%?[,\s]+){2}-?[\d.]+%?\s*(?:[,/]\s*)?(?:\b\d+(?:\.\d+)?|\.\d+)?%?\))$/iu;
|
|
44
|
+
// pin value/types/color/index.ts `color.test` for the OBJECT arm: an own `red` property is an RGBA
|
|
45
|
+
// record, an own `hue` property an HSLA record. `Object.hasOwn` is the modern spelling of the pin's
|
|
46
|
+
// `Object.prototype.hasOwnProperty.call` and answers identically.
|
|
47
|
+
function isColorObject(value) {
|
|
48
|
+
return Object.hasOwn(value, 'red') || Object.hasOwn(value, 'hue');
|
|
49
|
+
}
|
|
50
|
+
const NOT_A_COLOR = { kind: 'not-a-color' };
|
|
51
|
+
function asRgba(value) {
|
|
52
|
+
if (typeof value === 'string') {
|
|
53
|
+
if (!isColor(value))
|
|
54
|
+
return NOT_A_COLOR;
|
|
55
|
+
const verdict = parseColorVerdict(value);
|
|
56
|
+
return verdict.refusal === null
|
|
57
|
+
? { kind: 'rgba', value: verdict.parsed }
|
|
58
|
+
: { kind: 'unparseable', refusal: verdict.refusal };
|
|
59
|
+
}
|
|
60
|
+
if (typeof value !== 'object' || value === null)
|
|
61
|
+
return NOT_A_COLOR;
|
|
62
|
+
if (Object.hasOwn(value, 'red'))
|
|
63
|
+
return { kind: 'rgba', value: value };
|
|
64
|
+
if (Object.hasOwn(value, 'hue')) {
|
|
65
|
+
const hsla = value;
|
|
66
|
+
return {
|
|
67
|
+
kind: 'rgba',
|
|
68
|
+
value: hslaToRgba(hsla.hue, hsla.saturation, hsla.lightness, hsla.alpha),
|
|
69
|
+
};
|
|
70
|
+
}
|
|
71
|
+
return NOT_A_COLOR;
|
|
72
|
+
}
|
|
73
|
+
// The pin's factory-time stringification of the endpoint that failed `asRgba`, reproduced so the
|
|
74
|
+
// same TypeError escapes at the same moment (LOOP Decision 53). Which pin arm would own the pair
|
|
75
|
+
// decides which operation the pin would fault on:
|
|
76
|
+
// - a `singleColorRegex` string origin, or a colour RECORD (the pin's object branch sends
|
|
77
|
+
// red/hue records to `mixColor` too): `mixColor`'s `asRGBA` interpolates the endpoint into its
|
|
78
|
+
// `warning()` template literal BEFORE returning false — throwing on a `Symbol`, an object with
|
|
79
|
+
// no `toString`, or a throwing `toString`; a nullish target stringifies fine there.
|
|
80
|
+
// - any other string origin core recognizes (a named colour, whitespace-padded rgb — the pairs
|
|
81
|
+
// core's WIDER recognizer routes here): `mixComplex`'s `analyseComplexValue`
|
|
82
|
+
// (value/types/complex/index.ts:21-22) opens with `const originalValue = value.toString()` and
|
|
83
|
+
// immediately parses the result with `.replace(complexRegex, …)` — throwing on a nullish
|
|
84
|
+
// target, on a target with no `toString`, AND on a `toString` that returns a non-string
|
|
85
|
+
// (`originalValue.replace is not a function`); tolerating a `Symbol` (its `toString` returns
|
|
86
|
+
// a string).
|
|
87
|
+
// For every pair the pin tolerates the operation is inert and the caller's step stands. `from` is
|
|
88
|
+
// never the failing endpoint here: `getMixer` only routes origins `asRgba` resolves.
|
|
89
|
+
function pinStringification(from, to) {
|
|
90
|
+
if (typeof from === 'string' && !SINGLE_COLOR_REGEX.test(from)) {
|
|
91
|
+
return pinComplexStringification(to);
|
|
92
|
+
}
|
|
93
|
+
return `${to}`;
|
|
94
|
+
}
|
|
95
|
+
// pin value/types/complex/index.ts `analyseComplexValue`'s fault surface, operation for operation:
|
|
96
|
+
// `const originalValue = value.toString()` then `originalValue.replace(complexRegex, …)`. The
|
|
97
|
+
// parameter is NAMED `value` because V8 quotes the receiver's source text in the TypeError, so the
|
|
98
|
+
// pin's message escapes byte-identically only under the pin's own identifier (the precedent is
|
|
99
|
+
// `arrayMixer`'s `blendValue`). The parse that follows the replace is the pin's semantics, not
|
|
100
|
+
// its fault surface, and is not reproduced. One acknowledged tail: the pin's `tokenised.split(...)`
|
|
101
|
+
// on the replace RESULT can still throw there (a `toString` returning a non-primitive object with
|
|
102
|
+
// a hostile `replace`) and is not reproduced — a contract-breaking constructed input, recorded by
|
|
103
|
+
// the confirming review as a non-blocking minor.
|
|
104
|
+
function pinComplexStringification(value) {
|
|
105
|
+
const originalValue = value.toString();
|
|
106
|
+
return originalValue.replace(/$/, '');
|
|
107
|
+
}
|
|
108
|
+
function colorMixer(from, to) {
|
|
109
|
+
const fromColor = asRgba(from);
|
|
110
|
+
const toColor = asRgba(to);
|
|
111
|
+
if (fromColor.kind === 'unparseable')
|
|
112
|
+
throw new Error(fromColor.refusal);
|
|
113
|
+
if (toColor.kind === 'unparseable')
|
|
114
|
+
throw new Error(toColor.refusal);
|
|
115
|
+
if (fromColor.kind === 'not-a-color' || toColor.kind === 'not-a-color') {
|
|
116
|
+
pinStringification(from, to);
|
|
117
|
+
return mixImmediate(from, to);
|
|
118
|
+
}
|
|
119
|
+
const fromRgba = fromColor.value;
|
|
120
|
+
const toRgba = toColor.value;
|
|
121
|
+
return (p) => transformColor(mixColor(fromRgba, toRgba, p));
|
|
122
|
+
}
|
|
123
|
+
// The one core value seam (SPEC-VALUE-TYPES §3) — the pin's `mixComplex` position in the dispatch
|
|
124
|
+
// table. A non-string target has no decomposition here, so it stays the seam's own loud
|
|
125
|
+
// cross-family refusal (REQ-VALUETYPE-008, `motion.value-seam-strictness`).
|
|
126
|
+
function seamMixer(from, to) {
|
|
127
|
+
if (typeof to !== 'string') {
|
|
128
|
+
throw new Error(`mix: cannot mix ${JSON.stringify(from)} with ${JSON.stringify(to)} — a value-seam origin ` +
|
|
129
|
+
'needs a string target of one value family (REQ-VALUETYPE-008)');
|
|
130
|
+
}
|
|
131
|
+
const fromTyped = parseValue(from);
|
|
132
|
+
const toTyped = parseValue(to);
|
|
133
|
+
return (p) => {
|
|
134
|
+
const committed = transformValue(mixTyped(fromTyped, toTyped, p));
|
|
135
|
+
return typeof committed === 'number' ? String(committed) : committed;
|
|
136
|
+
};
|
|
137
|
+
}
|
|
138
|
+
// pin mix/complex.ts `mixArray`: the ORIGIN governs length and arm choice, and ONE output array is
|
|
139
|
+
// mutated in place and handed back on every call.
|
|
140
|
+
function arrayMixer(from, to) {
|
|
141
|
+
const origin = from;
|
|
142
|
+
const target = to;
|
|
143
|
+
const output = [...origin];
|
|
144
|
+
const numValues = output.length;
|
|
145
|
+
// Named `blendValue` to match the pin's own local: `Array#map` SKIPS holes, so a sparse origin
|
|
146
|
+
// leaves a hole here and the call below raises the pin's `blendValue[i] is not a function`
|
|
147
|
+
// TypeError — byte-identical only if the identifier is. Guarding the hole instead would suppress
|
|
148
|
+
// a pin fault of exactly the class LOOP Decision 25 keeps.
|
|
149
|
+
const blendValue = origin.map((value, i) => getMixer(value)(value, target[i]));
|
|
150
|
+
return (p) => {
|
|
151
|
+
for (let i = 0; i < numValues; i++) {
|
|
152
|
+
output[i] = blendValue[i](p);
|
|
153
|
+
}
|
|
154
|
+
return output;
|
|
155
|
+
};
|
|
156
|
+
}
|
|
157
|
+
// pin mix/complex.ts `mixObject`: a UNION snapshot of both sides, only both-defined keys blended,
|
|
158
|
+
// and ONE output object mutated in place and handed back on every call. `for…in` and the direct
|
|
159
|
+
// `origin[key]` read are the pin's own operations — a null origin against a populated target
|
|
160
|
+
// raises the pin's `TypeError` here, which the fidelity presumption keeps rather than guarding.
|
|
161
|
+
function objectMixer(from, to) {
|
|
162
|
+
const origin = from;
|
|
163
|
+
const target = to;
|
|
164
|
+
const output = { ...origin, ...target };
|
|
165
|
+
const blendValue = {};
|
|
166
|
+
for (const key in output) {
|
|
167
|
+
if (origin[key] !== undefined && target[key] !== undefined) {
|
|
168
|
+
blendValue[key] = getMixer(origin[key])(origin[key], target[key]);
|
|
169
|
+
}
|
|
170
|
+
}
|
|
171
|
+
return (p) => {
|
|
172
|
+
for (const key in blendValue) {
|
|
173
|
+
output[key] = blendValue[key](p);
|
|
174
|
+
}
|
|
175
|
+
return output;
|
|
176
|
+
};
|
|
177
|
+
}
|
|
178
|
+
// pin mix/complex.ts `getMixer`, branch for branch. `typeof from === 'object'` deliberately
|
|
179
|
+
// includes `null`, exactly as the pin's does.
|
|
180
|
+
function getMixer(from) {
|
|
181
|
+
if (typeof from === 'number')
|
|
182
|
+
return numberMixer;
|
|
183
|
+
if (typeof from === 'string') {
|
|
184
|
+
if (isCssVariableToken(from))
|
|
185
|
+
return mixImmediate;
|
|
186
|
+
return isColor(from) ? colorMixer : seamMixer;
|
|
187
|
+
}
|
|
188
|
+
if (Array.isArray(from))
|
|
189
|
+
return arrayMixer;
|
|
190
|
+
if (typeof from === 'object') {
|
|
191
|
+
return from !== null && isColorObject(from) ? colorMixer : objectMixer;
|
|
192
|
+
}
|
|
193
|
+
return mixImmediate;
|
|
194
|
+
}
|
|
195
|
+
export function motionMix(from, to, p) {
|
|
196
|
+
// pin mix/index.ts: the immediate form requires all THREE arguments to be numbers; otherwise the
|
|
197
|
+
// third is ignored and the factory is returned.
|
|
198
|
+
if (typeof from === 'number' && typeof to === 'number' && typeof p === 'number') {
|
|
199
|
+
return mixNumber(from, to, p);
|
|
200
|
+
}
|
|
201
|
+
return getMixer(from)(from, to);
|
|
202
|
+
}
|