@sarmal/core 0.27.0 → 0.28.1

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.
Files changed (80) hide show
  1. package/dist/auto-init.cjs +106 -145
  2. package/dist/auto-init.js +105 -144
  3. package/dist/cli.js +103 -145
  4. package/dist/cli.js.map +1 -1
  5. package/dist/curves/artemis2.cjs +10 -16
  6. package/dist/curves/artemis2.d.cts +1 -1
  7. package/dist/curves/artemis2.d.ts +1 -1
  8. package/dist/curves/artemis2.js +9 -15
  9. package/dist/curves/astroid.cjs +4 -4
  10. package/dist/curves/astroid.d.cts +1 -1
  11. package/dist/curves/astroid.d.ts +1 -1
  12. package/dist/curves/astroid.js +3 -3
  13. package/dist/curves/deltoid.cjs +4 -4
  14. package/dist/curves/deltoid.d.cts +1 -1
  15. package/dist/curves/deltoid.d.ts +1 -1
  16. package/dist/curves/deltoid.js +3 -3
  17. package/dist/curves/epicycloid3.cjs +4 -4
  18. package/dist/curves/epicycloid3.d.cts +1 -1
  19. package/dist/curves/epicycloid3.d.ts +1 -1
  20. package/dist/curves/epicycloid3.js +3 -3
  21. package/dist/curves/epitrochoid7.cjs +5 -5
  22. package/dist/curves/epitrochoid7.d.cts +1 -1
  23. package/dist/curves/epitrochoid7.d.ts +1 -1
  24. package/dist/curves/epitrochoid7.js +4 -4
  25. package/dist/curves/index.cjs +43 -59
  26. package/dist/curves/index.d.cts +29 -29
  27. package/dist/curves/index.d.ts +29 -29
  28. package/dist/curves/index.js +43 -75
  29. package/dist/curves/lame.cjs +5 -6
  30. package/dist/curves/lame.d.cts +1 -1
  31. package/dist/curves/lame.d.ts +1 -1
  32. package/dist/curves/lame.js +4 -5
  33. package/dist/curves/lissajous32.cjs +4 -4
  34. package/dist/curves/lissajous32.d.cts +1 -1
  35. package/dist/curves/lissajous32.d.ts +1 -1
  36. package/dist/curves/lissajous32.js +3 -3
  37. package/dist/curves/lissajous43.cjs +4 -4
  38. package/dist/curves/lissajous43.d.cts +1 -1
  39. package/dist/curves/lissajous43.d.ts +1 -1
  40. package/dist/curves/lissajous43.js +3 -3
  41. package/dist/curves/rose3.cjs +4 -4
  42. package/dist/curves/rose3.d.cts +1 -1
  43. package/dist/curves/rose3.d.ts +1 -1
  44. package/dist/curves/rose3.js +3 -3
  45. package/dist/curves/rose5.cjs +4 -4
  46. package/dist/curves/rose5.d.cts +1 -1
  47. package/dist/curves/rose5.d.ts +1 -1
  48. package/dist/curves/rose5.js +3 -3
  49. package/dist/curves/rose52.cjs +5 -5
  50. package/dist/curves/rose52.d.cts +1 -1
  51. package/dist/curves/rose52.d.ts +1 -1
  52. package/dist/curves/rose52.js +4 -4
  53. package/dist/curves/star.cjs +5 -8
  54. package/dist/curves/star.d.cts +1 -1
  55. package/dist/curves/star.d.ts +1 -1
  56. package/dist/curves/star.js +4 -7
  57. package/dist/curves/star4.cjs +5 -8
  58. package/dist/curves/star4.d.cts +1 -1
  59. package/dist/curves/star4.d.ts +1 -1
  60. package/dist/curves/star4.js +4 -7
  61. package/dist/curves/star7.cjs +5 -8
  62. package/dist/curves/star7.d.cts +1 -1
  63. package/dist/curves/star7.d.ts +1 -1
  64. package/dist/curves/star7.js +4 -7
  65. package/dist/index.cjs +94 -131
  66. package/dist/index.d.cts +30 -78
  67. package/dist/index.d.ts +30 -78
  68. package/dist/index.js +94 -152
  69. package/dist/renderer-shared-OR--cv-t.d.ts +15 -26
  70. package/dist/renderer-shared-jqw_Q1WO.d.cts +15 -26
  71. package/dist/terminal.cjs +52 -75
  72. package/dist/terminal.cjs.map +1 -1
  73. package/dist/terminal.d.cts +14 -31
  74. package/dist/terminal.d.ts +14 -31
  75. package/dist/terminal.js +51 -74
  76. package/dist/terminal.js.map +1 -1
  77. package/dist/types-zbxUgcmZ.d.cts +266 -280
  78. package/dist/types-zbxUgcmZ.d.ts +266 -280
  79. package/package.json +9 -3
  80. package/skills/core/SKILL.md +151 -0
package/dist/index.cjs CHANGED
@@ -1,4 +1,4 @@
1
- "use strict";
1
+ 'use strict';
2
2
 
3
3
  // src/engine.ts
4
4
  var TWO_PI = Math.PI * 2;
@@ -63,13 +63,13 @@ function resolveCurve(curveDef) {
63
63
  period,
64
64
  speed,
65
65
  skeleton: curveDef.skeleton,
66
- skeletonFn: curveDef.skeletonFn,
66
+ skeletonFn: curveDef.skeletonFn
67
67
  };
68
68
  }
69
69
  function createEngine(curveDef, trailLength = 120) {
70
70
  if (!Number.isFinite(trailLength) || trailLength <= 0) {
71
71
  throw new RangeError(
72
- `[sarmal] trailLength must be a positive finite number, got ${trailLength}`,
72
+ `[sarmal] trailLength must be a positive finite number, got ${trailLength}`
73
73
  );
74
74
  }
75
75
  let curve = resolveCurve(curveDef);
@@ -110,8 +110,7 @@ function createEngine(curveDef, trailLength = 120) {
110
110
  actualTime += deltaTime;
111
111
  if (morphCurveB !== null && _morphAlpha !== null) {
112
112
  const a = curve.fn(phase, actualTime, EMPTY_PARAMS);
113
- const phaseB =
114
- _morphStrategy === "normalized" ? (phase / curve.period) * morphCurveB.period : phase;
113
+ const phaseB = _morphStrategy === "normalized" ? phase / curve.period * morphCurveB.period : phase;
115
114
  const b = morphCurveB.fn(phaseB, actualTime, EMPTY_PARAMS);
116
115
  trail.push(a.x + (b.x - a.x) * _morphAlpha, a.y + (b.y - a.y) * _morphAlpha);
117
116
  } else {
@@ -138,14 +137,14 @@ function createEngine(curveDef, trailLength = 120) {
138
137
  trail.clear();
139
138
  },
140
139
  jump(newPhase, { clearTrail = false } = {}) {
141
- phase = ((newPhase % curve.period) + curve.period) % curve.period;
140
+ phase = (newPhase % curve.period + curve.period) % curve.period;
142
141
  if (clearTrail) {
143
142
  trail.clear();
144
143
  }
145
144
  },
146
145
  seek(targetPhase, { wrap = false, step = curve.period / trailLength } = {}) {
147
146
  const advance = curve.speed * step;
148
- const target = ((targetPhase % curve.period) + curve.period) % curve.period;
147
+ const target = (targetPhase % curve.period + curve.period) % curve.period;
149
148
  const targetTime = target / curve.speed;
150
149
  phase = target;
151
150
  actualTime = targetTime;
@@ -154,7 +153,7 @@ function createEngine(curveDef, trailLength = 120) {
154
153
  const count = wrap ? trailLength : Math.min(trailLength, pointsFromStart);
155
154
  for (let i = count - 1; i >= 0; i--) {
156
155
  const samplePhase = target - i * advance;
157
- const wrappedPhase = ((samplePhase % curve.period) + curve.period) % curve.period;
156
+ const wrappedPhase = (samplePhase % curve.period + curve.period) % curve.period;
158
157
  const elapsed = targetTime - i * step;
159
158
  const point = curve.fn(wrappedPhase, elapsed, EMPTY_PARAMS);
160
159
  trail.push(point.x, point.y);
@@ -171,16 +170,13 @@ function createEngine(curveDef, trailLength = 120) {
171
170
  ...frozenB,
172
171
  fn: (samplePhase, elapsed, params) => {
173
172
  const a = frozenA.fn(samplePhase, elapsed, params);
174
- const phaseB =
175
- frozenStrategy === "normalized"
176
- ? (samplePhase / frozenA.period) * frozenB.period
177
- : samplePhase;
173
+ const phaseB = frozenStrategy === "normalized" ? samplePhase / frozenA.period * frozenB.period : samplePhase;
178
174
  const b = frozenB.fn(phaseB, elapsed, params);
179
175
  return {
180
176
  x: a.x + (b.x - a.x) * frozenAlpha,
181
- y: a.y + (b.y - a.y) * frozenAlpha,
177
+ y: a.y + (b.y - a.y) * frozenAlpha
182
178
  };
183
- },
179
+ }
184
180
  };
185
181
  }
186
182
  _morphStrategy = strategy;
@@ -193,7 +189,7 @@ function createEngine(curveDef, trailLength = 120) {
193
189
  completeMorph() {
194
190
  if (morphCurveB !== null) {
195
191
  if (_morphStrategy === "normalized" && curve.period !== morphCurveB.period) {
196
- phase = (phase / curve.period) * morphCurveB.period;
192
+ phase = phase / curve.period * morphCurveB.period;
197
193
  }
198
194
  curve = morphCurveB;
199
195
  }
@@ -205,22 +201,19 @@ function createEngine(curveDef, trailLength = 120) {
205
201
  const points2 = new Array(steps);
206
202
  if (morphCurveB !== null && _morphAlpha !== null) {
207
203
  for (let i = 0; i < steps; i++) {
208
- const samplePhase = (i / (steps - 1)) * curve.period;
204
+ const samplePhase = i / (steps - 1) * curve.period;
209
205
  const a = sampleSkeleton(curve, samplePhase);
210
- const phaseB =
211
- _morphStrategy === "normalized"
212
- ? (samplePhase / curve.period) * morphCurveB.period
213
- : samplePhase;
206
+ const phaseB = _morphStrategy === "normalized" ? samplePhase / curve.period * morphCurveB.period : samplePhase;
214
207
  const b = sampleSkeleton(morphCurveB, phaseB);
215
208
  points2[i] = {
216
209
  x: a.x + (b.x - a.x) * _morphAlpha,
217
- y: a.y + (b.y - a.y) * _morphAlpha,
210
+ y: a.y + (b.y - a.y) * _morphAlpha
218
211
  };
219
212
  }
220
213
  return points2;
221
214
  }
222
215
  for (let i = 0; i < steps; i++) {
223
- const samplePhase = (i / (steps - 1)) * curve.period;
216
+ const samplePhase = i / (steps - 1) * curve.period;
224
217
  points2[i] = sampleSkeleton(curve, samplePhase);
225
218
  }
226
219
  return points2;
@@ -262,7 +255,7 @@ function createEngine(curveDef, trailLength = 120) {
262
255
  _speedTransition.reject(new Error("Speed transition cancelled"));
263
256
  _speedTransition = null;
264
257
  }
265
- },
258
+ }
266
259
  };
267
260
  }
268
261
 
@@ -301,15 +294,7 @@ function computeNormal(trail, i) {
301
294
  const tangent = computeTangent(trail, i);
302
295
  return { x: -tangent.y, y: tangent.x };
303
296
  }
304
- function computeTrailQuad(
305
- trail,
306
- i,
307
- trailCount,
308
- toX,
309
- toY,
310
- minWidth = TRAIL_MIN_WIDTH,
311
- maxWidth = TRAIL_MAX_WIDTH,
312
- ) {
297
+ function computeTrailQuad(trail, i, trailCount, toX, toY, minWidth = TRAIL_MIN_WIDTH, maxWidth = TRAIL_MAX_WIDTH) {
313
298
  const progress = i / (trailCount - 1);
314
299
  const nextProgress = (i + 1) / (trailCount - 1);
315
300
  const opacity = Math.pow(progress, TRAIL_FADE_CURVE) * TRAIL_MAX_OPACITY;
@@ -333,16 +318,13 @@ function computeTrailQuad(
333
318
  r1x: nx - n1.x * w1,
334
319
  r1y: ny - n1.y * w1,
335
320
  opacity,
336
- progress,
321
+ progress
337
322
  };
338
323
  }
339
324
  function computeBoundaries(pts, logicalWidth, logicalHeight, minPaddingPx = FIT_PADDING_MIN) {
340
325
  if (pts.length === 0) return null;
341
326
  const first = pts[0];
342
- let minX = first.x,
343
- maxX = first.x,
344
- minY = first.y,
345
- maxY = first.y;
327
+ let minX = first.x, maxX = first.x, minY = first.y, maxY = first.y;
346
328
  for (const p of pts) {
347
329
  if (p.x < minX) {
348
330
  minX = p.x;
@@ -361,7 +343,7 @@ function computeBoundaries(pts, logicalWidth, logicalHeight, minPaddingPx = FIT_
361
343
  const h = maxY - minY;
362
344
  if (w === 0 && h === 0) {
363
345
  throw new Error(
364
- "[sarmal] Degenerate curve: all skeleton points are identical. Check that your curve fn returns distinct points for different values of t.",
346
+ "[sarmal] Degenerate curve: all skeleton points are identical. Check that your curve fn returns distinct points for different values of t."
365
347
  );
366
348
  }
367
349
  const scaleXProportional = logicalWidth / (w * (1 + FIT_PADDING * 2));
@@ -372,12 +354,12 @@ function computeBoundaries(pts, logicalWidth, logicalHeight, minPaddingPx = FIT_
372
354
  scaleXProportional,
373
355
  scaleYProportional,
374
356
  scaleXMinPadding,
375
- scaleYMinPadding,
357
+ scaleYMinPadding
376
358
  );
377
359
  return {
378
360
  scale,
379
361
  offsetX: (logicalWidth - w * scale) / 2 - minX * scale,
380
- offsetY: (logicalHeight - h * scale) / 2 - minY * scale,
362
+ offsetY: (logicalHeight - h * scale) / 2 - minY * scale
381
363
  };
382
364
  }
383
365
  function enginePassthroughs(engine) {
@@ -388,7 +370,7 @@ function enginePassthroughs(engine) {
388
370
  getSpeed: engine.getSpeed,
389
371
  resetSpeed: engine.resetSpeed,
390
372
  setSpeedOver: engine.setSpeedOver,
391
- getSarmalSkeleton: engine.getSarmalSkeleton,
373
+ getSarmalSkeleton: engine.getSarmalSkeleton
392
374
  };
393
375
  }
394
376
  var palettes = {
@@ -397,16 +379,16 @@ var palettes = {
397
379
  ocean: ["#1e3a8a", "#06b6d4", "#22d3ee", "#e0f2fe"],
398
380
  ice: ["#1e3a8a", "#67e8f9"],
399
381
  fire: ["#7f1d1d", "#fbbf24"],
400
- forest: ["#14532d", "#86efac"],
382
+ forest: ["#14532d", "#86efac"]
401
383
  };
402
384
  function hexToRgb(hex) {
403
385
  const n = parseInt(hex.slice(1), 16);
404
- return { r: n >> 16, g: (n >> 8) & 255, b: n & 255 };
386
+ return { r: n >> 16, g: n >> 8 & 255, b: n & 255 };
405
387
  }
406
388
  var lerpRgb = (a, b, t) => ({
407
389
  r: Math.round(a.r + (b.r - a.r) * t),
408
390
  g: Math.round(a.g + (b.g - a.g) * t),
409
- b: Math.round(a.b + (b.b - a.b) * t),
391
+ b: Math.round(a.b + (b.b - a.b) * t)
410
392
  });
411
393
  function getPaletteColor(palette, position, timeOffset = 0) {
412
394
  if (palette.length === 0) {
@@ -415,7 +397,7 @@ function getPaletteColor(palette, position, timeOffset = 0) {
415
397
  if (palette.length === 1) {
416
398
  return hexToRgb(palette[0]);
417
399
  }
418
- const cyclePos = (((position + timeOffset) % 1) + 1) % 1;
400
+ const cyclePos = ((position + timeOffset) % 1 + 1) % 1;
419
401
  const scaled = cyclePos * palette.length;
420
402
  const idx = Math.floor(scaled);
421
403
  const t = scaled - idx;
@@ -430,7 +412,7 @@ var RENDER_OPTION_KEYS = /* @__PURE__ */ new Set([
430
412
  "headColor",
431
413
  "skeletonColor",
432
414
  "trailStyle",
433
- "headRadius",
415
+ "headRadius"
434
416
  ]);
435
417
  function validateRenderOptions(partial) {
436
418
  for (const key of Object.keys(partial)) {
@@ -458,7 +440,7 @@ function assertTrailColor(value) {
458
440
  if (typeof value === "string") {
459
441
  if (!HEX_COLOR_RE.test(value)) {
460
442
  throw new TypeError(
461
- `[sarmal] setRenderOptions: trailColor must be a 6-digit hex string, got "${value}"`,
443
+ `[sarmal] setRenderOptions: trailColor must be a 6-digit hex string, got "${value}"`
462
444
  );
463
445
  }
464
446
  return;
@@ -466,21 +448,21 @@ function assertTrailColor(value) {
466
448
  if (Array.isArray(value)) {
467
449
  if (value.length < 2) {
468
450
  throw new RangeError(
469
- `[sarmal] setRenderOptions: trailColor array must have at least 2 entries, got ${value.length}`,
451
+ `[sarmal] setRenderOptions: trailColor array must have at least 2 entries, got ${value.length}`
470
452
  );
471
453
  }
472
454
  for (let i = 0; i < value.length; i++) {
473
455
  const entry = value[i];
474
456
  if (typeof entry !== "string" || !HEX_COLOR_RE.test(entry)) {
475
457
  throw new TypeError(
476
- `[sarmal] setRenderOptions: trailColor[${i}] must be a 6-digit hex string, got ${JSON.stringify(entry)}`,
458
+ `[sarmal] setRenderOptions: trailColor[${i}] must be a 6-digit hex string, got ${JSON.stringify(entry)}`
477
459
  );
478
460
  }
479
461
  }
480
462
  return;
481
463
  }
482
464
  throw new TypeError(
483
- `[sarmal] setRenderOptions: trailColor must be a 6-digit hex string or an array of hex strings, got ${JSON.stringify(value)}`,
465
+ `[sarmal] setRenderOptions: trailColor must be a 6-digit hex string or an array of hex strings, got ${JSON.stringify(value)}`
484
466
  );
485
467
  }
486
468
  function assertHeadColor(value) {
@@ -489,7 +471,7 @@ function assertHeadColor(value) {
489
471
  }
490
472
  if (typeof value !== "string" || !HEX_COLOR_RE.test(value)) {
491
473
  throw new TypeError(
492
- `[sarmal] setRenderOptions: headColor must be a 6-digit hex string or null, got ${JSON.stringify(value)}`,
474
+ `[sarmal] setRenderOptions: headColor must be a 6-digit hex string or null, got ${JSON.stringify(value)}`
493
475
  );
494
476
  }
495
477
  }
@@ -499,26 +481,26 @@ function assertSkeletonColor(value) {
499
481
  }
500
482
  if (typeof value !== "string" || !HEX_COLOR_RE.test(value)) {
501
483
  throw new TypeError(
502
- `[sarmal] setRenderOptions: skeletonColor must be a 6-digit hex string or "transparent", got ${JSON.stringify(value)}`,
484
+ `[sarmal] setRenderOptions: skeletonColor must be a 6-digit hex string or "transparent", got ${JSON.stringify(value)}`
503
485
  );
504
486
  }
505
487
  }
506
488
  function assertTrailStyle(value) {
507
489
  if (!TRAIL_STYLES.includes(value)) {
508
490
  throw new RangeError(
509
- `[sarmal] setRenderOptions: trailStyle must be one of "default", "gradient-static", "gradient-animated", got ${JSON.stringify(value)}`,
491
+ `[sarmal] setRenderOptions: trailStyle must be one of "default", "gradient-static", "gradient-animated", got ${JSON.stringify(value)}`
510
492
  );
511
493
  }
512
494
  }
513
495
  function assertHeadRadius(value) {
514
496
  if (typeof value !== "number") {
515
497
  throw new TypeError(
516
- `[sarmal] setRenderOptions: headRadius must be a number, got ${JSON.stringify(value)}`,
498
+ `[sarmal] setRenderOptions: headRadius must be a number, got ${JSON.stringify(value)}`
517
499
  );
518
500
  }
519
501
  if (!Number.isFinite(value) || value <= 0) {
520
502
  throw new TypeError(
521
- `[sarmal] setRenderOptions: headRadius must be a finite positive number, got ${value}`,
503
+ `[sarmal] setRenderOptions: headRadius must be a finite positive number, got ${value}`
522
504
  );
523
505
  }
524
506
  }
@@ -540,13 +522,13 @@ function resolveHeadColor(trailColor, trailStyle) {
540
522
  function warnIfTrailColorMismatch(trailColor, trailStyle) {
541
523
  if (trailStyle === "default" && Array.isArray(trailColor)) {
542
524
  console.warn(
543
- '[sarmal] trailColor is an array but trailStyle is "default"; only the first color will be used. Pass a gradient trailStyle to use the whole palette.',
525
+ '[sarmal] trailColor is an array but trailStyle is "default"; only the first color will be used. Pass a gradient trailStyle to use the whole palette.'
544
526
  );
545
527
  return;
546
528
  }
547
529
  if (trailStyle !== "default" && typeof trailColor === "string") {
548
530
  console.warn(
549
- `[sarmal] trailColor is a single color but trailStyle is "${trailStyle}"; the trail will render as a solid color. Pass an array of hex colors to use a real gradient.`,
531
+ `[sarmal] trailColor is a single color but trailStyle is "${trailStyle}"; the trail will render as a solid color. Pass an array of hex colors to use a real gradient.`
550
532
  );
551
533
  }
552
534
  }
@@ -556,7 +538,7 @@ var getHeadDotRadius = (w, h) => Math.max(1, 3 * Math.sqrt(Math.min(w, h) / 160)
556
538
  var WHITE_HEX = "#ffffff";
557
539
  function hexToRgbComponents(hex) {
558
540
  const n = parseInt(hex.slice(1), 16);
559
- return `${n >> 16},${(n >> 8) & 255},${n & 255}`;
541
+ return `${n >> 16},${n >> 8 & 255},${n & 255}`;
560
542
  }
561
543
  function applyDprSizing(target, logicalWidth, logicalHeight, dpr) {
562
544
  target.style.width = `${logicalWidth}px`;
@@ -683,7 +665,7 @@ function createRenderer(options) {
683
665
  i,
684
666
  trailCount,
685
667
  toX,
686
- toY,
668
+ toY
687
669
  );
688
670
  if (trailStyle === "default") {
689
671
  ctx.fillStyle = `rgba(${trailSolidRgb},${opacity})`;
@@ -848,7 +830,7 @@ function createRenderer(options) {
848
830
  if (partial.trailColor !== void 0 || partial.trailStyle !== void 0) {
849
831
  warnIfTrailColorMismatch(trailColor, trailStyle);
850
832
  }
851
- },
833
+ }
852
834
  };
853
835
  const pauseOnHidden = options.pauseOnHidden !== false;
854
836
  function handleVisibilityChange() {
@@ -898,10 +880,8 @@ function sampleCurveSkeleton(curveDef) {
898
880
  const samples = Math.ceil(period * 50);
899
881
  const pts = Array.from({ length: samples });
900
882
  for (let i = 0; i < samples; i++) {
901
- const phase = (i / (samples - 1)) * period;
902
- pts[i] = curveDef.skeletonFn
903
- ? curveDef.skeletonFn(phase)
904
- : curveDef.fn(phase, 0, EMPTY_PARAMS2);
883
+ const phase = i / (samples - 1) * period;
884
+ pts[i] = curveDef.skeletonFn ? curveDef.skeletonFn(phase) : curveDef.fn(phase, 0, EMPTY_PARAMS2);
905
885
  }
906
886
  return pts;
907
887
  }
@@ -913,7 +893,7 @@ function createSVGRenderer(options) {
913
893
  const poolSize = engine.trailLength;
914
894
  if (poolSize > HIGH_TRAIL_LENGTH_THRESHOLD) {
915
895
  console.warn(
916
- `[sarmal] High trailLength in SVG renderer (${poolSize}). Consider using the canvas renderer for long trails.`,
896
+ `[sarmal] High trailLength in SVG renderer (${poolSize}). Consider using the canvas renderer for long trails.`
917
897
  );
918
898
  }
919
899
  let trailStyle = options.trailStyle ?? "default";
@@ -932,9 +912,9 @@ function createSVGRenderer(options) {
932
912
  return rect.width && rect.height ? Math.min(rect.width, rect.height) : 200;
933
913
  }
934
914
  const containerPx = getContainerPixelSize();
935
- const svgTrailMinWidth = (TRAIL_MIN_WIDTH * viewSize) / containerPx;
936
- const svgTrailMaxWidth = (TRAIL_MAX_WIDTH * viewSize) / containerPx;
937
- const svgSkeletonStrokeWidth = String((SKELETON_STROKE_WIDTH_PX * viewSize) / containerPx);
915
+ const svgTrailMinWidth = TRAIL_MIN_WIDTH * viewSize / containerPx;
916
+ const svgTrailMaxWidth = TRAIL_MAX_WIDTH * viewSize / containerPx;
917
+ const svgSkeletonStrokeWidth = String(SKELETON_STROKE_WIDTH_PX * viewSize / containerPx);
938
918
  headRadius = options.headRadius ?? SVG_DEFAULT_HEAD_RADIUS;
939
919
  container.setAttribute("viewBox", `0 0 ${viewSize} ${viewSize}`);
940
920
  container.setAttribute("role", "img");
@@ -1022,7 +1002,7 @@ function createSVGRenderer(options) {
1022
1002
  px,
1023
1003
  py,
1024
1004
  svgTrailMinWidth,
1025
- svgTrailMaxWidth,
1005
+ svgTrailMaxWidth
1026
1006
  );
1027
1007
  const d = `M${l0x.toFixed(2)} ${l0y.toFixed(2)} L${l1x.toFixed(2)} ${l1y.toFixed(2)} L${r1x.toFixed(2)} ${r1y.toFixed(2)} L${r0x.toFixed(2)} ${r0y.toFixed(2)} Z`;
1028
1008
  trailPaths[i].setAttribute("d", d);
@@ -1050,8 +1030,7 @@ function createSVGRenderer(options) {
1050
1030
  let animationId = null;
1051
1031
  let lastTime = 0;
1052
1032
  let pausedByVisibility = false;
1053
- const prefersReducedMotion =
1054
- typeof window !== "undefined" && window.matchMedia("(prefers-reduced-motion: reduce)").matches;
1033
+ const prefersReducedMotion = typeof window !== "undefined" && window.matchMedia("(prefers-reduced-motion: reduce)").matches;
1055
1034
  let morphResolve = null;
1056
1035
  let morphReject = null;
1057
1036
  let morphDurationMs = DEFAULT_MORPH_DURATION_MS;
@@ -1069,7 +1048,7 @@ function createSVGRenderer(options) {
1069
1048
  skeletonPathA.setAttribute("visibility", "visible");
1070
1049
  skeletonPathA.setAttribute(
1071
1050
  "stroke-opacity",
1072
- String((1 - morphAlpha) * DEFAULT_SKELETON_OPACITY),
1051
+ String((1 - morphAlpha) * DEFAULT_SKELETON_OPACITY)
1073
1052
  );
1074
1053
  }
1075
1054
  if (morphPathBBuilt) {
@@ -1223,7 +1202,7 @@ function createSVGRenderer(options) {
1223
1202
  if (partial.trailColor !== void 0 || partial.trailStyle !== void 0) {
1224
1203
  warnIfTrailColorMismatch(trailColor, trailStyle);
1225
1204
  }
1226
- },
1205
+ }
1227
1206
  };
1228
1207
  const pauseOnHidden = options.pauseOnHidden !== false;
1229
1208
  function handleVisibilityChange() {
@@ -1261,13 +1240,7 @@ var PERIOD = 2 * Math.PI;
1261
1240
  function catmullRom1D(p0, p1, p2, p3, u) {
1262
1241
  const u2 = u * u;
1263
1242
  const u3 = u2 * u;
1264
- return (
1265
- 0.5 *
1266
- (2 * p1 +
1267
- (-p0 + p2) * u +
1268
- (2 * p0 - 5 * p1 + 4 * p2 - p3) * u2 +
1269
- (-p0 + 3 * p1 - 3 * p2 + p3) * u3)
1270
- );
1243
+ return 0.5 * (2 * p1 + (-p0 + p2) * u + (2 * p0 - 5 * p1 + 4 * p2 - p3) * u2 + (-p0 + 3 * p1 - 3 * p2 + p3) * u3);
1271
1244
  }
1272
1245
  function evaluateCatmullRom(points2, phase) {
1273
1246
  const N = points2.length;
@@ -1277,7 +1250,7 @@ function evaluateCatmullRom(points2, phase) {
1277
1250
  if (N === 1) {
1278
1251
  return { x: points2[0][0], y: points2[0][1] };
1279
1252
  }
1280
- phase = ((phase % PERIOD) + PERIOD) % PERIOD;
1253
+ phase = (phase % PERIOD + PERIOD) % PERIOD;
1281
1254
  const segmentSize = PERIOD / N;
1282
1255
  let i = Math.floor(phase / segmentSize);
1283
1256
  if (i >= N) {
@@ -1291,7 +1264,7 @@ function evaluateCatmullRom(points2, phase) {
1291
1264
  const p3 = points2[(i + 2) % N];
1292
1265
  return {
1293
1266
  x: catmullRom1D(p0[0], p1[0], p2[0], p3[0], u),
1294
- y: catmullRom1D(p0[1], p1[1], p2[1], p3[1], u),
1267
+ y: catmullRom1D(p0[1], p1[1], p2[1], p3[1], u)
1295
1268
  };
1296
1269
  }
1297
1270
  function drawCurve(points2, opts) {
@@ -1301,20 +1274,20 @@ function drawCurve(points2, opts) {
1301
1274
  const first = points2[0];
1302
1275
  if (points2.every((p) => p[0] === first[0] && p[1] === first[1])) {
1303
1276
  console.warn(
1304
- "[sarmal].drawCurve: all control points are identical. The curve will be a single point.",
1277
+ "[sarmal].drawCurve: all control points are identical. The curve will be a single point."
1305
1278
  );
1306
1279
  }
1307
1280
  const maxAbs = points2.reduce((m, p) => Math.max(m, Math.abs(p[0]), Math.abs(p[1])), 0);
1308
1281
  if (maxAbs > 2) {
1309
1282
  console.warn(
1310
- `[sarmal].drawCurve: control points extend to \xB1${maxAbs.toFixed(1)}, which may render off-screen. Coordinates should be in [-1, 1].`,
1283
+ `[sarmal].drawCurve: control points extend to \xB1${maxAbs.toFixed(1)}, which may render off-screen. Coordinates should be in [-1, 1].`
1311
1284
  );
1312
1285
  }
1313
1286
  const pts = points2.map(([x, y]) => [x, y]);
1314
1287
  return {
1315
1288
  name: opts?.name ?? "drawn",
1316
1289
  fn: (phase) => evaluateCatmullRom(pts, phase),
1317
- period: PERIOD,
1290
+ period: PERIOD
1318
1291
  };
1319
1292
  }
1320
1293
 
@@ -1340,11 +1313,11 @@ var points = [
1340
1313
  [-0.69, -0.84],
1341
1314
  [-0.87, -0.66],
1342
1315
  [-0.9, -0.47],
1343
- [-0.76, -0.35],
1316
+ [-0.76, -0.35]
1344
1317
  ];
1345
1318
  var artemis2 = {
1346
1319
  ...drawCurve(points, { name: "Artemis II" }),
1347
- speed: 0.7,
1320
+ speed: 0.7
1348
1321
  };
1349
1322
 
1350
1323
  // src/curves/astroid.ts
@@ -1354,14 +1327,14 @@ function astroidFn(phase, _elapsed, _params) {
1354
1327
  const s = Math.sin(phase);
1355
1328
  return {
1356
1329
  x: c * c * c,
1357
- y: s * s * s,
1330
+ y: s * s * s
1358
1331
  };
1359
1332
  }
1360
1333
  var astroid = {
1361
1334
  name: "Astroid",
1362
1335
  fn: astroidFn,
1363
1336
  period: TWO_PI2,
1364
- speed: 1.1,
1337
+ speed: 1.1
1365
1338
  };
1366
1339
 
1367
1340
  // src/curves/deltoid.ts
@@ -1369,14 +1342,14 @@ var TWO_PI3 = Math.PI * 2;
1369
1342
  function deltoidFn(phase, _elapsed, _params) {
1370
1343
  return {
1371
1344
  x: 2 * Math.cos(phase) + Math.cos(2 * phase),
1372
- y: 2 * Math.sin(phase) - Math.sin(2 * phase),
1345
+ y: 2 * Math.sin(phase) - Math.sin(2 * phase)
1373
1346
  };
1374
1347
  }
1375
1348
  var deltoid = {
1376
1349
  name: "Deltoid",
1377
1350
  fn: deltoidFn,
1378
1351
  period: TWO_PI3,
1379
- speed: 0.9,
1352
+ speed: 0.9
1380
1353
  };
1381
1354
 
1382
1355
  // src/curves/epicycloid3.ts
@@ -1384,14 +1357,14 @@ var TWO_PI4 = Math.PI * 2;
1384
1357
  function epicycloid3Fn(phase, _elapsed, _params) {
1385
1358
  return {
1386
1359
  x: 4 * Math.cos(phase) - Math.cos(4 * phase),
1387
- y: 4 * Math.sin(phase) - Math.sin(4 * phase),
1360
+ y: 4 * Math.sin(phase) - Math.sin(4 * phase)
1388
1361
  };
1389
1362
  }
1390
1363
  var epicycloid3 = {
1391
1364
  name: "Epicycloid (n=3)",
1392
1365
  fn: epicycloid3Fn,
1393
1366
  period: TWO_PI4,
1394
- speed: 0.75,
1367
+ speed: 0.75
1395
1368
  };
1396
1369
 
1397
1370
  // src/curves/epitrochoid7.ts
@@ -1400,14 +1373,14 @@ function epitrochoid7Fn(phase, _elapsed, _params) {
1400
1373
  const d = 1 + 0.55 * Math.sin(phase * 0.5);
1401
1374
  return {
1402
1375
  x: 7 * Math.cos(phase) - d * Math.cos(7 * phase),
1403
- y: 7 * Math.sin(phase) - d * Math.sin(7 * phase),
1376
+ y: 7 * Math.sin(phase) - d * Math.sin(7 * phase)
1404
1377
  };
1405
1378
  }
1406
1379
  function epitrochoid7SkeletonFn(phase) {
1407
1380
  const d = 1.275;
1408
1381
  return {
1409
1382
  x: 7 * Math.cos(phase) - d * Math.cos(7 * phase),
1410
- y: 7 * Math.sin(phase) - d * Math.sin(7 * phase),
1383
+ y: 7 * Math.sin(phase) - d * Math.sin(7 * phase)
1411
1384
  };
1412
1385
  }
1413
1386
  var epitrochoid7 = {
@@ -1415,7 +1388,7 @@ var epitrochoid7 = {
1415
1388
  fn: epitrochoid7Fn,
1416
1389
  period: TWO_PI5,
1417
1390
  speed: 1.4,
1418
- skeletonFn: epitrochoid7SkeletonFn,
1391
+ skeletonFn: epitrochoid7SkeletonFn
1419
1392
  };
1420
1393
 
1421
1394
  // src/curves/lissajous32.ts
@@ -1424,7 +1397,7 @@ function lissajous32Fn(phase, elapsed, _params) {
1424
1397
  const phi = elapsed * 0.45;
1425
1398
  return {
1426
1399
  x: Math.sin(3 * phase + phi),
1427
- y: Math.sin(2 * phase),
1400
+ y: Math.sin(2 * phase)
1428
1401
  };
1429
1402
  }
1430
1403
  var lissajous32 = {
@@ -1432,7 +1405,7 @@ var lissajous32 = {
1432
1405
  fn: lissajous32Fn,
1433
1406
  period: TWO_PI6,
1434
1407
  speed: 2,
1435
- skeleton: "live",
1408
+ skeleton: "live"
1436
1409
  };
1437
1410
 
1438
1411
  // src/curves/lissajous43.ts
@@ -1441,7 +1414,7 @@ function lissajous43Fn(phase, elapsed, _params) {
1441
1414
  const phi = elapsed * 0.38;
1442
1415
  return {
1443
1416
  x: Math.sin(4 * phase + phi),
1444
- y: Math.sin(3 * phase),
1417
+ y: Math.sin(3 * phase)
1445
1418
  };
1446
1419
  }
1447
1420
  var lissajous43 = {
@@ -1449,18 +1422,17 @@ var lissajous43 = {
1449
1422
  fn: lissajous43Fn,
1450
1423
  period: TWO_PI7,
1451
1424
  speed: 1.8,
1452
- skeleton: "live",
1425
+ skeleton: "live"
1453
1426
  };
1454
1427
 
1455
1428
  // src/curves/lame.ts
1456
1429
  var TWO_PI8 = Math.PI * 2;
1457
1430
  function lameFn(phase, elapsed, _params) {
1458
1431
  const p = 1.75 + 1.25 * Math.sin(elapsed * 0.48);
1459
- const c = Math.cos(phase),
1460
- s = Math.sin(phase);
1432
+ const c = Math.cos(phase), s = Math.sin(phase);
1461
1433
  return {
1462
1434
  x: Math.sign(c) * Math.pow(Math.abs(c), p),
1463
- y: Math.sign(s) * Math.pow(Math.abs(s), p),
1435
+ y: Math.sign(s) * Math.pow(Math.abs(s), p)
1464
1436
  };
1465
1437
  }
1466
1438
  var lame = {
@@ -1468,7 +1440,7 @@ var lame = {
1468
1440
  fn: lameFn,
1469
1441
  period: TWO_PI8,
1470
1442
  speed: 1,
1471
- skeleton: "live",
1443
+ skeleton: "live"
1472
1444
  };
1473
1445
 
1474
1446
  // src/curves/rose3.ts
@@ -1477,14 +1449,14 @@ function rose3Fn(phase, _elapsed, _params) {
1477
1449
  const r = Math.cos(3 * phase);
1478
1450
  return {
1479
1451
  x: r * Math.cos(phase),
1480
- y: r * Math.sin(phase),
1452
+ y: r * Math.sin(phase)
1481
1453
  };
1482
1454
  }
1483
1455
  var rose3 = {
1484
1456
  name: "Rose (n=3)",
1485
1457
  fn: rose3Fn,
1486
1458
  period: TWO_PI9,
1487
- speed: 1.15,
1459
+ speed: 1.15
1488
1460
  };
1489
1461
 
1490
1462
  // src/curves/rose5.ts
@@ -1493,87 +1465,78 @@ function rose5Fn(phase, _elapsed, _params) {
1493
1465
  const r = Math.cos(5 * phase);
1494
1466
  return {
1495
1467
  x: r * Math.cos(phase),
1496
- y: r * Math.sin(phase),
1468
+ y: r * Math.sin(phase)
1497
1469
  };
1498
1470
  }
1499
1471
  var rose5 = {
1500
1472
  name: "Rose (n=5)",
1501
1473
  fn: rose5Fn,
1502
1474
  period: TWO_PI10,
1503
- speed: 1,
1475
+ speed: 1
1504
1476
  };
1505
1477
 
1506
1478
  // src/curves/rose52.ts
1507
1479
  var FOUR_PI = Math.PI * 4;
1508
1480
  function rose52Fn(phase, _elapsed, _params) {
1509
- const r = Math.cos((5 / 2) * phase);
1481
+ const r = Math.cos(5 / 2 * phase);
1510
1482
  return {
1511
1483
  x: r * Math.cos(phase),
1512
- y: r * Math.sin(phase),
1484
+ y: r * Math.sin(phase)
1513
1485
  };
1514
1486
  }
1515
1487
  var rose52 = {
1516
1488
  name: "Rose (n=5/2)",
1517
1489
  fn: rose52Fn,
1518
1490
  period: FOUR_PI,
1519
- speed: 0.8,
1491
+ speed: 0.8
1520
1492
  };
1521
1493
 
1522
1494
  // src/curves/star.ts
1523
1495
  var TWO_PI11 = Math.PI * 2;
1524
1496
  function starFn(phase, _elapsed, _params) {
1525
- const r =
1526
- Math.abs(Math.cos((5 / 2) * phase)) +
1527
- 0.35 * Math.abs(Math.cos((15 / 2) * phase)) +
1528
- 0.15 * Math.abs(Math.cos((25 / 2) * phase));
1497
+ const r = Math.abs(Math.cos(5 / 2 * phase)) + 0.35 * Math.abs(Math.cos(15 / 2 * phase)) + 0.15 * Math.abs(Math.cos(25 / 2 * phase));
1529
1498
  return {
1530
1499
  x: r * Math.cos(phase),
1531
- y: r * Math.sin(phase),
1500
+ y: r * Math.sin(phase)
1532
1501
  };
1533
1502
  }
1534
1503
  var star = {
1535
1504
  name: "Star",
1536
1505
  fn: starFn,
1537
1506
  period: TWO_PI11,
1538
- speed: 1,
1507
+ speed: 1
1539
1508
  };
1540
1509
 
1541
1510
  // src/curves/star4.ts
1542
1511
  var TWO_PI12 = Math.PI * 2;
1543
1512
  function star4Fn(phase, _elapsed, _params) {
1544
- const r =
1545
- Math.abs(Math.cos(2 * phase)) +
1546
- 0.35 * Math.abs(Math.cos(6 * phase)) +
1547
- 0.15 * Math.abs(Math.cos(10 * phase));
1513
+ const r = Math.abs(Math.cos(2 * phase)) + 0.35 * Math.abs(Math.cos(6 * phase)) + 0.15 * Math.abs(Math.cos(10 * phase));
1548
1514
  return {
1549
1515
  x: r * Math.cos(phase),
1550
- y: r * Math.sin(phase),
1516
+ y: r * Math.sin(phase)
1551
1517
  };
1552
1518
  }
1553
1519
  var star4 = {
1554
1520
  name: "Star (4-arm)",
1555
1521
  fn: star4Fn,
1556
1522
  period: TWO_PI12,
1557
- speed: 1,
1523
+ speed: 1
1558
1524
  };
1559
1525
 
1560
1526
  // src/curves/star7.ts
1561
1527
  var TWO_PI13 = Math.PI * 2;
1562
1528
  function star7Fn(phase, _elapsed, _params) {
1563
- const r =
1564
- Math.abs(Math.cos((7 / 2) * phase)) +
1565
- 0.35 * Math.abs(Math.cos((21 / 2) * phase)) +
1566
- 0.15 * Math.abs(Math.cos((35 / 2) * phase));
1529
+ const r = Math.abs(Math.cos(7 / 2 * phase)) + 0.35 * Math.abs(Math.cos(21 / 2 * phase)) + 0.15 * Math.abs(Math.cos(35 / 2 * phase));
1567
1530
  return {
1568
1531
  x: r * Math.cos(phase),
1569
- y: r * Math.sin(phase),
1532
+ y: r * Math.sin(phase)
1570
1533
  };
1571
1534
  }
1572
1535
  var star7 = {
1573
1536
  name: "Star (7-arm)",
1574
1537
  fn: star7Fn,
1575
1538
  period: TWO_PI13,
1576
- speed: 1,
1539
+ speed: 1
1577
1540
  };
1578
1541
 
1579
1542
  // src/curves/index.ts
@@ -1591,7 +1554,7 @@ var curves = {
1591
1554
  lissajous32,
1592
1555
  lissajous43,
1593
1556
  epicycloid3,
1594
- lame,
1557
+ lame
1595
1558
  };
1596
1559
 
1597
1560
  // src/index.ts
@@ -1622,4 +1585,4 @@ exports.palettes = palettes;
1622
1585
  exports.rose3 = rose3;
1623
1586
  exports.rose5 = rose5;
1624
1587
  //# sourceMappingURL=index.cjs.map
1625
- //# sourceMappingURL=index.cjs.map
1588
+ //# sourceMappingURL=index.cjs.map