@almadar/ui 2.53.0 → 2.54.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/avl/index.js CHANGED
@@ -49187,449 +49187,7 @@ AvlCosmicZoom.displayName = "AvlCosmicZoom";
49187
49187
 
49188
49188
  // components/organisms/avl/AvlOrbitalsCosmicZoom.tsx
49189
49189
  init_avl_schema_parser();
49190
- init_Box();
49191
- init_Typography();
49192
- var UNIT_DISPLAY_W = 240;
49193
- var UNIT_DISPLAY_H = 160;
49194
- function layoutOrbitals(count, containerW, containerH) {
49195
- if (count === 0) return [];
49196
- if (count === 1) return [{ cx: containerW / 2, cy: containerH / 2 }];
49197
- const cols = Math.min(count, Math.ceil(Math.sqrt(count)));
49198
- const rows = Math.ceil(count / cols);
49199
- const cellW = containerW / (cols + 0.3);
49200
- const cellH = containerH / (rows + 0.3);
49201
- const originX = (containerW - cols * cellW) / 2 + cellW / 2;
49202
- const originY = (containerH - rows * cellH) / 2 + cellH / 2;
49203
- return Array.from({ length: count }, (_, i) => ({
49204
- cx: originX + i % cols * cellW,
49205
- cy: originY + Math.floor(i / cols) * cellH
49206
- }));
49207
- }
49208
- var avlOczWireId = 0;
49209
- var EventWireOverlay = ({
49210
- orbitalViews,
49211
- crossLinks,
49212
- color,
49213
- animated,
49214
- containerW,
49215
- containerH
49216
- }) => {
49217
- const ids = React125__default.useMemo(() => {
49218
- avlOczWireId += 1;
49219
- return { arrow: `avl-ocz-wire-${avlOczWireId}-arrow` };
49220
- }, []);
49221
- const posMap = useMemo(() => {
49222
- const m = /* @__PURE__ */ new Map();
49223
- for (const ov of orbitalViews) m.set(ov.name, { cx: ov.cx, cy: ov.cy });
49224
- return m;
49225
- }, [orbitalViews]);
49226
- const wiresByPair = useMemo(() => {
49227
- const map = /* @__PURE__ */ new Map();
49228
- for (const link of crossLinks) {
49229
- const key = `${link.emitterOrbital}__${link.listenerOrbital}`;
49230
- const arr = map.get(key) ?? [];
49231
- arr.push(link);
49232
- map.set(key, arr);
49233
- }
49234
- return map;
49235
- }, [crossLinks]);
49236
- const orbitalR = UNIT_DISPLAY_W * 0.38;
49237
- return /* @__PURE__ */ jsxs(
49238
- "svg",
49239
- {
49240
- style: {
49241
- position: "absolute",
49242
- inset: 0,
49243
- width: "100%",
49244
- height: "100%",
49245
- pointerEvents: "none",
49246
- overflow: "visible"
49247
- },
49248
- viewBox: `0 0 ${containerW} ${containerH}`,
49249
- preserveAspectRatio: "xMidYMid meet",
49250
- children: [
49251
- /* @__PURE__ */ jsx("defs", { children: /* @__PURE__ */ jsx(
49252
- "marker",
49253
- {
49254
- id: ids.arrow,
49255
- markerWidth: "8",
49256
- markerHeight: "6",
49257
- refX: "7",
49258
- refY: "3",
49259
- orient: "auto",
49260
- markerUnits: "strokeWidth",
49261
- children: /* @__PURE__ */ jsx("path", { d: "M0,0 L8,3 L0,6 Z", fill: color, opacity: 0.6 })
49262
- }
49263
- ) }),
49264
- animated && /* @__PURE__ */ jsx("style", { children: `
49265
- @keyframes avl-ocz-flow {
49266
- from { stroke-dashoffset: 20; }
49267
- to { stroke-dashoffset: 0; }
49268
- }
49269
- ` }),
49270
- Array.from(wiresByPair.entries()).map(
49271
- ([pairKey, links]) => links.map((link, wireIdx) => {
49272
- const fromPos = posMap.get(link.emitterOrbital);
49273
- const toPos = posMap.get(link.listenerOrbital);
49274
- if (!fromPos || !toPos) return null;
49275
- const dx = toPos.cx - fromPos.cx;
49276
- const dy = toPos.cy - fromPos.cy;
49277
- const dist = Math.sqrt(dx * dx + dy * dy) || 1;
49278
- const nx = dx / dist;
49279
- const ny = dy / dist;
49280
- const x1 = fromPos.cx + nx * orbitalR;
49281
- const y1 = fromPos.cy + ny * orbitalR;
49282
- const x2 = toPos.cx - nx * (orbitalR + 6);
49283
- const y2 = toPos.cy - ny * (orbitalR + 6);
49284
- const offset = 25 + wireIdx * 18;
49285
- const { cpx, cpy } = curveControlPoint(x1, y1, x2, y2, offset);
49286
- const pathD = `M${x1},${y1} Q${cpx},${cpy} ${x2},${y2}`;
49287
- const t = 0.5;
49288
- const lx = (1 - t) * (1 - t) * x1 + 2 * (1 - t) * t * cpx + t * t * x2;
49289
- const ly = (1 - t) * (1 - t) * y1 + 2 * (1 - t) * t * cpy + t * t * y2;
49290
- const labelW = link.eventName.length * 5.5 + 12;
49291
- return /* @__PURE__ */ jsxs("g", { children: [
49292
- /* @__PURE__ */ jsx(
49293
- "path",
49294
- {
49295
- d: pathD,
49296
- fill: "none",
49297
- stroke: color,
49298
- strokeWidth: 1.2,
49299
- strokeDasharray: animated ? "6 4" : "4 3",
49300
- markerEnd: `url(#${ids.arrow})`,
49301
- opacity: 0.5,
49302
- style: animated ? { animation: "avl-ocz-flow 1.5s linear infinite" } : void 0
49303
- }
49304
- ),
49305
- /* @__PURE__ */ jsx(
49306
- "rect",
49307
- {
49308
- x: lx - labelW / 2,
49309
- y: ly - 8,
49310
- width: labelW,
49311
- height: 14,
49312
- rx: 3,
49313
- fill: "var(--color-background, #fff)",
49314
- stroke: color,
49315
- strokeWidth: 0.5,
49316
- opacity: 0.9
49317
- }
49318
- ),
49319
- /* @__PURE__ */ jsx(
49320
- "text",
49321
- {
49322
- x: lx,
49323
- y: ly + 3,
49324
- textAnchor: "middle",
49325
- fill: color,
49326
- fontSize: 7,
49327
- fontWeight: 600,
49328
- fontFamily: "monospace",
49329
- opacity: 0.8,
49330
- children: link.eventName
49331
- }
49332
- )
49333
- ] }, `${pairKey}-${wireIdx}`);
49334
- })
49335
- )
49336
- ]
49337
- }
49338
- );
49339
- };
49340
- var InfoPanel = ({ view, crossLinks, color }) => {
49341
- const emitsOut = crossLinks.filter((l) => l.emitterOrbital === view.name);
49342
- const listensIn = crossLinks.filter((l) => l.listenerOrbital === view.name);
49343
- return /* @__PURE__ */ jsxs(
49344
- Box,
49345
- {
49346
- position: "absolute",
49347
- rounded: "lg",
49348
- paddingX: "md",
49349
- paddingY: "sm",
49350
- bg: "overlay",
49351
- style: {
49352
- left: view.cx - 120,
49353
- top: view.cy + UNIT_DISPLAY_H / 2 + 4,
49354
- width: 240,
49355
- border: `1px solid ${color}`,
49356
- zIndex: 20,
49357
- pointerEvents: "none"
49358
- },
49359
- children: [
49360
- /* @__PURE__ */ jsx(Typography, { weight: "semibold", style: { marginBottom: 4, color }, children: view.name }),
49361
- /* @__PURE__ */ jsxs(Text, { variant: "small", style: { opacity: 0.7, color }, children: [
49362
- "Entity: ",
49363
- view.entityName,
49364
- " (",
49365
- view.fieldCount,
49366
- " fields, ",
49367
- view.persistence,
49368
- ")"
49369
- ] }),
49370
- /* @__PURE__ */ jsxs(Text, { variant: "small", style: { opacity: 0.7, color }, children: [
49371
- "Traits: ",
49372
- view.traits.map((t) => t.name).join(", ") || "none"
49373
- ] }),
49374
- view.pages.length > 0 && /* @__PURE__ */ jsxs(Text, { variant: "small", style: { opacity: 0.7, color }, children: [
49375
- "Pages: ",
49376
- view.pages.map((p2) => p2.name).join(", ")
49377
- ] }),
49378
- emitsOut.length > 0 && /* @__PURE__ */ jsxs(Text, { variant: "small", style: { opacity: 0.7, color }, children: [
49379
- "Emits \u2192 ",
49380
- emitsOut.map((l) => `${l.eventName} \u2192 ${l.listenerOrbital}`).join(", ")
49381
- ] }),
49382
- listensIn.length > 0 && /* @__PURE__ */ jsxs(Text, { variant: "small", style: { opacity: 0.7, color }, children: [
49383
- "Listens \u2190 ",
49384
- listensIn.map((l) => `${l.eventName} \u2190 ${l.emitterOrbital}`).join(", ")
49385
- ] })
49386
- ]
49387
- }
49388
- );
49389
- };
49390
- var AvlOrbitalsCosmicZoom = ({
49391
- schema: schemaProp,
49392
- className,
49393
- color = "var(--color-primary, #4A90D9)",
49394
- animated = true,
49395
- width = "100%",
49396
- height = 450,
49397
- highlightedOrbital,
49398
- onOrbitalSelect,
49399
- minZoom = 0.4,
49400
- maxZoom = 3
49401
- }) => {
49402
- const parsedSchema = useMemo(() => {
49403
- if (typeof schemaProp === "string") return JSON.parse(schemaProp);
49404
- return schemaProp;
49405
- }, [schemaProp]);
49406
- const { orbitals, crossLinks } = useMemo(
49407
- () => parseApplicationLevel(parsedSchema),
49408
- [parsedSchema]
49409
- );
49410
- const containerW = typeof width === "number" ? width : 800;
49411
- const containerH = typeof height === "number" ? height : 450;
49412
- const positions = useMemo(
49413
- () => layoutOrbitals(orbitals.length, containerW, containerH),
49414
- [orbitals.length, containerW, containerH]
49415
- );
49416
- const orbitalViews = useMemo(
49417
- () => orbitals.map((o, i) => ({
49418
- name: o.name,
49419
- entityName: o.entityName,
49420
- fieldCount: o.fieldCount,
49421
- persistence: o.persistence || "persistent",
49422
- traits: o.traitNames.map((n) => ({ name: n })),
49423
- pages: o.pageNames.map((n) => ({ name: n })),
49424
- cx: positions[i]?.cx ?? 0,
49425
- cy: positions[i]?.cy ?? 0
49426
- })),
49427
- [orbitals, positions]
49428
- );
49429
- const [selected, setSelected] = useState(null);
49430
- const handleSelect = useCallback(
49431
- (name) => {
49432
- setSelected((prev) => prev === name ? null : name);
49433
- onOrbitalSelect?.(name);
49434
- },
49435
- [onOrbitalSelect]
49436
- );
49437
- const selectedView = orbitalViews.find((o) => o.name === selected);
49438
- const [zoom, setZoom] = useState(1);
49439
- const [pan, setPan] = useState({ x: 0, y: 0 });
49440
- const dragStateRef = useRef(null);
49441
- const transformWrapperRef = useRef(null);
49442
- const clampZoom = useCallback(
49443
- (z) => Math.max(minZoom, Math.min(maxZoom, z)),
49444
- [minZoom, maxZoom]
49445
- );
49446
- const handlePointerDown = useCallback((e) => {
49447
- if (e.target.closest("[data-orbital-tile]")) return;
49448
- dragStateRef.current = {
49449
- startX: e.clientX,
49450
- startY: e.clientY,
49451
- panX: pan.x,
49452
- panY: pan.y
49453
- };
49454
- e.target.setPointerCapture(e.pointerId);
49455
- }, [pan]);
49456
- const handlePointerMove = useCallback((e) => {
49457
- const drag = dragStateRef.current;
49458
- if (!drag) return;
49459
- setPan({
49460
- x: drag.panX + (e.clientX - drag.startX),
49461
- y: drag.panY + (e.clientY - drag.startY)
49462
- });
49463
- }, []);
49464
- const handlePointerUp = useCallback((e) => {
49465
- if (!dragStateRef.current) return;
49466
- dragStateRef.current = null;
49467
- try {
49468
- e.target.releasePointerCapture(e.pointerId);
49469
- } catch {
49470
- }
49471
- }, []);
49472
- const panRef = useRef(pan);
49473
- const zoomRef = useRef(zoom);
49474
- useEffect(() => {
49475
- panRef.current = pan;
49476
- }, [pan]);
49477
- useEffect(() => {
49478
- zoomRef.current = zoom;
49479
- }, [zoom]);
49480
- useEffect(() => {
49481
- const wrapper = transformWrapperRef.current;
49482
- if (!wrapper) return;
49483
- const wheelListener = (e) => {
49484
- e.preventDefault();
49485
- const rect = wrapper.getBoundingClientRect();
49486
- const cursorX = e.clientX - rect.left;
49487
- const cursorY = e.clientY - rect.top;
49488
- const currentZoom = zoomRef.current;
49489
- const currentPan = panRef.current;
49490
- const worldX = (cursorX - currentPan.x) / currentZoom;
49491
- const worldY = (cursorY - currentPan.y) / currentZoom;
49492
- const delta = e.deltaY > 0 ? -0.1 : 0.1;
49493
- const nextZoom = clampZoom(currentZoom * (1 + delta));
49494
- const nextPanX = cursorX - worldX * nextZoom;
49495
- const nextPanY = cursorY - worldY * nextZoom;
49496
- setZoom(nextZoom);
49497
- setPan({ x: nextPanX, y: nextPanY });
49498
- };
49499
- wrapper.addEventListener("wheel", wheelListener, { passive: false });
49500
- return () => wrapper.removeEventListener("wheel", wheelListener);
49501
- }, [clampZoom]);
49502
- const zoomIn = useCallback(() => setZoom((z) => clampZoom(z * 1.2)), [clampZoom]);
49503
- const zoomOut = useCallback(() => setZoom((z) => clampZoom(z / 1.2)), [clampZoom]);
49504
- const resetZoom = useCallback(() => {
49505
- setZoom(1);
49506
- setPan({ x: 0, y: 0 });
49507
- }, []);
49508
- return /* @__PURE__ */ jsxs(
49509
- Box,
49510
- {
49511
- className,
49512
- position: "relative",
49513
- overflow: "visible",
49514
- style: { width, height: containerH },
49515
- children: [
49516
- /* @__PURE__ */ jsx(
49517
- "div",
49518
- {
49519
- ref: transformWrapperRef,
49520
- onPointerDown: handlePointerDown,
49521
- onPointerMove: handlePointerMove,
49522
- onPointerUp: handlePointerUp,
49523
- onPointerCancel: handlePointerUp,
49524
- style: {
49525
- position: "absolute",
49526
- inset: 0,
49527
- overflow: "hidden",
49528
- cursor: dragStateRef.current ? "grabbing" : "grab",
49529
- touchAction: "none"
49530
- },
49531
- children: /* @__PURE__ */ jsxs(
49532
- "div",
49533
- {
49534
- style: {
49535
- position: "absolute",
49536
- inset: 0,
49537
- transform: `translate(${pan.x}px, ${pan.y}px) scale(${zoom})`,
49538
- transformOrigin: "0 0"
49539
- },
49540
- children: [
49541
- /* @__PURE__ */ jsx(
49542
- EventWireOverlay,
49543
- {
49544
- orbitalViews,
49545
- crossLinks,
49546
- color,
49547
- animated,
49548
- containerW,
49549
- containerH
49550
- }
49551
- ),
49552
- orbitalViews.map((view) => {
49553
- const isHighlighted = view.name === highlightedOrbital;
49554
- return /* @__PURE__ */ jsx(
49555
- Box,
49556
- {
49557
- role: "button",
49558
- tabIndex: 0,
49559
- "data-orbital-tile": "true",
49560
- onClick: () => handleSelect(view.name),
49561
- onKeyDown: (e) => {
49562
- if (e.key === "Enter" || e.key === " ") handleSelect(view.name);
49563
- },
49564
- "aria-label": `Orbital: ${view.name}${isHighlighted ? " (highlighted)" : ""}`,
49565
- position: "absolute",
49566
- style: {
49567
- left: view.cx - UNIT_DISPLAY_W / 2,
49568
- top: view.cy - UNIT_DISPLAY_H / 2,
49569
- width: UNIT_DISPLAY_W,
49570
- height: UNIT_DISPLAY_H,
49571
- cursor: "pointer",
49572
- transition: "transform 0.2s ease, filter 0.2s ease, box-shadow 0.3s ease",
49573
- transform: selected === view.name ? "scale(1.05)" : "scale(1)",
49574
- filter: selected && selected !== view.name ? "opacity(0.5)" : "none",
49575
- // GAP-52: persistent highlight ring (independent from user selection)
49576
- boxShadow: isHighlighted ? `0 0 0 3px ${color}, 0 0 24px 4px ${color}` : "none",
49577
- borderRadius: isHighlighted ? "12px" : void 0,
49578
- zIndex: isHighlighted ? 11 : selected === view.name ? 10 : 1
49579
- },
49580
- children: /* @__PURE__ */ jsx(
49581
- AvlOrbitalUnit,
49582
- {
49583
- entityName: view.entityName,
49584
- fields: view.fieldCount,
49585
- persistence: view.persistence,
49586
- traits: view.traits,
49587
- pages: view.pages,
49588
- color,
49589
- animated: animated && (selected === view.name || isHighlighted)
49590
- }
49591
- )
49592
- },
49593
- view.name
49594
- );
49595
- }),
49596
- selectedView && /* @__PURE__ */ jsx(
49597
- InfoPanel,
49598
- {
49599
- view: selectedView,
49600
- crossLinks,
49601
- color
49602
- }
49603
- )
49604
- ]
49605
- }
49606
- )
49607
- }
49608
- ),
49609
- /* @__PURE__ */ jsxs(
49610
- Box,
49611
- {
49612
- position: "absolute",
49613
- style: {
49614
- top: 12,
49615
- right: 12,
49616
- display: "flex",
49617
- flexDirection: "column",
49618
- gap: 4,
49619
- zIndex: 30
49620
- },
49621
- children: [
49622
- /* @__PURE__ */ jsx(Button, { variant: "secondary", size: "sm", onClick: zoomIn, title: "Zoom in", action: "COSMIC_ZOOM_IN", children: /* @__PURE__ */ jsx(Icon, { name: "plus", size: "sm" }) }),
49623
- /* @__PURE__ */ jsx(Button, { variant: "secondary", size: "sm", onClick: zoomOut, title: "Zoom out", action: "COSMIC_ZOOM_OUT", children: /* @__PURE__ */ jsx(Icon, { name: "minus", size: "sm" }) }),
49624
- /* @__PURE__ */ jsx(Button, { variant: "secondary", size: "sm", onClick: resetZoom, title: "Reset", action: "COSMIC_ZOOM_RESET", children: /* @__PURE__ */ jsx(Icon, { name: "maximize", size: "sm" }) })
49625
- ]
49626
- }
49627
- )
49628
- ]
49629
- }
49630
- );
49631
- };
49632
- AvlOrbitalsCosmicZoom.displayName = "AvlOrbitalsCosmicZoom";
49190
+ init_avl_zoom_state();
49633
49191
  init_types();
49634
49192
  var SWIM_GUTTER2 = 120;
49635
49193
  var CENTER_W2 = 360;
@@ -49920,63 +49478,670 @@ var AvlTransitionScene = ({
49920
49478
  return /* @__PURE__ */ jsxs("g", { children: [
49921
49479
  /* @__PURE__ */ jsx("text", { x: SECTION_LEFT, y: secY + 12, fill: color, fontSize: 10, fontWeight: 600, opacity: 0.4, fontFamily: "inherit", children: "GUARD" }),
49922
49480
  /* @__PURE__ */ jsx(
49923
- "polygon",
49481
+ "polygon",
49482
+ {
49483
+ points: `${CONTENT_LEFT + 6},${secY + 22} ${CONTENT_LEFT + 2},${secY + 26} ${CONTENT_LEFT + 6},${secY + 30} ${CONTENT_LEFT + 10},${secY + 26}`,
49484
+ fill: "none",
49485
+ stroke: color,
49486
+ strokeWidth: 1,
49487
+ opacity: 0.5
49488
+ }
49489
+ ),
49490
+ /* @__PURE__ */ jsx("text", { x: CONTENT_LEFT + 18, y: secY + 29, fill: color, fontSize: 12, fontWeight: 400, opacity: 0.6, fontFamily: "inherit", children: data.guard.label })
49491
+ ] });
49492
+ })(),
49493
+ hasEffects && (() => {
49494
+ const secY = cardY + headerH + sectionGap + triggerH + guardH;
49495
+ return /* @__PURE__ */ jsxs("g", { children: [
49496
+ /* @__PURE__ */ jsx("text", { x: SECTION_LEFT, y: secY + 12, fill: color, fontSize: 10, fontWeight: 600, opacity: 0.4, fontFamily: "inherit", children: "EFFECTS" }),
49497
+ effects.map((eff, i) => {
49498
+ const rowY = secY + 22 + i * effectRowH;
49499
+ const effectType = mapEffectType(eff.type);
49500
+ const argsText = eff.args.length > 0 ? eff.args.join(" \xB7 ") : "";
49501
+ return /* @__PURE__ */ jsxs("g", { children: [
49502
+ /* @__PURE__ */ jsx(
49503
+ AvlEffect,
49504
+ {
49505
+ x: CONTENT_LEFT + 10,
49506
+ y: rowY + 6,
49507
+ effectType,
49508
+ size: 10,
49509
+ showBackground: true
49510
+ }
49511
+ ),
49512
+ /* @__PURE__ */ jsx("text", { x: CONTENT_LEFT + 28, y: rowY + 10, fill: color, fontSize: 12, fontWeight: 500, opacity: 0.8, fontFamily: "inherit", children: eff.type }),
49513
+ argsText && /* @__PURE__ */ jsx("text", { x: CONTENT_LEFT + 28 + eff.type.length * 7 + 8, y: rowY + 10, fill: color, fontSize: 10, fontWeight: 400, opacity: 0.5, fontFamily: "monospace", children: argsText })
49514
+ ] }, `eff-${i}`);
49515
+ })
49516
+ ] });
49517
+ })(),
49518
+ hasSlots && (() => {
49519
+ const secY = cardY + headerH + sectionGap + triggerH + guardH + effectsH;
49520
+ return /* @__PURE__ */ jsxs("g", { children: [
49521
+ /* @__PURE__ */ jsx("text", { x: SECTION_LEFT, y: secY + 12, fill: color, fontSize: 10, fontWeight: 600, opacity: 0.4, fontFamily: "inherit", children: "SLOTS" }),
49522
+ data.slotTargets.map((slot, i) => {
49523
+ const rowY = secY + 22 + i * 22;
49524
+ return /* @__PURE__ */ jsxs("g", { children: [
49525
+ /* @__PURE__ */ jsx("rect", { x: CONTENT_LEFT, y: rowY - 4, width: CARD_W - 56, height: 18, rx: 4, fill: color, fillOpacity: 0.04 }),
49526
+ /* @__PURE__ */ jsxs("text", { x: CONTENT_LEFT + 8, y: rowY + 8, fill: color, fontSize: 11, fontFamily: "inherit", children: [
49527
+ slot.name,
49528
+ ": ",
49529
+ slot.pattern
49530
+ ] })
49531
+ ] }, `slot-${i}`);
49532
+ })
49533
+ ] });
49534
+ })()
49535
+ ] });
49536
+ };
49537
+ AvlTransitionScene.displayName = "AvlTransitionScene";
49538
+
49539
+ // components/organisms/avl/AvlOrbitalsCosmicZoom.tsx
49540
+ init_Box();
49541
+ init_Stack();
49542
+ init_Typography();
49543
+ var UNIT_DISPLAY_W = 240;
49544
+ var UNIT_DISPLAY_H = 160;
49545
+ function layoutOrbitals(count, containerW, containerH) {
49546
+ if (count === 0) return [];
49547
+ if (count === 1) return [{ cx: containerW / 2, cy: containerH / 2 }];
49548
+ const cols = Math.min(count, Math.ceil(Math.sqrt(count)));
49549
+ const rows = Math.ceil(count / cols);
49550
+ const cellW = containerW / (cols + 0.3);
49551
+ const cellH = containerH / (rows + 0.3);
49552
+ const originX = (containerW - cols * cellW) / 2 + cellW / 2;
49553
+ const originY = (containerH - rows * cellH) / 2 + cellH / 2;
49554
+ return Array.from({ length: count }, (_, i) => ({
49555
+ cx: originX + i % cols * cellW,
49556
+ cy: originY + Math.floor(i / cols) * cellH
49557
+ }));
49558
+ }
49559
+ var avlOczWireId = 0;
49560
+ var EventWireOverlay = ({
49561
+ orbitalViews,
49562
+ crossLinks,
49563
+ color,
49564
+ animated,
49565
+ containerW,
49566
+ containerH
49567
+ }) => {
49568
+ const ids = React125__default.useMemo(() => {
49569
+ avlOczWireId += 1;
49570
+ return { arrow: `avl-ocz-wire-${avlOczWireId}-arrow` };
49571
+ }, []);
49572
+ const posMap = useMemo(() => {
49573
+ const m = /* @__PURE__ */ new Map();
49574
+ for (const ov of orbitalViews) m.set(ov.name, { cx: ov.cx, cy: ov.cy });
49575
+ return m;
49576
+ }, [orbitalViews]);
49577
+ const wiresByPair = useMemo(() => {
49578
+ const map = /* @__PURE__ */ new Map();
49579
+ for (const link of crossLinks) {
49580
+ const key = `${link.emitterOrbital}__${link.listenerOrbital}`;
49581
+ const arr = map.get(key) ?? [];
49582
+ arr.push(link);
49583
+ map.set(key, arr);
49584
+ }
49585
+ return map;
49586
+ }, [crossLinks]);
49587
+ const orbitalR = UNIT_DISPLAY_W * 0.38;
49588
+ return /* @__PURE__ */ jsxs(
49589
+ "svg",
49590
+ {
49591
+ style: {
49592
+ position: "absolute",
49593
+ inset: 0,
49594
+ width: "100%",
49595
+ height: "100%",
49596
+ pointerEvents: "none",
49597
+ overflow: "visible"
49598
+ },
49599
+ viewBox: `0 0 ${containerW} ${containerH}`,
49600
+ preserveAspectRatio: "xMidYMid meet",
49601
+ children: [
49602
+ /* @__PURE__ */ jsx("defs", { children: /* @__PURE__ */ jsx(
49603
+ "marker",
49604
+ {
49605
+ id: ids.arrow,
49606
+ markerWidth: "8",
49607
+ markerHeight: "6",
49608
+ refX: "7",
49609
+ refY: "3",
49610
+ orient: "auto",
49611
+ markerUnits: "strokeWidth",
49612
+ children: /* @__PURE__ */ jsx("path", { d: "M0,0 L8,3 L0,6 Z", fill: color, opacity: 0.6 })
49613
+ }
49614
+ ) }),
49615
+ animated && /* @__PURE__ */ jsx("style", { children: `
49616
+ @keyframes avl-ocz-flow {
49617
+ from { stroke-dashoffset: 20; }
49618
+ to { stroke-dashoffset: 0; }
49619
+ }
49620
+ ` }),
49621
+ Array.from(wiresByPair.entries()).map(
49622
+ ([pairKey, links]) => links.map((link, wireIdx) => {
49623
+ const fromPos = posMap.get(link.emitterOrbital);
49624
+ const toPos = posMap.get(link.listenerOrbital);
49625
+ if (!fromPos || !toPos) return null;
49626
+ const dx = toPos.cx - fromPos.cx;
49627
+ const dy = toPos.cy - fromPos.cy;
49628
+ const dist = Math.sqrt(dx * dx + dy * dy) || 1;
49629
+ const nx = dx / dist;
49630
+ const ny = dy / dist;
49631
+ const x1 = fromPos.cx + nx * orbitalR;
49632
+ const y1 = fromPos.cy + ny * orbitalR;
49633
+ const x2 = toPos.cx - nx * (orbitalR + 6);
49634
+ const y2 = toPos.cy - ny * (orbitalR + 6);
49635
+ const offset = 25 + wireIdx * 18;
49636
+ const { cpx, cpy } = curveControlPoint(x1, y1, x2, y2, offset);
49637
+ const pathD = `M${x1},${y1} Q${cpx},${cpy} ${x2},${y2}`;
49638
+ const t = 0.5;
49639
+ const lx = (1 - t) * (1 - t) * x1 + 2 * (1 - t) * t * cpx + t * t * x2;
49640
+ const ly = (1 - t) * (1 - t) * y1 + 2 * (1 - t) * t * cpy + t * t * y2;
49641
+ const labelW = link.eventName.length * 5.5 + 12;
49642
+ return /* @__PURE__ */ jsxs("g", { children: [
49643
+ /* @__PURE__ */ jsx(
49644
+ "path",
49645
+ {
49646
+ d: pathD,
49647
+ fill: "none",
49648
+ stroke: color,
49649
+ strokeWidth: 1.2,
49650
+ strokeDasharray: animated ? "6 4" : "4 3",
49651
+ markerEnd: `url(#${ids.arrow})`,
49652
+ opacity: 0.5,
49653
+ style: animated ? { animation: "avl-ocz-flow 1.5s linear infinite" } : void 0
49654
+ }
49655
+ ),
49656
+ /* @__PURE__ */ jsx(
49657
+ "rect",
49658
+ {
49659
+ x: lx - labelW / 2,
49660
+ y: ly - 8,
49661
+ width: labelW,
49662
+ height: 14,
49663
+ rx: 3,
49664
+ fill: "var(--color-background, #fff)",
49665
+ stroke: color,
49666
+ strokeWidth: 0.5,
49667
+ opacity: 0.9
49668
+ }
49669
+ ),
49670
+ /* @__PURE__ */ jsx(
49671
+ "text",
49672
+ {
49673
+ x: lx,
49674
+ y: ly + 3,
49675
+ textAnchor: "middle",
49676
+ fill: color,
49677
+ fontSize: 7,
49678
+ fontWeight: 600,
49679
+ fontFamily: "monospace",
49680
+ opacity: 0.8,
49681
+ children: link.eventName
49682
+ }
49683
+ )
49684
+ ] }, `${pairKey}-${wireIdx}`);
49685
+ })
49686
+ )
49687
+ ]
49688
+ }
49689
+ );
49690
+ };
49691
+ var AvlOrbitalsCosmicZoom = ({
49692
+ schema: schemaProp,
49693
+ className,
49694
+ color = "var(--color-primary, #4A90D9)",
49695
+ animated = true,
49696
+ width = "100%",
49697
+ height = 450,
49698
+ highlightedOrbital,
49699
+ onOrbitalSelect,
49700
+ minZoom = 0.4,
49701
+ maxZoom = 3
49702
+ }) => {
49703
+ const parsedSchema = useMemo(() => {
49704
+ if (typeof schemaProp === "string") return JSON.parse(schemaProp);
49705
+ return schemaProp;
49706
+ }, [schemaProp]);
49707
+ const { orbitals, crossLinks } = useMemo(
49708
+ () => parseApplicationLevel(parsedSchema),
49709
+ [parsedSchema]
49710
+ );
49711
+ const containerW = typeof width === "number" ? width : 800;
49712
+ const containerH = typeof height === "number" ? height : 450;
49713
+ const positions = useMemo(
49714
+ () => layoutOrbitals(orbitals.length, containerW, containerH),
49715
+ [orbitals.length, containerW, containerH]
49716
+ );
49717
+ const orbitalViews = useMemo(
49718
+ () => orbitals.map((o, i) => ({
49719
+ name: o.name,
49720
+ entityName: o.entityName,
49721
+ fieldCount: o.fieldCount,
49722
+ persistence: o.persistence || "persistent",
49723
+ traits: o.traitNames.map((n) => ({ name: n })),
49724
+ pages: o.pageNames.map((n) => ({ name: n })),
49725
+ cx: positions[i]?.cx ?? 0,
49726
+ cy: positions[i]?.cy ?? 0
49727
+ })),
49728
+ [orbitals, positions]
49729
+ );
49730
+ const [state, dispatch] = useReducer(zoomReducer, initialZoomState);
49731
+ const drilledForHighlightRef = useRef(false);
49732
+ useEffect(() => {
49733
+ if (!highlightedOrbital) return;
49734
+ if (drilledForHighlightRef.current) return;
49735
+ drilledForHighlightRef.current = true;
49736
+ dispatch({ type: "ZOOM_INTO_ORBITAL", orbital: highlightedOrbital, targetPosition: { x: 0, y: 0 } });
49737
+ Promise.resolve().then(() => dispatch({ type: "ANIMATION_COMPLETE" }));
49738
+ }, [highlightedOrbital]);
49739
+ const breadcrumbs = useMemo(() => getBreadcrumbs(state), [state]);
49740
+ const handleSelect = useCallback(
49741
+ (name) => {
49742
+ dispatch({ type: "ZOOM_INTO_ORBITAL", orbital: name, targetPosition: { x: 0, y: 0 } });
49743
+ Promise.resolve().then(() => dispatch({ type: "ANIMATION_COMPLETE" }));
49744
+ onOrbitalSelect?.(name);
49745
+ },
49746
+ [onOrbitalSelect]
49747
+ );
49748
+ const handleTraitSelect = useCallback((traitName) => {
49749
+ dispatch({ type: "ZOOM_INTO_TRAIT", trait: traitName, targetPosition: { x: 0, y: 0 } });
49750
+ Promise.resolve().then(() => dispatch({ type: "ANIMATION_COMPLETE" }));
49751
+ }, []);
49752
+ const handleTransitionSelect = useCallback((transitionIndex) => {
49753
+ dispatch({ type: "ZOOM_INTO_TRANSITION", transitionIndex, targetPosition: { x: 0, y: 0 } });
49754
+ Promise.resolve().then(() => dispatch({ type: "ANIMATION_COMPLETE" }));
49755
+ }, []);
49756
+ const handleZoomOut = useCallback(() => {
49757
+ dispatch({ type: "ZOOM_OUT" });
49758
+ Promise.resolve().then(() => dispatch({ type: "ANIMATION_COMPLETE" }));
49759
+ }, []);
49760
+ const handleBreadcrumbClick = useCallback((targetLevel) => {
49761
+ const order = ["application", "orbital", "trait", "transition"];
49762
+ const currentIdx = order.indexOf(state.level);
49763
+ const targetIdx = order.indexOf(targetLevel);
49764
+ const steps = currentIdx - targetIdx;
49765
+ for (let i = 0; i < steps; i++) {
49766
+ dispatch({ type: "ZOOM_OUT" });
49767
+ }
49768
+ Promise.resolve().then(() => dispatch({ type: "ANIMATION_COMPLETE" }));
49769
+ }, [state.level]);
49770
+ useEffect(() => {
49771
+ if (state.level === "application") return;
49772
+ const onKey = (e) => {
49773
+ if (e.key === "Escape") handleZoomOut();
49774
+ };
49775
+ window.addEventListener("keydown", onKey);
49776
+ return () => window.removeEventListener("keydown", onKey);
49777
+ }, [handleZoomOut, state.level]);
49778
+ const orbitalLevelData = useMemo(() => {
49779
+ if (!state.selectedOrbital) return null;
49780
+ return parseOrbitalLevel(parsedSchema, state.selectedOrbital);
49781
+ }, [parsedSchema, state.selectedOrbital]);
49782
+ const traitLevelData = useMemo(() => {
49783
+ if (!state.selectedOrbital || !state.selectedTrait) return null;
49784
+ return parseTraitLevel(parsedSchema, state.selectedOrbital, state.selectedTrait);
49785
+ }, [parsedSchema, state.selectedOrbital, state.selectedTrait]);
49786
+ const transitionLevelData = useMemo(() => {
49787
+ if (!state.selectedOrbital || !state.selectedTrait || state.selectedTransition === null) return null;
49788
+ return parseTransitionLevel(
49789
+ parsedSchema,
49790
+ state.selectedOrbital,
49791
+ state.selectedTrait,
49792
+ state.selectedTransition
49793
+ );
49794
+ }, [parsedSchema, state.selectedOrbital, state.selectedTrait, state.selectedTransition]);
49795
+ const [zoom, setZoom] = useState(1);
49796
+ const [pan, setPan] = useState({ x: 0, y: 0 });
49797
+ const dragStateRef = useRef(null);
49798
+ const transformWrapperRef = useRef(null);
49799
+ const clampZoom = useCallback(
49800
+ (z) => Math.max(minZoom, Math.min(maxZoom, z)),
49801
+ [minZoom, maxZoom]
49802
+ );
49803
+ const handlePointerDown = useCallback((e) => {
49804
+ if (e.target.closest("[data-orbital-tile]")) return;
49805
+ dragStateRef.current = {
49806
+ startX: e.clientX,
49807
+ startY: e.clientY,
49808
+ panX: pan.x,
49809
+ panY: pan.y
49810
+ };
49811
+ e.target.setPointerCapture(e.pointerId);
49812
+ }, [pan]);
49813
+ const handlePointerMove = useCallback((e) => {
49814
+ const drag = dragStateRef.current;
49815
+ if (!drag) return;
49816
+ setPan({
49817
+ x: drag.panX + (e.clientX - drag.startX),
49818
+ y: drag.panY + (e.clientY - drag.startY)
49819
+ });
49820
+ }, []);
49821
+ const handlePointerUp = useCallback((e) => {
49822
+ if (!dragStateRef.current) return;
49823
+ dragStateRef.current = null;
49824
+ try {
49825
+ e.target.releasePointerCapture(e.pointerId);
49826
+ } catch {
49827
+ }
49828
+ }, []);
49829
+ const panRef = useRef(pan);
49830
+ const zoomRef = useRef(zoom);
49831
+ useEffect(() => {
49832
+ panRef.current = pan;
49833
+ }, [pan]);
49834
+ useEffect(() => {
49835
+ zoomRef.current = zoom;
49836
+ }, [zoom]);
49837
+ useEffect(() => {
49838
+ const wrapper = transformWrapperRef.current;
49839
+ if (!wrapper) return;
49840
+ const wheelListener = (e) => {
49841
+ e.preventDefault();
49842
+ const rect = wrapper.getBoundingClientRect();
49843
+ const cursorX = e.clientX - rect.left;
49844
+ const cursorY = e.clientY - rect.top;
49845
+ const currentZoom = zoomRef.current;
49846
+ const currentPan = panRef.current;
49847
+ const worldX = (cursorX - currentPan.x) / currentZoom;
49848
+ const worldY = (cursorY - currentPan.y) / currentZoom;
49849
+ const delta = e.deltaY > 0 ? -0.1 : 0.1;
49850
+ const nextZoom = clampZoom(currentZoom * (1 + delta));
49851
+ const nextPanX = cursorX - worldX * nextZoom;
49852
+ const nextPanY = cursorY - worldY * nextZoom;
49853
+ setZoom(nextZoom);
49854
+ setPan({ x: nextPanX, y: nextPanY });
49855
+ };
49856
+ wrapper.addEventListener("wheel", wheelListener, { passive: false });
49857
+ return () => wrapper.removeEventListener("wheel", wheelListener);
49858
+ }, [clampZoom]);
49859
+ const zoomIn = useCallback(() => setZoom((z) => clampZoom(z * 1.2)), [clampZoom]);
49860
+ const zoomOut = useCallback(() => setZoom((z) => clampZoom(z / 1.2)), [clampZoom]);
49861
+ const resetZoom = useCallback(() => {
49862
+ setZoom(1);
49863
+ setPan({ x: 0, y: 0 });
49864
+ }, []);
49865
+ return /* @__PURE__ */ jsxs(
49866
+ Box,
49867
+ {
49868
+ className,
49869
+ position: "relative",
49870
+ overflow: "visible",
49871
+ style: { width, height: containerH },
49872
+ children: [
49873
+ /* @__PURE__ */ jsx(
49874
+ Box,
49924
49875
  {
49925
- points: `${CONTENT_LEFT + 6},${secY + 22} ${CONTENT_LEFT + 2},${secY + 26} ${CONTENT_LEFT + 6},${secY + 30} ${CONTENT_LEFT + 10},${secY + 26}`,
49926
- fill: "none",
49927
- stroke: color,
49928
- strokeWidth: 1,
49929
- opacity: 0.5
49876
+ position: "absolute",
49877
+ style: {
49878
+ top: 12,
49879
+ left: 12,
49880
+ zIndex: 30,
49881
+ background: "var(--color-card, rgba(255,255,255,0.92))",
49882
+ padding: "4px 12px",
49883
+ borderRadius: 6,
49884
+ border: `1px solid ${color}`
49885
+ },
49886
+ children: /* @__PURE__ */ jsx(HStack, { gap: "xs", align: "center", children: breadcrumbs.map((crumb, i) => /* @__PURE__ */ jsxs(React125__default.Fragment, { children: [
49887
+ i > 0 && /* @__PURE__ */ jsx(Typography, { variant: "small", style: { opacity: 0.5, color }, children: "/" }),
49888
+ i < breadcrumbs.length - 1 ? /* @__PURE__ */ jsx(
49889
+ Box,
49890
+ {
49891
+ as: "span",
49892
+ onClick: () => handleBreadcrumbClick(crumb.level),
49893
+ style: { cursor: "pointer" },
49894
+ children: /* @__PURE__ */ jsx(
49895
+ Typography,
49896
+ {
49897
+ variant: "small",
49898
+ style: { color, textDecoration: "underline" },
49899
+ children: crumb.label
49900
+ }
49901
+ )
49902
+ }
49903
+ ) : /* @__PURE__ */ jsx(Typography, { variant: "small", weight: "bold", style: { color }, children: crumb.label })
49904
+ ] }, crumb.level)) })
49930
49905
  }
49931
49906
  ),
49932
- /* @__PURE__ */ jsx("text", { x: CONTENT_LEFT + 18, y: secY + 29, fill: color, fontSize: 12, fontWeight: 400, opacity: 0.6, fontFamily: "inherit", children: data.guard.label })
49933
- ] });
49934
- })(),
49935
- hasEffects && (() => {
49936
- const secY = cardY + headerH + sectionGap + triggerH + guardH;
49937
- return /* @__PURE__ */ jsxs("g", { children: [
49938
- /* @__PURE__ */ jsx("text", { x: SECTION_LEFT, y: secY + 12, fill: color, fontSize: 10, fontWeight: 600, opacity: 0.4, fontFamily: "inherit", children: "EFFECTS" }),
49939
- effects.map((eff, i) => {
49940
- const rowY = secY + 22 + i * effectRowH;
49941
- const effectType = mapEffectType(eff.type);
49942
- const argsText = eff.args.length > 0 ? eff.args.join(" \xB7 ") : "";
49943
- return /* @__PURE__ */ jsxs("g", { children: [
49944
- /* @__PURE__ */ jsx(
49945
- AvlEffect,
49907
+ state.level !== "application" && /* @__PURE__ */ jsx(
49908
+ Box,
49909
+ {
49910
+ position: "absolute",
49911
+ style: {
49912
+ bottom: 12,
49913
+ right: 12,
49914
+ zIndex: 30,
49915
+ background: "var(--color-card, rgba(255,255,255,0.85))",
49916
+ padding: "2px 8px",
49917
+ borderRadius: 4,
49918
+ opacity: 0.8
49919
+ },
49920
+ children: /* @__PURE__ */ jsx(Typography, { variant: "small", style: { color }, children: "Press Esc to zoom out" })
49921
+ }
49922
+ ),
49923
+ state.level === "application" && /* @__PURE__ */ jsxs(Fragment, { children: [
49924
+ /* @__PURE__ */ jsx(
49925
+ "div",
49926
+ {
49927
+ ref: transformWrapperRef,
49928
+ onPointerDown: handlePointerDown,
49929
+ onPointerMove: handlePointerMove,
49930
+ onPointerUp: handlePointerUp,
49931
+ onPointerCancel: handlePointerUp,
49932
+ style: {
49933
+ position: "absolute",
49934
+ inset: 0,
49935
+ overflow: "hidden",
49936
+ cursor: dragStateRef.current ? "grabbing" : "grab",
49937
+ touchAction: "none"
49938
+ },
49939
+ children: /* @__PURE__ */ jsxs(
49940
+ "div",
49941
+ {
49942
+ style: {
49943
+ position: "absolute",
49944
+ inset: 0,
49945
+ transform: `translate(${pan.x}px, ${pan.y}px) scale(${zoom})`,
49946
+ transformOrigin: "0 0"
49947
+ },
49948
+ children: [
49949
+ /* @__PURE__ */ jsx(
49950
+ EventWireOverlay,
49951
+ {
49952
+ orbitalViews,
49953
+ crossLinks,
49954
+ color,
49955
+ animated,
49956
+ containerW,
49957
+ containerH
49958
+ }
49959
+ ),
49960
+ orbitalViews.map((view) => {
49961
+ const isHighlighted = view.name === highlightedOrbital;
49962
+ return /* @__PURE__ */ jsx(
49963
+ Box,
49964
+ {
49965
+ role: "button",
49966
+ tabIndex: 0,
49967
+ "data-orbital-tile": "true",
49968
+ onClick: () => handleSelect(view.name),
49969
+ onKeyDown: (e) => {
49970
+ if (e.key === "Enter" || e.key === " ") handleSelect(view.name);
49971
+ },
49972
+ "aria-label": `Orbital: ${view.name}${isHighlighted ? " (highlighted)" : ""}`,
49973
+ position: "absolute",
49974
+ style: {
49975
+ left: view.cx - UNIT_DISPLAY_W / 2,
49976
+ top: view.cy - UNIT_DISPLAY_H / 2,
49977
+ width: UNIT_DISPLAY_W,
49978
+ height: UNIT_DISPLAY_H,
49979
+ cursor: "pointer",
49980
+ transition: "transform 0.2s ease, filter 0.2s ease, box-shadow 0.3s ease",
49981
+ // GAP-52: persistent highlight ring (independent from user selection)
49982
+ boxShadow: isHighlighted ? `0 0 0 3px ${color}, 0 0 24px 4px ${color}` : "none",
49983
+ borderRadius: isHighlighted ? "12px" : void 0,
49984
+ zIndex: isHighlighted ? 11 : 1
49985
+ },
49986
+ children: /* @__PURE__ */ jsx(
49987
+ AvlOrbitalUnit,
49988
+ {
49989
+ entityName: view.entityName,
49990
+ fields: view.fieldCount,
49991
+ persistence: view.persistence,
49992
+ traits: view.traits,
49993
+ pages: view.pages,
49994
+ color,
49995
+ animated: animated && isHighlighted
49996
+ }
49997
+ )
49998
+ },
49999
+ view.name
50000
+ );
50001
+ })
50002
+ ]
50003
+ }
50004
+ )
50005
+ }
50006
+ ),
50007
+ /* @__PURE__ */ jsxs(
50008
+ Box,
50009
+ {
50010
+ position: "absolute",
50011
+ style: {
50012
+ top: 12,
50013
+ right: 12,
50014
+ display: "flex",
50015
+ flexDirection: "column",
50016
+ gap: 4,
50017
+ zIndex: 30
50018
+ },
50019
+ children: [
50020
+ /* @__PURE__ */ jsx(Button, { variant: "secondary", size: "sm", onClick: zoomIn, title: "Zoom in", action: "COSMIC_ZOOM_IN", children: /* @__PURE__ */ jsx(Icon, { name: "plus", size: "sm" }) }),
50021
+ /* @__PURE__ */ jsx(Button, { variant: "secondary", size: "sm", onClick: zoomOut, title: "Zoom out", action: "COSMIC_ZOOM_OUT", children: /* @__PURE__ */ jsx(Icon, { name: "minus", size: "sm" }) }),
50022
+ /* @__PURE__ */ jsx(Button, { variant: "secondary", size: "sm", onClick: resetZoom, title: "Reset", action: "COSMIC_ZOOM_RESET", children: /* @__PURE__ */ jsx(Icon, { name: "maximize", size: "sm" }) })
50023
+ ]
50024
+ }
50025
+ )
50026
+ ] }),
50027
+ state.level === "orbital" && orbitalLevelData && /* @__PURE__ */ jsxs(
50028
+ Box,
50029
+ {
50030
+ position: "absolute",
50031
+ style: {
50032
+ inset: 0,
50033
+ paddingTop: 56,
50034
+ paddingBottom: 24,
50035
+ paddingLeft: 24,
50036
+ paddingRight: 24,
50037
+ display: "flex",
50038
+ alignItems: "stretch",
50039
+ justifyContent: "center",
50040
+ gap: 24
50041
+ },
50042
+ children: [
50043
+ /* @__PURE__ */ jsx(Box, { style: { flex: 1, maxWidth: 720, display: "flex", alignItems: "center", justifyContent: "center" }, children: /* @__PURE__ */ jsx(
50044
+ AvlOrbitalUnit,
50045
+ {
50046
+ entityName: orbitalLevelData.entity.name,
50047
+ fields: orbitalLevelData.entity.fields.length,
50048
+ persistence: orbitalLevelData.entity.persistence || "persistent",
50049
+ traits: orbitalLevelData.traits.map((t) => ({ name: t.name })),
50050
+ pages: orbitalLevelData.pages.map((p2) => ({ name: p2.name })),
50051
+ color,
50052
+ animated
50053
+ }
50054
+ ) }),
50055
+ /* @__PURE__ */ jsxs(
50056
+ Box,
50057
+ {
50058
+ style: {
50059
+ width: 220,
50060
+ padding: 12,
50061
+ display: "flex",
50062
+ flexDirection: "column",
50063
+ gap: 8,
50064
+ borderLeft: `1px solid ${color}`,
50065
+ opacity: 0.95
50066
+ },
50067
+ children: [
50068
+ /* @__PURE__ */ jsxs(Typography, { variant: "small", weight: "semibold", style: { color, marginBottom: 4 }, children: [
50069
+ "Traits (",
50070
+ orbitalLevelData.traits.length,
50071
+ ")"
50072
+ ] }),
50073
+ orbitalLevelData.traits.length === 0 && /* @__PURE__ */ jsx(Text, { variant: "small", style: { opacity: 0.6, color }, children: "No traits" }),
50074
+ orbitalLevelData.traits.map((trait) => /* @__PURE__ */ jsx(
50075
+ Button,
50076
+ {
50077
+ variant: "ghost",
50078
+ size: "sm",
50079
+ onClick: () => handleTraitSelect(trait.name),
50080
+ action: "COSMIC_DRILL_TRAIT",
50081
+ children: trait.name
50082
+ },
50083
+ trait.name
50084
+ )),
50085
+ orbitalLevelData.pages.length > 0 && /* @__PURE__ */ jsxs(Fragment, { children: [
50086
+ /* @__PURE__ */ jsxs(Typography, { variant: "small", weight: "semibold", style: { color, marginTop: 12 }, children: [
50087
+ "Pages (",
50088
+ orbitalLevelData.pages.length,
50089
+ ")"
50090
+ ] }),
50091
+ orbitalLevelData.pages.map((page) => /* @__PURE__ */ jsx(Text, { variant: "small", style: { opacity: 0.7, color }, children: page.name }, page.name))
50092
+ ] })
50093
+ ]
50094
+ }
50095
+ )
50096
+ ]
50097
+ }
50098
+ ),
50099
+ state.level === "trait" && traitLevelData && /* @__PURE__ */ jsx(
50100
+ Box,
50101
+ {
50102
+ position: "absolute",
50103
+ style: {
50104
+ inset: 0,
50105
+ paddingTop: 56,
50106
+ paddingBottom: 24,
50107
+ paddingLeft: 24,
50108
+ paddingRight: 24
50109
+ },
50110
+ children: /* @__PURE__ */ jsx("svg", { viewBox: "0 0 600 400", style: { width: "100%", height: "100%" }, children: /* @__PURE__ */ jsx(
50111
+ AvlTraitScene,
49946
50112
  {
49947
- x: CONTENT_LEFT + 10,
49948
- y: rowY + 6,
49949
- effectType,
49950
- size: 10,
49951
- showBackground: true
50113
+ data: traitLevelData,
50114
+ color,
50115
+ onTransitionClick: (idx) => handleTransitionSelect(idx)
49952
50116
  }
49953
- ),
49954
- /* @__PURE__ */ jsx("text", { x: CONTENT_LEFT + 28, y: rowY + 10, fill: color, fontSize: 12, fontWeight: 500, opacity: 0.8, fontFamily: "inherit", children: eff.type }),
49955
- argsText && /* @__PURE__ */ jsx("text", { x: CONTENT_LEFT + 28 + eff.type.length * 7 + 8, y: rowY + 10, fill: color, fontSize: 10, fontWeight: 400, opacity: 0.5, fontFamily: "monospace", children: argsText })
49956
- ] }, `eff-${i}`);
49957
- })
49958
- ] });
49959
- })(),
49960
- hasSlots && (() => {
49961
- const secY = cardY + headerH + sectionGap + triggerH + guardH + effectsH;
49962
- return /* @__PURE__ */ jsxs("g", { children: [
49963
- /* @__PURE__ */ jsx("text", { x: SECTION_LEFT, y: secY + 12, fill: color, fontSize: 10, fontWeight: 600, opacity: 0.4, fontFamily: "inherit", children: "SLOTS" }),
49964
- data.slotTargets.map((slot, i) => {
49965
- const rowY = secY + 22 + i * 22;
49966
- return /* @__PURE__ */ jsxs("g", { children: [
49967
- /* @__PURE__ */ jsx("rect", { x: CONTENT_LEFT, y: rowY - 4, width: CARD_W - 56, height: 18, rx: 4, fill: color, fillOpacity: 0.04 }),
49968
- /* @__PURE__ */ jsxs("text", { x: CONTENT_LEFT + 8, y: rowY + 8, fill: color, fontSize: 11, fontFamily: "inherit", children: [
49969
- slot.name,
49970
- ": ",
49971
- slot.pattern
49972
- ] })
49973
- ] }, `slot-${i}`);
49974
- })
49975
- ] });
49976
- })()
49977
- ] });
50117
+ ) })
50118
+ }
50119
+ ),
50120
+ state.level === "transition" && transitionLevelData && /* @__PURE__ */ jsx(
50121
+ Box,
50122
+ {
50123
+ position: "absolute",
50124
+ style: {
50125
+ inset: 0,
50126
+ paddingTop: 56,
50127
+ paddingBottom: 24,
50128
+ paddingLeft: 24,
50129
+ paddingRight: 24
50130
+ },
50131
+ children: /* @__PURE__ */ jsx("svg", { viewBox: "0 0 600 400", style: { width: "100%", height: "100%" }, children: /* @__PURE__ */ jsx(
50132
+ AvlTransitionScene,
50133
+ {
50134
+ data: transitionLevelData,
50135
+ color
50136
+ }
50137
+ ) })
50138
+ }
50139
+ )
50140
+ ]
50141
+ }
50142
+ );
49978
50143
  };
49979
- AvlTransitionScene.displayName = "AvlTransitionScene";
50144
+ AvlOrbitalsCosmicZoom.displayName = "AvlOrbitalsCosmicZoom";
49980
50145
  var AvlClickTarget = ({
49981
50146
  x,
49982
50147
  y,