@vizij/node-graph-authoring 0.0.5 → 0.1.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/index.cjs CHANGED
@@ -33,9 +33,7 @@ __export(index_exports, {
33
33
  bindingTargetFromInput: () => bindingTargetFromInput,
34
34
  bindingToDefinition: () => bindingToDefinition,
35
35
  buildCanonicalBindingExpression: () => buildCanonicalBindingExpression,
36
- buildDefaultSlotExpression: () => buildDefaultSlotExpression,
37
36
  buildMachineReport: () => buildMachineReport,
38
- buildPiecewiseRemapExpression: () => buildPiecewiseRemapExpression,
39
37
  buildRigGraphSpec: () => buildRigGraphSpec,
40
38
  collectExpressionReferences: () => collectExpressionReferences,
41
39
  compileIrGraph: () => compileIrGraph,
@@ -43,7 +41,6 @@ __export(index_exports, {
43
41
  createDefaultBindings: () => createDefaultBindings,
44
42
  createDefaultInputValues: () => createDefaultInputValues,
45
43
  createDefaultParentBinding: () => createDefaultParentBinding,
46
- createDefaultRemap: () => createDefaultRemap,
47
44
  createExpressionVariableTable: () => createExpressionVariableTable,
48
45
  createIrGraphBuilder: () => createIrGraphBuilder,
49
46
  createLegacyIrGraph: () => createLegacyIrGraph,
@@ -53,20 +50,19 @@ __export(index_exports, {
53
50
  mapExpression: () => mapExpression,
54
51
  parseControlExpression: () => parseControlExpression,
55
52
  reconcileBindings: () => reconcileBindings,
56
- remapValue: () => remapValue,
57
53
  removeBindingSlot: () => removeBindingSlot,
58
54
  toIrBindingSummary: () => toIrBindingSummary,
59
55
  updateBindingExpression: () => updateBindingExpression,
60
56
  updateBindingSlotAlias: () => updateBindingSlotAlias,
61
- updateBindingSlotRemap: () => updateBindingSlotRemap,
62
57
  updateBindingSlotValueType: () => updateBindingSlotValueType,
63
58
  updateBindingWithInput: () => updateBindingWithInput
64
59
  });
65
60
  module.exports = __toCommonJS(index_exports);
66
61
 
67
62
  // src/graphBuilder.ts
68
- var import_utils2 = require("@vizij/utils");
69
- var import_utils3 = require("@vizij/utils");
63
+ var import_utils4 = require("@vizij/utils");
64
+ var import_utils5 = require("@vizij/utils");
65
+ var import_metadata2 = require("@vizij/node-graph-wasm/metadata");
70
66
 
71
67
  // src/state.ts
72
68
  var import_utils = require("@vizij/utils");
@@ -108,9 +104,6 @@ function bindingTargetFromInput(input) {
108
104
  valueType: "scalar"
109
105
  };
110
106
  }
111
- var DEFAULT_INPUT_RANGE = { min: -1, max: 1 };
112
- var DEFAULT_INPUT_ANCHOR = 0;
113
- var EPSILON = 1e-6;
114
107
  var LEGACY_SLOT_PATTERN = /^slot_(\d+)$/i;
115
108
  var ALIAS_SANITIZE_PATTERN = /[^A-Za-z0-9_]+/g;
116
109
  var PRIMARY_SLOT_ID = "s1";
@@ -186,131 +179,11 @@ function rewriteLegacyExpression(expression, replacements) {
186
179
  return `s${digits}`;
187
180
  });
188
181
  }
189
- function clamp(value, min, max) {
190
- return Math.min(max, Math.max(min, value));
191
- }
192
- function isFiniteNumber(value) {
193
- return typeof value === "number" && Number.isFinite(value);
194
- }
195
- function deriveOutputDefaults(target) {
196
- const { min, max } = target.range;
197
- const anchor = clamp(target.defaultValue, min, max);
198
- return {
199
- outLow: min,
200
- outAnchor: anchor,
201
- outHigh: max
202
- };
203
- }
204
- function deriveInputDefaults() {
205
- return {
206
- inLow: DEFAULT_INPUT_RANGE.min,
207
- inAnchor: DEFAULT_INPUT_ANCHOR,
208
- inHigh: DEFAULT_INPUT_RANGE.max
209
- };
210
- }
211
- function migrateLegacyRemap(legacy, target) {
212
- const inputDefaults = deriveInputDefaults();
213
- const outputDefaults = deriveOutputDefaults(target);
214
- const defaults = {
215
- inLow: inputDefaults.inLow,
216
- inAnchor: inputDefaults.inAnchor,
217
- inHigh: inputDefaults.inHigh,
218
- outLow: outputDefaults.outLow,
219
- outAnchor: outputDefaults.outAnchor,
220
- outHigh: outputDefaults.outHigh
221
- };
222
- if ("inLow" in legacy && "inHigh" in legacy && "outLow" in legacy && "outHigh" in legacy) {
223
- const inLow2 = isFiniteNumber(legacy.inLow) ? legacy.inLow : defaults.inLow;
224
- const inAnchor2 = isFiniteNumber(legacy.inAnchor) ? legacy.inAnchor : defaults.inAnchor;
225
- const inHigh2 = isFiniteNumber(legacy.inHigh) ? legacy.inHigh : defaults.inHigh;
226
- let outLow = isFiniteNumber(legacy.outLow) ? legacy.outLow : defaults.outLow;
227
- let outHigh = isFiniteNumber(legacy.outHigh) ? legacy.outHigh : defaults.outHigh;
228
- if (outLow > outHigh) {
229
- const low = outHigh;
230
- const high = outLow;
231
- outLow = low;
232
- outHigh = high;
233
- }
234
- const outAnchor2 = clamp(
235
- isFiniteNumber(legacy.outAnchor) ? legacy.outAnchor : defaults.outAnchor,
236
- outLow,
237
- outHigh
238
- );
239
- return {
240
- inLow: inLow2,
241
- inAnchor: inAnchor2,
242
- inHigh: inHigh2,
243
- outLow,
244
- outAnchor: outAnchor2,
245
- outHigh
246
- };
247
- }
248
- const legacyTyped = legacy;
249
- const inLow = isFiniteNumber(legacyTyped.inMin) ? legacyTyped.inMin : defaults.inLow;
250
- const inHigh = isFiniteNumber(legacyTyped.inMax) ? legacyTyped.inMax : defaults.inHigh;
251
- const inAnchor = (inLow + inHigh) / 2;
252
- const legacyOutMid = isFiniteNumber(legacyTyped.outMin) && isFiniteNumber(legacyTyped.outMax) ? (legacyTyped.outMin + legacyTyped.outMax) / 2 : defaults.outAnchor;
253
- const outAnchor = clamp(legacyOutMid, defaults.outLow, defaults.outHigh);
254
- return {
255
- inLow,
256
- inAnchor,
257
- inHigh,
258
- outLow: defaults.outLow,
259
- outAnchor,
260
- outHigh: defaults.outHigh
261
- };
262
- }
263
- function normalizeRemap(remap, target) {
264
- if (!remap) {
265
- return createDefaultRemap(target);
266
- }
267
- return migrateLegacyRemap(remap, target);
268
- }
269
- function cloneRemap(remap) {
270
- return (0, import_utils.cloneRemapSettings)(remap);
271
- }
272
182
  function cloneBindingMetadata(metadata) {
273
183
  if (!metadata) {
274
184
  return void 0;
275
185
  }
276
- return JSON.parse(JSON.stringify(metadata));
277
- }
278
- function sanitizeRemap(remap, target) {
279
- const normalized = normalizeRemap(remap, target);
280
- const outputDefaults = deriveOutputDefaults(target);
281
- if (!Number.isFinite(normalized.outLow)) {
282
- normalized.outLow = outputDefaults.outLow;
283
- }
284
- if (!Number.isFinite(normalized.outHigh)) {
285
- normalized.outHigh = outputDefaults.outHigh;
286
- }
287
- if (!Number.isFinite(normalized.outAnchor)) {
288
- normalized.outAnchor = outputDefaults.outAnchor;
289
- }
290
- if (normalized.outLow > normalized.outHigh) {
291
- const low = normalized.outHigh;
292
- const high = normalized.outLow;
293
- normalized.outLow = low;
294
- normalized.outHigh = high;
295
- }
296
- normalized.outAnchor = clamp(
297
- normalized.outAnchor,
298
- normalized.outLow,
299
- normalized.outHigh
300
- );
301
- return normalized;
302
- }
303
- function createDefaultRemap(target) {
304
- const inputDefaults = deriveInputDefaults();
305
- const outputDefaults = deriveOutputDefaults(target);
306
- return {
307
- inLow: inputDefaults.inLow,
308
- inAnchor: inputDefaults.inAnchor,
309
- inHigh: inputDefaults.inHigh,
310
- outLow: outputDefaults.outLow,
311
- outAnchor: outputDefaults.outAnchor,
312
- outHigh: outputDefaults.outHigh
313
- };
186
+ return (0, import_utils.cloneDeepSafe)(metadata);
314
187
  }
315
188
  function createDefaultBindings(components) {
316
189
  const bindings = {};
@@ -320,21 +193,18 @@ function createDefaultBindings(components) {
320
193
  return bindings;
321
194
  }
322
195
  function createDefaultBinding(component) {
323
- const remap = createDefaultRemap(component);
324
196
  const valueType = getTargetValueType(component);
325
197
  const slots = [
326
198
  {
327
199
  id: PRIMARY_SLOT_ID,
328
200
  alias: PRIMARY_SLOT_ALIAS,
329
201
  inputId: null,
330
- remap: cloneRemap(remap),
331
202
  valueType
332
203
  }
333
204
  ];
334
205
  return {
335
206
  targetId: component.id,
336
207
  inputId: null,
337
- remap,
338
208
  slots,
339
209
  expression: buildCanonicalExpressionFromSlots(slots)
340
210
  };
@@ -360,7 +230,6 @@ function createDefaultParentBinding(component) {
360
230
  };
361
231
  }
362
232
  function ensurePrimarySlot(binding, target) {
363
- const normalizedBindingRemap = sanitizeRemap(binding.remap, target);
364
233
  const targetValueType = getTargetValueType(target);
365
234
  const aliasReplacements = /* @__PURE__ */ new Map();
366
235
  const sourceSlots = Array.isArray(binding.slots) && binding.slots.length > 0 ? binding.slots : [
@@ -368,7 +237,6 @@ function ensurePrimarySlot(binding, target) {
368
237
  id: PRIMARY_SLOT_ID,
369
238
  alias: PRIMARY_SLOT_ALIAS,
370
239
  inputId: binding.inputId ?? null,
371
- remap: cloneRemap(normalizedBindingRemap),
372
240
  valueType: targetValueType
373
241
  }
374
242
  ];
@@ -383,8 +251,6 @@ function ensurePrimarySlot(binding, target) {
383
251
  if (replaced && replaced !== normalizedAlias) {
384
252
  aliasReplacements.set(replaced, normalizedAlias);
385
253
  }
386
- const slotRemapSource = slot.remap ?? (index === 0 ? normalizedBindingRemap : createDefaultRemap(target));
387
- const normalizedSlotRemap = sanitizeRemap(slotRemapSource, target);
388
254
  const inputId = slot.inputId !== void 0 && slot.inputId !== null ? slot.inputId : index === 0 ? binding.inputId ?? null : null;
389
255
  const slotValueType = sanitizeSlotValueType(
390
256
  slot.valueType,
@@ -394,13 +260,11 @@ function ensurePrimarySlot(binding, target) {
394
260
  id: normalizedId,
395
261
  alias: normalizedAlias,
396
262
  inputId,
397
- remap: cloneRemap(normalizedSlotRemap),
398
263
  valueType: slotValueType
399
264
  };
400
265
  }
401
266
  );
402
267
  const primary = normalizedSlots[0];
403
- const primaryRemap = sanitizeRemap(primary.remap, target);
404
268
  const primaryInputId = primary.inputId === import_utils.SELF_BINDING_ID ? import_utils.SELF_BINDING_ID : primary.inputId ?? binding.inputId ?? null;
405
269
  const primaryAlias = primaryInputId === import_utils.SELF_BINDING_ID ? "self" : primary.alias || PRIMARY_SLOT_ALIAS;
406
270
  normalizedSlots[0] = {
@@ -408,16 +272,13 @@ function ensurePrimarySlot(binding, target) {
408
272
  id: primary.id || PRIMARY_SLOT_ID,
409
273
  alias: primaryAlias,
410
274
  inputId: primaryInputId,
411
- remap: cloneRemap(primaryRemap),
412
275
  valueType: sanitizeSlotValueType(primary.valueType, targetValueType)
413
276
  };
414
277
  normalizedSlots.slice(1).forEach((slot, index) => {
415
- const slotRemap = sanitizeRemap(slot.remap, target);
416
278
  normalizedSlots[index + 1] = {
417
279
  ...slot,
418
280
  id: slot.id || defaultSlotId(index + 1),
419
281
  alias: slot.alias || defaultSlotId(index + 1),
420
- remap: cloneRemap(slotRemap),
421
282
  valueType: sanitizeSlotValueType(slot.valueType, targetValueType)
422
283
  };
423
284
  });
@@ -432,7 +293,6 @@ function ensurePrimarySlot(binding, target) {
432
293
  const normalizedBinding = {
433
294
  ...binding,
434
295
  inputId: normalizedSlots[0].inputId ?? null,
435
- remap: cloneRemap(primaryRemap),
436
296
  slots: normalizedSlots,
437
297
  expression
438
298
  };
@@ -459,14 +319,13 @@ function addBindingSlot(binding, target) {
459
319
  const nextIndex = base.slots.length + 1;
460
320
  const slotId = defaultSlotId(nextIndex - 1);
461
321
  const alias = slotId;
462
- const remap = createDefaultRemap(target);
463
322
  const nextSlots = [
464
323
  ...base.slots,
465
324
  {
466
325
  id: slotId,
467
326
  alias,
468
327
  inputId: null,
469
- remap: cloneRemap(remap)
328
+ valueType: getTargetValueType(target)
470
329
  }
471
330
  ];
472
331
  return ensurePrimarySlot(
@@ -580,50 +439,6 @@ function updateBindingExpression(binding, target, expression) {
580
439
  expression: trimmed.length > 0 ? trimmed : canonicalExpression
581
440
  };
582
441
  }
583
- function updateBindingSlotRemap(binding, target, slotId, field, value) {
584
- const base = ensurePrimarySlot(binding, target);
585
- const existingExpression = typeof base.expression === "string" ? base.expression.trim() : "";
586
- const canonicalBefore = buildCanonicalExpressionFromSlots(base.slots);
587
- const expressionWasDefault = expressionMatchesAliasOnly(existingExpression, base.slots) || expressionsEquivalent(existingExpression, canonicalBefore);
588
- const nextSlots = base.slots.map((slot) => {
589
- if (slot.id !== slotId) {
590
- return slot;
591
- }
592
- const updatedRemap = {
593
- ...slot.remap,
594
- [field]: value
595
- };
596
- const sanitized = sanitizeRemap(updatedRemap, target);
597
- return {
598
- ...slot,
599
- remap: cloneRemap(sanitized)
600
- };
601
- });
602
- const updated = ensurePrimarySlot(
603
- {
604
- ...base,
605
- slots: nextSlots
606
- },
607
- target
608
- );
609
- if (updated.slots[0]?.id === slotId) {
610
- updated.remap = {
611
- ...updated.remap,
612
- [field]: value
613
- };
614
- }
615
- if (!expressionWasDefault) {
616
- return updated;
617
- }
618
- const canonicalAfter = buildCanonicalExpressionFromSlots(updated.slots);
619
- if (expressionsEquivalent(updated.expression ?? "", canonicalAfter)) {
620
- return updated;
621
- }
622
- return {
623
- ...updated,
624
- expression: canonicalAfter
625
- };
626
- }
627
442
  function updateBindingWithInput(binding, target, input, slotId = PRIMARY_SLOT_ID) {
628
443
  const base = ensurePrimarySlot(binding, target);
629
444
  const existingExpression = typeof base.expression === "string" ? base.expression.trim() : "";
@@ -631,39 +446,27 @@ function updateBindingWithInput(binding, target, input, slotId = PRIMARY_SLOT_ID
631
446
  const expressionWasDefault = expressionMatchesAliasOnly(existingExpression, base.slots) || expressionsEquivalent(existingExpression, canonicalBefore);
632
447
  const slotIndex = base.slots.findIndex((slot) => slot.id === slotId);
633
448
  const effectiveIndex = slotIndex >= 0 ? slotIndex : base.slots.length;
634
- const slots = base.slots.map((slot) => ({
635
- ...slot,
636
- remap: cloneRemap(slot.remap)
637
- }));
449
+ const slots = base.slots.map((slot) => ({ ...slot }));
638
450
  if (slotIndex === -1) {
639
451
  const alias = slotId === PRIMARY_SLOT_ID && slots.length === 0 ? PRIMARY_SLOT_ALIAS : slotId;
640
452
  slots.push({
641
453
  id: slotId,
642
454
  alias,
643
455
  inputId: null,
644
- remap: cloneRemap(createDefaultRemap(target))
456
+ valueType: getTargetValueType(target)
645
457
  });
646
458
  }
647
459
  const currentSlot = slots[effectiveIndex];
648
460
  let nextBinding;
649
461
  if (!input) {
650
- const normalizedSlotRemap = sanitizeRemap(currentSlot.remap, target);
651
- const updatedRemap = {
652
- ...normalizedSlotRemap,
653
- inLow: DEFAULT_INPUT_RANGE.min,
654
- inAnchor: DEFAULT_INPUT_ANCHOR,
655
- inHigh: DEFAULT_INPUT_RANGE.max
656
- };
657
462
  slots[effectiveIndex] = {
658
463
  ...currentSlot,
659
- inputId: null,
660
- remap: cloneRemap(updatedRemap)
464
+ inputId: null
661
465
  };
662
466
  if (effectiveIndex === 0) {
663
467
  nextBinding = {
664
468
  ...base,
665
469
  inputId: null,
666
- remap: cloneRemap(updatedRemap),
667
470
  slots
668
471
  };
669
472
  } else {
@@ -673,24 +476,14 @@ function updateBindingWithInput(binding, target, input, slotId = PRIMARY_SLOT_ID
673
476
  };
674
477
  }
675
478
  } else {
676
- const normalizedRemap = sanitizeRemap(currentSlot.remap, target);
677
- const updatedRemap = {
678
- ...normalizedRemap,
679
- inLow: input.range.min,
680
- inAnchor: clamp(input.defaultValue, input.range.min, input.range.max),
681
- inHigh: input.range.max,
682
- ...deriveOutputDefaults(target)
683
- };
684
479
  slots[effectiveIndex] = {
685
480
  ...currentSlot,
686
- inputId: input.id,
687
- remap: cloneRemap(updatedRemap)
481
+ inputId: input.id
688
482
  };
689
483
  if (effectiveIndex === 0) {
690
484
  nextBinding = {
691
485
  ...base,
692
486
  inputId: input.id,
693
- remap: cloneRemap(updatedRemap),
694
487
  slots
695
488
  };
696
489
  } else {
@@ -712,26 +505,6 @@ function updateBindingWithInput(binding, target, input, slotId = PRIMARY_SLOT_ID
712
505
  expression: canonicalAfter
713
506
  };
714
507
  }
715
- function remapValue(value, remap) {
716
- const { inLow, inAnchor, inHigh, outLow, outAnchor, outHigh } = remap;
717
- if (Number.isNaN(value)) {
718
- return outAnchor;
719
- }
720
- if (value <= inAnchor) {
721
- const span2 = inAnchor - inLow;
722
- if (Math.abs(span2) < EPSILON) {
723
- return outLow;
724
- }
725
- const t2 = (value - inLow) / span2;
726
- return outLow + t2 * (outAnchor - outLow);
727
- }
728
- const span = inHigh - inAnchor;
729
- if (Math.abs(span) < EPSILON) {
730
- return outHigh;
731
- }
732
- const t = (value - inAnchor) / span;
733
- return outAnchor + t * (outHigh - outAnchor);
734
- }
735
508
  function reconcileBindings(previous, components) {
736
509
  const next = {};
737
510
  components.forEach((component) => {
@@ -749,12 +522,10 @@ function reconcileBindings(previous, components) {
749
522
  if (replaced && replaced !== normalizedAlias) {
750
523
  aliasReplacements.set(replaced, normalizedAlias);
751
524
  }
752
- const slotRemap = sanitizeRemap(slot.remap, component);
753
525
  return {
754
526
  ...slot,
755
527
  id: normalizedId,
756
- alias: normalizedAlias,
757
- remap: cloneRemap(slotRemap)
528
+ alias: normalizedAlias
758
529
  };
759
530
  });
760
531
  const primary = slots[0];
@@ -764,7 +535,6 @@ function reconcileBindings(previous, components) {
764
535
  ...ensured,
765
536
  targetId: component.id,
766
537
  inputId: primary.inputId ?? null,
767
- remap: cloneRemap(primary.remap),
768
538
  slots,
769
539
  expression
770
540
  };
@@ -777,11 +547,7 @@ function reconcileBindings(previous, components) {
777
547
  function bindingToDefinition(binding) {
778
548
  const definition = {
779
549
  inputId: binding.inputId ?? null,
780
- remap: cloneRemap(binding.remap),
781
- slots: binding.slots.map((slot) => ({
782
- ...slot,
783
- remap: cloneRemap(slot.remap)
784
- })),
550
+ slots: binding.slots.map((slot) => ({ ...slot })),
785
551
  expression: binding.expression,
786
552
  metadata: cloneBindingMetadata(binding.metadata)
787
553
  };
@@ -794,46 +560,12 @@ function bindingFromDefinition(target, definition) {
794
560
  const binding = {
795
561
  targetId: target.id,
796
562
  inputId: definition.inputId ?? null,
797
- remap: cloneRemap(definition.remap),
798
- slots: definition.slots.map((slot) => ({
799
- ...slot,
800
- remap: cloneRemap(slot.remap)
801
- })),
563
+ slots: definition.slots.map((slot) => ({ ...slot })),
802
564
  expression: definition.expression,
803
565
  metadata: cloneBindingMetadata(definition.metadata)
804
566
  };
805
567
  return ensureBindingStructure(binding, target);
806
568
  }
807
- function sanitizeLiteral(value) {
808
- if (!Number.isFinite(value)) {
809
- return 0;
810
- }
811
- if (Object.is(value, -0)) {
812
- return 0;
813
- }
814
- return value;
815
- }
816
- function formatVectorLiteral(values) {
817
- return `vec(${values.map((value) => sanitizeLiteral(value)).join(", ")})`;
818
- }
819
- function buildPiecewiseRemapExpression(alias, remap) {
820
- const sanitizedAlias = alias && alias.trim().length > 0 ? alias.trim() : PRIMARY_SLOT_ALIAS;
821
- const inputBreakpoints = [remap.inLow, remap.inAnchor, remap.inHigh];
822
- const outputBreakpoints = [remap.outLow, remap.outAnchor, remap.outHigh];
823
- return `piecewise_remap(${sanitizedAlias}, ${formatVectorLiteral(
824
- inputBreakpoints
825
- )}, ${formatVectorLiteral(outputBreakpoints)})`;
826
- }
827
- function isSelfAlias(alias) {
828
- return alias.trim().toLowerCase() === "self";
829
- }
830
- function buildDefaultSlotExpression(alias, inputId, remap) {
831
- const sanitizedAlias = alias && alias.trim().length > 0 ? alias.trim() : PRIMARY_SLOT_ALIAS;
832
- if (inputId === import_utils.SELF_BINDING_ID || isSelfAlias(sanitizedAlias)) {
833
- return sanitizedAlias;
834
- }
835
- return buildPiecewiseRemapExpression(sanitizedAlias, remap);
836
- }
837
569
  function normalizeSlotAliasForExpression(slot, index) {
838
570
  if (slot.alias && slot.alias.trim().length > 0) {
839
571
  return slot.alias.trim();
@@ -850,16 +582,7 @@ function buildAliasOnlyExpression(slots) {
850
582
  return slots.map((slot, index) => normalizeSlotAliasForExpression(slot, index)).join(" + ");
851
583
  }
852
584
  function buildCanonicalExpressionFromSlots(slots) {
853
- if (!slots.length) {
854
- return PRIMARY_SLOT_ALIAS;
855
- }
856
- return slots.map(
857
- (slot, index) => buildDefaultSlotExpression(
858
- normalizeSlotAliasForExpression(slot, index),
859
- slot.inputId ?? null,
860
- slot.remap
861
- )
862
- ).join(" + ");
585
+ return buildAliasOnlyExpression(slots);
863
586
  }
864
587
  function expressionsEquivalent(left, right) {
865
588
  return left.trim() === right.trim();
@@ -1970,9 +1693,7 @@ var DefaultExpressionVariableTable = class {
1970
1693
  targetId: options.targetId,
1971
1694
  animatableId: options.animatableId,
1972
1695
  component: options.component,
1973
- valueType: options.valueType,
1974
- remap: options.remap,
1975
- autoRemap: options.autoRemap
1696
+ valueType: options.valueType
1976
1697
  }
1977
1698
  });
1978
1699
  }
@@ -2069,9 +1790,6 @@ var RESERVED_EXPRESSION_VARIABLES = [
2069
1790
  ];
2070
1791
  var EXPRESSION_FUNCTION_VOCABULARY = SCALAR_FUNCTION_VOCABULARY;
2071
1792
 
2072
- // src/graphBuilder.ts
2073
- var import_metadata2 = require("@vizij/node-graph-wasm/metadata");
2074
-
2075
1793
  // src/ir/builder.ts
2076
1794
  var graphSequence = 0;
2077
1795
  function generateGraphId(faceId) {
@@ -2158,12 +1876,12 @@ function createLegacyIrGraph(payload) {
2158
1876
  function toIrBindingSummary(summaries) {
2159
1877
  return summaries.map((summary) => ({
2160
1878
  ...summary,
2161
- remap: { ...summary.remap },
2162
1879
  issues: summary.issues ? [...summary.issues] : void 0
2163
1880
  }));
2164
1881
  }
2165
1882
 
2166
1883
  // src/ir/compiler.ts
1884
+ var import_utils2 = require("@vizij/utils");
2167
1885
  function compileIrGraph(graph, options = {}) {
2168
1886
  const preferLegacy = options.preferLegacySpec === true;
2169
1887
  const legacySpec = graph.legacy?.spec;
@@ -2248,7 +1966,7 @@ function cloneJsonLike(value) {
2248
1966
  if (value === void 0 || value === null) {
2249
1967
  return value;
2250
1968
  }
2251
- return JSON.parse(JSON.stringify(value));
1969
+ return (0, import_utils2.cloneDeepSafe)(value);
2252
1970
  }
2253
1971
  function inlineSingleUseConstants(spec) {
2254
1972
  const nodes = spec.nodes ?? [];
@@ -2287,8 +2005,9 @@ function inlineSingleUseConstants(spec) {
2287
2005
  }
2288
2006
 
2289
2007
  // src/bindingMetadata.ts
2008
+ var import_utils3 = require("@vizij/utils");
2290
2009
  function cloneOperand(entry) {
2291
- return JSON.parse(JSON.stringify(entry));
2010
+ return (0, import_utils3.cloneDeepSafe)(entry);
2292
2011
  }
2293
2012
  function describeSlot(entry) {
2294
2013
  const metadata = entry.metadata;
@@ -2330,17 +2049,17 @@ function describeReference(node, variables) {
2330
2049
  function stringifyExpression(node) {
2331
2050
  switch (node.type) {
2332
2051
  case "Literal":
2333
- return Number.isFinite(node.value) ? `${node.value}` : "0";
2052
+ return Number.isFinite(node.value) ? `${node.value} ` : "0";
2334
2053
  case "VectorLiteral":
2335
2054
  return `vec(${node.values.join(", ")})`;
2336
2055
  case "Reference":
2337
2056
  return node.name;
2338
2057
  case "Unary":
2339
- return `${node.operator}${stringifyExpression(node.operand)}`;
2058
+ return `${node.operator}${stringifyExpression(node.operand)} `;
2340
2059
  case "Binary":
2341
- return `${stringifyExpression(node.left)} ${node.operator} ${stringifyExpression(node.right)}`;
2060
+ return `${stringifyExpression(node.left)} ${node.operator} ${stringifyExpression(node.right)} `;
2342
2061
  case "Function":
2343
- return `${node.name}(${node.args.map(stringifyExpression).join(", ")})`;
2062
+ return `${node.name} (${node.args.map(stringifyExpression).join(", ")})`;
2344
2063
  default:
2345
2064
  return "";
2346
2065
  }
@@ -2424,7 +2143,6 @@ function evaluateBinding({
2424
2143
  counter: 0,
2425
2144
  reservedNodes: /* @__PURE__ */ new Map(),
2426
2145
  nodeValueTypes: /* @__PURE__ */ new Map(),
2427
- slotRemapNodes: /* @__PURE__ */ new Map(),
2428
2146
  graphReservedNodes: context.graphReservedNodes,
2429
2147
  generateReservedNodeId: context.generateReservedNodeId
2430
2148
  };
@@ -2442,7 +2160,7 @@ function evaluateBinding({
2442
2160
  const slotId = slot.id && slot.id.length > 0 ? slot.id : alias;
2443
2161
  const slotValueType = slot.valueType === "vector" ? "vector" : "scalar";
2444
2162
  let slotOutputId;
2445
- if (slot.inputId === import_utils3.SELF_BINDING_ID) {
2163
+ if (slot.inputId === import_utils5.SELF_BINDING_ID) {
2446
2164
  if (selfNodeId) {
2447
2165
  slotOutputId = selfNodeId;
2448
2166
  hasActiveSlot = true;
@@ -2481,9 +2199,7 @@ function evaluateBinding({
2481
2199
  targetId,
2482
2200
  animatableId,
2483
2201
  component,
2484
- valueType: slotValueType,
2485
- remap: { ...slot.remap },
2486
- autoRemap: slot.inputId !== import_utils3.SELF_BINDING_ID && slotValueType === "scalar"
2202
+ valueType: slotValueType
2487
2203
  });
2488
2204
  setNodeValueType(
2489
2205
  exprContext,
@@ -2497,7 +2213,6 @@ function evaluateBinding({
2497
2213
  slotId,
2498
2214
  slotAlias: alias,
2499
2215
  inputId: slot.inputId ?? null,
2500
- remap: { ...slot.remap },
2501
2216
  expression: trimmedExpression,
2502
2217
  valueType: slotValueType,
2503
2218
  nodeId: slotOutputId,
@@ -2516,9 +2231,7 @@ function evaluateBinding({
2516
2231
  targetId,
2517
2232
  animatableId,
2518
2233
  component,
2519
- valueType: targetValueType,
2520
- remap: createDefaultRemap(target),
2521
- autoRemap: false
2234
+ valueType: targetValueType
2522
2235
  });
2523
2236
  setNodeValueType(
2524
2237
  exprContext,
@@ -2532,7 +2245,6 @@ function evaluateBinding({
2532
2245
  slotId: PRIMARY_SLOT_ID,
2533
2246
  slotAlias: alias,
2534
2247
  inputId: null,
2535
- remap: createDefaultRemap(target),
2536
2248
  expression: trimmedExpression,
2537
2249
  valueType: targetValueType,
2538
2250
  nodeId: constantId,
@@ -2729,73 +2441,6 @@ function ensureOperandValueType(context, operandId, expected, functionName, inpu
2729
2441
  `Function "${functionName}" expects ${expectation} input for "${inputId}", but the expression produced ${actual}.`
2730
2442
  );
2731
2443
  }
2732
- function resolveSlotReferenceNode(entry, fallbackNodeId, context) {
2733
- if (entry.kind !== "slot") {
2734
- return fallbackNodeId;
2735
- }
2736
- const metadata = entry.metadata;
2737
- if (!metadata || metadata.autoRemap === false || !metadata.remap) {
2738
- return fallbackNodeId;
2739
- }
2740
- if (metadata.valueType !== "scalar") {
2741
- return fallbackNodeId;
2742
- }
2743
- if (isIdentityRemap(metadata.remap)) {
2744
- return fallbackNodeId;
2745
- }
2746
- const cacheKey = metadata.slotId ?? entry.name;
2747
- const existing = context.slotRemapNodes.get(cacheKey);
2748
- if (existing) {
2749
- return existing;
2750
- }
2751
- const remapNodeId = createSlotRemapNode(
2752
- context,
2753
- fallbackNodeId,
2754
- metadata.remap,
2755
- metadata.slotAlias ?? cacheKey
2756
- );
2757
- context.slotRemapNodes.set(cacheKey, remapNodeId);
2758
- return remapNodeId;
2759
- }
2760
- function createSlotRemapNode(context, sourceNodeId, remap, slotKey) {
2761
- const safeSlotKey = sanitizeNodeId(slotKey || "slot");
2762
- const nodeId = `slot_remap_${safeSlotKey}_${context.counter++}`;
2763
- context.nodes.push({
2764
- id: nodeId,
2765
- type: "centered_remap",
2766
- inputDefaults: {
2767
- in_low: remap.inLow,
2768
- in_anchor: remap.inAnchor,
2769
- in_high: remap.inHigh,
2770
- out_low: remap.outLow,
2771
- out_anchor: remap.outAnchor,
2772
- out_high: remap.outHigh
2773
- }
2774
- });
2775
- context.edges.push({
2776
- from: { nodeId: sourceNodeId },
2777
- to: { nodeId, portId: "in" }
2778
- });
2779
- setNodeValueType(context, nodeId, "scalar");
2780
- return nodeId;
2781
- }
2782
- function isIdentityRemap(remap) {
2783
- return nearlyEqual(remap.inLow, remap.outLow) && nearlyEqual(remap.inAnchor, remap.outAnchor) && nearlyEqual(remap.inHigh, remap.outHigh);
2784
- }
2785
- function nearlyEqual(a, b, epsilon = 1e-4) {
2786
- return Math.abs(a - b) <= epsilon;
2787
- }
2788
- var REMAP_FUNCTION_NODE_TYPES = /* @__PURE__ */ new Set([
2789
- "piecewise_remap",
2790
- "centered_remap",
2791
- "remap"
2792
- ]);
2793
- function shouldSkipAutoRemapForArgument(nodeType, index) {
2794
- if (!REMAP_FUNCTION_NODE_TYPES.has(nodeType)) {
2795
- return false;
2796
- }
2797
- return index === 0;
2798
- }
2799
2444
  function getConstantNodeId(context, value) {
2800
2445
  const key = Number.isFinite(value) ? value.toString() : "NaN";
2801
2446
  const existing = context.constants.get(key);
@@ -3254,8 +2899,7 @@ var BINARY_FUNCTION_OPERATOR_MAP = {
3254
2899
  "&&": "and",
3255
2900
  "||": "or"
3256
2901
  };
3257
- function materializeExpression(node, context, variables, issues, options) {
3258
- const autoRemap = options?.autoRemap !== false;
2902
+ function materializeExpression(node, context, variables, issues) {
3259
2903
  switch (node.type) {
3260
2904
  case "Literal": {
3261
2905
  return getConstantNodeId(context, node.value);
@@ -3270,10 +2914,7 @@ function materializeExpression(node, context, variables, issues, options) {
3270
2914
  return getConstantNodeId(context, 0);
3271
2915
  }
3272
2916
  const mappedId = entry.nodeId ?? getConstantNodeId(context, 0);
3273
- if (!autoRemap || entry.kind !== "slot") {
3274
- return mappedId;
3275
- }
3276
- return resolveSlotReferenceNode(entry, mappedId, context);
2917
+ return mappedId;
3277
2918
  }
3278
2919
  case "Unary": {
3279
2920
  const operandId = materializeExpression(
@@ -3411,13 +3052,7 @@ function materializeExpression(node, context, variables, issues, options) {
3411
3052
  );
3412
3053
  const operandNodes = argNodes.slice(0, operandLimit);
3413
3054
  const operands = operandNodes.map(
3414
- (arg, index) => materializeExpression(
3415
- arg,
3416
- context,
3417
- variables,
3418
- issues,
3419
- shouldSkipAutoRemapForArgument(definition.nodeType, index) ? { autoRemap: false } : void 0
3420
- )
3055
+ (arg, _index) => materializeExpression(arg, context, variables, issues)
3421
3056
  );
3422
3057
  const paramArgStart = operandLimit;
3423
3058
  const paramArgNodes = paramArgCount > 0 ? argNodes.slice(paramArgStart, paramArgStart + paramArgCount) : [];
@@ -3493,7 +3128,7 @@ function buildRigGraphSpec({
3493
3128
  try {
3494
3129
  const target = bindingTargetFromInput(input);
3495
3130
  const binding = ensureBindingStructure(inputBindingRaw, target);
3496
- const requiresSelf = binding.inputId === import_utils3.SELF_BINDING_ID || binding.slots.some((slot) => slot.inputId === import_utils3.SELF_BINDING_ID);
3131
+ const requiresSelf = binding.inputId === import_utils5.SELF_BINDING_ID || binding.slots.some((slot) => slot.inputId === import_utils5.SELF_BINDING_ID);
3497
3132
  let selfNodeId;
3498
3133
  if (requiresSelf) {
3499
3134
  const sliderNodeId = `input_raw_${sanitizeNodeId(inputId)}`;
@@ -3619,7 +3254,6 @@ function buildRigGraphSpec({
3619
3254
  slotId: PRIMARY_SLOT_ID,
3620
3255
  slotAlias: PRIMARY_SLOT_ALIAS,
3621
3256
  inputId: null,
3622
- remap: createDefaultRemap(target),
3623
3257
  expression: PRIMARY_SLOT_ALIAS,
3624
3258
  valueType: target.valueType === "vector" ? "vector" : "scalar",
3625
3259
  issues: ["Binding not found."],
@@ -3674,7 +3308,7 @@ function buildRigGraphSpec({
3674
3308
  let sourceId = entry.values.get(componentKey);
3675
3309
  if (!sourceId) {
3676
3310
  const componentDefault = entry.defaults.get(componentKey) ?? extractComponentDefault(
3677
- (0, import_utils2.buildAnimatableValue)(entry.animatable, void 0),
3311
+ (0, import_utils4.buildAnimatableValue)(entry.animatable, void 0),
3678
3312
  componentKey
3679
3313
  );
3680
3314
  const constNodeId = `const_${safeId}_${componentKey}`;
@@ -3777,7 +3411,6 @@ function buildRigGraphSpec({
3777
3411
  }),
3778
3412
  bindings: filteredSummaryBindings.map((binding) => ({
3779
3413
  ...binding,
3780
- remap: { ...binding.remap },
3781
3414
  expression: binding.expression,
3782
3415
  valueType: binding.valueType,
3783
3416
  issues: binding.issues ? [...binding.issues] : void 0,
@@ -3812,7 +3445,6 @@ function buildRigGraphSpec({
3812
3445
  bindings: toIrBindingSummary(
3813
3446
  filteredSummaryBindings.map((binding) => ({
3814
3447
  ...binding,
3815
- remap: { ...binding.remap },
3816
3448
  issues: binding.issues ? [...binding.issues] : void 0
3817
3449
  }))
3818
3450
  )
@@ -3931,7 +3563,7 @@ function cloneJsonLike2(value) {
3931
3563
  if (value === void 0 || value === null) {
3932
3564
  return value;
3933
3565
  }
3934
- return JSON.parse(JSON.stringify(value));
3566
+ return (0, import_utils4.cloneDeepSafe)(value);
3935
3567
  }
3936
3568
  function validateRemapDefaults(nodes) {
3937
3569
  const issues = [];
@@ -3959,15 +3591,8 @@ function validateRemapDefaults(nodes) {
3959
3591
 
3960
3592
  // src/ir/inspection.ts
3961
3593
  var import_metadata3 = require("@vizij/node-graph-wasm/metadata");
3594
+ var import_utils6 = require("@vizij/utils");
3962
3595
  var MACHINE_REPORT_VERSION = 1;
3963
- var REMAP_KEYS = [
3964
- "inLow",
3965
- "inAnchor",
3966
- "inHigh",
3967
- "outLow",
3968
- "outAnchor",
3969
- "outHigh"
3970
- ];
3971
3596
  var DEFAULT_DIFF_LIMIT = 50;
3972
3597
  function buildMachineReport(result) {
3973
3598
  return {
@@ -4008,7 +3633,6 @@ function normalizeGraphBindingSummaries(bindings) {
4008
3633
  slotId: binding.slotId,
4009
3634
  slotAlias: binding.slotAlias,
4010
3635
  inputId: binding.inputId ?? null,
4011
- remap: normalizeRemap2(binding.remap),
4012
3636
  expression: binding.expression,
4013
3637
  valueType: binding.valueType,
4014
3638
  nodeId: binding.nodeId,
@@ -4023,7 +3647,7 @@ function cloneBindingMetadata2(metadata) {
4023
3647
  if (!metadata) {
4024
3648
  return void 0;
4025
3649
  }
4026
- return JSON.parse(JSON.stringify(metadata));
3650
+ return (0, import_utils6.cloneDeepSafe)(metadata);
4027
3651
  }
4028
3652
  function normalizeIssues(issues) {
4029
3653
  const byTargetEntries = Object.entries(issues.byTarget ?? {}).map(
@@ -4107,7 +3731,6 @@ function normalizeIrGraphSummary(summary) {
4107
3731
  function normalizeIrBindingSummaries(bindings) {
4108
3732
  const normalized = bindings.map((binding) => ({
4109
3733
  ...binding,
4110
- remap: sortPlainObject(binding.remap),
4111
3734
  issues: normalizeStringArray(binding.issues)
4112
3735
  }));
4113
3736
  normalized.sort((a, b) => bindingSortKey(a).localeCompare(bindingSortKey(b)));
@@ -4210,13 +3833,6 @@ function normalizeRegistryParamSpec(param) {
4210
3833
  }
4211
3834
  return normalized;
4212
3835
  }
4213
- function normalizeRemap2(remap) {
4214
- const normalized = {};
4215
- REMAP_KEYS.forEach((key) => {
4216
- normalized[key] = remap[key];
4217
- });
4218
- return normalized;
4219
- }
4220
3836
  function normalizeStringArray(values) {
4221
3837
  if (!values || values.length === 0) {
4222
3838
  return void 0;
@@ -4368,9 +3984,7 @@ function normalizeDiffLimit(limit) {
4368
3984
  bindingTargetFromInput,
4369
3985
  bindingToDefinition,
4370
3986
  buildCanonicalBindingExpression,
4371
- buildDefaultSlotExpression,
4372
3987
  buildMachineReport,
4373
- buildPiecewiseRemapExpression,
4374
3988
  buildRigGraphSpec,
4375
3989
  collectExpressionReferences,
4376
3990
  compileIrGraph,
@@ -4378,7 +3992,6 @@ function normalizeDiffLimit(limit) {
4378
3992
  createDefaultBindings,
4379
3993
  createDefaultInputValues,
4380
3994
  createDefaultParentBinding,
4381
- createDefaultRemap,
4382
3995
  createExpressionVariableTable,
4383
3996
  createIrGraphBuilder,
4384
3997
  createLegacyIrGraph,
@@ -4388,12 +4001,10 @@ function normalizeDiffLimit(limit) {
4388
4001
  mapExpression,
4389
4002
  parseControlExpression,
4390
4003
  reconcileBindings,
4391
- remapValue,
4392
4004
  removeBindingSlot,
4393
4005
  toIrBindingSummary,
4394
4006
  updateBindingExpression,
4395
4007
  updateBindingSlotAlias,
4396
- updateBindingSlotRemap,
4397
4008
  updateBindingSlotValueType,
4398
4009
  updateBindingWithInput
4399
4010
  });