@pixodesk/svg-animator-vue 1.0.16 → 1.0.17

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.umd.js CHANGED
@@ -56810,7 +56810,7 @@ ${codeFrame}` : message);
56810
56810
  if (typeof raw === "object") {
56811
56811
  const obj = raw;
56812
56812
  if (obj.keyframes) {
56813
- return { kind: "animated", keyframes: obj.keyframes, autoOrient: obj.autoOrient };
56813
+ return { kind: "animated", keyframes: obj.keyframes, autoOrient: obj.autoOrient, loop: obj.loop };
56814
56814
  }
56815
56815
  if (obj.value !== void 0) return { kind: "static", value: obj.value };
56816
56816
  }
@@ -56898,6 +56898,7 @@ ${codeFrame}` : message);
56898
56898
  if (v.kind === "animated") {
56899
56899
  const animTr = { keyframes: v.keyframes.map((kf) => keyframeWith(kf, partsRecord(part, kf.value, void 0))) };
56900
56900
  if (v.autoOrient) animTr.autoOrient = true;
56901
+ if (v.loop !== void 0) animTr.loop = v.loop;
56901
56902
  return {
56902
56903
  type: "g",
56903
56904
  animate: { transform: animTr },
@@ -56916,9 +56917,11 @@ ${codeFrame}` : message);
56916
56917
  return { type: "g", transform: { value: { translate: sign(v.value) } }, children: [inner] };
56917
56918
  }
56918
56919
  if (v.kind === "animated") {
56920
+ const animTr = { keyframes: v.keyframes.map((kf) => keyframeWith(kf, { translate: sign(kf.value) })) };
56921
+ if (v.loop !== void 0) animTr.loop = v.loop;
56919
56922
  return {
56920
56923
  type: "g",
56921
- animate: { transform: { keyframes: v.keyframes.map((kf) => keyframeWith(kf, { translate: sign(kf.value) })) } },
56924
+ animate: { transform: animTr },
56922
56925
  children: [inner]
56923
56926
  };
56924
56927
  }
@@ -56926,8 +56929,8 @@ ${codeFrame}` : message);
56926
56929
  }
56927
56930
  function identifyContentRefTargets(node, ctx, allocator) {
56928
56931
  var _a, _b, _c;
56929
- if (node.type === "use" && ((_b = (_a = node.effects) == null ? void 0 : _a.ref) == null ? void 0 : _b.type) === "content") {
56930
- const baseId = node.effects.ref.baseId;
56932
+ if (node.type === "use" && ((_b = (_a = node.effects) == null ? void 0 : _a.clone) == null ? void 0 : _b.type) === "content") {
56933
+ const baseId = node.effects.clone.baseId;
56931
56934
  if (typeof baseId === "string" && baseId && !ctx.contentRefInnerIds.has(baseId)) {
56932
56935
  ctx.contentRefInnerIds.set(baseId, allocator(baseId));
56933
56936
  }
@@ -56975,6 +56978,8 @@ ${codeFrame}` : message);
56975
56978
  });
56976
56979
  const outerAnimTr = { keyframes: outerKfs };
56977
56980
  if (animTr.autoOrient) outerAnimTr.autoOrient = true;
56981
+ const srcLoop = animTr.loop;
56982
+ if (srcLoop !== void 0) outerAnimTr.loop = srcLoop;
56978
56983
  out.animate = { transform: outerAnimTr };
56979
56984
  const innerHasPivotedPart = kfs.some((kf) => {
56980
56985
  const v = kf.value || {};
@@ -56996,7 +57001,9 @@ ${codeFrame}` : message);
56996
57001
  delete node.animate.transform;
56997
57002
  if (node.animate && Object.keys(node.animate).length === 0) delete node.animate;
56998
57003
  } else {
56999
- node.animate.transform = { keyframes: innerKfs };
57004
+ const innerAnimTr = { keyframes: innerKfs };
57005
+ if (srcLoop !== void 0) innerAnimTr.loop = srcLoop;
57006
+ node.animate.transform = innerAnimTr;
57000
57007
  }
57001
57008
  didLiftAnimate = true;
57002
57009
  }
@@ -57717,9 +57724,10 @@ ${codeFrame}` : message);
57717
57724
  stretch: px.number().optional(),
57718
57725
  timeCrop: px.tuple([px.number(), px.number()]).optional()
57719
57726
  }));
57720
- var PxRefEffectSchema = implementsInterface()(px.object({
57727
+ var PxCloneEffectSchema = implementsInterface()(px.object({
57728
+ type: px.string().optional(),
57721
57729
  baseId: px.string().optional(),
57722
- type: px.string().optional()
57730
+ retime: PxRetimeEffectSchema.optional()
57723
57731
  }));
57724
57732
  var PxGradientType = {
57725
57733
  linear: "linear",
@@ -57760,9 +57768,8 @@ ${codeFrame}` : message);
57760
57768
  repeater: PxRepeaterEffectSchema.optional(),
57761
57769
  maskedBy: PxMaskedByEffectSchema.optional(),
57762
57770
  trimPath: PxTrimPathEffectSchema.optional(),
57763
- retime: PxRetimeEffectSchema.optional(),
57771
+ clone: PxCloneEffectSchema.optional(),
57764
57772
  isCombinedShape: px.boolean().optional(),
57765
- ref: PxRefEffectSchema.optional(),
57766
57773
  fillGradient: PxFillGradientEffectSchema.optional(),
57767
57774
  strokeGradient: PxStrokeGradientEffectSchema.optional(),
57768
57775
  textAlongPath: PxTextAlongPathEffectSchema.optional()
@@ -57977,6 +57984,7 @@ ${codeFrame}` : message);
57977
57984
  const animBlock = stops;
57978
57985
  const kfs = animBlock.keyframes;
57979
57986
  if (!Array.isArray(kfs) || !kfs.length) return [];
57987
+ const loopFromSource = animBlock.loop;
57980
57988
  let stopCount = 0;
57981
57989
  for (const kf of kfs) {
57982
57990
  const v = (_a = kf.value) != null ? _a : kf.v;
@@ -57989,7 +57997,7 @@ ${codeFrame}` : message);
57989
57997
  const s = (_d = (_c = firstKfValue == null ? void 0 : firstKfValue[i]) != null ? _c : prevDefinedStop(kfs, 0, i)) != null ? _d : { offset: i / Math.max(1, stopCount - 1), color: "#000000" };
57990
57998
  baselineStops.push({ offset: s.offset, color: s.color });
57991
57999
  }
57992
- return baselineStops.map((bs, i) => animatedStopNode(bs, kfs, i, ctx));
58000
+ return baselineStops.map((bs, i) => animatedStopNode(bs, kfs, i, ctx, loopFromSource));
57993
58001
  }
57994
58002
  function staticStopNode(s) {
57995
58003
  return {
@@ -57998,7 +58006,7 @@ ${codeFrame}` : message);
57998
58006
  stopColor: s.color
57999
58007
  };
58000
58008
  }
58001
- function animatedStopNode(baseline, kfs, stopIdx, _ctx) {
58009
+ function animatedStopNode(baseline, kfs, stopIdx, _ctx, loop) {
58002
58010
  var _a, _b, _c, _d, _e;
58003
58011
  const colorKfs = [];
58004
58012
  const offsetKfs = [];
@@ -58023,8 +58031,14 @@ ${codeFrame}` : message);
58023
58031
  stopColor: baseline.color
58024
58032
  };
58025
58033
  const animate = {};
58026
- if (colorKfs.length) animate.stopColor = { keyframes: colorKfs };
58027
- if (offsetVaries && offsetKfs.length) animate.offset = { keyframes: offsetKfs };
58034
+ if (colorKfs.length) {
58035
+ animate.stopColor = { keyframes: colorKfs };
58036
+ if (loop !== void 0) animate.stopColor.loop = loop;
58037
+ }
58038
+ if (offsetVaries && offsetKfs.length) {
58039
+ animate.offset = { keyframes: offsetKfs };
58040
+ if (loop !== void 0) animate.offset.loop = loop;
58041
+ }
58028
58042
  if (Object.keys(animate).length) stop.animate = animate;
58029
58043
  return stop;
58030
58044
  }
@@ -58087,9 +58101,11 @@ ${codeFrame}` : message);
58087
58101
  return { type: "g", transform: { value: partsRecord(part, invertPartValue(part, v.value), origin) }, children: [inner] };
58088
58102
  }
58089
58103
  if (v.kind === "animated") {
58104
+ const animTr = { keyframes: v.keyframes.map((kf) => keyframeWith(kf, partsRecord(part, invertPartValue(part, kf.value), origin))) };
58105
+ if (v.loop !== void 0) animTr.loop = v.loop;
58090
58106
  return {
58091
58107
  type: "g",
58092
- animate: { transform: { keyframes: v.keyframes.map((kf) => keyframeWith(kf, partsRecord(part, invertPartValue(part, kf.value), origin))) } },
58108
+ animate: { transform: animTr },
58093
58109
  children: [inner]
58094
58110
  };
58095
58111
  }
@@ -58126,10 +58142,16 @@ ${codeFrame}` : message);
58126
58142
  scaleKfs.push(__spreadProps(__spreadValues({}, baseKf), { value: rec }));
58127
58143
  }
58128
58144
  }
58145
+ const srcLoop = animTr == null ? void 0 : animTr.loop;
58146
+ const withLoop = (kfs2) => {
58147
+ const block = { keyframes: kfs2 };
58148
+ if (srcLoop !== void 0) block.loop = srcLoop;
58149
+ return block;
58150
+ };
58129
58151
  let n = inner;
58130
- if (translateKfs.length) n = { type: "g", animate: { transform: { keyframes: translateKfs } }, children: [n] };
58131
- if (rotateKfs.length) n = { type: "g", animate: { transform: { keyframes: rotateKfs } }, children: [n] };
58132
- if (scaleKfs.length) n = { type: "g", animate: { transform: { keyframes: scaleKfs } }, children: [n] };
58152
+ if (translateKfs.length) n = { type: "g", animate: { transform: withLoop(translateKfs) }, children: [n] };
58153
+ if (rotateKfs.length) n = { type: "g", animate: { transform: withLoop(rotateKfs) }, children: [n] };
58154
+ if (scaleKfs.length) n = { type: "g", animate: { transform: withLoop(scaleKfs) }, children: [n] };
58133
58155
  return n;
58134
58156
  }
58135
58157
  function nodeHasBodyTransform(node) {
@@ -58361,16 +58383,18 @@ ${codeFrame}` : message);
58361
58383
  return seen ? [x, y] : void 0;
58362
58384
  }
58363
58385
  var CONTENT_SUBREF = "content";
58364
- function applyRefAndTransformationEffect(node, ref3, transformation, ctx) {
58365
- if (ref3) {
58366
- const baseId = ref3.baseId;
58367
- if (!baseId) {
58368
- ctx.errors.push("ref: missing baseId");
58369
- } else {
58370
- const targetId = ref3.type === CONTENT_SUBREF ? ctx.contentRefInnerIds.get(baseId) || baseId : baseId;
58371
- node.href = "#" + targetId;
58372
- }
58386
+ function applyRefHref(node, clone2, ctx) {
58387
+ if (!clone2) return;
58388
+ const baseId = clone2.baseId;
58389
+ if (!baseId) {
58390
+ if (clone2.type === CONTENT_SUBREF) ctx.errors.push("clone: content ref missing baseId");
58391
+ return;
58373
58392
  }
58393
+ const targetId = clone2.type === CONTENT_SUBREF ? ctx.contentRefInnerIds.get(baseId) || baseId : baseId;
58394
+ node.href = "#" + targetId;
58395
+ }
58396
+ function applyRefAndTransformationEffect(node, clone2, transformation, ctx) {
58397
+ applyRefHref(node, clone2, ctx);
58374
58398
  return applyTransformationEffect(node, transformation, ctx);
58375
58399
  }
58376
58400
  function applyRepeaterEffect(node, fx, ctx) {
@@ -58477,22 +58501,32 @@ ${codeFrame}` : message);
58477
58501
  stretch: parent.stretch * child.stretch
58478
58502
  };
58479
58503
  }
58480
- function applyAllRetimeEffects(root, ctx) {
58504
+ function readCloneRetime(n) {
58505
+ var _a, _b;
58506
+ return (_b = (_a = n.effects) == null ? void 0 : _a.clone) == null ? void 0 : _b.retime;
58507
+ }
58508
+ function clearCloneRetime(n) {
58481
58509
  var _a;
58510
+ const clone2 = (_a = n.effects) == null ? void 0 : _a.clone;
58511
+ if (!clone2) return;
58512
+ delete clone2.retime;
58513
+ if (Object.keys(clone2).length === 0) delete n.effects.clone;
58514
+ if (n.effects && Object.keys(n.effects).length === 0) delete n.effects;
58515
+ }
58516
+ function applyAllRetimeEffects(root, ctx) {
58482
58517
  ctx.idMap.clear();
58483
58518
  indexById(root, ctx.idMap);
58484
58519
  const sites = [];
58485
58520
  const collect = (n) => {
58486
- var _a2, _b;
58487
- if ((_a2 = n.effects) == null ? void 0 : _a2.retime) sites.push(n);
58488
- (_b = n.children) == null ? void 0 : _b.forEach(collect);
58521
+ var _a;
58522
+ if (readCloneRetime(n)) sites.push(n);
58523
+ (_a = n.children) == null ? void 0 : _a.forEach(collect);
58489
58524
  };
58490
58525
  collect(root);
58491
58526
  for (const useNode of sites) {
58492
- const retime = (_a = useNode.effects) == null ? void 0 : _a.retime;
58527
+ const retime = readCloneRetime(useNode);
58493
58528
  if (!retime) continue;
58494
- delete useNode.effects.retime;
58495
- if (Object.keys(useNode.effects).length === 0) delete useNode.effects;
58529
+ clearCloneRetime(useNode);
58496
58530
  materialiseRetime(useNode, asRetime(retime), ctx);
58497
58531
  }
58498
58532
  }
@@ -58516,7 +58550,6 @@ ${codeFrame}` : message);
58516
58550
  }
58517
58551
  }
58518
58552
  function buildChainClone(targetId, accum, ctx, chain) {
58519
- var _a, _b;
58520
58553
  if (chain.has(targetId)) {
58521
58554
  ctx.errors.push('retime: loop via "' + targetId + '"');
58522
58555
  return void 0;
@@ -58533,25 +58566,43 @@ ${codeFrame}` : message);
58533
58566
  } else {
58534
58567
  remapKeyframeTimes(cloneNode, accum.start, accum.stretch);
58535
58568
  }
58536
- if ((_a = cloneNode.effects) == null ? void 0 : _a.retime) {
58537
- delete cloneNode.effects.retime;
58538
- if (Object.keys(cloneNode.effects).length === 0) delete cloneNode.effects;
58539
- }
58569
+ clearCloneRetime(cloneNode);
58540
58570
  if (target.type === "use" && target.href) {
58541
58571
  const subId = stripHash(target.href);
58542
58572
  if (subId) {
58543
- const innerRetime = (_b = target.effects) == null ? void 0 : _b.retime;
58573
+ const innerRetime = readCloneRetime(target);
58544
58574
  const subAccum = innerRetime ? concatRetime(asRetime(innerRetime), accum) : accum;
58545
58575
  const subChain = new Set(chain);
58546
58576
  subChain.add(targetId);
58547
58577
  const subId2 = buildChainClone(subId, subAccum, ctx, subChain);
58548
58578
  if (subId2) cloneNode.href = "#" + subId2;
58549
58579
  }
58580
+ } else {
58581
+ materialiseNestedRetimeUses(cloneNode, accum, ctx, chain, targetId);
58550
58582
  }
58551
58583
  ctx.defs.push(cloneNode);
58552
58584
  if (typeof cloneNode.id === "string") ctx.idMap.set(cloneNode.id, cloneNode);
58553
58585
  return typeof cloneNode.id === "string" ? cloneNode.id : void 0;
58554
58586
  }
58587
+ function materialiseNestedRetimeUses(node, accum, ctx, chain, parentTargetId) {
58588
+ const visit = (n) => {
58589
+ var _a;
58590
+ const retime = readCloneRetime(n);
58591
+ if (n.type === "use" && retime && n.href) {
58592
+ const subId = stripHash(n.href);
58593
+ if (subId) {
58594
+ const subAccum = concatRetime(asRetime(retime), accum);
58595
+ const subChain = new Set(chain);
58596
+ subChain.add(parentTargetId);
58597
+ const subId2 = buildChainClone(subId, subAccum, ctx, subChain);
58598
+ if (subId2) n.href = "#" + subId2;
58599
+ }
58600
+ clearCloneRetime(n);
58601
+ }
58602
+ (_a = n.children) == null ? void 0 : _a.forEach(visit);
58603
+ };
58604
+ visit(node);
58605
+ }
58555
58606
  function remapKeyframeTimes(node, start, stretch) {
58556
58607
  var _a;
58557
58608
  remapKeyframeTimesOnly(node, start, stretch);
@@ -58594,12 +58645,14 @@ ${codeFrame}` : message);
58594
58645
  node[attrName] = String(raw);
58595
58646
  return;
58596
58647
  }
58597
- if (typeof raw === "object") {
58648
+ if (typeof raw === "object" && raw !== null) {
58598
58649
  const obj = raw;
58599
58650
  if (Array.isArray(obj.keyframes)) {
58600
58651
  const prevAnimate = node.animate && typeof node.animate === "object" && !Array.isArray(node.animate) ? node.animate : void 0;
58601
58652
  const animate = __spreadValues({}, prevAnimate || {});
58602
- animate[attrName] = { keyframes: obj.keyframes };
58653
+ const block = { keyframes: obj.keyframes };
58654
+ if (obj.loop !== void 0) block.loop = obj.loop;
58655
+ animate[attrName] = block;
58603
58656
  node.animate = animate;
58604
58657
  return;
58605
58658
  }
@@ -59656,16 +59709,67 @@ ${codeFrame}` : message);
59656
59709
  looped.push(pushed);
59657
59710
  }
59658
59711
  }
59659
- for (let rep = 0; rep < fullReps; rep++) {
59660
- const distFromBoundary = loop.before ? fullReps - 1 - rep : rep;
59661
- const isReversed = !!loop.alternate && distFromBoundary % 2 === 0;
59662
- const repStart = fillStart + rep * segDuration;
59663
- appendRep(repStart, isReversed);
59712
+ function appendRepTail(repStart, isReversed, tailFraction) {
59713
+ let entries;
59714
+ if (isReversed) {
59715
+ entries = [];
59716
+ for (let i = template.length - 1; i >= 0; i--) {
59717
+ entries.push({
59718
+ relT: 1 - template[i].relT,
59719
+ v: template[i].v,
59720
+ e: i > 0 ? reverseEasing(template[i - 1].e) : void 0,
59721
+ tangentIn: template[i].tangentOut,
59722
+ tangentOut: template[i].tangentIn
59723
+ });
59724
+ }
59725
+ } else {
59726
+ entries = template;
59727
+ }
59728
+ const startRelT = 1 - tailFraction;
59729
+ for (let i = 0; i < entries.length; i++) {
59730
+ const entry = entries[i];
59731
+ if (entry.relT < startRelT - 1e-9) continue;
59732
+ const prev = entries[i - 1];
59733
+ if (prev && prev.relT < startRelT - 1e-9 && entry.relT > startRelT + 1e-9) {
59734
+ const intervalSpan = entry.relT - prev.relT;
59735
+ const localFrac = (startRelT - prev.relT) / intervalSpan;
59736
+ const easedFrac = prev.e ? cubicBezier(prev.e)(localFrac) : localFrac;
59737
+ const startValue = interpolateValue(propName, prev.v, entry.v, easedFrac);
59738
+ const { right: rightEasing } = splitEasing(prev.e, localFrac);
59739
+ looped.push({ t: repStart, v: startValue, e: rightEasing });
59740
+ }
59741
+ const pushed = {
59742
+ t: repStart + (entry.relT - startRelT) * segDuration,
59743
+ v: entry.v,
59744
+ e: i < entries.length - 1 ? entry.e : void 0
59745
+ };
59746
+ if (entry.tangentIn) pushed.tangentIn = entry.tangentIn;
59747
+ if (entry.tangentOut) pushed.tangentOut = entry.tangentOut;
59748
+ looped.push(pushed);
59749
+ }
59664
59750
  }
59665
- if (partialFraction > 1e-9) {
59666
- const isReversed = !!loop.alternate && fullReps % 2 === 0;
59667
- const repStart = fillStart + fullReps * segDuration;
59668
- appendRep(repStart, isReversed, partialFraction);
59751
+ if (loop.before) {
59752
+ if (partialFraction > 1e-9) {
59753
+ const isReversed = !!loop.alternate && fullReps % 2 === 0;
59754
+ appendRepTail(fillStart, isReversed, partialFraction);
59755
+ }
59756
+ for (let rep = 0; rep < fullReps; rep++) {
59757
+ const distFromBoundary = fullReps - 1 - rep;
59758
+ const isReversed = !!loop.alternate && distFromBoundary % 2 === 0;
59759
+ const repStart = fillStart + remainder + rep * segDuration;
59760
+ appendRep(repStart, isReversed);
59761
+ }
59762
+ } else {
59763
+ for (let rep = 0; rep < fullReps; rep++) {
59764
+ const isReversed = !!loop.alternate && rep % 2 === 0;
59765
+ const repStart = fillStart + rep * segDuration;
59766
+ appendRep(repStart, isReversed);
59767
+ }
59768
+ if (partialFraction > 1e-9) {
59769
+ const isReversed = !!loop.alternate && fullReps % 2 === 0;
59770
+ const repStart = fillStart + fullReps * segDuration;
59771
+ appendRep(repStart, isReversed, partialFraction);
59772
+ }
59669
59773
  }
59670
59774
  if (loop.before) {
59671
59775
  return [...looped, ...keyframes];
@@ -59982,7 +60086,6 @@ ${codeFrame}` : message);
59982
60086
  if (!trimPath) return node;
59983
60087
  const trimAllAsOne = !!trimPath.trimAllAsOne;
59984
60088
  const leafEntries = [];
59985
- let acc = 0;
59986
60089
  const measure = (n) => {
59987
60090
  if (Array.isArray(n.children) && n.children.length > 0) {
59988
60091
  for (const ch of n.children) measure(ch);
@@ -59994,15 +60097,22 @@ ${codeFrame}` : message);
59994
60097
  if (!subpaths.length) return;
59995
60098
  const entry = { leaf: n, subpaths: [] };
59996
60099
  for (const sp of subpaths) {
59997
- if (!trimAllAsOne) acc = 0;
59998
60100
  const lengthPx = pxBezierPathLength(sp);
59999
- entry.subpaths.push({ subpath: sp, lengthPx, startOffsetPx: acc });
60000
- acc += lengthPx;
60101
+ entry.subpaths.push({ subpath: sp, lengthPx, startOffsetPx: 0 });
60001
60102
  }
60002
60103
  leafEntries.push(entry);
60003
60104
  };
60004
60105
  measure(node);
60005
60106
  if (!leafEntries.length) return node;
60107
+ let acc = 0;
60108
+ const iterOrder = trimAllAsOne ? [...leafEntries].reverse() : leafEntries;
60109
+ for (const entry of iterOrder) {
60110
+ for (const sp of entry.subpaths) {
60111
+ if (!trimAllAsOne) acc = 0;
60112
+ sp.startOffsetPx = acc;
60113
+ acc += sp.lengthPx;
60114
+ }
60115
+ }
60006
60116
  const chainLengthPx = acc;
60007
60117
  if (trimAllAsOne && chainLengthPx < 1e-3) return node;
60008
60118
  const offsetReadRaw = readAnimatable(trimPath.offset);
@@ -60129,10 +60239,12 @@ ${codeFrame}` : message);
60129
60239
  value: map((_c = kf.value) != null ? _c : kf.v),
60130
60240
  easing: (_d = kf.easing) != null ? _d : kf.e
60131
60241
  };
60132
- })
60242
+ }),
60243
+ loop: read.loop
60133
60244
  };
60134
60245
  }
60135
60246
  function applyAttr(node, attrName, attr) {
60247
+ var _a, _b;
60136
60248
  if (!attr) return;
60137
60249
  if (attr.kind === "static") {
60138
60250
  node[attrName] = attr.value;
@@ -60140,9 +60252,16 @@ ${codeFrame}` : message);
60140
60252
  }
60141
60253
  const prevAnimate = node.animate && typeof node.animate === "object" && !Array.isArray(node.animate) ? node.animate : void 0;
60142
60254
  const animate = __spreadValues({}, prevAnimate || {});
60143
- animate[attrName] = { keyframes: attr.keyframes };
60255
+ const block = { keyframes: attr.keyframes };
60256
+ if (attr.loop !== void 0) block.loop = attr.loop;
60257
+ animate[attrName] = block;
60144
60258
  node.animate = animate;
60259
+ const firstKf = attr.keyframes[0];
60260
+ if (firstKf && ((_a = firstKf.value) != null ? _a : firstKf.v) !== void 0) {
60261
+ node[attrName] = (_b = firstKf.value) != null ? _b : firstKf.v;
60262
+ }
60145
60263
  }
60264
+ var OPACITY_STEP_MS = 10;
60146
60265
  function computeOpacityFromRange(rangeRead) {
60147
60266
  var _a, _b, _c, _d, _e, _f;
60148
60267
  const hide = (v) => v[0] === v[1];
@@ -60168,9 +60287,9 @@ ${codeFrame}` : message);
60168
60287
  const nextHide = nextKf ? thisHide && hide((_f = nextKf.value) != null ? _f : nextKf.v) : thisHide;
60169
60288
  if (prevHide && !nextHide) {
60170
60289
  out.push({ time: t, value: 0 });
60171
- out.push({ time: t + 1, value: 1 });
60290
+ out.push({ time: t + OPACITY_STEP_MS, value: 1 });
60172
60291
  } else if (!prevHide && nextHide) {
60173
- out.push({ time: t - 1, value: 1 });
60292
+ out.push({ time: t - OPACITY_STEP_MS, value: 1 });
60174
60293
  out.push({ time: t, value: 0 });
60175
60294
  }
60176
60295
  }
@@ -60301,6 +60420,7 @@ ${codeFrame}` : message);
60301
60420
  return "M" + (x + w) + "," + y + "L" + (x + w) + "," + (y + h3) + "L" + x + "," + (y + h3) + "L" + x + "," + y + "L" + (x + w) + "," + y + "z";
60302
60421
  }
60303
60422
  function applyPlayerEffects(root) {
60423
+ var _a;
60304
60424
  const ctx = {
60305
60425
  defs: [],
60306
60426
  warnings: [],
@@ -60308,7 +60428,10 @@ ${codeFrame}` : message);
60308
60428
  idMap: /* @__PURE__ */ new Map(),
60309
60429
  nextId: 0,
60310
60430
  contentRefInnerIds: /* @__PURE__ */ new Map(),
60311
- maskAncestorChains: /* @__PURE__ */ new Map()
60431
+ maskAncestorChains: /* @__PURE__ */ new Map(),
60432
+ // Resolved engine: `frames` ONLY when explicitly set; auto/webapi/unset →
60433
+ // webapi (we're not 100% sure it's frames, and CSS/WAAPI need the inline form).
60434
+ engine: ((_a = getAnimatorConfig(root)) == null ? void 0 : _a.mode) === PxAnimatorMode.frames ? PxAnimatorEngine.frames : PxAnimatorEngine.webapi
60312
60435
  };
60313
60436
  const working = clone(root);
60314
60437
  indexById(working, ctx.idMap);
@@ -60325,7 +60448,7 @@ ${codeFrame}` : message);
60325
60448
  const originalId = typeof node.id === "string" ? node.id : void 0;
60326
60449
  const innerIdForContentRef = originalId ? ctx.contentRefInnerIds.get(originalId) : void 0;
60327
60450
  if (!fx && !innerIdForContentRef) return node;
60328
- const { transformation, repeater, maskedBy, trimPath, retime, ref: ref3, fillGradient, strokeGradient, textAlongPath } = fx != null ? fx : {};
60451
+ const { transformation, repeater, maskedBy, trimPath, clone: cloneFx, fillGradient, strokeGradient, textAlongPath } = fx != null ? fx : {};
60329
60452
  const isCombinedShape = fx == null ? void 0 : fx.isCombinedShape;
60330
60453
  if (fx) delete node.effects;
60331
60454
  let n = node;
@@ -60336,11 +60459,12 @@ ${codeFrame}` : message);
60336
60459
  n = applyRepeaterEffect(n, repeater, ctx);
60337
60460
  n = applyMaskedByEffect(n, maskedBy, transformation, ctx);
60338
60461
  if (innerIdForContentRef) {
60462
+ applyRefHref(n, cloneFx, ctx);
60339
60463
  n = splitForContentRef(n, transformation, originalId, innerIdForContentRef, ctx);
60340
60464
  } else {
60341
- n = applyRefAndTransformationEffect(n, ref3, transformation, ctx);
60465
+ n = applyRefAndTransformationEffect(n, cloneFx, transformation, ctx);
60342
60466
  }
60343
- if (retime) node.effects = { retime };
60467
+ if (cloneFx == null ? void 0 : cloneFx.retime) node.effects = { clone: { retime: cloneFx.retime } };
60344
60468
  if (originalId) ctx.idMap.set(originalId, n);
60345
60469
  return n;
60346
60470
  }
@@ -60355,13 +60479,30 @@ ${codeFrame}` : message);
60355
60479
  if (animatedIds.size === 0) return root;
60356
60480
  let idCounter = 0;
60357
60481
  const genId3 = () => "_lw_use_mat_" + ++idCounter;
60482
+ const rootViewport = readRootViewport(root);
60358
60483
  const defsCollector = [];
60359
- const walked = walkAndMaterialise2(root, idMap, animatedIds, genId3, defsCollector);
60484
+ const walked = walkAndMaterialise2(root, idMap, animatedIds, genId3, defsCollector, rootViewport);
60360
60485
  if (defsCollector.length === 0) return walked;
60361
60486
  const defsNode = { type: "defs", children: defsCollector };
60362
60487
  const newChildren = [...(_a = walked.children) != null ? _a : [], defsNode];
60363
60488
  return __spreadProps(__spreadValues({}, walked), { children: newChildren });
60364
60489
  }
60490
+ function readRootViewport(root) {
60491
+ const vb = parseViewBox(root.viewBox);
60492
+ if (vb) return [vb[2], vb[3]];
60493
+ const w = numericAttr(root.width);
60494
+ const h3 = numericAttr(root.height);
60495
+ if (w !== void 0 && h3 !== void 0) return [w, h3];
60496
+ return [1, 1];
60497
+ }
60498
+ function numericAttr(v) {
60499
+ if (typeof v === "number") return v;
60500
+ if (typeof v === "string") {
60501
+ const n = parseFloat(v);
60502
+ return Number.isFinite(n) ? n : void 0;
60503
+ }
60504
+ return void 0;
60505
+ }
60365
60506
  function buildIdMap(root) {
60366
60507
  const map = /* @__PURE__ */ new Map();
60367
60508
  const visit = (n) => {
@@ -60413,16 +60554,22 @@ ${codeFrame}` : message);
60413
60554
  if (typeof href !== "string") return void 0;
60414
60555
  return href.startsWith("#") ? href.slice(1) : href;
60415
60556
  }
60416
- function materialiseOneUse(useNode, target, idMap, animatedIds, genId3, defsCollector) {
60557
+ function materialiseOneUse(useNode, target, idMap, animatedIds, genId3, defsCollector, rootViewport) {
60558
+ var _a, _b, _c, _d;
60417
60559
  const clone2 = deepClonePxNode(target);
60418
60560
  regenerateIdsAndRewriteRefs(clone2, genId3);
60419
- const rewrittenClone = clone2.type === "symbol" ? rewriteSymbolRootToGroup(clone2, genId3, defsCollector) : clone2;
60420
- const materialisedClone = walkAndMaterialise2(rewrittenClone, idMap, animatedIds, genId3, defsCollector);
60561
+ const symbolViewBox = clone2.type === "symbol" ? parseViewBox(clone2.viewBox) : void 0;
60562
+ const useW = (_b = (_a = numericAttr(useNode.width)) != null ? _a : symbolViewBox == null ? void 0 : symbolViewBox[2]) != null ? _b : rootViewport[0];
60563
+ const useH = (_d = (_c = numericAttr(useNode.height)) != null ? _c : symbolViewBox == null ? void 0 : symbolViewBox[3]) != null ? _d : rootViewport[1];
60564
+ const rewrittenClone = clone2.type === "symbol" ? rewriteSymbolRootToGroup(clone2, genId3, defsCollector, useW, useH) : clone2;
60565
+ const materialisedClone = walkAndMaterialise2(rewrittenClone, idMap, animatedIds, genId3, defsCollector, rootViewport);
60421
60566
  const newNode = __spreadProps(__spreadValues({}, useNode), { type: "g", children: [materialisedClone] });
60422
60567
  delete newNode.href;
60568
+ delete newNode.width;
60569
+ delete newNode.height;
60423
60570
  return applyUseOffsetToG(newNode);
60424
60571
  }
60425
- function rewriteSymbolRootToGroup(symbolNode, genId3, defsCollector) {
60572
+ function rewriteSymbolRootToGroup(symbolNode, genId3, defsCollector, useW, useH) {
60426
60573
  const viewBox = parseViewBox(symbolNode.viewBox);
60427
60574
  const g = __spreadProps(__spreadValues({}, symbolNode), { type: "g" });
60428
60575
  delete g.viewBox;
@@ -60431,9 +60578,14 @@ ${codeFrame}` : message);
60431
60578
  delete g.height;
60432
60579
  if (!viewBox) return g;
60433
60580
  const [vbX, vbY, vbW, vbH] = viewBox;
60434
- if (vbX !== 0 || vbY !== 0) {
60435
- g.transform = "translate(" + -vbX + "," + -vbY + ")";
60436
- }
60581
+ const scale = vbW > 0 && vbH > 0 ? Math.min(useW / vbW, useH / vbH) : 1;
60582
+ const xOff = (useW - vbW * scale) / 2;
60583
+ const yOff = (useH - vbH * scale) / 2;
60584
+ const parts = [];
60585
+ if (xOff !== 0 || yOff !== 0) parts.push("translate(" + xOff + "," + yOff + ")");
60586
+ if (scale !== 1) parts.push("scale(" + scale + ")");
60587
+ if (vbX !== 0 || vbY !== 0) parts.push("translate(" + -vbX + "," + -vbY + ")");
60588
+ if (parts.length) g.transform = parts.join("");
60437
60589
  const clipId = genId3();
60438
60590
  defsCollector.push({
60439
60591
  type: "clipPath",
@@ -60449,18 +60601,18 @@ ${codeFrame}` : message);
60449
60601
  if (parts.length < 4 || parts.some((n) => !Number.isFinite(n))) return void 0;
60450
60602
  return [parts[0], parts[1], parts[2], parts[3]];
60451
60603
  }
60452
- function walkAndMaterialise2(node, idMap, animatedIds, genId3, defsCollector) {
60604
+ function walkAndMaterialise2(node, idMap, animatedIds, genId3, defsCollector, rootViewport) {
60453
60605
  if (node.type === "use" && typeof node.href === "string") {
60454
60606
  const targetId = stripHash2(node.href);
60455
60607
  if (targetId && animatedIds.has(targetId)) {
60456
60608
  const target = idMap.get(targetId);
60457
- if (target) return materialiseOneUse(node, target, idMap, animatedIds, genId3, defsCollector);
60609
+ if (target) return materialiseOneUse(node, target, idMap, animatedIds, genId3, defsCollector, rootViewport);
60458
60610
  }
60459
60611
  }
60460
60612
  if (!node.children) return node;
60461
60613
  let changed = false;
60462
60614
  const newChildren = node.children.map((ch) => {
60463
- const m = walkAndMaterialise2(ch, idMap, animatedIds, genId3, defsCollector);
60615
+ const m = walkAndMaterialise2(ch, idMap, animatedIds, genId3, defsCollector, rootViewport);
60464
60616
  if (m !== ch) changed = true;
60465
60617
  return m;
60466
60618
  });
@@ -60474,6 +60626,36 @@ ${codeFrame}` : message);
60474
60626
  if (engine === PxAnimatorEngine.webapi) {
60475
60627
  root = materialiseMotionPathsInTree(root, opts == null ? void 0 : opts.motionPath);
60476
60628
  root = materialiseAnimatedUseInstances(root);
60629
+ root = pruneUnreferencedDefs(root);
60630
+ }
60631
+ return root;
60632
+ }
60633
+ function pruneUnreferencedDefs(root) {
60634
+ const stripHash3 = (h3) => h3.startsWith("#") ? h3.slice(1) : h3;
60635
+ const walk = (n, fn) => {
60636
+ var _a;
60637
+ fn(n);
60638
+ (_a = n.children) == null ? void 0 : _a.forEach((c) => walk(c, fn));
60639
+ };
60640
+ let changed = true;
60641
+ while (changed) {
60642
+ changed = false;
60643
+ const referenced = /* @__PURE__ */ new Set();
60644
+ walk(root, (n) => {
60645
+ if (n.type === "use" && typeof n.href === "string") referenced.add(stripHash3(n.href));
60646
+ });
60647
+ walk(root, (n) => {
60648
+ if (!n.children) return;
60649
+ let kept = n.children;
60650
+ if (n.type === "defs") {
60651
+ kept = kept.filter((c) => !((c.type === "g" || c.type === "symbol") && typeof c.id === "string" && !referenced.has(c.id)));
60652
+ }
60653
+ kept = kept.filter((c) => !(c.type === "defs" && (!c.children || c.children.length === 0)));
60654
+ if (kept.length !== n.children.length) {
60655
+ n.children = kept;
60656
+ changed = true;
60657
+ }
60658
+ });
60477
60659
  }
60478
60660
  return root;
60479
60661
  }
@@ -60504,6 +60686,13 @@ ${codeFrame}` : message);
60504
60686
  ]);
60505
60687
  var IMAGE_REF_ATTRS_LOWER = /* @__PURE__ */ new Set(["href", "xlink:href", "src"]);
60506
60688
  var DATA_RASTER_IMAGE_RE = /^data:image\/(?:png|jpe?g|gif|webp|bmp);base64,/i;
60689
+ var DATA_SVG_IMAGE_RE = /^data:image\/svg\+xml(?:;[^,]*)?,/i;
60690
+ var DATA_IMAGE_BASE64_PAYLOAD_RE = /^data:image\/[^;,]*;base64,([A-Za-z0-9+/]{8})/i;
60691
+ var BASE64_RASTER_MAGICS = ["iVBORw0K", "/9j/", "R0lGOD", "UklGR", "Qk"];
60692
+ function isContentSniffedRasterImage(str) {
60693
+ const m = DATA_IMAGE_BASE64_PAYLOAD_RE.exec(str);
60694
+ return !!m && BASE64_RASTER_MAGICS.some((magic) => m[1].startsWith(magic));
60695
+ }
60507
60696
  function isDangerousAttrName(nameLower) {
60508
60697
  if (nameLower.startsWith("on")) return true;
60509
60698
  return false;
@@ -60526,8 +60715,8 @@ ${codeFrame}` : message);
60526
60715
  const str = String(value);
60527
60716
  if (str.startsWith("#")) return value;
60528
60717
  if (/^url\(#[^)]+\)$/.test(str)) return value;
60529
- if (IMAGE_REF_ATTRS_LOWER.has(nameLower) && DATA_RASTER_IMAGE_RE.test(str)) return value;
60530
- console.warn('Attribute "' + nameLower + '" blocked: must be #id, url(#id), or base64 raster data: URI, got:', value);
60718
+ if (IMAGE_REF_ATTRS_LOWER.has(nameLower) && (DATA_RASTER_IMAGE_RE.test(str) || DATA_SVG_IMAGE_RE.test(str) || isContentSniffedRasterImage(str))) return value;
60719
+ console.warn('Attribute "' + nameLower + '" blocked: must be #id, url(#id), or data:image/\u2026 URI, got:', value);
60531
60720
  return void 0;
60532
60721
  }
60533
60722
  return value;