@vectojs/core 1.7.1 → 1.8.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.js CHANGED
@@ -3,7 +3,7 @@
3
3
 
4
4
 
5
5
 
6
- var _chunkZBKKRYDHjs = require('./chunk-ZBKKRYDH.js');
6
+ var _chunkBA5HUUDFjs = require('./chunk-BA5HUUDF.js');
7
7
 
8
8
 
9
9
 
@@ -26,12 +26,13 @@ var _chunkBPMNCGU7js = require('./chunk-BPMNCGU7.js');
26
26
 
27
27
 
28
28
 
29
- var _chunkDFNK6OV6js = require('./chunk-DFNK6OV6.js');
30
29
 
30
+ var _chunkFIQAIF55js = require('./chunk-FIQAIF55.js');
31
31
 
32
32
 
33
33
 
34
- var _chunkCTZQOM5Zjs = require('./chunk-CTZQOM5Z.js');
34
+
35
+ var _chunk4AR425ARjs = require('./chunk-4AR425AR.js');
35
36
 
36
37
  // src/tree/ComputeParticleEntity.ts
37
38
  var PARTICLE_STRIDE_FLOATS = 8;
@@ -43,7 +44,7 @@ var PARTICLE_OFFSET_ORIGIN_X = 4;
43
44
  var PARTICLE_OFFSET_ORIGIN_Y = 5;
44
45
  var PARTICLE_OFFSET_SIZE = 6;
45
46
  var PARTICLE_OFFSET_LIFE = 7;
46
- var ComputeParticleEntity = (_class = class extends _chunkDFNK6OV6js.Entity {
47
+ var ComputeParticleEntity = (_class = class extends _chunkFIQAIF55js.Entity {
47
48
 
48
49
 
49
50
 
@@ -317,6 +318,297 @@ function parseInlinePx(value) {
317
318
  const n = parseFloat(value);
318
319
  return Number.isFinite(n) && n > 0 ? n : null;
319
320
  }
321
+ function collectTextNodes(root) {
322
+ const out = [];
323
+ const walker = document.createTreeWalker(root, NodeFilter.SHOW_TEXT);
324
+ for (let n = walker.nextNode(); n; n = walker.nextNode()) out.push(n);
325
+ return out;
326
+ }
327
+ var caretGraphemeSegmenter = typeof Intl !== "undefined" && typeof Intl.Segmenter === "function" ? new Intl.Segmenter(void 0, { granularity: "grapheme" }) : null;
328
+ var caretWordSegmenter = typeof Intl !== "undefined" && typeof Intl.Segmenter === "function" ? new Intl.Segmenter(void 0, { granularity: "word" }) : null;
329
+ function graphemeBoundaries(text) {
330
+ if (!caretGraphemeSegmenter) {
331
+ const boundaries2 = [0];
332
+ for (let offset = 0; offset < text.length; ) {
333
+ const codePoint = _nullishCoalesce(text.codePointAt(offset), () => ( 0));
334
+ offset += codePoint > 65535 ? 2 : 1;
335
+ boundaries2.push(offset);
336
+ }
337
+ return boundaries2;
338
+ }
339
+ const boundaries = [0];
340
+ for (const segment of caretGraphemeSegmenter.segment(text)) {
341
+ const end = segment.index + segment.segment.length;
342
+ if (end > boundaries[boundaries.length - 1]) boundaries.push(end);
343
+ }
344
+ return boundaries;
345
+ }
346
+ function distanceToRectSquared(rect, x, y) {
347
+ const dx = x < rect.left ? rect.left - x : x > rect.right ? x - rect.right : 0;
348
+ const dy = y < rect.top ? rect.top - y : y > rect.bottom ? y - rect.bottom : 0;
349
+ return dx * dx + dy * dy;
350
+ }
351
+ function nearestOffsetForPoint(node, x, y) {
352
+ const boundaries = graphemeBoundaries(node.data);
353
+ const range = document.createRange();
354
+ let nearest = { offset: _nullishCoalesce(boundaries[0], () => ( 0)), distance: Infinity };
355
+ for (const offset of boundaries) {
356
+ range.setStart(node, offset);
357
+ range.collapse(true);
358
+ const rect = range.getBoundingClientRect();
359
+ const distance = distanceToRectSquared(rect, x, y);
360
+ if (distance < nearest.distance) nearest = { offset, distance };
361
+ }
362
+ return nearest;
363
+ }
364
+ function gridCellCaret(cell, localX) {
365
+ const node = cell.firstChild;
366
+ if (!(node instanceof Text)) return null;
367
+ const sourceLength = Number(_nullishCoalesce(cell.dataset.vectoGridSourceLength, () => ( node.data.length)));
368
+ const level = Number(_nullishCoalesce(cell.dataset.vectoGridLevel, () => ( 0)));
369
+ const cellX = Number(_nullishCoalesce(cell.dataset.vectoGridX, () => ( 0)));
370
+ const advance = Number(_nullishCoalesce(cell.dataset.vectoGridAdvance, () => ( 0)));
371
+ const caretOffsets = (_nullishCoalesce(cell.dataset.vectoGridCaretOffsets, () => ( `0,${sourceLength}`))).split(",").map(Number).filter((offset) => Number.isInteger(offset) && offset >= 0 && offset <= sourceLength);
372
+ const visuallyRtl = (level & 1) !== 0;
373
+ const visualFraction = advance > 0 ? Math.max(0, Math.min(1, (localX - cellX) / advance)) : 0;
374
+ const sourceFraction = visuallyRtl ? 1 - visualFraction : visualFraction;
375
+ const caretIndex = Math.round(sourceFraction * Math.max(0, caretOffsets.length - 1));
376
+ return {
377
+ node,
378
+ offset: _nullishCoalesce(caretOffsets[caretIndex], () => ( 0))
379
+ };
380
+ }
381
+ function nearestGridPositionInLine(line, localX) {
382
+ let nearest = null;
383
+ for (const cell of line.querySelectorAll("[data-vecto-grid-cell]")) {
384
+ const x = Number(_nullishCoalesce(cell.dataset.vectoGridX, () => ( 0)));
385
+ const advance = Number(_nullishCoalesce(cell.dataset.vectoGridAdvance, () => ( 0)));
386
+ if (localX >= x && localX <= x + advance) return gridCellCaret(cell, localX);
387
+ const distance = localX < x ? x - localX : localX - (x + advance);
388
+ if (!nearest || distance < nearest.distance) nearest = { cell, distance };
389
+ }
390
+ if (!nearest) return null;
391
+ return gridCellCaret(nearest.cell, localX);
392
+ }
393
+ function parseCssMatrix(transform) {
394
+ if (!transform || transform === "none") return [1, 0, 0, 1];
395
+ const values = transform.slice(transform.indexOf("(") + 1, transform.lastIndexOf(")")).split(",").map(Number);
396
+ return values.length >= 4 && values.slice(0, 4).every(Number.isFinite) ? [values[0], values[1], values[2], values[3]] : [1, 0, 0, 1];
397
+ }
398
+ function clientToGridLocal(contentEl, canvas, clientX, clientY) {
399
+ const line = contentEl.querySelector("[data-vecto-grid-line]");
400
+ const originMarker = _optionalChain([line, 'optionalAccess', _13 => _13.querySelector, 'call', _14 => _14('[data-vecto-grid-basis="origin"]')]);
401
+ const xMarker = _optionalChain([line, 'optionalAccess', _15 => _15.querySelector, 'call', _16 => _16('[data-vecto-grid-basis="x"]')]);
402
+ const yMarker = _optionalChain([line, 'optionalAccess', _17 => _17.querySelector, 'call', _18 => _18('[data-vecto-grid-basis="y"]')]);
403
+ if (line && originMarker && xMarker && yMarker) {
404
+ const origin = originMarker.getBoundingClientRect();
405
+ const xPoint = xMarker.getBoundingClientRect();
406
+ const yPoint = yMarker.getBoundingClientRect();
407
+ const xx = xPoint.left - origin.left;
408
+ const xy = xPoint.top - origin.top;
409
+ const yx = yPoint.left - origin.left;
410
+ const yy = yPoint.top - origin.top;
411
+ const determinant2 = xx * yy - xy * yx;
412
+ if (Number.isFinite(determinant2) && Math.abs(determinant2) > 1e-9) {
413
+ const dx2 = clientX - origin.left;
414
+ const dy2 = clientY - origin.top;
415
+ return {
416
+ x: (Number.parseFloat(line.style.left) || 0) + (yy * dx2 - yx * dy2) / determinant2,
417
+ y: (Number.parseFloat(line.style.top) || 0) + (-xy * dx2 + xx * dy2) / determinant2
418
+ };
419
+ }
420
+ }
421
+ const [a, b, c, d] = parseCssMatrix(getComputedStyle(contentEl).transform);
422
+ const canvasRect = canvas.getBoundingClientRect();
423
+ const logicalWidth = Number.parseFloat(canvas.style.width) || canvas.clientWidth || canvas.width;
424
+ const logicalHeight = Number.parseFloat(canvas.style.height) || canvas.clientHeight || canvas.height;
425
+ const scaleX = logicalWidth > 0 ? canvasRect.width / logicalWidth : 1;
426
+ const scaleY = logicalHeight > 0 ? canvasRect.height / logicalHeight : 1;
427
+ const worldX = (clientX - canvasRect.left) / scaleX;
428
+ const worldY = (clientY - canvasRect.top) / scaleY;
429
+ const dx = worldX - (Number.parseFloat(contentEl.style.left) || 0);
430
+ const dy = worldY - (Number.parseFloat(contentEl.style.top) || 0);
431
+ const determinant = a * d - b * c;
432
+ if (!Number.isFinite(determinant) || Math.abs(determinant) <= 1e-9) return null;
433
+ return {
434
+ x: (d * dx - c * dy) / determinant,
435
+ y: (-b * dx + a * dy) / determinant
436
+ };
437
+ }
438
+ function nearestGridPosition(contentEl, canvas, clientX, clientY) {
439
+ const lines = [...contentEl.querySelectorAll("[data-vecto-grid-line]")];
440
+ if (lines.length === 0) return null;
441
+ const [a, b, c, d] = parseCssMatrix(getComputedStyle(contentEl).transform);
442
+ if (a > 0 && d > 0 && Math.abs(b) <= 1e-9 && Math.abs(c) <= 1e-9) {
443
+ let nearest2 = null;
444
+ for (const line of lines) {
445
+ const rect = line.getBoundingClientRect();
446
+ const dy = clientY < rect.top ? rect.top - clientY : clientY > rect.bottom ? clientY - rect.bottom : 0;
447
+ const dx = clientX < rect.left ? rect.left - clientX : clientX > rect.right ? clientX - rect.right : 0;
448
+ const distance = dy * 4096 + dx;
449
+ if (!nearest2 || distance < nearest2.distance) nearest2 = { line, distance, rect };
450
+ }
451
+ if (!nearest2) return null;
452
+ const localWidth = Number.parseFloat(nearest2.line.style.width) || 0;
453
+ const scaleX = localWidth > 0 && nearest2.rect.width > 0 ? nearest2.rect.width / localWidth : 1;
454
+ const localX = (clientX - nearest2.rect.left) / scaleX;
455
+ return nearestGridPositionInLine(nearest2.line, localX);
456
+ }
457
+ const local = clientToGridLocal(contentEl, canvas, clientX, clientY);
458
+ if (!local) return null;
459
+ let nearest = null;
460
+ for (const line of lines) {
461
+ const left = Number.parseFloat(line.style.left) || 0;
462
+ const top = Number.parseFloat(line.style.top) || 0;
463
+ const width = Number.parseFloat(line.style.width) || 0;
464
+ const height = Number.parseFloat(line.style.height) || 0;
465
+ const dy = local.y < top ? top - local.y : local.y > top + height ? local.y - top - height : 0;
466
+ const dx = local.x < left ? left - local.x : local.x > left + width ? local.x - left - width : 0;
467
+ const distance = dy * 4096 + dx;
468
+ if (!nearest || distance < nearest.distance) nearest = { line, distance };
469
+ }
470
+ if (!nearest) return null;
471
+ const lineLeft = Number.parseFloat(nearest.line.style.left) || 0;
472
+ return nearestGridPositionInLine(nearest.line, local.x - lineLeft);
473
+ }
474
+ function nearestTextPositionInLine(line, x, y) {
475
+ const texts = collectTextNodes(line);
476
+ if (texts.length === 0) return null;
477
+ let nearest = null;
478
+ for (const node of texts) {
479
+ const candidate = nearestOffsetForPoint(node, x, y);
480
+ if (!nearest || candidate.distance < nearest.distance) {
481
+ let { offset } = candidate;
482
+ while (offset > 0 && node.data[offset - 1] === "\n") offset--;
483
+ nearest = { position: { node, offset }, distance: candidate.distance };
484
+ }
485
+ }
486
+ return _nullishCoalesce(_optionalChain([nearest, 'optionalAccess', _19 => _19.position]), () => ( null));
487
+ }
488
+ function nearestTextPositionInProjection(contentEl, canvas, x, y, eventTarget) {
489
+ if (contentEl.dataset.vectoContentGrid !== void 0) {
490
+ return nearestGridPosition(contentEl, canvas, x, y);
491
+ }
492
+ let targetLine = eventTarget;
493
+ while (targetLine && targetLine.parentElement !== contentEl) {
494
+ if (!contentEl.contains(targetLine)) {
495
+ targetLine = null;
496
+ break;
497
+ }
498
+ targetLine = targetLine.parentElement;
499
+ }
500
+ if (_optionalChain([targetLine, 'optionalAccess', _20 => _20.parentElement]) === contentEl) {
501
+ return nearestTextPositionInLine(targetLine, x, y);
502
+ }
503
+ let bestLine = null;
504
+ let bestDist = Infinity;
505
+ for (let i = 0; i < contentEl.children.length; i++) {
506
+ const child = contentEl.children[i];
507
+ const rect = child.getBoundingClientRect();
508
+ if (rect.width <= 0 && rect.height <= 0) continue;
509
+ const dy = y < rect.top ? rect.top - y : y > rect.bottom ? y - rect.bottom : 0;
510
+ const dx = x < rect.left ? rect.left - x : x > rect.right ? x - rect.right : 0;
511
+ const dist = dy * 4096 + dx;
512
+ if (dist < bestDist) {
513
+ bestDist = dist;
514
+ bestLine = child;
515
+ }
516
+ }
517
+ if (bestLine) return nearestTextPositionInLine(bestLine, x, y);
518
+ return nearestTextPositionInLine(contentEl, x, y);
519
+ }
520
+ function projectionAbsoluteOffset(root, caret) {
521
+ let offset = 0;
522
+ for (const node of collectTextNodes(root)) {
523
+ if (node === caret.node) return offset + Math.min(caret.offset, node.data.length);
524
+ offset += node.data.length;
525
+ }
526
+ return null;
527
+ }
528
+ function projectionCaretAt(root, absoluteOffset, affinity) {
529
+ const nodes = collectTextNodes(root);
530
+ if (nodes.length === 0) return null;
531
+ let remaining = Math.max(0, absoluteOffset);
532
+ for (let index = 0; index < nodes.length; index++) {
533
+ const node = nodes[index];
534
+ if (remaining < node.data.length || remaining === node.data.length && affinity === "backward") {
535
+ return { node, offset: remaining };
536
+ }
537
+ if (remaining === node.data.length && index === nodes.length - 1) {
538
+ return { node, offset: remaining };
539
+ }
540
+ remaining -= node.data.length;
541
+ }
542
+ const last = nodes[nodes.length - 1];
543
+ return { node: last, offset: last.data.length };
544
+ }
545
+ function selectProjectionUnit(selection, root, caret, unit) {
546
+ const absoluteOffset = projectionAbsoluteOffset(root, caret);
547
+ const text = _nullishCoalesce(root.textContent, () => ( ""));
548
+ if (absoluteOffset === null || text.length === 0) return false;
549
+ let start = absoluteOffset;
550
+ let end = absoluteOffset;
551
+ if (unit === "line") {
552
+ for (let index = Math.max(0, absoluteOffset - 1); index >= 0; index--) {
553
+ if (text[index] === "\n" || text[index] === "\r") {
554
+ start = index + 1;
555
+ if (text[index] === "\r" && text[index + 1] === "\n") start++;
556
+ break;
557
+ }
558
+ }
559
+ const cr = text.indexOf("\r", absoluteOffset);
560
+ const lf = text.indexOf("\n", absoluteOffset);
561
+ const separator = [cr, lf].filter((index) => index >= 0).sort((a, b) => a - b)[0];
562
+ end = separator === void 0 ? text.length : separator;
563
+ } else if (caretWordSegmenter) {
564
+ const segments = [...caretWordSegmenter.segment(text)];
565
+ const selected = _nullishCoalesce(_nullishCoalesce(segments.find(
566
+ (segment) => segment.isWordLike && absoluteOffset >= segment.index && absoluteOffset <= segment.index + segment.segment.length
567
+ ), () => ( segments.find((segment) => segment.isWordLike && segment.index >= absoluteOffset))), () => ( [...segments].reverse().find((segment) => segment.isWordLike)));
568
+ if (selected) {
569
+ start = selected.index;
570
+ end = selected.index + selected.segment.length;
571
+ }
572
+ } else {
573
+ const isWord = (character) => /[\p{L}\p{N}_]/u.test(character);
574
+ while (start > 0 && isWord(text[start - 1])) start--;
575
+ while (end < text.length && isWord(text[end])) end++;
576
+ }
577
+ const anchor = projectionCaretAt(root, start, "forward");
578
+ const focus = projectionCaretAt(root, end, "backward");
579
+ if (!anchor || !focus) return false;
580
+ selection.setBaseAndExtent(anchor.node, anchor.offset, focus.node, focus.offset);
581
+ return true;
582
+ }
583
+ function extendSelection(selection, anchor, focus) {
584
+ try {
585
+ selection.setBaseAndExtent(anchor.node, anchor.offset, focus.node, focus.offset);
586
+ return;
587
+ } catch (e3) {
588
+ }
589
+ try {
590
+ selection.collapse(anchor.node, anchor.offset);
591
+ selection.extend(focus.node, focus.offset);
592
+ return;
593
+ } catch (e4) {
594
+ }
595
+ const anchorRange = document.createRange();
596
+ anchorRange.setStart(anchor.node, anchor.offset);
597
+ anchorRange.collapse(true);
598
+ const focusRange = document.createRange();
599
+ focusRange.setStart(focus.node, focus.offset);
600
+ focusRange.collapse(true);
601
+ const range = document.createRange();
602
+ if (anchorRange.compareBoundaryPoints(Range.START_TO_START, focusRange) <= 0) {
603
+ range.setStart(anchor.node, anchor.offset);
604
+ range.setEnd(focus.node, focus.offset);
605
+ } else {
606
+ range.setStart(focus.node, focus.offset);
607
+ range.setEnd(anchor.node, anchor.offset);
608
+ }
609
+ selection.removeAllRanges();
610
+ selection.addRange(range);
611
+ }
320
612
  var Scene = (_class2 = class _Scene {
321
613
  static __initStatic() {this.webglCreator = null}
322
614
  static __initStatic2() {this.webgpuManagerClass = null}
@@ -355,7 +647,7 @@ var Scene = (_class2 = class _Scene {
355
647
  __init14() {this.reducedMotionQuery = null}
356
648
  /** True when the OS asks for reduced motion and we respect it. Read by the animation drivers. */
357
649
  get prefersReducedMotion() {
358
- return this.respectReducedMotion && !!_optionalChain([this, 'access', _13 => _13.reducedMotionQuery, 'optionalAccess', _14 => _14.matches]);
650
+ return this.respectReducedMotion && !!_optionalChain([this, 'access', _21 => _21.reducedMotionQuery, 'optionalAccess', _22 => _22.matches]);
359
651
  }
360
652
  /**
361
653
  * Throttle interval (ms) for the a11y/automation shadow sync. `0` = every
@@ -373,63 +665,81 @@ var Scene = (_class2 = class _Scene {
373
665
  __init18() {this.a11yElements = /* @__PURE__ */ new Map()}
374
666
  /** DOM nodes mirroring static text content, keyed by entity id. */
375
667
  __init19() {this.contentElements = /* @__PURE__ */ new Map()}
376
- __init20() {this.contentProjectionEnabled = true}
668
+ /** Pending cold font-calibration frame per projected grid entity. */
669
+ __init20() {this.contentGridCalibrationFrames = /* @__PURE__ */ new Map()}
670
+ /** Detached, untransformed font probes used by the cold calibration pass. */
671
+ __init21() {this.contentGridCalibrationProbes = /* @__PURE__ */ new Map()}
672
+ /** Invalidates grid font calibration after browser font availability changes. */
673
+ __init22() {this.contentFontEpoch = 0}
674
+ /** Cached Canvas-to-client scale for the current font/viewport epoch. */
675
+ __init23() {this.contentMetricScaleEpoch = -1}
676
+ __init24() {this.contentMetricScaleX = 1}
677
+ __init25() {this.contentProjectionEnabled = true}
678
+ /**
679
+ * True while a text-selection drag that started on a projection's blank
680
+ * region (no text node under the press) is being driven manually — the
681
+ * browser has no native anchor for it, so mousemove extends the Selection
682
+ * from the position we resolved ourselves.
683
+ */
684
+ __init26() {this.blankRegionSelectionDrag = false}
685
+ __init27() {this.contentSelectionAnchor = null}
686
+ __init28() {this.contentSelectionEndListener = null}
377
687
  // Animation/interactive flags collected during the render walk (tree-walk
378
688
  // fusion): the loop reads last frame's answers instead of re-walking the
379
689
  // tree up to 4× per tick. Start true so the first tick stays conservative.
380
- __init21() {this.frameHadAnimation = true}
381
- __init22() {this.frameHadInteractive = true}
690
+ __init29() {this.frameHadAnimation = true}
691
+ __init30() {this.frameHadInteractive = true}
382
692
 
383
- __init23() {this.focusedA11yElement = null}
384
- __init24() {this.caretBlinkTimer = null}
385
- __init25() {this.a11yNeedsReorder = true}
386
- __init26() {this.portalRoot = null}
387
- __init27() {this.fullViewportElements = []}
388
- __init28() {this.normalElements = []}
389
- __init29() {this.activeIds = /* @__PURE__ */ new Set()}
390
- __init30() {this.activePortalsThisFrame = /* @__PURE__ */ new Set()}
391
- __init31() {this.activePortalsPrevFrame = /* @__PURE__ */ new Set()}
392
- __init32() {this.portalEntities = /* @__PURE__ */ new Map()}
393
- __init33() {this.renderOrderCounter = 0}
693
+ __init31() {this.focusedA11yElement = null}
694
+ __init32() {this.caretBlinkTimer = null}
695
+ __init33() {this.a11yNeedsReorder = true}
696
+ __init34() {this.portalRoot = null}
697
+ __init35() {this.fullViewportElements = []}
698
+ __init36() {this.normalElements = []}
699
+ __init37() {this.activeIds = /* @__PURE__ */ new Set()}
700
+ __init38() {this.activePortalsThisFrame = /* @__PURE__ */ new Set()}
701
+ __init39() {this.activePortalsPrevFrame = /* @__PURE__ */ new Set()}
702
+ __init40() {this.portalEntities = /* @__PURE__ */ new Map()}
703
+ __init41() {this.renderOrderCounter = 0}
394
704
  // Optional WebGL point-cloud layer (see SceneOptions.pointBackend).
395
- __init34() {this.pointRenderer = null}
396
- __init35() {this.glCanvas = null}
705
+ __init42() {this.pointRenderer = null}
706
+ __init43() {this.glCanvas = null}
397
707
 
398
708
 
399
709
 
400
- __init36() {this.disableWindowResize = false}
710
+ __init44() {this.disableWindowResize = false}
401
711
  // WebGPU properties
402
- __init37() {this.destroyed = false}
403
- __init38() {this.device = null}
404
- __init39() {this.deviceLost = false}
405
- __init40() {this.particleBackend = "auto"}
406
- __init41() {this._webgpuDisabled = false}
712
+ __init45() {this.destroyed = false}
713
+ __init46() {this.device = null}
714
+ __init47() {this.deviceLost = false}
715
+ __init48() {this.particleBackend = "auto"}
716
+ __init49() {this._webgpuDisabled = false}
407
717
  get webgpuDisabled() {
408
718
  return this._webgpuDisabled || this.particleBackend === "cpu";
409
719
  }
410
720
  set webgpuDisabled(value) {
411
721
  this._webgpuDisabled = value;
412
722
  }
413
- __init42() {this.recoveryTimerId = null}
414
- __init43() {this.manager = null}
415
- __init44() {this.initializingWebGPU = false}
416
- __init45() {this.gpuCanvas = null}
417
- __init46() {this.gpuContext = null}
723
+ __init50() {this.recoveryTimerId = null}
724
+ __init51() {this.manager = null}
725
+ __init52() {this.initializingWebGPU = false}
726
+ __init53() {this.gpuCanvas = null}
727
+ __init54() {this.gpuContext = null}
418
728
  /** True while the GPU canvas holds a presented particle frame (needs clearing when they leave). */
419
- __init47() {this.gpuHasContent = false}
420
- __init48() {this.mouseX = -9999}
421
- __init49() {this.mouseY = -9999}
422
- __init50() {this.pointerMoveListener = null}
423
- __init51() {this.pointerLeaveListener = null}
424
- __init52() {this.hasWarnedZeroSize = false}
425
- __init53() {this.fontLoadHandler = null}
426
- constructor(canvas, options = {}) {;_class2.prototype.__init7.call(this);_class2.prototype.__init8.call(this);_class2.prototype.__init9.call(this);_class2.prototype.__init10.call(this);_class2.prototype.__init11.call(this);_class2.prototype.__init12.call(this);_class2.prototype.__init13.call(this);_class2.prototype.__init14.call(this);_class2.prototype.__init15.call(this);_class2.prototype.__init16.call(this);_class2.prototype.__init17.call(this);_class2.prototype.__init18.call(this);_class2.prototype.__init19.call(this);_class2.prototype.__init20.call(this);_class2.prototype.__init21.call(this);_class2.prototype.__init22.call(this);_class2.prototype.__init23.call(this);_class2.prototype.__init24.call(this);_class2.prototype.__init25.call(this);_class2.prototype.__init26.call(this);_class2.prototype.__init27.call(this);_class2.prototype.__init28.call(this);_class2.prototype.__init29.call(this);_class2.prototype.__init30.call(this);_class2.prototype.__init31.call(this);_class2.prototype.__init32.call(this);_class2.prototype.__init33.call(this);_class2.prototype.__init34.call(this);_class2.prototype.__init35.call(this);_class2.prototype.__init36.call(this);_class2.prototype.__init37.call(this);_class2.prototype.__init38.call(this);_class2.prototype.__init39.call(this);_class2.prototype.__init40.call(this);_class2.prototype.__init41.call(this);_class2.prototype.__init42.call(this);_class2.prototype.__init43.call(this);_class2.prototype.__init44.call(this);_class2.prototype.__init45.call(this);_class2.prototype.__init46.call(this);_class2.prototype.__init47.call(this);_class2.prototype.__init48.call(this);_class2.prototype.__init49.call(this);_class2.prototype.__init50.call(this);_class2.prototype.__init51.call(this);_class2.prototype.__init52.call(this);_class2.prototype.__init53.call(this);
729
+ __init55() {this.gpuHasContent = false}
730
+ __init56() {this.mouseX = -9999}
731
+ __init57() {this.mouseY = -9999}
732
+ __init58() {this.pointerMoveListener = null}
733
+ __init59() {this.pointerLeaveListener = null}
734
+ __init60() {this.hasWarnedZeroSize = false}
735
+ __init61() {this.fontLoadHandler = null}
736
+ constructor(canvas, options = {}) {;_class2.prototype.__init7.call(this);_class2.prototype.__init8.call(this);_class2.prototype.__init9.call(this);_class2.prototype.__init10.call(this);_class2.prototype.__init11.call(this);_class2.prototype.__init12.call(this);_class2.prototype.__init13.call(this);_class2.prototype.__init14.call(this);_class2.prototype.__init15.call(this);_class2.prototype.__init16.call(this);_class2.prototype.__init17.call(this);_class2.prototype.__init18.call(this);_class2.prototype.__init19.call(this);_class2.prototype.__init20.call(this);_class2.prototype.__init21.call(this);_class2.prototype.__init22.call(this);_class2.prototype.__init23.call(this);_class2.prototype.__init24.call(this);_class2.prototype.__init25.call(this);_class2.prototype.__init26.call(this);_class2.prototype.__init27.call(this);_class2.prototype.__init28.call(this);_class2.prototype.__init29.call(this);_class2.prototype.__init30.call(this);_class2.prototype.__init31.call(this);_class2.prototype.__init32.call(this);_class2.prototype.__init33.call(this);_class2.prototype.__init34.call(this);_class2.prototype.__init35.call(this);_class2.prototype.__init36.call(this);_class2.prototype.__init37.call(this);_class2.prototype.__init38.call(this);_class2.prototype.__init39.call(this);_class2.prototype.__init40.call(this);_class2.prototype.__init41.call(this);_class2.prototype.__init42.call(this);_class2.prototype.__init43.call(this);_class2.prototype.__init44.call(this);_class2.prototype.__init45.call(this);_class2.prototype.__init46.call(this);_class2.prototype.__init47.call(this);_class2.prototype.__init48.call(this);_class2.prototype.__init49.call(this);_class2.prototype.__init50.call(this);_class2.prototype.__init51.call(this);_class2.prototype.__init52.call(this);_class2.prototype.__init53.call(this);_class2.prototype.__init54.call(this);_class2.prototype.__init55.call(this);_class2.prototype.__init56.call(this);_class2.prototype.__init57.call(this);_class2.prototype.__init58.call(this);_class2.prototype.__init59.call(this);_class2.prototype.__init60.call(this);_class2.prototype.__init61.call(this);
427
737
  this.canvas = canvas;
428
738
  this.debugA11y = _nullishCoalesce(options.debugA11y, () => ( false));
429
739
  this.disableWindowResize = _nullishCoalesce(options.disableWindowResize, () => ( false));
430
740
  if (this.disableWindowResize) {
431
- const styleWidth = parseInlinePx(_optionalChain([canvas, 'access', _15 => _15.style, 'optionalAccess', _16 => _16.width]));
432
- const styleHeight = parseInlinePx(_optionalChain([canvas, 'access', _17 => _17.style, 'optionalAccess', _18 => _18.height]));
741
+ const styleWidth = parseInlinePx(_optionalChain([canvas, 'access', _23 => _23.style, 'optionalAccess', _24 => _24.width]));
742
+ const styleHeight = parseInlinePx(_optionalChain([canvas, 'access', _25 => _25.style, 'optionalAccess', _26 => _26.height]));
433
743
  this.width = _nullishCoalesce(styleWidth, () => ( (canvas.width || canvas.clientWidth || 0)));
434
744
  this.height = _nullishCoalesce(styleHeight, () => ( (canvas.height || canvas.clientHeight || 0)));
435
745
  } else {
@@ -437,7 +747,7 @@ var Scene = (_class2 = class _Scene {
437
747
  this.height = typeof window !== "undefined" ? window.innerHeight : canvas.clientHeight || canvas.height || 600;
438
748
  }
439
749
  const globalProcess = typeof globalThis !== "undefined" ? globalThis.process : void 0;
440
- const isTest = globalProcess && (_optionalChain([globalProcess, 'access', _19 => _19.env, 'optionalAccess', _20 => _20.NODE_ENV]) === "test" || _optionalChain([globalProcess, 'access', _21 => _21.env, 'optionalAccess', _22 => _22.VITEST]) === "true");
750
+ const isTest = globalProcess && (_optionalChain([globalProcess, 'access', _27 => _27.env, 'optionalAccess', _28 => _28.NODE_ENV]) === "test" || _optionalChain([globalProcess, 'access', _29 => _29.env, 'optionalAccess', _30 => _30.VITEST]) === "true");
441
751
  this.maxFPS = _nullishCoalesce(options.maxFPS, () => ( (isTest ? 0 : 60)));
442
752
  this.respectReducedMotion = _nullishCoalesce(options.respectReducedMotion, () => ( true));
443
753
  this.autoThrottle = _nullishCoalesce(options.autoThrottle, () => ( true));
@@ -445,7 +755,7 @@ var Scene = (_class2 = class _Scene {
445
755
  this.a11ySyncInterval = _nullishCoalesce(options.a11ySyncInterval, () => ( 0));
446
756
  this.contentProjectionEnabled = _nullishCoalesce(options.contentProjection, () => ( true));
447
757
  this.reducedMotionQuery = typeof window !== "undefined" && typeof window.matchMedia === "function" ? window.matchMedia("(prefers-reduced-motion: reduce)") : null;
448
- this.root = new class RootEntity extends _chunkDFNK6OV6js.Entity {
758
+ this.root = new class RootEntity extends _chunkFIQAIF55js.Entity {
449
759
  isPointInside() {
450
760
  return false;
451
761
  }
@@ -454,7 +764,7 @@ var Scene = (_class2 = class _Scene {
454
764
  }
455
765
  }("root");
456
766
  this.root._scene = this;
457
- this.overlayRoot = new class OverlayRoot extends _chunkDFNK6OV6js.Entity {
767
+ this.overlayRoot = new class OverlayRoot extends _chunkFIQAIF55js.Entity {
458
768
  isPointInside() {
459
769
  return false;
460
770
  }
@@ -482,16 +792,88 @@ var Scene = (_class2 = class _Scene {
482
792
  this.a11yRoot.style.zIndex = "10";
483
793
  this.a11yRoot.style.userSelect = "text";
484
794
  this.a11yRoot.addEventListener("mousedown", (e) => {
795
+ if (e.button !== 0) return;
485
796
  const target = e.target;
486
- if (target !== this.a11yRoot && target.closest("[data-vecto-content]") && getComputedStyle(target.closest("[data-vecto-content]")).pointerEvents === "auto") {
487
- this.a11yRoot.style.pointerEvents = "auto";
797
+ const contentEl = target.closest("[data-vecto-content]");
798
+ if (target === this.a11yRoot || !contentEl) return;
799
+ if (getComputedStyle(contentEl).pointerEvents !== "auto") return;
800
+ const selection = window.getSelection();
801
+ if (!selection) return;
802
+ this.a11yRoot.style.pointerEvents = "auto";
803
+ const resolved = nearestTextPositionInProjection(
804
+ contentEl,
805
+ this.canvas,
806
+ e.clientX,
807
+ e.clientY,
808
+ target
809
+ );
810
+ if (resolved) {
811
+ if (e.detail >= 2) {
812
+ selection.removeAllRanges();
813
+ selectProjectionUnit(selection, contentEl, resolved, e.detail >= 3 ? "line" : "word");
814
+ this.endContentSelectionDrag();
815
+ e.preventDefault();
816
+ return;
817
+ }
818
+ const existingAnchor = e.shiftKey && selection.anchorNode instanceof Text ? { node: selection.anchorNode, offset: selection.anchorOffset } : null;
819
+ const anchor = existingAnchor && this.a11yRoot.contains(existingAnchor.node) ? existingAnchor : resolved;
820
+ if (e.shiftKey && existingAnchor) extendSelection(selection, anchor, resolved);
821
+ else selection.collapse(resolved.node, resolved.offset);
822
+ this.contentSelectionAnchor = anchor;
823
+ this.blankRegionSelectionDrag = true;
824
+ e.preventDefault();
488
825
  }
489
826
  });
490
- const endDrag = () => {
491
- if (this.a11yRoot) this.a11yRoot.style.pointerEvents = "none";
492
- };
827
+ this.a11yRoot.addEventListener("dblclick", (e) => {
828
+ const target = e.target;
829
+ const contentEl = target.closest("[data-vecto-content]");
830
+ if (!contentEl || getComputedStyle(contentEl).pointerEvents !== "auto") return;
831
+ const selection = window.getSelection();
832
+ const caret = nearestTextPositionInProjection(
833
+ contentEl,
834
+ this.canvas,
835
+ e.clientX,
836
+ e.clientY,
837
+ target
838
+ );
839
+ if (!selection || !caret) return;
840
+ selection.removeAllRanges();
841
+ selectProjectionUnit(selection, contentEl, caret, "word");
842
+ this.endContentSelectionDrag();
843
+ e.preventDefault();
844
+ });
845
+ this.a11yRoot.addEventListener("mousemove", (e) => {
846
+ if (!this.blankRegionSelectionDrag) return;
847
+ const selection = window.getSelection();
848
+ if (!selection || selection.rangeCount === 0) return;
849
+ const target = e.target;
850
+ let contentEl = target.closest("[data-vecto-content]");
851
+ if (!contentEl) {
852
+ let bestDistance = Infinity;
853
+ for (const candidate of this.contentElements.values()) {
854
+ if (getComputedStyle(candidate).pointerEvents !== "auto") continue;
855
+ const rect = candidate.getBoundingClientRect();
856
+ const dx = e.clientX < rect.left ? rect.left - e.clientX : e.clientX > rect.right ? e.clientX - rect.right : 0;
857
+ const dy = e.clientY < rect.top ? rect.top - e.clientY : e.clientY > rect.bottom ? e.clientY - rect.bottom : 0;
858
+ const distance = dx * dx + dy * dy;
859
+ if (distance < bestDistance) {
860
+ bestDistance = distance;
861
+ contentEl = candidate;
862
+ }
863
+ }
864
+ }
865
+ const focus = contentEl ? nearestTextPositionInProjection(contentEl, this.canvas, e.clientX, e.clientY, target) : null;
866
+ const anchor = this.contentSelectionAnchor;
867
+ if (focus && anchor) {
868
+ extendSelection(selection, anchor, focus);
869
+ }
870
+ });
871
+ const endDrag = () => this.endContentSelectionDrag();
493
872
  this.a11yRoot.addEventListener("mouseup", endDrag);
494
873
  this.a11yRoot.addEventListener("mouseleave", endDrag);
874
+ window.addEventListener("mouseup", endDrag);
875
+ window.addEventListener("blur", endDrag);
876
+ this.contentSelectionEndListener = endDrag;
495
877
  if (canvas.parentElement) {
496
878
  canvas.parentElement.appendChild(this.a11yRoot);
497
879
  }
@@ -533,7 +915,8 @@ var Scene = (_class2 = class _Scene {
533
915
  };
534
916
  if (typeof document !== "undefined" && document.fonts) {
535
917
  this.fontLoadHandler = () => {
536
- _chunkDFNK6OV6js.clearCssLineBoxMetrics.call(void 0, );
918
+ _chunkFIQAIF55js.clearCssLineBoxMetrics.call(void 0, );
919
+ this.contentFontEpoch++;
537
920
  this.markDirty();
538
921
  };
539
922
  document.fonts.ready.then(this.fontLoadHandler);
@@ -541,6 +924,18 @@ var Scene = (_class2 = class _Scene {
541
924
  }
542
925
  this.setupEvents();
543
926
  }
927
+ endContentSelectionDrag() {
928
+ this.blankRegionSelectionDrag = false;
929
+ this.contentSelectionAnchor = null;
930
+ if (this.a11yRoot) this.a11yRoot.style.pointerEvents = "none";
931
+ }
932
+ releaseContentSelectionForRebuild(el) {
933
+ const selection = typeof window !== "undefined" && typeof window.getSelection === "function" ? window.getSelection() : null;
934
+ const ownsSelection = this.contentSelectionAnchor && el.contains(this.contentSelectionAnchor.node) || (_optionalChain([selection, 'optionalAccess', _31 => _31.anchorNode]) ? el.contains(selection.anchorNode) : false) || (_optionalChain([selection, 'optionalAccess', _32 => _32.focusNode]) ? el.contains(selection.focusNode) : false);
935
+ if (!ownsSelection) return;
936
+ this.endContentSelectionDrag();
937
+ _optionalChain([selection, 'optionalAccess', _33 => _33.removeAllRanges, 'call', _34 => _34()]);
938
+ }
544
939
  /**
545
940
  * Expose the underlying {@link IRenderer} for advanced direct-draw operations.
546
941
  *
@@ -551,7 +946,7 @@ var Scene = (_class2 = class _Scene {
551
946
  }
552
947
  /** Convert browser viewport coordinates into this Scene's logical coordinates. */
553
948
  clientToScene(clientX, clientY) {
554
- const rect = _optionalChain([this, 'access', _23 => _23.canvas, 'access', _24 => _24.getBoundingClientRect, 'optionalCall', _25 => _25()]);
949
+ const rect = _optionalChain([this, 'access', _35 => _35.canvas, 'access', _36 => _36.getBoundingClientRect, 'optionalCall', _37 => _37()]);
555
950
  if (!rect) return { x: clientX, y: clientY };
556
951
  const cssWidth = rect.width || this.canvas.clientWidth || this.width;
557
952
  const cssHeight = rect.height || this.canvas.clientHeight || this.height;
@@ -571,6 +966,24 @@ var Scene = (_class2 = class _Scene {
571
966
  this.root.add(entity);
572
967
  return this;
573
968
  }
969
+ clearContentGridState(entityId, el) {
970
+ const calibrationFrame = this.contentGridCalibrationFrames.get(entityId);
971
+ if (calibrationFrame !== void 0 && typeof cancelAnimationFrame === "function") {
972
+ cancelAnimationFrame(calibrationFrame);
973
+ }
974
+ this.contentGridCalibrationFrames.delete(entityId);
975
+ _optionalChain([this, 'access', _38 => _38.contentGridCalibrationProbes, 'access', _39 => _39.get, 'call', _40 => _40(entityId), 'optionalAccess', _41 => _41.remove, 'call', _42 => _42()]);
976
+ this.contentGridCalibrationProbes.delete(entityId);
977
+ delete el.dataset.vectoGridCalibrationPending;
978
+ delete el.dataset.vectoGridCalibration;
979
+ delete el.dataset.vectoGridReady;
980
+ delete el.dataset.vectoContentGrid;
981
+ delete el.dataset.vectoGridCarriers;
982
+ delete el.dataset.vectoGridMaterializeMs;
983
+ delete el.dataset.vectoGridCalibrationSamples;
984
+ delete el.dataset.vectoGridCalibrationMs;
985
+ this.releaseContentSelectionForRebuild(el);
986
+ }
574
987
  removeA11yRecursively(node) {
575
988
  if (node.isDOMPortal) {
576
989
  node.domElement.remove();
@@ -580,6 +993,7 @@ var Scene = (_class2 = class _Scene {
580
993
  }
581
994
  const contentEl = this.contentElements.get(node.id);
582
995
  if (contentEl) {
996
+ this.clearContentGridState(node.id, contentEl);
583
997
  contentEl.remove();
584
998
  this.contentElements.delete(node.id);
585
999
  this.a11yNeedsReorder = true;
@@ -661,6 +1075,11 @@ var Scene = (_class2 = class _Scene {
661
1075
  if (typeof window !== "undefined" && !this.disableWindowResize) {
662
1076
  window.removeEventListener("resize", this.resizeHandler);
663
1077
  }
1078
+ if (typeof window !== "undefined" && this.contentSelectionEndListener) {
1079
+ window.removeEventListener("mouseup", this.contentSelectionEndListener);
1080
+ window.removeEventListener("blur", this.contentSelectionEndListener);
1081
+ this.contentSelectionEndListener = null;
1082
+ }
664
1083
  if (typeof window !== "undefined" && this.canvas && typeof this.canvas.removeEventListener === "function") {
665
1084
  if (this.pointerMoveListener) {
666
1085
  this.canvas.removeEventListener("pointermove", this.pointerMoveListener);
@@ -669,15 +1088,24 @@ var Scene = (_class2 = class _Scene {
669
1088
  this.canvas.removeEventListener("pointerleave", this.pointerLeaveListener);
670
1089
  }
671
1090
  }
672
- _optionalChain([this, 'access', _26 => _26.a11yRoot, 'optionalAccess', _27 => _27.remove, 'call', _28 => _28()]);
673
- _optionalChain([this, 'access', _29 => _29.portalRoot, 'optionalAccess', _30 => _30.remove, 'call', _31 => _31()]);
1091
+ _optionalChain([this, 'access', _43 => _43.a11yRoot, 'optionalAccess', _44 => _44.remove, 'call', _45 => _45()]);
1092
+ _optionalChain([this, 'access', _46 => _46.portalRoot, 'optionalAccess', _47 => _47.remove, 'call', _48 => _48()]);
674
1093
  this.a11yElements.clear();
675
1094
  for (const el of this.contentElements.values()) el.remove();
676
1095
  this.contentElements.clear();
677
- _optionalChain([this, 'access', _32 => _32.pointRenderer, 'optionalAccess', _33 => _33.destroy, 'call', _34 => _34()]);
678
- _optionalChain([this, 'access', _35 => _35.renderer, 'access', _36 => _36.dispose, 'optionalCall', _37 => _37()]);
679
- _optionalChain([this, 'access', _38 => _38.glCanvas, 'optionalAccess', _39 => _39.remove, 'call', _40 => _40()]);
680
- _optionalChain([this, 'access', _41 => _41.gpuCanvas, 'optionalAccess', _42 => _42.remove, 'call', _43 => _43()]);
1096
+ if (typeof cancelAnimationFrame === "function") {
1097
+ for (const frame of this.contentGridCalibrationFrames.values()) {
1098
+ cancelAnimationFrame(frame);
1099
+ }
1100
+ }
1101
+ this.contentGridCalibrationFrames.clear();
1102
+ for (const probe of this.contentGridCalibrationProbes.values()) probe.remove();
1103
+ this.contentGridCalibrationProbes.clear();
1104
+ this.endContentSelectionDrag();
1105
+ _optionalChain([this, 'access', _49 => _49.pointRenderer, 'optionalAccess', _50 => _50.destroy, 'call', _51 => _51()]);
1106
+ _optionalChain([this, 'access', _52 => _52.renderer, 'access', _53 => _53.dispose, 'optionalCall', _54 => _54()]);
1107
+ _optionalChain([this, 'access', _55 => _55.glCanvas, 'optionalAccess', _56 => _56.remove, 'call', _57 => _57()]);
1108
+ _optionalChain([this, 'access', _58 => _58.gpuCanvas, 'optionalAccess', _59 => _59.remove, 'call', _60 => _60()]);
681
1109
  this.gpuCanvas = null;
682
1110
  this.gpuContext = null;
683
1111
  if (this.recoveryTimerId) {
@@ -689,7 +1117,7 @@ var Scene = (_class2 = class _Scene {
689
1117
  this.manager = null;
690
1118
  }
691
1119
  if (this.device) {
692
- _optionalChain([this, 'access', _44 => _44.device, 'access', _45 => _45.destroy, 'optionalCall', _46 => _46()]);
1120
+ _optionalChain([this, 'access', _61 => _61.device, 'access', _62 => _62.destroy, 'optionalCall', _63 => _63()]);
693
1121
  this.device = null;
694
1122
  }
695
1123
  }
@@ -831,15 +1259,15 @@ var Scene = (_class2 = class _Scene {
831
1259
  el.style.background = "transparent";
832
1260
  }
833
1261
  el.addEventListener("click", (e) => {
834
- node.dispatchEvent(new (0, _chunkDFNK6OV6js.VectoJSEvent)("click", node, e));
1262
+ node.dispatchEvent(new (0, _chunkFIQAIF55js.VectoJSEvent)("click", node, e));
835
1263
  });
836
1264
  el.addEventListener("mouseenter", (e) => {
837
1265
  if (this.debugA11y) el.style.backgroundColor = "rgba(56, 189, 248, 0.2)";
838
- node.dispatchEvent(new (0, _chunkDFNK6OV6js.VectoJSEvent)("hover", node, e, false));
1266
+ node.dispatchEvent(new (0, _chunkFIQAIF55js.VectoJSEvent)("hover", node, e, false));
839
1267
  });
840
1268
  el.addEventListener("mouseleave", (e) => {
841
1269
  if (this.debugA11y) el.style.backgroundColor = "rgba(56, 189, 248, 0.05)";
842
- node.dispatchEvent(new (0, _chunkDFNK6OV6js.VectoJSEvent)("pointerleave", node, e, false));
1270
+ node.dispatchEvent(new (0, _chunkFIQAIF55js.VectoJSEvent)("pointerleave", node, e, false));
843
1271
  });
844
1272
  const capEl = el;
845
1273
  const releasePointer = (event) => {
@@ -855,32 +1283,32 @@ var Scene = (_class2 = class _Scene {
855
1283
  };
856
1284
  el.addEventListener("pointerdown", (e) => {
857
1285
  if (typeof capEl.setPointerCapture === "function") capEl.setPointerCapture(e.pointerId);
858
- node.dispatchEvent(new (0, _chunkDFNK6OV6js.VectoJSEvent)("pointerdown", node, e));
1286
+ node.dispatchEvent(new (0, _chunkFIQAIF55js.VectoJSEvent)("pointerdown", node, e));
859
1287
  });
860
1288
  el.addEventListener("pointerup", (e) => {
861
1289
  releasePointer(e);
862
- node.dispatchEvent(new (0, _chunkDFNK6OV6js.VectoJSEvent)("pointerup", node, e));
1290
+ node.dispatchEvent(new (0, _chunkFIQAIF55js.VectoJSEvent)("pointerup", node, e));
863
1291
  });
864
1292
  el.addEventListener("pointercancel", (e) => {
865
1293
  releasePointer(e);
866
- node.dispatchEvent(new (0, _chunkDFNK6OV6js.VectoJSEvent)("pointercancel", node, e));
1294
+ node.dispatchEvent(new (0, _chunkFIQAIF55js.VectoJSEvent)("pointercancel", node, e));
867
1295
  });
868
1296
  el.addEventListener(
869
1297
  "pointermove",
870
- (e) => node.dispatchEvent(new (0, _chunkDFNK6OV6js.VectoJSEvent)("pointermove", node, e))
1298
+ (e) => node.dispatchEvent(new (0, _chunkFIQAIF55js.VectoJSEvent)("pointermove", node, e))
871
1299
  );
872
1300
  el.addEventListener(
873
1301
  "wheel",
874
1302
  (e) => {
875
- node.dispatchEvent(new (0, _chunkDFNK6OV6js.VectoJSEvent)("wheel", node, e));
1303
+ node.dispatchEvent(new (0, _chunkFIQAIF55js.VectoJSEvent)("wheel", node, e));
876
1304
  },
877
1305
  { passive: false }
878
1306
  );
879
1307
  el.addEventListener("keydown", (e) => {
880
- node.dispatchEvent(new (0, _chunkDFNK6OV6js.VectoJSEvent)("keydown", node, e));
1308
+ node.dispatchEvent(new (0, _chunkFIQAIF55js.VectoJSEvent)("keydown", node, e));
881
1309
  });
882
1310
  el.addEventListener("keyup", (e) => {
883
- node.dispatchEvent(new (0, _chunkDFNK6OV6js.VectoJSEvent)("keyup", node, e));
1311
+ node.dispatchEvent(new (0, _chunkFIQAIF55js.VectoJSEvent)("keyup", node, e));
884
1312
  });
885
1313
  if (el instanceof HTMLInputElement || el instanceof HTMLTextAreaElement) {
886
1314
  const input = el;
@@ -907,7 +1335,7 @@ var Scene = (_class2 = class _Scene {
907
1335
  });
908
1336
  el.addEventListener("compositionupdate", (e) => {
909
1337
  const data = _nullishCoalesce(e.data, () => ( ""));
910
- composition = { start: _nullishCoalesce(_optionalChain([composition, 'optionalAccess', _47 => _47.start]), () => ( 0)), length: data.length };
1338
+ composition = { start: _nullishCoalesce(_optionalChain([composition, 'optionalAccess', _64 => _64.start]), () => ( 0)), length: data.length };
911
1339
  forward();
912
1340
  });
913
1341
  el.addEventListener("compositionend", () => {
@@ -940,7 +1368,7 @@ var Scene = (_class2 = class _Scene {
940
1368
  el.addEventListener("keydown", (e) => {
941
1369
  if (e.key === "Enter" || e.key === " ") {
942
1370
  e.preventDefault();
943
- node.dispatchEvent(new (0, _chunkDFNK6OV6js.VectoJSEvent)("click", node, e));
1371
+ node.dispatchEvent(new (0, _chunkFIQAIF55js.VectoJSEvent)("click", node, e));
944
1372
  }
945
1373
  });
946
1374
  }
@@ -958,6 +1386,10 @@ var Scene = (_class2 = class _Scene {
958
1386
  if (attrs.label !== void 0 && el.getAttribute("aria-label") !== attrs.label) {
959
1387
  el.setAttribute("aria-label", attrs.label);
960
1388
  }
1389
+ const semanticPointerEvents = _nullishCoalesce(attrs.pointerEvents, () => ( "auto"));
1390
+ if (el.style.pointerEvents !== semanticPointerEvents) {
1391
+ el.style.pointerEvents = semanticPointerEvents;
1392
+ }
961
1393
  const implicitTabIndex = !isNativelyFocusable(el) && attrs.role && INTERACTIVE_A11Y_ROLES.has(attrs.role) ? 0 : null;
962
1394
  const desiredTabIndex = _nullishCoalesce(attrs.tabIndex, () => ( implicitTabIndex));
963
1395
  if (desiredTabIndex === null) {
@@ -1074,6 +1506,7 @@ var Scene = (_class2 = class _Scene {
1074
1506
  let el = this.contentElements.get(node.id);
1075
1507
  if (!projection || !projection.text) {
1076
1508
  if (el) {
1509
+ this.clearContentGridState(node.id, el);
1077
1510
  el.remove();
1078
1511
  this.contentElements.delete(node.id);
1079
1512
  this.a11yNeedsReorder = true;
@@ -1096,7 +1529,7 @@ var Scene = (_class2 = class _Scene {
1096
1529
  el.addEventListener(
1097
1530
  "wheel",
1098
1531
  (e2) => {
1099
- node.dispatchEvent(new (0, _chunkDFNK6OV6js.VectoJSEvent)("wheel", node, e2));
1532
+ node.dispatchEvent(new (0, _chunkFIQAIF55js.VectoJSEvent)("wheel", node, e2));
1100
1533
  },
1101
1534
  { passive: false }
1102
1535
  );
@@ -1105,13 +1538,19 @@ var Scene = (_class2 = class _Scene {
1105
1538
  this.a11yNeedsReorder = true;
1106
1539
  }
1107
1540
  const lines = projection.lines;
1108
- if (lines && lines.length > 0) {
1541
+ if (!projection.grid && el.dataset.vectoContentGrid !== void 0) {
1542
+ this.clearContentGridState(node.id, el);
1543
+ }
1544
+ if (projection.grid) {
1545
+ this.syncContentGridProjection(node, el, projection, projection.grid);
1546
+ } else if (lines && lines.length > 0) {
1109
1547
  const signature = JSON.stringify({
1110
1548
  lines,
1111
1549
  fallbackFont: _nullishCoalesce(projection.font, () => ( "")),
1112
1550
  fallbackLineHeight: _nullishCoalesce(projection.lineHeight, () => ( 16))
1113
1551
  });
1114
1552
  if (el.dataset.vectoProjectionLines !== signature) {
1553
+ this.releaseContentSelectionForRebuild(el);
1115
1554
  el.replaceChildren();
1116
1555
  for (let index = 0; index < lines.length; index++) {
1117
1556
  const line = lines[index];
@@ -1121,7 +1560,7 @@ var Scene = (_class2 = class _Scene {
1121
1560
  lineElement.style.position = "absolute";
1122
1561
  lineElement.dir = "auto";
1123
1562
  lineElement.style.left = `${line.x}px`;
1124
- lineElement.style.top = `${line.y + line.baseline - _chunkDFNK6OV6js.cssLineBoxBaseline.call(void 0, lineFont, lineHeight2)}px`;
1563
+ lineElement.style.top = `${line.y + line.baseline - _chunkFIQAIF55js.cssLineBoxBaseline.call(void 0, lineFont, lineHeight2)}px`;
1125
1564
  lineElement.style.whiteSpace = "pre";
1126
1565
  if (lineFont) lineElement.style.font = lineFont;
1127
1566
  lineElement.style.lineHeight = `${lineHeight2}px`;
@@ -1143,13 +1582,21 @@ var Scene = (_class2 = class _Scene {
1143
1582
  el.dataset.vectoProjectionLines = signature;
1144
1583
  }
1145
1584
  } else {
1146
- if (el.textContent !== projection.text) el.textContent = projection.text;
1585
+ if (el.textContent !== projection.text) {
1586
+ this.releaseContentSelectionForRebuild(el);
1587
+ el.textContent = projection.text;
1588
+ }
1147
1589
  delete el.dataset.vectoProjectionLines;
1148
1590
  }
1149
1591
  const font = _nullishCoalesce(projection.font, () => ( ""));
1150
1592
  if (el.style.font !== font) el.style.font = font;
1151
1593
  const lineHeight = projection.lineHeight !== void 0 ? `${projection.lineHeight}px` : "";
1152
1594
  if (el.style.lineHeight !== lineHeight) el.style.lineHeight = lineHeight;
1595
+ const ligatures = projection.ligatures === "none" ? "none" : "";
1596
+ if (el.style.getPropertyValue("font-variant-ligatures") !== ligatures) {
1597
+ el.style.setProperty("font-variant-ligatures", ligatures);
1598
+ el.style.setProperty("font-kerning", ligatures ? "none" : "");
1599
+ }
1153
1600
  const hidden = node.interactive ? "true" : null;
1154
1601
  if (el.getAttribute("aria-hidden") !== hidden) {
1155
1602
  if (hidden) el.setAttribute("aria-hidden", hidden);
@@ -1165,7 +1612,7 @@ var Scene = (_class2 = class _Scene {
1165
1612
  const { a, b, c, d, e, f } = node.getWorldTransform();
1166
1613
  const contentX = _nullishCoalesce(projection.contentX, () => ( 0));
1167
1614
  const contentY = _nullishCoalesce(projection.contentY, () => ( 0));
1168
- const baselineOffset = lines && lines.length > 0 ? 0 : projection.baseline === void 0 ? 0 : projection.baseline - _chunkDFNK6OV6js.cssLineBoxBaseline.call(void 0, font, _nullishCoalesce(projection.lineHeight, () => ( 16)));
1615
+ const baselineOffset = lines && lines.length > 0 ? 0 : projection.baseline === void 0 ? 0 : projection.baseline - _chunkFIQAIF55js.cssLineBoxBaseline.call(void 0, font, _nullishCoalesce(projection.lineHeight, () => ( 16)));
1169
1616
  const localY = contentY + baselineOffset;
1170
1617
  el.style.left = `${e + a * contentX + c * localY}px`;
1171
1618
  el.style.top = `${f + b * contentX + d * localY}px`;
@@ -1211,6 +1658,245 @@ var Scene = (_class2 = class _Scene {
1211
1658
  const display = visible ? "" : "none";
1212
1659
  if (el.style.display !== display) el.style.display = display;
1213
1660
  }
1661
+ /**
1662
+ * Materialize a prepared grid in logical source order while positioning each
1663
+ * carrier from the shared canvas geometry. Browser font measurement happens
1664
+ * later in one cold read/write batch, never inside projection synchronization.
1665
+ */
1666
+ syncContentGridProjection(node, el, projection, grid) {
1667
+ if (grid.source !== projection.text) {
1668
+ throw new Error("ContentProjection.grid.source must equal ContentProjection.text");
1669
+ }
1670
+ const signature = `${grid.revision}`;
1671
+ if (el.dataset.vectoContentGrid !== signature) {
1672
+ const materializeStart = typeof performance !== "undefined" ? performance.now() : 0;
1673
+ this.clearContentGridState(node.id, el);
1674
+ el.replaceChildren();
1675
+ const projectionLines = _nullishCoalesce(projection.lines, () => ( []));
1676
+ for (let lineIndex = 0; lineIndex < grid.lines.length; lineIndex++) {
1677
+ const gridLine = grid.lines[lineIndex];
1678
+ const projectedLine = projectionLines[lineIndex];
1679
+ const lineHeight = _nullishCoalesce(_optionalChain([projectedLine, 'optionalAccess', _65 => _65.lineHeight]), () => ( grid.lineHeight));
1680
+ const baseline = _nullishCoalesce(_optionalChain([projectedLine, 'optionalAccess', _66 => _66.baseline]), () => ( grid.baseline));
1681
+ const lineFont = _nullishCoalesce(_optionalChain([projectedLine, 'optionalAccess', _67 => _67.font]), () => ( grid.font));
1682
+ const lineElement = document.createElement("span");
1683
+ lineElement.dir = "ltr";
1684
+ lineElement.dataset.vectoGridLine = `${lineIndex}`;
1685
+ lineElement.style.position = "absolute";
1686
+ lineElement.style.left = `${_nullishCoalesce(_optionalChain([projectedLine, 'optionalAccess', _68 => _68.x]), () => ( 0))}px`;
1687
+ lineElement.style.top = `${(_nullishCoalesce(_optionalChain([projectedLine, 'optionalAccess', _69 => _69.y]), () => ( lineIndex * grid.lineHeight))) + baseline - _chunkFIQAIF55js.cssLineBoxBaseline.call(void 0, lineFont, lineHeight)}px`;
1688
+ lineElement.style.width = `${gridLine.width}px`;
1689
+ lineElement.style.height = `${lineHeight}px`;
1690
+ lineElement.style.whiteSpace = "pre";
1691
+ lineElement.style.font = lineFont;
1692
+ lineElement.style.lineHeight = `${lineHeight}px`;
1693
+ if (gridLine.cells.length === 0) {
1694
+ lineElement.textContent = grid.source.slice(gridLine.sourceEnd, gridLine.nextSourceStart);
1695
+ } else {
1696
+ let logicalX = 0;
1697
+ for (let cellIndex = 0; cellIndex < gridLine.cells.length; cellIndex++) {
1698
+ const cell = gridLine.cells[cellIndex];
1699
+ const cellElement = document.createElement("span");
1700
+ cellElement.dir = "ltr";
1701
+ const separator = cellIndex === gridLine.cells.length - 1 ? grid.source.slice(gridLine.sourceEnd, gridLine.nextSourceStart) : "";
1702
+ const sourceText = grid.source.slice(cell.sourceStart, cell.sourceEnd);
1703
+ cellElement.textContent = sourceText + separator;
1704
+ cellElement.dataset.vectoGridCell = `${cellIndex}`;
1705
+ cellElement.dataset.vectoGridSourceLength = `${sourceText.length}`;
1706
+ cellElement.dataset.vectoGridSourceStart = `${cell.sourceStart}`;
1707
+ cellElement.dataset.vectoGridSourceEnd = `${cell.sourceEnd}`;
1708
+ cellElement.dataset.vectoGridCaretOffsets = cell.sourceCaretOffsets.join(",");
1709
+ cellElement.dataset.vectoGridLevel = `${cell.level}`;
1710
+ cellElement.dataset.vectoGridAdvance = `${cell.advance}`;
1711
+ cellElement.dataset.vectoGridX = `${cell.x}`;
1712
+ cellElement.style.position = "relative";
1713
+ cellElement.style.display = "inline-block";
1714
+ cellElement.style.left = `${cell.x - logicalX}px`;
1715
+ cellElement.style.top = "0";
1716
+ cellElement.style.width = `${cell.advance}px`;
1717
+ cellElement.style.height = `${lineHeight}px`;
1718
+ cellElement.style.boxSizing = "border-box";
1719
+ cellElement.style.verticalAlign = "top";
1720
+ cellElement.style.whiteSpace = "pre";
1721
+ cellElement.style.font = lineFont;
1722
+ cellElement.style.lineHeight = `${lineHeight}px`;
1723
+ cellElement.style.transformOrigin = "0 50%";
1724
+ lineElement.appendChild(cellElement);
1725
+ logicalX += cell.advance;
1726
+ }
1727
+ }
1728
+ if (lineIndex === 0) {
1729
+ for (const [basis, left, top] of [
1730
+ ["origin", 0, 0],
1731
+ ["x", 1, 0],
1732
+ ["y", 0, 1]
1733
+ ]) {
1734
+ const marker = document.createElement("span");
1735
+ marker.dataset.vectoGridBasis = basis;
1736
+ marker.setAttribute("aria-hidden", "true");
1737
+ marker.style.position = "absolute";
1738
+ marker.style.left = `${left}px`;
1739
+ marker.style.top = `${top}px`;
1740
+ marker.style.width = "0";
1741
+ marker.style.height = "0";
1742
+ marker.style.pointerEvents = "none";
1743
+ marker.style.userSelect = "none";
1744
+ lineElement.appendChild(marker);
1745
+ }
1746
+ }
1747
+ el.appendChild(lineElement);
1748
+ }
1749
+ el.dataset.vectoProjectionLines = signature;
1750
+ el.dataset.vectoContentGrid = signature;
1751
+ el.dataset.vectoGridCarriers = `${el.querySelectorAll("[data-vecto-grid-cell]").length}`;
1752
+ if (typeof performance !== "undefined") {
1753
+ el.dataset.vectoGridMaterializeMs = `${performance.now() - materializeStart}`;
1754
+ }
1755
+ delete el.dataset.vectoGridCalibration;
1756
+ delete el.dataset.vectoGridReady;
1757
+ }
1758
+ const pageScaleX = this.getContentMetricScaleX();
1759
+ const calibrationKey = `${signature}:${this.contentFontEpoch}:${pageScaleX.toFixed(4)}`;
1760
+ if (el.dataset.vectoGridCalibration !== calibrationKey) {
1761
+ this.scheduleContentGridCalibration(node.id, el, calibrationKey, pageScaleX);
1762
+ }
1763
+ }
1764
+ getContentMetricScaleX() {
1765
+ if (this.contentMetricScaleEpoch === this.contentFontEpoch) {
1766
+ return this.contentMetricScaleX;
1767
+ }
1768
+ const rect = this.canvas.getBoundingClientRect();
1769
+ const inlineWidth = parseInlinePx(this.canvas.style.width);
1770
+ const logicalWidth = _nullishCoalesce(inlineWidth, () => ( (this.canvas.clientWidth || this.width)));
1771
+ const scale = logicalWidth > 0 ? rect.width / logicalWidth : 1;
1772
+ this.contentMetricScaleX = Number.isFinite(scale) && scale > 0 ? scale : 1;
1773
+ this.contentMetricScaleEpoch = this.contentFontEpoch;
1774
+ return this.contentMetricScaleX;
1775
+ }
1776
+ scheduleContentGridCalibration(entityId, el, calibrationKey, pageScaleX) {
1777
+ if (typeof requestAnimationFrame !== "function") return;
1778
+ if (el.dataset.vectoGridCalibrationPending === calibrationKey) return;
1779
+ const previous = this.contentGridCalibrationFrames.get(entityId);
1780
+ if (previous !== void 0 && typeof cancelAnimationFrame === "function") {
1781
+ cancelAnimationFrame(previous);
1782
+ }
1783
+ _optionalChain([this, 'access', _70 => _70.contentGridCalibrationProbes, 'access', _71 => _71.get, 'call', _72 => _72(entityId), 'optionalAccess', _73 => _73.remove, 'call', _74 => _74()]);
1784
+ this.contentGridCalibrationProbes.delete(entityId);
1785
+ const calibrationStart = typeof performance !== "undefined" ? performance.now() : 0;
1786
+ const probe = document.createElement("div");
1787
+ probe.setAttribute("aria-hidden", "true");
1788
+ probe.dataset.vectoGridProbe = entityId;
1789
+ probe.style.position = "absolute";
1790
+ probe.style.left = "-100000px";
1791
+ probe.style.top = "0";
1792
+ probe.style.width = "100000px";
1793
+ probe.style.height = "1px";
1794
+ probe.style.visibility = "hidden";
1795
+ probe.style.pointerEvents = "none";
1796
+ probe.style.whiteSpace = "pre";
1797
+ probe.style.contain = "layout style paint";
1798
+ const probeOrigin = document.createElement("span");
1799
+ probeOrigin.style.position = "absolute";
1800
+ probeOrigin.style.left = "0";
1801
+ probeOrigin.style.top = "0";
1802
+ const probeX = document.createElement("span");
1803
+ probeX.style.position = "absolute";
1804
+ probeX.style.left = "1px";
1805
+ probeX.style.top = "0";
1806
+ probe.append(probeOrigin, probeX);
1807
+ const measurements = [];
1808
+ const measurementsByKey = /* @__PURE__ */ new Map();
1809
+ for (const target of el.querySelectorAll("[data-vecto-grid-cell]")) {
1810
+ const sourceLength = Number(_nullishCoalesce(target.dataset.vectoGridSourceLength, () => ( 0)));
1811
+ const targetWidth = Number(_nullishCoalesce(target.dataset.vectoGridAdvance, () => ( 0)));
1812
+ if (sourceLength <= 0 || targetWidth <= 0) continue;
1813
+ const sourceText = _nullishCoalesce(_optionalChain([target, 'access', _75 => _75.textContent, 'optionalAccess', _76 => _76.slice, 'call', _77 => _77(0, sourceLength)]), () => ( ""));
1814
+ if (!sourceText) continue;
1815
+ const measurementKey = JSON.stringify([
1816
+ target.style.font,
1817
+ target.style.lineHeight,
1818
+ targetWidth,
1819
+ sourceText
1820
+ ]);
1821
+ const shared = measurementsByKey.get(measurementKey);
1822
+ if (shared) {
1823
+ shared.targets.push(target);
1824
+ continue;
1825
+ }
1826
+ const carrier = document.createElement("span");
1827
+ carrier.dir = "ltr";
1828
+ carrier.style.position = "absolute";
1829
+ carrier.style.left = "0";
1830
+ carrier.style.top = "0";
1831
+ carrier.style.whiteSpace = "pre";
1832
+ carrier.style.font = target.style.font;
1833
+ carrier.style.lineHeight = target.style.lineHeight;
1834
+ carrier.style.fontVariantLigatures = "none";
1835
+ carrier.style.fontKerning = "none";
1836
+ const source = document.createTextNode(sourceText);
1837
+ carrier.appendChild(source);
1838
+ probe.appendChild(carrier);
1839
+ const measurement = { targets: [target], targetWidth, sourceLength, source };
1840
+ measurements.push(measurement);
1841
+ measurementsByKey.set(measurementKey, measurement);
1842
+ }
1843
+ (_nullishCoalesce(_nullishCoalesce(this.a11yRoot, () => ( document.body)), () => ( document.documentElement))).appendChild(probe);
1844
+ el.dataset.vectoGridCalibrationSamples = `${measurements.length}`;
1845
+ this.contentGridCalibrationProbes.set(entityId, probe);
1846
+ el.dataset.vectoGridCalibrationPending = calibrationKey;
1847
+ delete el.dataset.vectoGridReady;
1848
+ const readFrame = requestAnimationFrame(() => {
1849
+ if (!el.isConnected || el.dataset.vectoGridCalibrationPending !== calibrationKey) {
1850
+ probe.remove();
1851
+ this.contentGridCalibrationProbes.delete(entityId);
1852
+ this.contentGridCalibrationFrames.delete(entityId);
1853
+ return;
1854
+ }
1855
+ const updates = [];
1856
+ const probeOriginRect = probeOrigin.getBoundingClientRect();
1857
+ const probeXRect = probeX.getBoundingClientRect();
1858
+ const basisScale = Math.abs(probeXRect.left - probeOriginRect.left);
1859
+ const projectionPageScaleX = Number.isFinite(basisScale) && basisScale > 0 ? basisScale : pageScaleX;
1860
+ let valid = true;
1861
+ for (const measurement of measurements) {
1862
+ const range = document.createRange();
1863
+ range.setStart(measurement.source, 0);
1864
+ range.setEnd(measurement.source, measurement.sourceLength);
1865
+ const natural = range.getBoundingClientRect().width;
1866
+ if (!Number.isFinite(natural) || natural <= 0) {
1867
+ valid = false;
1868
+ break;
1869
+ }
1870
+ const scale = measurement.targetWidth * projectionPageScaleX / natural;
1871
+ for (const element of measurement.targets) updates.push({ element, scale });
1872
+ }
1873
+ probe.remove();
1874
+ this.contentGridCalibrationProbes.delete(entityId);
1875
+ if (!valid) {
1876
+ delete el.dataset.vectoGridCalibrationPending;
1877
+ this.contentGridCalibrationFrames.delete(entityId);
1878
+ return;
1879
+ }
1880
+ const writeFrame = requestAnimationFrame(() => {
1881
+ if (!el.isConnected || el.dataset.vectoGridCalibrationPending !== calibrationKey) {
1882
+ this.contentGridCalibrationFrames.delete(entityId);
1883
+ return;
1884
+ }
1885
+ for (const { element, scale } of updates) {
1886
+ element.style.transform = Math.abs(scale - 1) <= 1e-3 ? "" : `scaleX(${scale})`;
1887
+ }
1888
+ el.dataset.vectoGridCalibration = calibrationKey;
1889
+ el.dataset.vectoGridReady = "true";
1890
+ if (typeof performance !== "undefined") {
1891
+ el.dataset.vectoGridCalibrationMs = `${performance.now() - calibrationStart}`;
1892
+ }
1893
+ delete el.dataset.vectoGridCalibrationPending;
1894
+ this.contentGridCalibrationFrames.delete(entityId);
1895
+ });
1896
+ this.contentGridCalibrationFrames.set(entityId, writeFrame);
1897
+ });
1898
+ this.contentGridCalibrationFrames.set(entityId, readFrame);
1899
+ }
1214
1900
  enforceA11yDomOrder() {
1215
1901
  if (!this.a11yRoot) return;
1216
1902
  this.fullViewportElements.length = 0;
@@ -1274,12 +1960,12 @@ var Scene = (_class2 = class _Scene {
1274
1960
  syncOverlayGeometry() {
1275
1961
  const parent = this.canvas.parentElement;
1276
1962
  if (!parent) return;
1277
- const canvasRect = _optionalChain([this, 'access', _48 => _48.canvas, 'access', _49 => _49.getBoundingClientRect, 'optionalCall', _50 => _50()]);
1278
- const parentRect = _optionalChain([parent, 'access', _51 => _51.getBoundingClientRect, 'optionalCall', _52 => _52()]);
1279
- const cssWidth = _optionalChain([canvasRect, 'optionalAccess', _53 => _53.width]) || this.canvas.clientWidth || this.width;
1280
- const cssHeight = _optionalChain([canvasRect, 'optionalAccess', _54 => _54.height]) || this.canvas.clientHeight || this.height;
1281
- const left = (_nullishCoalesce(_optionalChain([canvasRect, 'optionalAccess', _55 => _55.left]), () => ( 0))) - (_nullishCoalesce(_optionalChain([parentRect, 'optionalAccess', _56 => _56.left]), () => ( 0))) - (parent.clientLeft || 0) + parent.scrollLeft;
1282
- const top = (_nullishCoalesce(_optionalChain([canvasRect, 'optionalAccess', _57 => _57.top]), () => ( 0))) - (_nullishCoalesce(_optionalChain([parentRect, 'optionalAccess', _58 => _58.top]), () => ( 0))) - (parent.clientTop || 0) + parent.scrollTop;
1963
+ const canvasRect = _optionalChain([this, 'access', _78 => _78.canvas, 'access', _79 => _79.getBoundingClientRect, 'optionalCall', _80 => _80()]);
1964
+ const parentRect = _optionalChain([parent, 'access', _81 => _81.getBoundingClientRect, 'optionalCall', _82 => _82()]);
1965
+ const cssWidth = _optionalChain([canvasRect, 'optionalAccess', _83 => _83.width]) || this.canvas.clientWidth || this.width;
1966
+ const cssHeight = _optionalChain([canvasRect, 'optionalAccess', _84 => _84.height]) || this.canvas.clientHeight || this.height;
1967
+ const left = (_nullishCoalesce(_optionalChain([canvasRect, 'optionalAccess', _85 => _85.left]), () => ( 0))) - (_nullishCoalesce(_optionalChain([parentRect, 'optionalAccess', _86 => _86.left]), () => ( 0))) - (parent.clientLeft || 0) + parent.scrollLeft;
1968
+ const top = (_nullishCoalesce(_optionalChain([canvasRect, 'optionalAccess', _87 => _87.top]), () => ( 0))) - (_nullishCoalesce(_optionalChain([parentRect, 'optionalAccess', _88 => _88.top]), () => ( 0))) - (parent.clientTop || 0) + parent.scrollTop;
1283
1969
  const scaleX = this.width > 0 ? cssWidth / this.width : 1;
1284
1970
  const scaleY = this.height > 0 ? cssHeight / this.height : 1;
1285
1971
  for (const root of [this.a11yRoot, this.portalRoot]) {
@@ -1404,7 +2090,7 @@ var Scene = (_class2 = class _Scene {
1404
2090
  * (and {@link respectReducedMotion} is on). `0` means uncapped.
1405
2091
  */
1406
2092
  effectiveMaxFPS() {
1407
- const reduced = this.respectReducedMotion && !!_optionalChain([this, 'access', _59 => _59.reducedMotionQuery, 'optionalAccess', _60 => _60.matches]);
2093
+ const reduced = this.respectReducedMotion && !!_optionalChain([this, 'access', _89 => _89.reducedMotionQuery, 'optionalAccess', _90 => _90.matches]);
1408
2094
  if (reduced)
1409
2095
  return this.maxFPS > 0 ? Math.min(this.maxFPS, REDUCED_MOTION_FPS) : REDUCED_MOTION_FPS;
1410
2096
  return this.maxFPS;
@@ -1582,7 +2268,7 @@ var Scene = (_class2 = class _Scene {
1582
2268
  }
1583
2269
  renderer.clear();
1584
2270
  if (isMainRenderer) {
1585
- _optionalChain([this, 'access', _61 => _61.pointRenderer, 'optionalAccess', _62 => _62.begin, 'call', _63 => _63()]);
2271
+ _optionalChain([this, 'access', _91 => _91.pointRenderer, 'optionalAccess', _92 => _92.begin, 'call', _93 => _93()]);
1586
2272
  }
1587
2273
  const vw = this.width;
1588
2274
  const vh = this.height;
@@ -1720,9 +2406,9 @@ var Scene = (_class2 = class _Scene {
1720
2406
  }
1721
2407
  renderer.flush();
1722
2408
  if (isMainRenderer) {
1723
- _optionalChain([this, 'access', _64 => _64.pointRenderer, 'optionalAccess', _65 => _65.flush, 'call', _66 => _66()]);
2409
+ _optionalChain([this, 'access', _94 => _94.pointRenderer, 'optionalAccess', _95 => _95.flush, 'call', _96 => _96()]);
1724
2410
  }
1725
- _optionalChain([renderer, 'access', _67 => _67.present, 'optionalCall', _68 => _68()]);
2411
+ _optionalChain([renderer, 'access', _97 => _97.present, 'optionalCall', _98 => _98()]);
1726
2412
  }
1727
2413
  /**
1728
2414
  * Export the current scene state to a lightweight, flat SVG XML string.
@@ -1738,10 +2424,11 @@ var Scene = (_class2 = class _Scene {
1738
2424
  resize(width, height) {
1739
2425
  this.width = width;
1740
2426
  this.height = height;
2427
+ this.contentFontEpoch++;
1741
2428
  if (typeof this.renderer.resize === "function") {
1742
2429
  this.renderer.resize(width, height);
1743
2430
  }
1744
- _optionalChain([this, 'access', _69 => _69.pointRenderer, 'optionalAccess', _70 => _70.resize, 'call', _71 => _71(width, height)]);
2431
+ _optionalChain([this, 'access', _99 => _99.pointRenderer, 'optionalAccess', _100 => _100.resize, 'call', _101 => _101(width, height)]);
1745
2432
  if (this.gpuCanvas) {
1746
2433
  this.gpuCanvas.width = width;
1747
2434
  this.gpuCanvas.height = height;
@@ -1789,7 +2476,7 @@ var Scene = (_class2 = class _Scene {
1789
2476
  });
1790
2477
  pass.end();
1791
2478
  this.device.queue.submit([encoder.finish()]);
1792
- } catch (e3) {
2479
+ } catch (e5) {
1793
2480
  }
1794
2481
  this.gpuHasContent = false;
1795
2482
  }
@@ -1926,27 +2613,27 @@ var Scene = (_class2 = class _Scene {
1926
2613
  // src/components/TextEntity.ts
1927
2614
  var sharedMeasurer;
1928
2615
  function defaultMeasurer() {
1929
- if (sharedMeasurer === void 0) sharedMeasurer = _chunkZBKKRYDHjs.createCanvasMeasurer.call(void 0, "sans-serif");
2616
+ if (sharedMeasurer === void 0) sharedMeasurer = _chunkBA5HUUDFjs.createCanvasMeasurer.call(void 0, "sans-serif");
1930
2617
  return sharedMeasurer;
1931
2618
  }
1932
- var TextEntity = (_class3 = class extends _chunkDFNK6OV6js.Entity {
2619
+ var TextEntity = (_class3 = class extends _chunkFIQAIF55js.Entity {
1933
2620
 
1934
2621
 
1935
2622
 
1936
2623
 
1937
- __init54() {this.nodes = []}
2624
+ __init62() {this.nodes = []}
1938
2625
 
1939
- __init55() {this.fillStyle = "#94a3b8"}
1940
- __init56() {this.strokeStyle = null}
1941
- __init57() {this.hoveredFillStyle = "#ffffff"}
1942
- __init58() {this.lineWidth = 1}
1943
- __init59() {this.isHovered = false}
2626
+ __init63() {this.fillStyle = "#94a3b8"}
2627
+ __init64() {this.strokeStyle = null}
2628
+ __init65() {this.hoveredFillStyle = "#ffffff"}
2629
+ __init66() {this.lineWidth = 1}
2630
+ __init67() {this.isHovered = false}
1944
2631
  constructor(text, atlas, maxWidth, fontSize = 24) {
1945
- super();_class3.prototype.__init54.call(this);_class3.prototype.__init55.call(this);_class3.prototype.__init56.call(this);_class3.prototype.__init57.call(this);_class3.prototype.__init58.call(this);_class3.prototype.__init59.call(this);;
2632
+ super();_class3.prototype.__init62.call(this);_class3.prototype.__init63.call(this);_class3.prototype.__init64.call(this);_class3.prototype.__init65.call(this);_class3.prototype.__init66.call(this);_class3.prototype.__init67.call(this);;
1946
2633
  this.text = text;
1947
2634
  this.atlas = atlas;
1948
2635
  this.fontSize = fontSize;
1949
- this.layout = new (0, _chunkZBKKRYDHjs.LayoutEngine)(maxWidth, 1e4, defaultMeasurer());
2636
+ this.layout = new (0, _chunkBA5HUUDFjs.LayoutEngine)(maxWidth, 1e4, defaultMeasurer());
1950
2637
  this.prepared = this.layout.prepare(this.text, this.atlas, this.fontSize);
1951
2638
  this.applyLayout();
1952
2639
  this.interactive = true;
@@ -2055,17 +2742,17 @@ var TextEntity = (_class3 = class extends _chunkDFNK6OV6js.Entity {
2055
2742
  }, _class3);
2056
2743
 
2057
2744
  // src/components/GridTextEntity.ts
2058
- var GridTextEntity = (_class4 = class extends _chunkDFNK6OV6js.Entity {
2745
+ var GridTextEntity = (_class4 = class extends _chunkFIQAIF55js.Entity {
2059
2746
 
2060
- __init60() {this.fillStyle = "#ffffff"}
2061
- __init61() {this.grid = []}
2747
+ __init68() {this.fillStyle = "#ffffff"}
2748
+ __init69() {this.grid = []}
2062
2749
  // Array of rows
2063
- __init62() {this.cols = 0}
2064
- __init63() {this.rows = 0}
2750
+ __init70() {this.cols = 0}
2751
+ __init71() {this.rows = 0}
2065
2752
 
2066
2753
 
2067
2754
  constructor(_atlas, fontSize = 10) {
2068
- super();_class4.prototype.__init60.call(this);_class4.prototype.__init61.call(this);_class4.prototype.__init62.call(this);_class4.prototype.__init63.call(this);;
2755
+ super();_class4.prototype.__init68.call(this);_class4.prototype.__init69.call(this);_class4.prototype.__init70.call(this);_class4.prototype.__init71.call(this);;
2069
2756
  this.fontSize = fontSize;
2070
2757
  this.charWidth = fontSize * 1;
2071
2758
  this.charHeight = fontSize * 1.1;
@@ -2074,7 +2761,7 @@ var GridTextEntity = (_class4 = class extends _chunkDFNK6OV6js.Entity {
2074
2761
  updateGrid(ascii) {
2075
2762
  this.grid = ascii;
2076
2763
  this.rows = ascii.length;
2077
- this.cols = _optionalChain([ascii, 'access', _72 => _72[0], 'optionalAccess', _73 => _73.length]) || 0;
2764
+ this.cols = _optionalChain([ascii, 'access', _102 => _102[0], 'optionalAccess', _103 => _103.length]) || 0;
2078
2765
  }
2079
2766
  isPointInside(_globalX, _globalY) {
2080
2767
  return false;
@@ -2149,7 +2836,7 @@ function distSqToSegment(px, py, x1, y1, x2, y2) {
2149
2836
  const ey = py - cy;
2150
2837
  return ex * ex + ey * ey;
2151
2838
  }
2152
- var SplineEntity = (_class5 = class extends _chunkDFNK6OV6js.Entity {
2839
+ var SplineEntity = (_class5 = class extends _chunkFIQAIF55js.Entity {
2153
2840
 
2154
2841
 
2155
2842
 
@@ -2157,23 +2844,23 @@ var SplineEntity = (_class5 = class extends _chunkDFNK6OV6js.Entity {
2157
2844
 
2158
2845
 
2159
2846
 
2160
- __init64() {this.offscreen = null}
2161
- __init65() {this.baked = false}
2847
+ __init72() {this.offscreen = null}
2848
+ __init73() {this.baked = false}
2162
2849
  /** Logical (CSS-pixel) size of the baked bitmap — the blit destination size. */
2163
- __init66() {this.bakedWidth = 0}
2164
- __init67() {this.bakedHeight = 0}
2850
+ __init74() {this.bakedWidth = 0}
2851
+ __init75() {this.bakedHeight = 0}
2165
2852
  /** Gradient strokes can't be baked to a solid-color bitmap; they render per-frame. */
2166
2853
 
2167
2854
  /** Lazily-flattened polylines (one Float32Array of [x,y,...] per segment) for hit-testing. */
2168
- __init68() {this.polylines = null}
2855
+ __init76() {this.polylines = null}
2169
2856
  /**
2170
2857
  * When `true`, the renderer draws a rounded-rect outline of the entity's
2171
2858
  * local bounds after painting the curves. Useful for drag feedback and
2172
2859
  * debugging hit areas. Defaults to `false`.
2173
2860
  */
2174
- __init69() {this.showBounds = false}
2861
+ __init77() {this.showBounds = false}
2175
2862
  constructor(doc, opts = {}) {
2176
- super();_class5.prototype.__init64.call(this);_class5.prototype.__init65.call(this);_class5.prototype.__init66.call(this);_class5.prototype.__init67.call(this);_class5.prototype.__init68.call(this);_class5.prototype.__init69.call(this);;
2863
+ super();_class5.prototype.__init72.call(this);_class5.prototype.__init73.call(this);_class5.prototype.__init74.call(this);_class5.prototype.__init75.call(this);_class5.prototype.__init76.call(this);_class5.prototype.__init77.call(this);;
2177
2864
  this.doc = doc;
2178
2865
  this.lineWidth = _nullishCoalesce(opts.lineWidth, () => ( 2));
2179
2866
  this.cache = _nullishCoalesce(opts.cache, () => ( true));
@@ -2184,7 +2871,7 @@ var SplineEntity = (_class5 = class extends _chunkDFNK6OV6js.Entity {
2184
2871
  this.width = this.bounds.width;
2185
2872
  this.height = this.bounds.height;
2186
2873
  const isGradient = (c) => c !== null && !Array.isArray(c);
2187
- this.containsGradient = (_nullishCoalesce(_optionalChain([this, 'access', _74 => _74.doc, 'access', _75 => _75.equations, 'optionalAccess', _76 => _76.some, 'call', _77 => _77((eq) => isGradient(eq.color_rgb))]), () => ( false))) || (_nullishCoalesce(_optionalChain([this, 'access', _78 => _78.doc, 'access', _79 => _79.paths, 'optionalAccess', _80 => _80.some, 'call', _81 => _81((p) => isGradient(p.color_rgb))]), () => ( false)));
2874
+ this.containsGradient = (_nullishCoalesce(_optionalChain([this, 'access', _104 => _104.doc, 'access', _105 => _105.equations, 'optionalAccess', _106 => _106.some, 'call', _107 => _107((eq) => isGradient(eq.color_rgb))]), () => ( false))) || (_nullishCoalesce(_optionalChain([this, 'access', _108 => _108.doc, 'access', _109 => _109.paths, 'optionalAccess', _110 => _110.some, 'call', _111 => _111((p) => isGradient(p.color_rgb))]), () => ( false)));
2188
2875
  this.interactive = true;
2189
2876
  }
2190
2877
  computeBounds() {
@@ -2426,9 +3113,9 @@ async function loadSpline(url) {
2426
3113
  // src/math/SpatialHashGrid.ts
2427
3114
  var SpatialHashGrid = (_class6 = class {
2428
3115
 
2429
- __init70() {this.grid = /* @__PURE__ */ new Map()}
2430
- __init71() {this.entityCells = /* @__PURE__ */ new Map()}
2431
- constructor(cellSize = 64) {;_class6.prototype.__init70.call(this);_class6.prototype.__init71.call(this);
3116
+ __init78() {this.grid = /* @__PURE__ */ new Map()}
3117
+ __init79() {this.entityCells = /* @__PURE__ */ new Map()}
3118
+ constructor(cellSize = 64) {;_class6.prototype.__init78.call(this);_class6.prototype.__init79.call(this);
2432
3119
  this.cellSize = cellSize;
2433
3120
  }
2434
3121
  hash(cx, cy) {
@@ -2482,7 +3169,7 @@ var SpatialHashGrid = (_class6 = class {
2482
3169
  const keys = this.entityCells.get(id);
2483
3170
  if (!keys) return;
2484
3171
  for (const key of keys) {
2485
- _optionalChain([this, 'access', _82 => _82.grid, 'access', _83 => _83.get, 'call', _84 => _84(key), 'optionalAccess', _85 => _85.delete, 'call', _86 => _86(id)]);
3172
+ _optionalChain([this, 'access', _112 => _112.grid, 'access', _113 => _113.get, 'call', _114 => _114(key), 'optionalAccess', _115 => _115.delete, 'call', _116 => _116(id)]);
2486
3173
  }
2487
3174
  this.entityCells.delete(id);
2488
3175
  }
@@ -2518,20 +3205,20 @@ var SpatialHashGrid = (_class6 = class {
2518
3205
  }, _class6);
2519
3206
 
2520
3207
  // src/tree/DOMPortalEntity.ts
2521
- var DOMPortalEntity = (_class7 = class extends _chunkDFNK6OV6js.Entity {
3208
+ var DOMPortalEntity = (_class7 = class extends _chunkFIQAIF55js.Entity {
2522
3209
 
2523
- __init72() {this.isDOMPortal = true}
2524
- __init73() {this.domListeners = []}
2525
- __init74() {this.resizeObserver = null}
2526
- __init75() {this.cachedWidth = 100}
2527
- __init76() {this.cachedHeight = 100}
2528
- __init77() {this.lastWidth = ""}
2529
- __init78() {this.lastHeight = ""}
2530
- __init79() {this.lastTransform = ""}
2531
- __init80() {this.lastZIndex = ""}
2532
- __init81() {this.lastOpacity = ""}
3210
+ __init80() {this.isDOMPortal = true}
3211
+ __init81() {this.domListeners = []}
3212
+ __init82() {this.resizeObserver = null}
3213
+ __init83() {this.cachedWidth = 100}
3214
+ __init84() {this.cachedHeight = 100}
3215
+ __init85() {this.lastWidth = ""}
3216
+ __init86() {this.lastHeight = ""}
3217
+ __init87() {this.lastTransform = ""}
3218
+ __init88() {this.lastZIndex = ""}
3219
+ __init89() {this.lastOpacity = ""}
2533
3220
  constructor(domElement, width, height, id) {
2534
- super(id);_class7.prototype.__init72.call(this);_class7.prototype.__init73.call(this);_class7.prototype.__init74.call(this);_class7.prototype.__init75.call(this);_class7.prototype.__init76.call(this);_class7.prototype.__init77.call(this);_class7.prototype.__init78.call(this);_class7.prototype.__init79.call(this);_class7.prototype.__init80.call(this);_class7.prototype.__init81.call(this);;
3221
+ super(id);_class7.prototype.__init80.call(this);_class7.prototype.__init81.call(this);_class7.prototype.__init82.call(this);_class7.prototype.__init83.call(this);_class7.prototype.__init84.call(this);_class7.prototype.__init85.call(this);_class7.prototype.__init86.call(this);_class7.prototype.__init87.call(this);_class7.prototype.__init88.call(this);_class7.prototype.__init89.call(this);;
2535
3222
  this.domElement = domElement;
2536
3223
  this.width = _nullishCoalesce(width, () => ( 0));
2537
3224
  this.height = _nullishCoalesce(height, () => ( 0));
@@ -2560,7 +3247,7 @@ var DOMPortalEntity = (_class7 = class extends _chunkDFNK6OV6js.Entity {
2560
3247
  ];
2561
3248
  for (const type of events) {
2562
3249
  const handler = (e) => {
2563
- this.dispatchEvent(new (0, _chunkDFNK6OV6js.VectoJSEvent)(type, this, e));
3250
+ this.dispatchEvent(new (0, _chunkFIQAIF55js.VectoJSEvent)(type, this, e));
2564
3251
  };
2565
3252
  this.domElement.addEventListener(type, handler);
2566
3253
  this.domListeners.push({ type, handler, capture: false });
@@ -2571,7 +3258,7 @@ var DOMPortalEntity = (_class7 = class extends _chunkDFNK6OV6js.Entity {
2571
3258
  ];
2572
3259
  for (const { native, vecto } of hoverEvents) {
2573
3260
  const handler = (e) => {
2574
- this.dispatchEvent(new (0, _chunkDFNK6OV6js.VectoJSEvent)(vecto, this, e, false));
3261
+ this.dispatchEvent(new (0, _chunkFIQAIF55js.VectoJSEvent)(vecto, this, e, false));
2575
3262
  };
2576
3263
  this.domElement.addEventListener(native, handler);
2577
3264
  this.domListeners.push({ type: native, handler, capture: false });
@@ -2579,7 +3266,7 @@ var DOMPortalEntity = (_class7 = class extends _chunkDFNK6OV6js.Entity {
2579
3266
  const focusEvents = ["focus", "blur"];
2580
3267
  for (const type of focusEvents) {
2581
3268
  const handler = (e) => {
2582
- this.dispatchEvent(new (0, _chunkDFNK6OV6js.VectoJSEvent)(type, this, e, true));
3269
+ this.dispatchEvent(new (0, _chunkFIQAIF55js.VectoJSEvent)(type, this, e, true));
2583
3270
  };
2584
3271
  this.domElement.addEventListener(type, handler, true);
2585
3272
  this.domListeners.push({ type, handler, capture: true });
@@ -2666,4 +3353,5 @@ Scene.registerWebGPUParticleSystemManager(_chunkBPMNCGU7js.WebGPUParticleSystemM
2666
3353
 
2667
3354
 
2668
3355
 
2669
- exports.ArabicShaper = _chunkCTZQOM5Zjs.ArabicShaper; exports.BidiResolver = _chunkCTZQOM5Zjs.BidiResolver; exports.CanvasRenderer = _chunkBPMNCGU7js.CanvasRenderer; exports.ComputeParticleEntity = ComputeParticleEntity; exports.DOMPortalEntity = DOMPortalEntity; exports.Easing = _chunkDFNK6OV6js.Easing; exports.Entity = _chunkDFNK6OV6js.Entity; exports.GridTextEntity = GridTextEntity; exports.LayoutEngine = _chunkZBKKRYDHjs.LayoutEngine; exports.LayoutResultBuffer = _chunkZBKKRYDHjs.LayoutResultBuffer; exports.LayoutWorkerManager = _chunkCTZQOM5Zjs.LayoutWorkerManager; exports.MSDFFont = _chunkDFNK6OV6js.MSDFFont; exports.MSDFTextEntity = _chunkDFNK6OV6js.MSDFTextEntity; exports.PARTICLE_OFFSET_LIFE = PARTICLE_OFFSET_LIFE; exports.PARTICLE_OFFSET_ORIGIN_X = PARTICLE_OFFSET_ORIGIN_X; exports.PARTICLE_OFFSET_ORIGIN_Y = PARTICLE_OFFSET_ORIGIN_Y; exports.PARTICLE_OFFSET_POSITION_X = PARTICLE_OFFSET_POSITION_X; exports.PARTICLE_OFFSET_POSITION_Y = PARTICLE_OFFSET_POSITION_Y; exports.PARTICLE_OFFSET_SIZE = PARTICLE_OFFSET_SIZE; exports.PARTICLE_OFFSET_VELOCITY_X = PARTICLE_OFFSET_VELOCITY_X; exports.PARTICLE_OFFSET_VELOCITY_Y = PARTICLE_OFFSET_VELOCITY_Y; exports.PARTICLE_STRIDE_FLOATS = PARTICLE_STRIDE_FLOATS; exports.REDUCED_MOTION_FPS = REDUCED_MOTION_FPS; exports.SVGEntity = _chunkDFNK6OV6js.SVGEntity; exports.SVGRenderer = _chunkBPMNCGU7js.SVGRenderer; exports.Scene = Scene; exports.SpatialHashGrid = SpatialHashGrid; exports.SplineEntity = SplineEntity; exports.SpringDriver = _chunkDFNK6OV6js.SpringDriver; exports.SpringPhysics = _chunkDFNK6OV6js.SpringPhysics; exports.TextEntity = TextEntity; exports.TweenDriver = _chunkDFNK6OV6js.TweenDriver; exports.VectoJSEvent = _chunkDFNK6OV6js.VectoJSEvent; exports.WebGPUParticleSystemManager = _chunkBPMNCGU7js.WebGPUParticleSystemManager; exports.clearCssLineBoxMetrics = _chunkDFNK6OV6js.clearCssLineBoxMetrics; exports.computeLineSegments = _chunkZBKKRYDHjs.computeLineSegments; exports.createCanvasMeasurer = _chunkZBKKRYDHjs.createCanvasMeasurer; exports.createWebGLPointRenderer = _chunkBPMNCGU7js.createWebGLPointRenderer; exports.cssLineBoxBaseline = _chunkDFNK6OV6js.cssLineBoxBaseline; exports.isSafeUrl = _chunkBPMNCGU7js.isSafeUrl; exports.isTweenConfig = _chunkDFNK6OV6js.isTweenConfig; exports.loadSpline = loadSpline; exports.parseColorToRGBA = _chunkBPMNCGU7js.parseColorToRGBA; exports.polySegmentToBezier = polySegmentToBezier; exports.sanitizeUrl = _chunkBPMNCGU7js.sanitizeUrl;
3356
+
3357
+ exports.ArabicShaper = _chunk4AR425ARjs.ArabicShaper; exports.BidiResolver = _chunk4AR425ARjs.BidiResolver; exports.CanvasRenderer = _chunkBPMNCGU7js.CanvasRenderer; exports.ComputeParticleEntity = ComputeParticleEntity; exports.DOMPortalEntity = DOMPortalEntity; exports.Easing = _chunkFIQAIF55js.Easing; exports.Entity = _chunkFIQAIF55js.Entity; exports.GridTextEntity = GridTextEntity; exports.LayoutEngine = _chunkBA5HUUDFjs.LayoutEngine; exports.LayoutResultBuffer = _chunkBA5HUUDFjs.LayoutResultBuffer; exports.LayoutWorkerManager = _chunk4AR425ARjs.LayoutWorkerManager; exports.MSDFFont = _chunkFIQAIF55js.MSDFFont; exports.MSDFTextEntity = _chunkFIQAIF55js.MSDFTextEntity; exports.PARTICLE_OFFSET_LIFE = PARTICLE_OFFSET_LIFE; exports.PARTICLE_OFFSET_ORIGIN_X = PARTICLE_OFFSET_ORIGIN_X; exports.PARTICLE_OFFSET_ORIGIN_Y = PARTICLE_OFFSET_ORIGIN_Y; exports.PARTICLE_OFFSET_POSITION_X = PARTICLE_OFFSET_POSITION_X; exports.PARTICLE_OFFSET_POSITION_Y = PARTICLE_OFFSET_POSITION_Y; exports.PARTICLE_OFFSET_SIZE = PARTICLE_OFFSET_SIZE; exports.PARTICLE_OFFSET_VELOCITY_X = PARTICLE_OFFSET_VELOCITY_X; exports.PARTICLE_OFFSET_VELOCITY_Y = PARTICLE_OFFSET_VELOCITY_Y; exports.PARTICLE_STRIDE_FLOATS = PARTICLE_STRIDE_FLOATS; exports.REDUCED_MOTION_FPS = REDUCED_MOTION_FPS; exports.SVGEntity = _chunkFIQAIF55js.SVGEntity; exports.SVGRenderer = _chunkBPMNCGU7js.SVGRenderer; exports.Scene = Scene; exports.SpatialHashGrid = SpatialHashGrid; exports.SplineEntity = SplineEntity; exports.SpringDriver = _chunkFIQAIF55js.SpringDriver; exports.SpringPhysics = _chunkFIQAIF55js.SpringPhysics; exports.TextEntity = TextEntity; exports.TweenDriver = _chunkFIQAIF55js.TweenDriver; exports.VectoJSEvent = _chunkFIQAIF55js.VectoJSEvent; exports.WebGPUParticleSystemManager = _chunkBPMNCGU7js.WebGPUParticleSystemManager; exports.clearCssLineBoxMetrics = _chunkFIQAIF55js.clearCssLineBoxMetrics; exports.computeLineSegments = _chunkBA5HUUDFjs.computeLineSegments; exports.createCanvasMeasurer = _chunkBA5HUUDFjs.createCanvasMeasurer; exports.createWebGLPointRenderer = _chunkBPMNCGU7js.createWebGLPointRenderer; exports.cssLineBoxBaseline = _chunkFIQAIF55js.cssLineBoxBaseline; exports.isSafeUrl = _chunkBPMNCGU7js.isSafeUrl; exports.isTweenConfig = _chunkFIQAIF55js.isTweenConfig; exports.loadSpline = loadSpline; exports.parseColorToRGBA = _chunkBPMNCGU7js.parseColorToRGBA; exports.polySegmentToBezier = polySegmentToBezier; exports.prepareContentGrid = _chunkFIQAIF55js.prepareContentGrid; exports.sanitizeUrl = _chunkBPMNCGU7js.sanitizeUrl;