@canvas-harness/core 0.1.14 → 0.1.16

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.map CHANGED
@@ -1 +1 @@
1
- {"version":3,"sources":["../src/types/primitives.ts","../src/types/edge.ts","../src/types/background.ts","../src/ids/index.ts","../src/camera/index.ts","../src/spatial/aabb.ts","../src/spatial/grid.ts","../src/spatial/node-aabb.ts","../src/edges/project.ts","../src/edges/auto-route.ts","../src/edges/clip.ts","../src/edges/aabb.ts","../src/edges/samples.ts","../src/edges/self-loop.ts","../src/edges/cache.ts","../src/edges/arc-length.ts","../src/edges/midpoint.ts","../src/edges/arrowhead.ts","../src/render/rough/cache.ts","../src/render/shapes/defaults.ts","../src/text/tokens.ts","../src/text/defaults.ts","../src/text/math/loader.ts","../src/text/math/cache.ts","../src/text/measure.ts","../src/text/layout.ts","../src/text/font-epoch.ts","../src/text/render-scale.ts","../src/text/estimate-height.ts","../src/text/paint-canvas.ts","../src/text/bitmap-cache.ts","../src/edges/freehand.ts","../src/edges/draw.ts","../src/node-types/define-node.ts","../src/edit/auto-fit.ts","../src/edit/markdown-shortcuts.ts","../src/edit/textarea-editor.ts","../src/assets/image.ts","../src/assets/svg.ts","../src/store/conflict.ts","../src/store/interaction.ts","../src/store/inverse-op.ts","../src/store/presence.ts","../src/store/store.ts","../src/store/sync.ts","../src/store/palm-rejection.ts","../src/codec/index.ts","../src/render/canvas-setup.ts","../src/render/frame-loop.ts","../src/render/assets/cache.ts","../src/render/assets/paint.ts","../src/render/background.ts","../src/hit-test/handle.ts","../src/render/overlay.ts","../src/render/paint-frame.ts","../src/render/rough/constants.ts","../src/render/color.ts","../src/render/shapes/path-helpers.ts","../src/render/shapes/draw-shape.ts","../src/render/rough/loader.ts","../src/render/rough/paths.ts","../src/render/rough/tone-down.ts","../src/render/rough/draw.ts","../src/render/shapes/content-bounds.ts","../src/render/transform.ts","../src/render/renderer.ts","../src/render/minimap.ts","../src/hit-test/node.ts","../src/hit-test/edge.ts","../src/hit-test/store-query.ts","../src/clipboard/serialize.ts","../src/clipboard/index.ts","../src/export/png.ts","../src/export/svg.ts","../src/ai/context.ts","../src/ai/op-schemas.ts","../src/extension/index.ts","../src/index.ts"],"names":["a","b","samples","cached","segLen","cache","isMoving","getLineAdvance","lineWidth","x","next","newSel","opts","MAX_ENTRIES","loadPromise","readyCallbacks","TONE_BLEND","ex","ey","DEFAULT_BACKGROUND","MIN_READABLE_FONT_PX","DEFAULT_PADDING","unionBounds","bothEndsInside"],"mappings":"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","file":"index.js","sourcesContent":["/**\n * Branded ID types so node/edge/group ids never accidentally cross.\n */\nexport type NodeId = string & { readonly __brand: 'NodeId' }\nexport type EdgeId = string & { readonly __brand: 'EdgeId' }\nexport type GroupId = string & { readonly __brand: 'GroupId' }\nexport type ClientId = string & { readonly __brand: 'ClientId' }\nexport type BatchId = string & { readonly __brand: 'BatchId' }\n\nexport const asNodeId = (s: string): NodeId => s as NodeId\nexport const asEdgeId = (s: string): EdgeId => s as EdgeId\nexport const asGroupId = (s: string): GroupId => s as GroupId\nexport const asClientId = (s: string): ClientId => s as ClientId\nexport const asBatchId = (s: string): BatchId => s as BatchId\n\n/**\n * A point in world coordinates.\n */\nexport type Vec2 = { x: number; y: number }\n\n/**\n * An axis-aligned rectangle in world coordinates.\n * x/y is the top-left; w/h extend toward +x/+y.\n */\nexport type WorldRect = { x: number; y: number; w: number; h: number }\n\nexport const SCHEMA_VERSION = 1 as const\nexport type SchemaVersion = typeof SCHEMA_VERSION\n","import type { EdgeId, GroupId, NodeId, Vec2 } from './primitives'\nimport type { EdgeStyle } from './style'\n\nexport type PathStyle = 'straight' | 'bezier' | 'polyline'\n\n/**\n * Edge endpoint — see ARCHITECTURE.md §6.1.\n *\n * Attached: `localOffset` is in the node's pre-rotation local frame,\n * top-left origin, absolute pixels. Endpoint follows the node\n * automatically via projection at render time.\n * Free-floating: `worldPoint` is in world coordinates.\n */\nexport type EdgeEnd = { nodeId: NodeId; localOffset: Vec2 } | { worldPoint: Vec2 }\n\nexport const isAttached = (e: EdgeEnd): e is { nodeId: NodeId; localOffset: Vec2 } => 'nodeId' in e\n\n/**\n * Scene edge — see ARCHITECTURE.md §3.3.\n */\nexport type Edge = {\n id: EdgeId\n\n source: EdgeEnd\n target: EdgeEnd\n pathStyle: PathStyle\n control?: Vec2[]\n\n z: number\n groups: GroupId[]\n locked?: boolean\n hidden?: boolean\n\n content?: string\n style?: EdgeStyle\n data?: unknown\n}\n","/**\n * Canvas background — see ARCHITECTURE.md §4 (rendering pipeline).\n *\n * Local-only render-time config (not part of the synced scene). Drives\n * the page color plus an optional infinite dot / grid pattern that\n * helps spatial orientation while panning.\n *\n * Patterns are world-space: dots/lines are anchored to the world\n * origin, so panning moves *through* them rather than dragging them\n * along.\n */\nexport type CanvasBackgroundPattern = 'none' | 'dots' | 'grid'\n\nexport type CanvasBackground = {\n /** Page background color. Default `'#f8fafc'`. */\n color?: string\n /** Pattern overlay on top of the color. Default `'none'`. */\n pattern?: CanvasBackgroundPattern\n /** World units between adjacent dots / grid lines. Default `20`. */\n gap?: number\n /** Color of the dots / grid lines. Default `'#cbd5e1'`. */\n patternColor?: string\n /**\n * Hide the pattern when `camera.z < minZoom`. Useful to declutter\n * zoomed-out views and skip the per-frame pattern paint cost. Default\n * `0` (no minimum — pattern shows at any zoom, subject to the LOD\n * skip when individual cells would be sub-2px).\n */\n minZoom?: number\n /**\n * Hide the pattern when `camera.z > maxZoom`. Default `Infinity` (no\n * maximum). Most consumers won't need this; useful if you want the\n * pattern to disappear when zoomed in past a \"detail\" threshold.\n */\n maxZoom?: number\n}\n\nexport const DEFAULT_BACKGROUND: Required<CanvasBackground> = {\n color: '#f8fafc',\n pattern: 'none',\n gap: 20,\n patternColor: '#cbd5e1',\n minZoom: 0,\n maxZoom: Number.POSITIVE_INFINITY,\n}\n","/**\n * ID generation — see ARCHITECTURE.md §10.8.\n *\n * Default scheme: `${clientId}-${counter}`. Collision-free across clients\n * without coordination, human-readable in dev tools, monotonic per client.\n *\n * Consumers may override via `createCanvasStore({ idGenerator })`.\n */\nimport type { ClientId } from '../types'\n\nexport type IdGenerator = () => string\n\n/**\n * Generates a random short client id like \"u-7f3a\".\n * Used when no `clientId` is passed and no `sync` adapter is attached.\n */\nexport const randomClientId = (): ClientId => {\n const hex = Math.floor(Math.random() * 0xffff)\n .toString(16)\n .padStart(4, '0')\n return `u-${hex}` as ClientId\n}\n\n/**\n * Builds an id generator that prefixes a stable client id with an\n * incrementing counter. Each call returns a fresh, never-recycled id.\n */\nexport const makeIdGenerator = (clientId: ClientId): IdGenerator => {\n let counter = 0\n return () => `${clientId}-${counter++}`\n}\n","/**\n * Camera math — see ARCHITECTURE.md §4.3 and §13.4.\n *\n * The camera maps world coordinates to screen coordinates via:\n * screen = (world - camera.{x,y}) * camera.z\n * world = screen / camera.z + camera.{x,y}\n *\n * camera.{x,y} is the world-space point shown at screen (0,0).\n * camera.z is the zoom factor (1 = identity).\n */\nimport type { CameraState, Vec2, WorldRect } from '../types'\n\nexport const DEFAULT_CAMERA: CameraState = { x: 0, y: 0, z: 1 }\n\nexport const MIN_ZOOM = 0.05\nexport const MAX_ZOOM = 16\n\n/**\n * Converts a screen-space point to world coords given the current camera.\n */\nexport const screenToWorld = (screen: Vec2, camera: CameraState): Vec2 => ({\n x: screen.x / camera.z + camera.x,\n y: screen.y / camera.z + camera.y,\n})\n\n/**\n * Converts a world-space point to screen coords given the current camera.\n */\nexport const worldToScreen = (world: Vec2, camera: CameraState): Vec2 => ({\n x: (world.x - camera.x) * camera.z,\n y: (world.y - camera.y) * camera.z,\n})\n\n/**\n * Computes the world-space rect currently visible inside a viewport of the\n * given screen-space size. Used for viewport culling queries.\n */\nexport const viewportWorldRect = (\n camera: CameraState,\n viewportW: number,\n viewportH: number,\n): WorldRect => ({\n x: camera.x,\n y: camera.y,\n w: viewportW / camera.z,\n h: viewportH / camera.z,\n})\n\n/**\n * Clamps a zoom factor to the supported range.\n */\nexport const clampZoom = (z: number): number => {\n if (!Number.isFinite(z)) return 1\n return Math.max(MIN_ZOOM, Math.min(MAX_ZOOM, z))\n}\n\n/**\n * Applies a zoom delta keeping the world point under `screenAnchor` stationary.\n * Useful for wheel-zoom and pinch-zoom — keeps focus where the user looks.\n */\nexport const zoomAtScreenPoint = (\n camera: CameraState,\n newZoom: number,\n screenAnchor: Vec2,\n): CameraState => {\n const z = clampZoom(newZoom)\n const worldAnchor = screenToWorld(screenAnchor, camera)\n // Solve for new x/y so that worldToScreen(worldAnchor, new) === screenAnchor.\n return {\n x: worldAnchor.x - screenAnchor.x / z,\n y: worldAnchor.y - screenAnchor.y / z,\n z,\n }\n}\n\n/**\n * Pans the camera by a screen-space delta (e.g. from a drag gesture).\n */\nexport const panByScreen = (camera: CameraState, deltaScreen: Vec2): CameraState => ({\n x: camera.x - deltaScreen.x / camera.z,\n y: camera.y - deltaScreen.y / camera.z,\n z: camera.z,\n})\n","import type { Vec2, WorldRect } from '../types'\n\n/**\n * AABB utilities. Rectangles are { x, y, w, h } in world space.\n */\n\nexport const rectContainsPoint = (r: WorldRect, p: Vec2): boolean =>\n p.x >= r.x && p.x <= r.x + r.w && p.y >= r.y && p.y <= r.y + r.h\n\nexport const rectsIntersect = (a: WorldRect, b: WorldRect): boolean =>\n a.x < b.x + b.w && a.x + a.w > b.x && a.y < b.y + b.h && a.y + a.h > b.y\n\n/**\n * Inflate rect by a uniform world-space amount on all sides.\n */\nexport const inflateRect = (r: WorldRect, amount: number): WorldRect => ({\n x: r.x - amount,\n y: r.y - amount,\n w: r.w + amount * 2,\n h: r.h + amount * 2,\n})\n\n/**\n * Smallest AABB containing two points.\n */\nexport const rectFromPoints = (a: Vec2, b: Vec2): WorldRect => {\n const x = Math.min(a.x, b.x)\n const y = Math.min(a.y, b.y)\n return { x, y, w: Math.abs(b.x - a.x), h: Math.abs(b.y - a.y) }\n}\n\n/**\n * Smallest AABB containing all given rects. Returns null for empty input.\n */\nexport const unionRects = (rects: WorldRect[]): WorldRect | null => {\n if (rects.length === 0) return null\n let minX = Number.POSITIVE_INFINITY\n let minY = Number.POSITIVE_INFINITY\n let maxX = Number.NEGATIVE_INFINITY\n let maxY = Number.NEGATIVE_INFINITY\n for (const r of rects) {\n if (r.x < minX) minX = r.x\n if (r.y < minY) minY = r.y\n if (r.x + r.w > maxX) maxX = r.x + r.w\n if (r.y + r.h > maxY) maxY = r.y + r.h\n }\n return { x: minX, y: minY, w: maxX - minX, h: maxY - minY }\n}\n","import type { Vec2, WorldRect } from '../types'\n/**\n * Uniform-grid spatial index — see ARCHITECTURE.md §7.\n *\n * Stores ids by their AABB, with each AABB occupying one or more grid cells.\n * Insert / remove / query are O(1) per cell touched; total per query is\n * O(cells × items-per-cell), which for our 256-unit cell size and\n * typical scene density is well under 1ms even at 50k items.\n *\n * Sized ~256 world units by default. Tune via the constructor.\n */\nimport { rectsIntersect } from './aabb'\n\nexport type SpatialId = string\n\nexport class UniformGrid {\n private readonly cellSize: number\n // cell key -> set of ids whose AABB intersects this cell\n private readonly cells = new Map<string, Set<SpatialId>>()\n // id -> AABB (cached so remove() can find which cells to clear)\n private readonly bounds = new Map<SpatialId, WorldRect>()\n\n constructor(cellSize = 256) {\n if (cellSize <= 0) throw new Error('cellSize must be positive')\n this.cellSize = cellSize\n }\n\n get size(): number {\n return this.bounds.size\n }\n\n /**\n * Inserts or replaces an entry. Removes previous cell membership if the id existed.\n */\n insert(id: SpatialId, aabb: WorldRect): void {\n const existing = this.bounds.get(id)\n if (existing) this.removeFromCells(id, existing)\n this.bounds.set(id, aabb)\n for (const key of this.cellKeysFor(aabb)) {\n let cell = this.cells.get(key)\n if (!cell) {\n cell = new Set()\n this.cells.set(key, cell)\n }\n cell.add(id)\n }\n }\n\n /**\n * Removes an entry. No-op if id is unknown.\n */\n remove(id: SpatialId): void {\n const aabb = this.bounds.get(id)\n if (!aabb) return\n this.removeFromCells(id, aabb)\n this.bounds.delete(id)\n }\n\n /**\n * Returns the stored AABB for an id, if any.\n */\n getAABB(id: SpatialId): WorldRect | undefined {\n return this.bounds.get(id)\n }\n\n /**\n * Returns ids whose AABB intersects the query rect.\n * Broad-phase only — callers do narrow-phase per id.\n */\n queryRect(rect: WorldRect): SpatialId[] {\n const result = new Set<SpatialId>()\n for (const key of this.cellKeysFor(rect)) {\n const cell = this.cells.get(key)\n if (!cell) continue\n for (const id of cell) {\n const aabb = this.bounds.get(id)\n if (aabb && rectsIntersect(aabb, rect)) result.add(id)\n }\n }\n return [...result]\n }\n\n /**\n * Returns ids whose AABB contains the point.\n */\n queryPoint(p: Vec2): SpatialId[] {\n return this.queryRect({ x: p.x, y: p.y, w: 0, h: 0 })\n }\n\n /**\n * Empties the index. O(1) on the bookkeeping; the GC handles the rest.\n */\n clear(): void {\n this.cells.clear()\n this.bounds.clear()\n }\n\n /**\n * Yields the cell keys that an AABB covers.\n */\n private *cellKeysFor(aabb: WorldRect): IterableIterator<string> {\n const cs = this.cellSize\n const x0 = Math.floor(aabb.x / cs)\n const y0 = Math.floor(aabb.y / cs)\n const x1 = Math.floor((aabb.x + aabb.w) / cs)\n const y1 = Math.floor((aabb.y + aabb.h) / cs)\n for (let cy = y0; cy <= y1; cy++) {\n for (let cx = x0; cx <= x1; cx++) {\n yield `${cx},${cy}`\n }\n }\n }\n\n private removeFromCells(id: SpatialId, aabb: WorldRect): void {\n for (const key of this.cellKeysFor(aabb)) {\n const cell = this.cells.get(key)\n if (!cell) continue\n cell.delete(id)\n if (cell.size === 0) this.cells.delete(key)\n }\n }\n}\n","/**\n * Compute world-space AABB for a (possibly rotated) node.\n *\n * For axis-aligned nodes (angle === 0): the AABB is the node rect itself.\n * For rotated nodes: enclose the 4 rotated corners.\n */\nimport type { Node, Vec2, WorldRect } from '../types'\n\nexport const nodeAABB = (node: Node): WorldRect => {\n if (node.angle === 0) {\n return { x: node.x, y: node.y, w: node.w, h: node.h }\n }\n\n const cx = node.x + node.w / 2\n const cy = node.y + node.h / 2\n const cos = Math.cos(node.angle)\n const sin = Math.sin(node.angle)\n\n const corners: Vec2[] = [\n rotatePoint(node.x, node.y, cx, cy, cos, sin),\n rotatePoint(node.x + node.w, node.y, cx, cy, cos, sin),\n rotatePoint(node.x + node.w, node.y + node.h, cx, cy, cos, sin),\n rotatePoint(node.x, node.y + node.h, cx, cy, cos, sin),\n ]\n\n let minX = corners[0]!.x\n let minY = corners[0]!.y\n let maxX = minX\n let maxY = minY\n for (let i = 1; i < corners.length; i++) {\n const c = corners[i]!\n if (c.x < minX) minX = c.x\n if (c.x > maxX) maxX = c.x\n if (c.y < minY) minY = c.y\n if (c.y > maxY) maxY = c.y\n }\n return { x: minX, y: minY, w: maxX - minX, h: maxY - minY }\n}\n\nconst rotatePoint = (\n px: number,\n py: number,\n cx: number,\n cy: number,\n cos: number,\n sin: number,\n): Vec2 => {\n const dx = px - cx\n const dy = py - cy\n return { x: cx + dx * cos - dy * sin, y: cy + dx * sin + dy * cos }\n}\n","/**\n * Edge endpoint projection — see ARCHITECTURE.md §6.1.\n *\n * An EdgeEnd is either { nodeId, localOffset } (attached) or\n * { worldPoint } (free-floating). This module computes the current\n * world-space position of an endpoint by reading the latest node\n * state — no caching, no sync code; the projection is the truth.\n */\nimport { isAttached } from '../types'\nimport type { EdgeEnd, Node, NodeId, Vec2 } from '../types'\n\n/**\n * Resolves an EdgeEnd to its current world coordinates.\n * Returns null when the endpoint is attached to a node that no longer exists.\n */\nexport const projectEndToWorld = (\n end: EdgeEnd,\n getNode: (id: NodeId) => Node | undefined,\n): Vec2 | null => {\n if (!isAttached(end)) return end.worldPoint\n const node = getNode(end.nodeId)\n if (!node) return null\n return nodeLocalToWorld(end.localOffset, node)\n}\n\n/**\n * Transforms a point in a node's pre-rotation local frame (top-left origin)\n * into world coordinates.\n */\nexport const nodeLocalToWorld = (local: Vec2, node: Node): Vec2 => {\n if (node.angle === 0) {\n return { x: node.x + local.x, y: node.y + local.y }\n }\n const cx = node.x + node.w / 2\n const cy = node.y + node.h / 2\n const cos = Math.cos(node.angle)\n const sin = Math.sin(node.angle)\n const dx = local.x - node.w / 2\n const dy = local.y - node.h / 2\n return { x: cx + dx * cos - dy * sin, y: cy + dx * sin + dy * cos }\n}\n\n/**\n * Transforms a world point into the node's pre-rotation local frame.\n * Used by auto-clip and by edge-creation snap-to-boundary logic.\n */\nexport const worldToNodeLocal = (world: Vec2, node: Node): Vec2 => {\n if (node.angle === 0) {\n return { x: world.x - node.x, y: world.y - node.y }\n }\n const cx = node.x + node.w / 2\n const cy = node.y + node.h / 2\n const cos = Math.cos(-node.angle)\n const sin = Math.sin(-node.angle)\n const dx = world.x - cx\n const dy = world.y - cy\n return { x: dx * cos - dy * sin + node.w / 2, y: dx * sin + dy * cos + node.h / 2 }\n}\n\n/**\n * Given a world point and a node, returns the local-frame coords of the\n * nearest point on the node's rect boundary. If the world point is inside\n * the rect, projects to the nearest edge; if outside, clamps to the\n * containing edge / corner.\n *\n * Used by the edge-creation gesture to snap endpoints to the node boundary.\n */\nexport const projectToNodeBoundary = (world: Vec2, node: Node): Vec2 => {\n const local = worldToNodeLocal(world, node)\n const clampedX = Math.max(0, Math.min(node.w, local.x))\n const clampedY = Math.max(0, Math.min(node.h, local.y))\n\n const isOutside = local.x < 0 || local.x > node.w || local.y < 0 || local.y > node.h\n if (isOutside) return { x: clampedX, y: clampedY }\n\n // Inside: project to the nearest edge.\n const distLeft = local.x\n const distRight = node.w - local.x\n const distTop = local.y\n const distBottom = node.h - local.y\n const minDist = Math.min(distLeft, distRight, distTop, distBottom)\n if (minDist === distLeft) return { x: 0, y: clampedY }\n if (minDist === distRight) return { x: node.w, y: clampedY }\n if (minDist === distTop) return { x: clampedX, y: 0 }\n return { x: clampedX, y: node.h }\n}\n","/**\n * Auto-routing for bezier edges — see ARCHITECTURE.md §6.6.\n *\n * Unified rule: for each attached endpoint, cast a ray from the node\n * center toward the other endpoint and pick the side the ray exits\n * through. The bezier's control point at that end leaves along that\n * side's outward normal. Endpoints themselves stay at the user-supplied\n * localOffset; the renderer's clipSamples trims any inside-rect portion.\n *\n * Rotation-aware: side selection happens in each node's pre-rotation\n * local frame, then the normal is rotated back into world.\n */\nimport type { Node, Vec2 } from '../types'\nimport { worldToNodeLocal } from './project'\n\n/** Max world-space distance a control point can sit from its endpoint. */\nconst CONTROL_MAX = 200\n/** Fraction of endpoint-to-endpoint distance used for the control offset. */\nconst CONTROL_FRACTION = 0.4\n\nexport type Side = 'n' | 's' | 'e' | 'w'\n\n/**\n * Picks the side of a node's local rect closest to the given local offset.\n * Used to determine which way a bezier should leave the node.\n */\nexport const sideOf = (node: Node, localX: number, localY: number): Side => {\n const distLeft = localX\n const distRight = node.w - localX\n const distTop = localY\n const distBottom = node.h - localY\n const minDist = Math.min(distLeft, distRight, distTop, distBottom)\n if (minDist === distLeft) return 'w'\n if (minDist === distRight) return 'e'\n if (minDist === distTop) return 'n'\n return 's'\n}\n\n/**\n * Outward-pointing unit vector for a given side, in the node's pre-rotation\n * local frame.\n */\nexport const sideNormalLocal = (side: Side): Vec2 => {\n switch (side) {\n case 'n':\n return { x: 0, y: -1 }\n case 's':\n return { x: 0, y: 1 }\n case 'e':\n return { x: 1, y: 0 }\n case 'w':\n return { x: -1, y: 0 }\n }\n}\n\n/**\n * Rotates a local-frame vector into world coordinates by the node's angle.\n */\nexport const rotateVecByAngle = (v: Vec2, angle: number): Vec2 => {\n if (angle === 0) return v\n const cos = Math.cos(angle)\n const sin = Math.sin(angle)\n return { x: v.x * cos - v.y * sin, y: v.x * sin + v.y * cos }\n}\n\n/**\n * Computes auto-routed control points for a cubic bezier between\n * sourceWorld and targetWorld. Each control point is offset along the\n * outward normal of its endpoint's attached node (if any).\n *\n * For free-floating endpoints (no node), the control aligns with the\n * source→target direction so the curve degenerates gracefully toward a\n * straight line.\n */\nexport const autoRouteControls = (\n sourceWorld: Vec2,\n targetWorld: Vec2,\n sourceNormalWorld: Vec2 | null,\n targetNormalWorld: Vec2 | null,\n): { c1: Vec2; c2: Vec2 } => {\n const dx = targetWorld.x - sourceWorld.x\n const dy = targetWorld.y - sourceWorld.y\n const dist = Math.hypot(dx, dy)\n const offset = Math.min(CONTROL_MAX, CONTROL_FRACTION * dist)\n\n // Fallback direction when no node attached.\n const fallbackSource = dist > 0 ? { x: dx / dist, y: dy / dist } : { x: 1, y: 0 }\n const fallbackTarget = dist > 0 ? { x: -dx / dist, y: -dy / dist } : { x: -1, y: 0 }\n\n const ns = sourceNormalWorld ?? fallbackSource\n const nt = targetNormalWorld ?? fallbackTarget\n\n return {\n c1: { x: sourceWorld.x + ns.x * offset, y: sourceWorld.y + ns.y * offset },\n c2: { x: targetWorld.x + nt.x * offset, y: targetWorld.y + nt.y * offset },\n }\n}\n\n/**\n * Picks which side of {@link node}'s rect the line from the node's\n * center to {@link towardWorld} exits through. The bezier auto-route\n * uses this to choose each endpoint's outgoing direction: the control\n * leaves along the chosen side's outward normal.\n *\n * Rotation-aware: the ray is computed in the node's pre-rotation local\n * frame so a rotated rect still picks its locally-correct side.\n */\nexport const sideToward = (node: Node, towardWorld: Vec2): Side => {\n const local = worldToNodeLocal(towardWorld, node)\n const halfW = node.w / 2\n const halfH = node.h / 2\n const dx = local.x - halfW\n const dy = local.y - halfH\n if (dx === 0 && dy === 0) return 'e'\n const tx = dx === 0 ? Number.POSITIVE_INFINITY : (dx > 0 ? halfW : -halfW) / dx\n const ty = dy === 0 ? Number.POSITIVE_INFINITY : (dy > 0 ? halfH : -halfH) / dy\n if (tx <= ty) return dx > 0 ? 'e' : 'w'\n return dy > 0 ? 's' : 'n'\n}\n","import type { Node, Vec2 } from '../types'\n/**\n * Auto-clip: hide the part of an edge that's inside its attached nodes.\n * See ARCHITECTURE.md §6.5.\n *\n * For each end, transform the polyline samples into the attached node's\n * pre-rotation local frame (collapsing the rotated-rect problem to\n * axis-aligned). Walk samples from that endpoint outward; the first\n * sample outside the rect is the exit. Sub-pixel interpolate between\n * the last-inside and first-outside samples for a clean clip point.\n */\nimport { nodeLocalToWorld, worldToNodeLocal } from './project'\n\n/**\n * Result of clipping the polyline against the two attached-node rects.\n * `startIndex` / `endIndex` are sample indices; the visible polyline is\n * `[startPoint, samples[startIndex+1..endIndex-1], endPoint]`.\n * If both ends are free-floating (no attached node), returns the full range.\n */\nexport type ClipResult = {\n startIndex: number\n endIndex: number\n startPoint: Vec2\n endPoint: Vec2\n visible: boolean\n}\n\nexport const fullVisibleClipResult = (samples: Vec2[]): ClipResult => ({\n startIndex: 0,\n endIndex: samples.length - 1,\n startPoint: samples[0] ?? { x: 0, y: 0 },\n endPoint: samples[samples.length - 1] ?? { x: 0, y: 0 },\n visible: samples.length >= 2,\n})\n\n/**\n * Clips a polyline against (up to) two attached-node rects.\n * `sourceNode` / `targetNode` are the nodes the source/target endpoints\n * attach to (null for free-floating endpoints).\n */\nexport const clipSamples = (\n samples: Vec2[],\n sourceNode: Node | null,\n targetNode: Node | null,\n): ClipResult => {\n if (samples.length < 2) return fullVisibleClipResult(samples)\n\n let startIndex = 0\n let startPoint = samples[0]!\n if (sourceNode) {\n const trimmed = trimFromStart(samples, sourceNode)\n if (!trimmed) return { ...fullVisibleClipResult(samples), visible: false }\n startIndex = trimmed.index\n startPoint = trimmed.point\n }\n\n let endIndex = samples.length - 1\n let endPoint = samples[endIndex]!\n if (targetNode) {\n const trimmed = trimFromEnd(samples, targetNode)\n if (!trimmed) return { ...fullVisibleClipResult(samples), visible: false }\n endIndex = trimmed.index\n endPoint = trimmed.point\n }\n\n // Source clip is strictly after target clip → nothing visible (clips\n // crossed over each other; happens when nodes overlap and edge ends\n // are inside both).\n if (startIndex > endIndex) {\n return {\n startIndex,\n endIndex,\n startPoint,\n endPoint,\n visible: false,\n }\n }\n\n return { startIndex, endIndex, startPoint, endPoint, visible: true }\n}\n\n/**\n * Walks samples from index 0 outward, returns the exit point where the\n * polyline first leaves the node's local rect. Returns null if every\n * sample is inside the rect (edge fully consumed by the node).\n */\nconst trimFromStart = (samples: Vec2[], node: Node): { index: number; point: Vec2 } | null => {\n const localSamples = samples.map(p => worldToNodeLocal(p, node))\n // Find first \"outside\" sample after we've seen at least one \"inside\".\n let lastInside = -1\n for (let i = 0; i < localSamples.length; i++) {\n const p = localSamples[i]!\n if (isInsideLocalRect(p, node.w, node.h)) {\n lastInside = i\n } else if (lastInside >= 0) {\n // Transition: lastInside → i is the crossing segment.\n const crossingLocal = segmentRectExit(localSamples[lastInside]!, p, node.w, node.h)\n return {\n index: i,\n point: nodeLocalToWorld(crossingLocal, node),\n }\n }\n // First sample already outside → the source endpoint is outside its node.\n // That's normal for free-floating endpoints; for attached endpoints it\n // happens when the node is small and the endpoint is exactly on the edge.\n if (i === 0 && !isInsideLocalRect(p, node.w, node.h)) {\n return { index: 0, point: samples[0]! }\n }\n }\n // Every sample inside → nothing visible.\n return null\n}\n\n/**\n * Mirror of trimFromStart: walk from the end backwards.\n */\nconst trimFromEnd = (samples: Vec2[], node: Node): { index: number; point: Vec2 } | null => {\n const localSamples = samples.map(p => worldToNodeLocal(p, node))\n let lastInside = -1\n for (let i = localSamples.length - 1; i >= 0; i--) {\n const p = localSamples[i]!\n if (isInsideLocalRect(p, node.w, node.h)) {\n lastInside = i\n } else if (lastInside >= 0) {\n const crossingLocal = segmentRectExit(localSamples[lastInside]!, p, node.w, node.h)\n return {\n index: i,\n point: nodeLocalToWorld(crossingLocal, node),\n }\n }\n if (i === localSamples.length - 1 && !isInsideLocalRect(p, node.w, node.h)) {\n return { index: i, point: samples[i]! }\n }\n }\n return null\n}\n\n/**\n * Boolean: is a local-frame point inside the rect [0..w, 0..h]?\n * Allows a tiny inset epsilon so the \"first sample on the boundary\"\n * case behaves consistently.\n */\nconst isInsideLocalRect = (p: Vec2, w: number, h: number): boolean => {\n const eps = 1e-6\n return p.x >= -eps && p.x <= w + eps && p.y >= -eps && p.y <= h + eps\n}\n\n/**\n * Given a local-frame segment from `inside` to `outside`, find the exact\n * point where it exits the rect [0..w, 0..h]. Tests against all 4 edges\n * and picks the smallest t in (0, 1].\n */\nconst segmentRectExit = (inside: Vec2, outside: Vec2, w: number, h: number): Vec2 => {\n let bestT = 1\n const ts: number[] = []\n if (outside.x !== inside.x) {\n ts.push(crossEdge(inside.x, outside.x, 0, inside, outside, h, /* checkY */ true))\n ts.push(crossEdge(inside.x, outside.x, w, inside, outside, h, true))\n }\n if (outside.y !== inside.y) {\n ts.push(crossEdgeY(inside.y, outside.y, 0, inside, outside, w))\n ts.push(crossEdgeY(inside.y, outside.y, h, inside, outside, w))\n }\n for (const t of ts) {\n if (t > 0 && t <= 1 && t < bestT) bestT = t\n }\n return {\n x: inside.x + bestT * (outside.x - inside.x),\n y: inside.y + bestT * (outside.y - inside.y),\n }\n}\n\n/**\n * Tests crossing of a segment with a vertical edge at x=edgeX.\n * Returns the parametric t along the segment, or Infinity if the\n * y at that t is outside [0..h].\n */\nconst crossEdge = (\n ax: number,\n bx: number,\n edgeX: number,\n a: Vec2,\n b: Vec2,\n h: number,\n _checkY: boolean,\n): number => {\n if (ax === bx) return Number.POSITIVE_INFINITY\n const t = (edgeX - ax) / (bx - ax)\n if (t < 0 || t > 1) return Number.POSITIVE_INFINITY\n const y = a.y + t * (b.y - a.y)\n if (y < -1e-6 || y > h + 1e-6) return Number.POSITIVE_INFINITY\n return t\n}\n\n/**\n * Tests crossing of a segment with a horizontal edge at y=edgeY.\n */\nconst crossEdgeY = (ay: number, by: number, edgeY: number, a: Vec2, b: Vec2, w: number): number => {\n if (ay === by) return Number.POSITIVE_INFINITY\n const t = (edgeY - ay) / (by - ay)\n if (t < 0 || t > 1) return Number.POSITIVE_INFINITY\n const x = a.x + t * (b.x - a.x)\n if (x < -1e-6 || x > w + 1e-6) return Number.POSITIVE_INFINITY\n return t\n}\n","/**\n * Edge AABB from samples — see ARCHITECTURE.md §6.12.\n *\n * Phase-1 had a crude AABB based on raw endpoint positions. Phase 4\n * computes the actual sample bounds + padding for arrowheads and labels,\n * which is what the spatial index needs for correct hit-testing.\n */\nimport type { Vec2, WorldRect } from '../types'\n\n/** Extra padding around sample bounds to cover arrowhead tips. */\nconst SAMPLE_PADDING = 12\n\nexport const edgeAABBFromSamples = (samples: Vec2[]): WorldRect => {\n if (samples.length === 0) return { x: 0, y: 0, w: 0, h: 0 }\n let minX = Number.POSITIVE_INFINITY\n let minY = Number.POSITIVE_INFINITY\n let maxX = Number.NEGATIVE_INFINITY\n let maxY = Number.NEGATIVE_INFINITY\n for (const p of samples) {\n if (p.x < minX) minX = p.x\n if (p.x > maxX) maxX = p.x\n if (p.y < minY) minY = p.y\n if (p.y > maxY) maxY = p.y\n }\n return {\n x: minX - SAMPLE_PADDING,\n y: minY - SAMPLE_PADDING,\n w: maxX - minX + SAMPLE_PADDING * 2,\n h: maxY - minY + SAMPLE_PADDING * 2,\n }\n}\n","/**\n * Curve sampling — see ARCHITECTURE.md §6.6 / §6.9.\n *\n * The polyline samples are the load-bearing data for everything edge-related:\n * paint, auto-clip, hit testing all walk the same array. Caching is in\n * cache.ts; this module is pure geometry.\n */\nimport type { PathStyle, Vec2 } from '../types'\n\n/** Default number of intermediate samples for a bezier (cubic). 32 is\n * indistinguishable from 64 at typical zoom; halve the array size. */\nexport const BEZIER_SEGMENTS = 32\n\n/**\n * Evaluates a cubic bezier at parameter t ∈ [0, 1].\n */\nexport const cubicBezier = (p0: Vec2, c1: Vec2, c2: Vec2, p1: Vec2, t: number): Vec2 => {\n const it = 1 - t\n const it2 = it * it\n const it3 = it2 * it\n const t2 = t * t\n const t3 = t2 * t\n return {\n x: it3 * p0.x + 3 * it2 * t * c1.x + 3 * it * t2 * c2.x + t3 * p1.x,\n y: it3 * p0.y + 3 * it2 * t * c1.y + 3 * it * t2 * c2.y + t3 * p1.y,\n }\n}\n\n/**\n * Tangent (unit vector) to a cubic bezier at parameter t.\n * Used for arrowhead orientation.\n */\nexport const cubicBezierTangent = (p0: Vec2, c1: Vec2, c2: Vec2, p1: Vec2, t: number): Vec2 => {\n const it = 1 - t\n const it2 = it * it\n const t2 = t * t\n // derivative of cubic bezier\n const dx = 3 * (it2 * (c1.x - p0.x) + 2 * it * t * (c2.x - c1.x) + t2 * (p1.x - c2.x))\n const dy = 3 * (it2 * (c1.y - p0.y) + 2 * it * t * (c2.y - c1.y) + t2 * (p1.y - c2.y))\n const len = Math.hypot(dx, dy)\n if (len === 0) return { x: 1, y: 0 }\n return { x: dx / len, y: dy / len }\n}\n\n/**\n * Samples a cubic bezier into BEZIER_SEGMENTS+1 evenly-spaced points\n * (in parameter space — not arc-length).\n */\nexport const sampleBezier = (\n p0: Vec2,\n c1: Vec2,\n c2: Vec2,\n p1: Vec2,\n segments: number = BEZIER_SEGMENTS,\n): Vec2[] => {\n const points: Vec2[] = new Array(segments + 1)\n for (let i = 0; i <= segments; i++) {\n const t = i / segments\n points[i] = cubicBezier(p0, c1, c2, p1, t)\n }\n return points\n}\n\n/**\n * Returns the polyline sample list for an edge given its path style,\n * world-projected endpoints, and (for bezier) control points or (for\n * polyline) midpoints. Straight = 2-point polyline.\n */\nexport const samplesFor = (\n pathStyle: PathStyle,\n source: Vec2,\n target: Vec2,\n controls: Vec2[] | undefined,\n): Vec2[] => {\n switch (pathStyle) {\n case 'straight':\n return [source, target]\n case 'polyline':\n return [source, ...(controls ?? []), target]\n case 'bezier': {\n const c1 = controls?.[0] ?? source\n const c2 = controls?.[1] ?? target\n return sampleBezier(source, c1, c2, target)\n }\n }\n}\n\n/**\n * Tangent at parameter t along the sampled polyline (arc-length-ish).\n * Used for arrowhead orientation when we don't have analytic curve info.\n * For straight/polyline this returns the segment direction; for bezier\n * we approximate by the direction between adjacent samples around the\n * target t.\n */\nexport const tangentAtArcLength = (samples: Vec2[], t: number): Vec2 => {\n if (samples.length < 2) return { x: 1, y: 0 }\n // Walk arc length to find the segment containing the target distance.\n const totalLengths: number[] = [0]\n let total = 0\n for (let i = 1; i < samples.length; i++) {\n const a = samples[i - 1]!\n const b = samples[i]!\n total += Math.hypot(b.x - a.x, b.y - a.y)\n totalLengths.push(total)\n }\n const target = total * Math.max(0, Math.min(1, t))\n let segIndex = 1\n for (; segIndex < totalLengths.length; segIndex++) {\n if (totalLengths[segIndex]! >= target) break\n }\n segIndex = Math.min(segIndex, samples.length - 1)\n const a = samples[segIndex - 1]!\n const b = samples[segIndex]!\n const dx = b.x - a.x\n const dy = b.y - a.y\n const len = Math.hypot(dx, dy)\n if (len === 0) return { x: 1, y: 0 }\n return { x: dx / len, y: dy / len }\n}\n","import type { Node, Vec2 } from '../types'\n/**\n * Self-loop case — see ARCHITECTURE.md §6.8.\n *\n * When source.nodeId === target.nodeId, the regular bezier between two\n * coincident points collapses. Generate a small loop on the top-right\n * corner instead: exit the top edge, arc outward, re-enter via the\n * right edge.\n */\nimport { autoRouteControls, rotateVecByAngle, sideNormalLocal } from './auto-route'\nimport { nodeLocalToWorld } from './project'\nimport { sampleBezier } from './samples'\n\n/** World-space loop radius factor based on max(w, h). */\nconst LOOP_SIZE_FRACTION = 0.6\n\n/**\n * Returns world-space (source, target, control1, control2) for a self-loop\n * on the given node. The loop exits from the top edge and re-enters via\n * the right edge.\n */\nexport const selfLoopGeometry = (\n node: Node,\n): { source: Vec2; target: Vec2; controls: [Vec2, Vec2] } => {\n const topAnchor = nodeLocalToWorld({ x: node.w / 2, y: 0 }, node)\n const rightAnchor = nodeLocalToWorld({ x: node.w, y: node.h / 2 }, node)\n const sourceNormal = rotateVecByAngle(sideNormalLocal('n'), node.angle)\n const targetNormal = rotateVecByAngle(sideNormalLocal('e'), node.angle)\n const offset = LOOP_SIZE_FRACTION * Math.max(node.w, node.h)\n const { c1, c2 } = autoRouteControlsAtOffset(\n topAnchor,\n rightAnchor,\n sourceNormal,\n targetNormal,\n offset,\n )\n return { source: topAnchor, target: rightAnchor, controls: [c1, c2] }\n}\n\n/**\n * Samples a self-loop given its node. Convenience wrapper that produces\n * the polyline samples auto-clip/hit-test/paint all consume.\n */\nexport const sampleSelfLoop = (node: Node): Vec2[] => {\n const { source, target, controls } = selfLoopGeometry(node)\n return sampleBezier(source, controls[0], controls[1], target)\n}\n\n/**\n * Like autoRouteControls but with an explicit offset; the loop wants a\n * larger control distance than the natural endpoint-distance formula\n * (which would be near-zero for coincident endpoints).\n */\nconst autoRouteControlsAtOffset = (\n source: Vec2,\n target: Vec2,\n sourceNormal: Vec2,\n targetNormal: Vec2,\n offset: number,\n): { c1: Vec2; c2: Vec2 } => {\n void autoRouteControls // (keep type linker happy if the helper isn't used)\n return {\n c1: { x: source.x + sourceNormal.x * offset, y: source.y + sourceNormal.y * offset },\n c2: { x: target.x + targetNormal.x * offset, y: target.y + targetNormal.y * offset },\n }\n}\n","/**\n * Edge geometry cache — see ARCHITECTURE.md §6.12.\n *\n * Stores per-edge sampled polylines + AABB, indexed by an opaque \"version\"\n * string derived from inputs (endpoints, controls, pathStyle, attached\n * node positions/angles/sizes). Cache invalidates implicitly when the\n * version key changes — no explicit deletes needed; we just refetch.\n *\n * For the renderer this means: edges paint in O(samples) per frame\n * after the first miss; sampling cost is paid only when geometry truly\n * changes. Phase-1's incidentEdges map drives \"moving node → its edges\n * version changes\" propagation.\n */\nimport { isAttached } from '../types'\nimport type { Edge, EdgeId, Node, NodeId, Vec2, WorldRect } from '../types'\nimport { edgeAABBFromSamples } from './aabb'\nimport { autoRouteControls, rotateVecByAngle, sideNormalLocal, sideToward } from './auto-route'\nimport { projectEndToWorld } from './project'\nimport { samplesFor } from './samples'\nimport { sampleSelfLoop } from './self-loop'\n\nexport type EdgeGeometry = {\n /** Endpoint world positions (post-projection, pre-clip). */\n source: Vec2\n target: Vec2\n /** Polyline samples for paint / hit-test / clip. */\n samples: Vec2[]\n /** AABB enclosing samples (padded for arrowheads). */\n aabb: WorldRect\n /** Whether the edge is a self-loop (source.nodeId === target.nodeId). */\n isSelfLoop: boolean\n /** Source/target attached node IDs (or null). Used by paint to clip. */\n sourceNodeId: NodeId | null\n targetNodeId: NodeId | null\n}\n\n/**\n * Computes edge geometry from current node state. No caching — callers\n * memoize on a version key (see makeEdgeVersion).\n */\nexport const computeEdgeGeometry = (\n edge: Edge,\n getNode: (id: NodeId) => Node | undefined,\n): EdgeGeometry | null => {\n const sourceNode = isAttached(edge.source) ? (getNode(edge.source.nodeId) ?? null) : null\n const targetNode = isAttached(edge.target) ? (getNode(edge.target.nodeId) ?? null) : null\n const sourceNodeId = sourceNode ? sourceNode.id : null\n const targetNodeId = targetNode ? targetNode.id : null\n\n // Self-loop shortcut.\n if (sourceNodeId && sourceNodeId === targetNodeId && sourceNode) {\n const samples = sampleSelfLoop(sourceNode)\n return {\n source: samples[0]!,\n target: samples[samples.length - 1]!,\n samples,\n aabb: edgeAABBFromSamples(samples),\n isSelfLoop: true,\n sourceNodeId,\n targetNodeId,\n }\n }\n\n const sourceWorld = projectEndToWorld(edge.source, getNode)\n const targetWorld = projectEndToWorld(edge.target, getNode)\n if (!sourceWorld || !targetWorld) return null\n\n let samples: Vec2[]\n if (edge.pathStyle === 'bezier') {\n let c1: Vec2\n let c2: Vec2\n if (edge.control && edge.control.length >= 2) {\n // User-controlled bezier (midpoint drag, explicit control). The\n // endpoints stay at their projected positions; clipSamples trims\n // the in-node portions on the renderer side.\n c1 = edge.control[0]!\n c2 = edge.control[1]!\n } else {\n // Unified auto-route: each attached endpoint's control leaves\n // along the outward normal of the side the source→target line\n // exits through. Endpoints stay at the user-supplied localOffset\n // — clipSamples handles hiding any inside-rect portion.\n const sourceNormal = sourceNode\n ? rotateVecByAngle(sideNormalLocal(sideToward(sourceNode, targetWorld)), sourceNode.angle)\n : null\n const targetNormal = targetNode\n ? rotateVecByAngle(sideNormalLocal(sideToward(targetNode, sourceWorld)), targetNode.angle)\n : null\n ;({ c1, c2 } = autoRouteControls(sourceWorld, targetWorld, sourceNormal, targetNormal))\n }\n samples = samplesFor('bezier', sourceWorld, targetWorld, [c1, c2])\n } else {\n samples = samplesFor(edge.pathStyle, sourceWorld, targetWorld, edge.control)\n }\n\n return {\n source: sourceWorld,\n target: targetWorld,\n samples,\n aabb: edgeAABBFromSamples(samples),\n isSelfLoop: false,\n sourceNodeId,\n targetNodeId,\n }\n}\n\n/**\n * Cache wrapper: stores last-computed geometry per edge id, keyed by an\n * integer version supplied by the caller. The store maintains the version\n * counter and bumps it on geometry-affecting mutations (edge.update or\n * incident node moves), so this cache becomes a pure integer-compare.\n *\n * Earlier versions of this file used a `toFixed(2)`-built string version\n * to detect changes implicitly. That allocated ~14 strings per edge per\n * paint and cost ~5-8ms at 2k visible edges. Explicit integer versioning\n * eliminates that entirely.\n */\nexport class EdgeGeometryCache {\n private readonly entries = new Map<EdgeId, { version: number; geom: EdgeGeometry }>()\n\n /**\n * Returns the cached geometry if `version` matches the cache entry;\n * otherwise recomputes via `computeEdgeGeometry`, stores, and returns.\n * Caller is responsible for passing the current store-managed version.\n */\n get(edge: Edge, version: number, getNode: (id: NodeId) => Node | undefined): EdgeGeometry | null {\n const cached = this.entries.get(edge.id)\n if (cached && cached.version === version) return cached.geom\n const geom = computeEdgeGeometry(edge, getNode)\n if (geom) this.entries.set(edge.id, { version, geom })\n else this.entries.delete(edge.id)\n return geom\n }\n\n delete(id: EdgeId): void {\n this.entries.delete(id)\n }\n\n clear(): void {\n this.entries.clear()\n }\n}\n","import type { Vec2 } from '../types'\n\n/**\n * Returns `{ point, tangent }` at fractional arc-length `t ∈ [0..1]`\n * along a sample polyline.\n *\n * Walks the polyline summing segment lengths until the target is\n * reached; linearly interpolates inside the last segment. The tangent\n * is the unit direction of that segment.\n *\n * Used by edge-label placement (see ARCHITECTURE.md §6.11) — labels at\n * arc-length 0.5 sit at the geometric midpoint regardless of curve\n * shape, and the tangent lets a label rotate to follow the edge.\n *\n * @example\n * const { point, tangent } = getPointAndTangentAtArcLength(geom.samples, 0.5)\n * ctx.translate(point.x, point.y)\n */\nexport const getPointAndTangentAtArcLength = (\n samples: readonly Vec2[],\n t: number,\n): { point: Vec2; tangent: Vec2 } => {\n if (samples.length < 2) {\n const p = samples[0] ?? { x: 0, y: 0 }\n return { point: p, tangent: { x: 1, y: 0 } }\n }\n const clamped = Math.max(0, Math.min(1, t))\n\n // First pass: total length.\n let total = 0\n for (let i = 1; i < samples.length; i++) {\n const a = samples[i - 1]!\n const b = samples[i]!\n total += Math.hypot(b.x - a.x, b.y - a.y)\n }\n if (total === 0) {\n const p = samples[0]!\n return { point: p, tangent: { x: 1, y: 0 } }\n }\n const target = clamped * total\n\n // Second pass: walk until we hit the target.\n let traveled = 0\n for (let i = 1; i < samples.length; i++) {\n const a = samples[i - 1]!\n const b = samples[i]!\n const segLen = Math.hypot(b.x - a.x, b.y - a.y)\n if (segLen === 0) continue\n if (traveled + segLen >= target) {\n const local = (target - traveled) / segLen\n return {\n point: { x: a.x + (b.x - a.x) * local, y: a.y + (b.y - a.y) * local },\n tangent: { x: (b.x - a.x) / segLen, y: (b.y - a.y) / segLen },\n }\n }\n traveled += segLen\n }\n // Fell off the end (t === 1 case).\n const last = samples[samples.length - 1]!\n const prev = samples[samples.length - 2]!\n const segLen = Math.hypot(last.x - prev.x, last.y - prev.y) || 1\n return {\n point: last,\n tangent: { x: (last.x - prev.x) / segLen, y: (last.y - prev.y) / segLen },\n }\n}\n","import type { Vec2 } from '../types'\n\n/**\n * Converts a single midpoint `P` (the point the user dragged the\n * bezier midpoint handle to) into a pair of cubic control points\n * `(c1, c2)` such that the resulting cubic **passes through `P` at\n * t = 0.5**.\n *\n * Math: a cubic Bezier with endpoints S, T and controls c1, c2 has\n *\n * B(0.5) = (1/8) · S + (3/8) · c1 + (3/8) · c2 + (1/8) · T\n *\n * Solving for c1 + c2 when B(0.5) = P:\n *\n * c1 + c2 = (8P − S − T) / 3\n *\n * One equation, two unknowns. The convention here: split symmetrically\n * (c1 = c2). That keeps the curve smooth and predictable for the user.\n * A two-handle form (c1 / c2 draggable independently) is the v1.x\n * follow-up.\n */\nexport const midpointToCubicControls = (\n source: Vec2,\n midpoint: Vec2,\n target: Vec2,\n): { c1: Vec2; c2: Vec2 } => {\n const c = {\n x: (8 * midpoint.x - source.x - target.x) / 6,\n y: (8 * midpoint.y - source.y - target.y) / 6,\n }\n return { c1: c, c2: { ...c } }\n}\n","/**\n * Arrowheads — see ARCHITECTURE.md §6.5 + §3.4 (4 styles).\n *\n * The arrowhead sits at the clipped endpoint of the edge; its direction\n * comes from the curve's tangent at that arc-length position. We draw\n * in world coords so the strokeWidth follows the camera transform —\n * scale of strokeWidth/scale gives a constant-screen-px width.\n */\nimport type { Arrowhead, Vec2 } from '../types'\n\n/** Arrow length in world units at zoom 1; scales with strokeWidth. */\nconst ARROW_BASE_LENGTH = 12\nconst ARROW_BASE_WIDTH = 8\n\n/**\n * Draws an arrowhead at the given world tip, pointing toward `tipDir`\n * (the unit tangent direction at that point — pointing FROM the curve\n * INTO the tip).\n */\nexport const drawArrowhead = (\n ctx: CanvasRenderingContext2D,\n kind: Arrowhead,\n tip: Vec2,\n tipDir: Vec2,\n strokeColor: string,\n strokeWidth: number,\n): void => {\n if (kind === 'none') return\n\n // Scale arrowhead with stroke width so styling stays consistent.\n const scale = Math.max(1, strokeWidth / 2)\n const len = ARROW_BASE_LENGTH * scale\n const half = (ARROW_BASE_WIDTH / 2) * scale\n\n // Perpendicular to tipDir (rotate 90° ccw).\n const px = -tipDir.y\n const py = tipDir.x\n\n // Two base corners of the arrowhead triangle.\n const baseCenter: Vec2 = { x: tip.x - tipDir.x * len, y: tip.y - tipDir.y * len }\n const left: Vec2 = { x: baseCenter.x + px * half, y: baseCenter.y + py * half }\n const right: Vec2 = { x: baseCenter.x - px * half, y: baseCenter.y - py * half }\n\n ctx.save()\n if (kind === 'arrow') {\n // Two short strokes from the tip back along the curve direction.\n ctx.strokeStyle = strokeColor\n ctx.lineWidth = strokeWidth\n ctx.lineCap = 'round'\n ctx.lineJoin = 'round'\n ctx.beginPath()\n ctx.moveTo(left.x, left.y)\n ctx.lineTo(tip.x, tip.y)\n ctx.lineTo(right.x, right.y)\n ctx.stroke()\n } else if (kind === 'arrow-filled') {\n ctx.fillStyle = strokeColor\n ctx.beginPath()\n ctx.moveTo(tip.x, tip.y)\n ctx.lineTo(left.x, left.y)\n ctx.lineTo(right.x, right.y)\n ctx.closePath()\n ctx.fill()\n } else if (kind === 'barb') {\n // Open arrow with the base barbed inward (a notched chevron).\n const notch: Vec2 = {\n x: baseCenter.x + tipDir.x * len * 0.35,\n y: baseCenter.y + tipDir.y * len * 0.35,\n }\n ctx.strokeStyle = strokeColor\n ctx.lineWidth = strokeWidth\n ctx.lineCap = 'round'\n ctx.lineJoin = 'round'\n ctx.fillStyle = strokeColor\n ctx.beginPath()\n ctx.moveTo(tip.x, tip.y)\n ctx.lineTo(left.x, left.y)\n ctx.lineTo(notch.x, notch.y)\n ctx.lineTo(right.x, right.y)\n ctx.closePath()\n ctx.fill()\n }\n ctx.restore()\n}\n\n/**\n * World-space length added to the visible arrowhead at a given stroke\n * width. Used to know how much to shorten the curve's visible portion\n * so the line tail doesn't poke through the arrowhead tip.\n */\nexport const arrowheadLength = (kind: Arrowhead, strokeWidth: number): number => {\n if (kind === 'none') return 0\n const scale = Math.max(1, strokeWidth / 2)\n return ARROW_BASE_LENGTH * scale\n}\n","import type { RoughDrawableLike } from './loader'\n\n/**\n * Bounded LRU cache of rough.js drawables keyed by shape signature.\n *\n * Building a drawable (`rc.generator.path(...)`) walks the SVG path\n * and emits jittered sub-paths — that's the expensive bit. Once built,\n * `rc.draw(drawable)` just strokes the cached path; cheap.\n *\n * Cache key composes all inputs that affect the generated path:\n * - primitive (rect / ellipse / diamond / capsule / edge)\n * - size + corner radius\n * - stroke color / style / width\n * - roughness + seed (jitter inputs)\n * - LOD bucket (curveStepCount, maxRandomnessOffset)\n *\n * On miss we build + insert; on overflow we evict the oldest entry.\n */\n\nconst cache = new Map<string, RoughDrawableLike>()\nconst MAX_ENTRIES = 1000\n\n/** Read-or-build for a drawable. `build` runs only on miss. */\nexport const getOrBuildDrawable = (\n key: string,\n build: () => RoughDrawableLike,\n): RoughDrawableLike => {\n const hit = cache.get(key)\n if (hit !== undefined) {\n // Touch — move to end (LRU).\n cache.delete(key)\n cache.set(key, hit)\n return hit\n }\n const drawable = build()\n if (cache.size >= MAX_ENTRIES) {\n // Evict oldest.\n const first = cache.keys().next().value\n if (first !== undefined) cache.delete(first)\n }\n cache.set(key, drawable)\n return drawable\n}\n\n/** Test / debug aid. */\nexport const clearRoughCache = (): void => {\n cache.clear()\n}\n\n/** Test / debug aid. */\nexport const getRoughCacheSize = (): number => cache.size\n\n/**\n * FNV-1a hash of a string id → 32-bit unsigned int. Used to derive\n * a stable per-node jitter seed so the wobble doesn't dance between\n * frames or sessions.\n */\nexport const seedFromId = (id: string): number => {\n let hash = 2166136261\n for (let i = 0; i < id.length; i += 1) {\n hash ^= id.charCodeAt(i)\n hash = Math.imul(hash, 16777619)\n }\n return hash >>> 0\n}\n","/**\n * Built-in style defaults — see ARCHITECTURE.md §3.4.\n *\n * Each render call resolves style via:\n * 1. node.style[token] if set\n * 2. theme(token) if a theme resolver is provided\n * 3. the value here\n */\nimport type { Style } from '../../types'\n\nexport const DEFAULT_STYLE: Required<\n Pick<\n Style,\n 'strokeColor' | 'strokeWidth' | 'strokeStyle' | 'backgroundColor' | 'opacity' | 'roundness'\n >\n> = {\n strokeColor: '#1f2937',\n strokeWidth: 2,\n strokeStyle: 'solid',\n backgroundColor: '#dbeafe',\n opacity: 100,\n roundness: 2,\n}\n\n/**\n * Resolves a style field with the precedence above.\n * `theme` lookup is optional and returns `undefined` if no override.\n *\n * Stable token catalog (consumer maps these to its design system):\n * - `strokeColor` edge + shape stroke\n * - `strokeWidth` shape + edge stroke width\n * - `backgroundColor` shape fill\n * - `textColor` shape text color\n * - `opacity` shape opacity (0-100)\n * - `selection.outline` selection outline color (overlay)\n * - `handle.fill` resize/rotate handle fill\n * - `handle.stroke` resize/rotate handle stroke\n * - `text.highlight` markdown ==highlight== chip color\n * - `text.codeBackground` markdown `code` chip color\n *\n * Tokens not in this list are passed through unchanged; consumers can\n * extend with their own (e.g. `node.shadow.color`).\n */\nexport type ThemeResolver = (token: string) => string | number | undefined\n\nexport const resolveColor = (\n style: Style | undefined,\n key: 'strokeColor' | 'backgroundColor' | 'textColor',\n fallback: string,\n theme?: ThemeResolver,\n): string => {\n const fromStyle = style?.[key]\n if (typeof fromStyle === 'string') return fromStyle\n const fromTheme = theme?.(key)\n if (typeof fromTheme === 'string') return fromTheme\n return fallback\n}\n\nexport const resolveStrokeWidth = (style: Style | undefined, theme?: ThemeResolver): number => {\n if (typeof style?.strokeWidth === 'number') return style.strokeWidth\n const fromTheme = theme?.('strokeWidth')\n if (typeof fromTheme === 'number') return fromTheme\n return DEFAULT_STYLE.strokeWidth\n}\n\nexport const resolveOpacity = (style: Style | undefined, theme?: ThemeResolver): number => {\n if (typeof style?.opacity === 'number') return style.opacity / 100\n const fromTheme = theme?.('opacity')\n if (typeof fromTheme === 'number') return fromTheme / 100\n return DEFAULT_STYLE.opacity / 100\n}\n\n/**\n * Returns true if a color string represents a fully-transparent paint —\n * either the literal `'transparent'` keyword or a hex with alpha 00.\n * Used everywhere we early-out on invisible fills/strokes.\n */\nexport const isFullyTransparent = (color: string): boolean => {\n if (color === 'transparent') return true\n if (color.length === 9 && color.startsWith('#') && color.slice(7, 9).toLowerCase() === '00')\n return true\n if (color.length === 5 && color.startsWith('#') && color[4] === '0') return true\n return false\n}\n\n/**\n * Maps the `strokeStyle` token to a canvas `setLineDash` argument.\n * Width-aware so dashes look right at different stroke widths.\n */\nexport const dashPatternFor = (\n strokeStyle: Style['strokeStyle'] | undefined,\n width: number,\n): number[] => {\n switch (strokeStyle) {\n case 'dashed':\n // Gap longer than dash so the pattern still reads as dashed when\n // rough.js's wobble + bowing eat into the gap on curved edges.\n // Previous 5:4 ratio (dash > gap) looked nearly continuous in\n // rough mode because the wobble closed the gaps.\n return [width * 3, width * 5]\n case 'dotted':\n // Small visible dot + generous gap. Non-zero dash so the pattern\n // also renders under default `butt` linecap (node strokes don't\n // override lineCap; the edge path sets `round` already). Gap is\n // tuned for the same wobble-survives-curvature reason as dashed.\n return [width * 1.5, width * 4]\n default:\n return []\n }\n}\n","/**\n * Lite-markdown tokenizer — ported verbatim from\n * `dim0/webui/src/components/markdown/canvas-lite-markdown.tsx`.\n *\n * The vocabulary is deliberately small: bold, italic, underline, strike,\n * highlight, inline code, links, fenced code blocks, hr lines. No\n * nesting, no escapes — single-pass regex tokenization keeps layout\n * fast at scale. See ARCHITECTURE.md §8.\n */\nexport type InlineType =\n | 'text'\n | 'bold'\n | 'italic'\n | 'underline'\n | 'strike'\n | 'highlight'\n | 'code'\n | 'link'\n /**\n * LaTeX math expression, content is the source between `$$...$$` (no\n * line breaks). Rendered via MathJax SVG output and rasterized to an\n * inline bitmap at paint time. See `text/math/`. Double-dollar\n * delimiters avoid the false-positives of single `$` in prose that\n * mentions currency (e.g. `$5 to $10`).\n */\n | 'math'\n\nexport type Token =\n | { type: InlineType; content: string }\n | { type: 'code-block'; content: string }\n | { type: 'br' }\n | { type: 'hr' }\n | { type: 'hr-double' }\n\n// Math `$$...$$` is matched first so its delimiters can't be confused\n// with italics (`*...*` etc.). Single `$` is treated as literal text —\n// avoids false-positives in prose mentioning currency (`$5 to $10`).\n// Empty math (`$$$$`) is intentionally not matched; lazy `+?` requires\n// at least one interior char.\nconst INLINE_PATTERN =\n /(\\$\\$[^\\n]+?\\$\\$|\\*\\*[^*]+\\*\\*|==[^=\\s](?:[^=]*?[^=\\s])?==|`[^`]+`|\\*[^*]+\\*|__[^_]+__|~~[^~]+~~|_[^_]+_|\\[[^\\]]+\\]\\([^)]+\\))/g\nconst HR_LINE_PATTERN = /^[ \\t]*---[ \\t]*$/\nconst DOUBLE_HR_LINE_PATTERN = /^[ \\t]*===[ \\t]*$/\n\n/**\n * Normalizes quick symbol shorthand to unicode glyphs before tokenization.\n */\nconst transformSymbols = (value: string) =>\n value.replace(/<=>|<->|<-|->|\\[\\]|\\[[vx]\\]/gi, match => {\n const normalized = match.toLowerCase()\n if (normalized === '->') return '→'\n if (normalized === '<-') return '←'\n if (normalized === '<->') return '↔'\n if (normalized === '<=>') return '⇔'\n if (normalized === '[]') return '☐'\n if (normalized === '[v]') return '✅'\n if (normalized === '[x]') return '❎'\n return match\n })\n\n/**\n * Tokenizes one line's inline content.\n */\nconst tokenizeInline = (segment: string): Token[] => {\n if (!segment) return []\n const tokens: Token[] = []\n let lastIndex = 0\n\n segment.replace(INLINE_PATTERN, (match, _group, offset) => {\n const idx = offset as number\n if (idx > lastIndex) {\n tokens.push({ type: 'text', content: transformSymbols(segment.slice(lastIndex, idx)) })\n }\n\n if (\n (match.startsWith('**') && match.endsWith('**')) ||\n (match.startsWith('__') && match.endsWith('__'))\n ) {\n tokens.push({ type: 'bold', content: transformSymbols(match.slice(2, -2)) })\n } else if (match.startsWith('*') && match.endsWith('*')) {\n tokens.push({ type: 'italic', content: transformSymbols(match.slice(1, -1)) })\n } else if (match.startsWith('~~') && match.endsWith('~~')) {\n tokens.push({ type: 'strike', content: transformSymbols(match.slice(2, -2)) })\n } else if (match.startsWith('==') && match.endsWith('==')) {\n tokens.push({ type: 'highlight', content: transformSymbols(match.slice(2, -2)) })\n } else if (match.startsWith('_') && match.endsWith('_')) {\n tokens.push({ type: 'underline', content: transformSymbols(match.slice(1, -1)) })\n } else if (match.startsWith('[') && match.includes('](') && match.endsWith(')')) {\n const splitIndex = match.indexOf('](')\n tokens.push({ type: 'link', content: transformSymbols(match.slice(1, splitIndex)) })\n } else if (match.startsWith('`') && match.endsWith('`')) {\n tokens.push({ type: 'code', content: match.slice(1, -1) })\n } else if (match.startsWith('$$') && match.endsWith('$$')) {\n // Strip the `$$...$$` delimiters; preserve interior whitespace\n // since LaTeX is whitespace-aware.\n tokens.push({ type: 'math', content: match.slice(2, -2) })\n } else {\n tokens.push({ type: 'text', content: transformSymbols(match) })\n }\n\n lastIndex = idx + match.length\n return match\n })\n\n if (lastIndex < segment.length) {\n tokens.push({ type: 'text', content: transformSymbols(segment.slice(lastIndex)) })\n }\n\n return tokens\n}\n\n/**\n * Tokenizes one line including hr / hr-double sentinels.\n */\nconst tokenizeLine = (line: string): Token[] => {\n if (DOUBLE_HR_LINE_PATTERN.test(line)) return [{ type: 'hr-double' }]\n if (HR_LINE_PATTERN.test(line)) return [{ type: 'hr' }]\n return tokenizeInline(line)\n}\n\n/**\n * Tokenizes plain-text sections (outside fenced code blocks) line by line.\n */\nconst tokenizeTextBlock = (block: string): Token[] => {\n if (!block) return []\n const tokens: Token[] = []\n const lines = block.split('\\n')\n lines.forEach((line, index) => {\n const lineTokens = tokenizeLine(line)\n tokens.push(...lineTokens)\n const isRuleLine =\n lineTokens.length === 1 &&\n (lineTokens[0]?.type === 'hr' || lineTokens[0]?.type === 'hr-double')\n if (index < lines.length - 1 && !isRuleLine) tokens.push({ type: 'br' })\n })\n return tokens\n}\n\n/**\n * Full markdown tokenizer with fenced code-block support. Code blocks\n * are display-only (no language badge / syntax highlighting).\n */\nexport const tokenize = (input: string): Token[] => {\n if (!input) return []\n const tokens: Token[] = []\n let cursor = 0\n\n while (cursor < input.length) {\n const fenceStart = input.indexOf('```', cursor)\n if (fenceStart === -1) {\n tokens.push(...tokenizeTextBlock(input.slice(cursor)))\n break\n }\n\n if (fenceStart > cursor) {\n tokens.push(...tokenizeTextBlock(input.slice(cursor, fenceStart)))\n }\n\n const fenceEnd = input.indexOf('```', fenceStart + 3)\n if (fenceEnd === -1) {\n tokens.push(...tokenizeTextBlock(input.slice(fenceStart)))\n break\n }\n\n const fenceContent = input.slice(fenceStart + 3, fenceEnd)\n const delimiterIndex = fenceContent.search(/[\\r\\n]/)\n let codeContent = fenceContent\n if (delimiterIndex >= 0) {\n codeContent = fenceContent.slice(delimiterIndex).replace(/^\\r?\\n/, '')\n }\n\n tokens.push({ type: 'code-block', content: codeContent.replace(/\\r\\n/g, '\\n') })\n cursor = fenceEnd + 3\n }\n\n return tokens\n}\n","/**\n * Font + line-height defaults — matches `dim0/webui/.../canvas-lite-markdown.tsx`\n * and `dim0/backend/topix/datatypes/note/style.py`.\n *\n * The maps below are the canonical contract between consumer style tokens\n * and concrete typography. Custom fonts live in the consumer's @font-face;\n * the library only renames them.\n */\nimport type { FontFamily, FontSize } from '../types'\n\n/**\n * Mirrors the font stacks defined in dim0's index.css so canvas measurement\n * matches DOM text. Custom fonts must be loaded by the consumer (via\n * @font-face / Google Fonts); the font-epoch reactivity (see font-epoch.ts)\n * invalidates the bitmap cache when fonts finish loading.\n */\nexport const FONT_FAMILY_MAP: Record<FontFamily, string> = {\n handwriting: '\"Architects Daughter\", cursive',\n 'sans-serif':\n '\"Atkinson Hyperlegible Next\", system-ui, -apple-system, BlinkMacSystemFont, \"Segoe UI\", Roboto, \"Helvetica Neue\", Arial, \"Noto Sans\", ui-sans-serif, sans-serif, \"Apple Color Emoji\", \"Segoe UI Emoji\", \"Segoe UI Symbol\", \"Noto Color Emoji\"',\n serif: '\"Lora\", \"Source Serif 4\", ui-serif, Georgia, Cambria, \"Times New Roman\", Times, serif',\n monospace:\n '\"Inconsolata\", ui-monospace, SFMono-Regular, Menlo, Monaco, Consolas, \"Liberation Mono\", \"Courier New\", monospace',\n informal: '\"Shantell Sans\", ui-handwriting, cursive',\n}\n\nexport const FONT_SIZE_MAP: Record<FontSize, number> = {\n S: 14,\n M: 16,\n L: 24,\n XL: 36,\n}\n\nexport const LINE_HEIGHT_MAP: Record<FontSize, number> = {\n S: 20,\n M: 24,\n L: 32,\n XL: 40,\n}\n\n// Layout-time visual constants. Match dim0 canvas-lite-markdown.\nexport const CODE_BLOCK_PADDING_X = 6\nexport const CODE_BLOCK_MARGIN_Y = 4\nexport const CONTENT_HEIGHT_BUFFER = 4\nexport const CONTENT_PADDING = 6\n\nexport const DEFAULT_TEXT_COLOR = '#1f2937'\nexport const DEFAULT_HIGHLIGHT_COLOR = '#fde047'\nexport const DEFAULT_HIGHLIGHT_COLOR_DARK = '#6b5a23'\nexport const LINK_COLOR = '#2563eb'\nexport const CODE_BG_COLOR = 'rgba(148, 163, 184, 0.18)'\n","/**\n * Lazy loader for MathJax — same pattern as `render/rough/loader.ts`.\n *\n * MathJax is ~600KB and only useful for scenes with LaTeX math. We\n * defer loading until the first `$$...$$` token requests a compile,\n * then convert LaTeX → SVG strings off the main rAF path.\n *\n * Loaded from jsDelivr CDN rather than bundled because the v4\n * tex-svg.js bundle uses `importScripts('sre/speech-worker.js')` for\n * accessibility; the relative URL resolves wrong when served from a\n * dev bundler's node_modules. The CDN serves sibling files at\n * predictable paths so the bundle finds its workers. Self-host by\n * pointing `VENDOR_URL` at your own copy of the v4 component files.\n *\n * Notes:\n * - MathJax's `tex-svg.js` bundle attaches itself to `window.MathJax`\n * when loaded. This is the documented v4 browser API.\n * - If a consumer also uses MathJax, they should configure the\n * global *before* canvas-harness's first math node loads.\n */\n\ntype MathJaxLike = {\n tex2svgPromise(\n source: string,\n opts?: { display?: boolean; em?: number; ex?: number; containerWidth?: number },\n ): Promise<MathJaxSvgElement>\n startup: {\n /**\n * The \"lite adaptor\" used by the SVG output in browser context.\n * `serializeXML` returns standalone-valid SVG markup with\n * namespaces intact (which `outerHTML` does not always do).\n */\n adaptor: {\n serializeXML?(el: MathJaxSvgElement): string\n outerHTML(el: MathJaxSvgElement): string\n }\n }\n}\n\n/**\n * MathJax returns a \"lite element\" virtual-DOM node, not a real SVG\n * element. We only need to serialize it via the adaptor.\n */\nexport type MathJaxSvgElement = unknown\n\n// `window.MathJax` is partially populated by us pre-load (config),\n// then fully populated by the tex-svg bundle post-load. We type it\n// as `unknown` here and cast at the two access sites.\ndeclare global {\n var MathJax: unknown\n}\n\nlet cached: MathJaxLike | null = null\nlet loadPromise: Promise<MathJaxLike | null> | null = null\nlet loadFailed = false\nconst readyCallbacks = new Set<() => void>()\n\n/**\n * Returns the configured MathJax instance if loaded, else `null` and\n * triggers the lazy import on first call. Subscribers via `onMathJaxReady`\n * are notified when the import resolves.\n */\nexport const getMathJax = (): MathJaxLike | null => {\n if (cached) return cached\n if (loadFailed) return null\n if (!loadPromise) {\n loadPromise = loadMathJax()\n .then(instance => {\n if (instance) {\n cached = instance\n // Fire pending callbacks ONLY on real load success — firing\n // on null would re-trigger cache drains in a loop.\n for (const cb of readyCallbacks) cb()\n } else {\n // SSR / no window — mark terminal so future `onMathJaxReady`\n // calls bail instead of accumulating callbacks.\n loadFailed = true\n }\n readyCallbacks.clear()\n return cached\n })\n .catch(err => {\n console.warn('[math] failed to load MathJax:', err)\n loadFailed = true\n readyCallbacks.clear()\n return null\n })\n }\n return null\n}\n\n/**\n * Registers a callback that fires once when MathJax becomes available.\n * No-op if already loaded — caller should check `getMathJax() !== null`\n * first. Used to trigger a re-paint of math-bearing text nodes.\n */\nexport const onMathJaxReady = (cb: () => void): void => {\n if (cached) return\n if (loadFailed) return\n readyCallbacks.add(cb)\n}\n\ntype MathJaxConfig = {\n startup?: { typeset?: boolean; promise?: Promise<void> }\n options?: {\n enableMenu?: boolean\n enableEnrichment?: boolean\n enableSpeech?: boolean\n enableComplexity?: boolean\n sre?: { speech?: 'none' | 'shallow' | 'deep' }\n }\n svg?: {\n scale?: number\n fontCache?: 'local' | 'global' | 'none'\n /**\n * v4 introduces inline-math linebreaking that splits long\n * formulas across MULTIPLE <svg> blocks separated by <mjx-break>\n * markers. Great for HTML flow layout, fatal for our Blob URL\n * pipeline (multiple root elements aren't valid in one SVG doc).\n * Disabling it forces one <svg> per formula no matter how wide.\n */\n linebreaks?: { inline?: boolean; width?: string }\n }\n}\n\nconst loadMathJax = async (): Promise<MathJaxLike | null> => {\n if (typeof window === 'undefined') return null\n\n // Configure before importing so MathJax picks up the settings. The\n // tex-svg bundle reads `window.MathJax` at script-execution time.\n // `fontCache: 'local'` embeds glyph paths inline in each SVG (bigger\n // SVG, no <defs> dependency). Required for SVGs that get detached\n // from MathJax's host container, like ours.\n const winAny = window as typeof window & { MathJax?: MathJaxConfig }\n // Disable a11y / SRE features. MathJax v4's tex-svg bundle tries to\n // load a speech-rule-engine worker by default for screen reader\n // support — its bundled path resolves to `http://sre//...` which\n // 404s in browsers and clutters the console. We're rendering to\n // canvas, not DOM — no AT to serve anyway.\n winAny.MathJax = {\n ...(winAny.MathJax ?? {}),\n startup: { typeset: false },\n options: {\n enableMenu: false,\n enableEnrichment: false,\n enableSpeech: false,\n enableComplexity: false,\n sre: { speech: 'none' },\n },\n // `fontCache: 'none'` inlines every glyph as a raw <path>\n // (slightly bigger SVG, no <use> references). Required for SVGs\n // we extract to a Blob URL and rasterize via <img> — `<use>`\n // refs to <defs> elsewhere in the page wouldn't resolve.\n // `linebreaks: { inline: false }` keeps the whole formula in one\n // <svg> element (v4 defaults to true for long inline math).\n svg: {\n scale: 1,\n fontCache: 'none',\n linebreaks: { inline: false },\n },\n }\n\n // Load via <script> tag from CDN rather than `import('mathjax/tex-svg.js')`.\n // The bundle's `importScripts('sre/speech-worker.js')` for the\n // accessibility feature uses a relative URL that Vite (and most\n // bundlers) can't serve from node_modules. The CDN serves sibling\n // files at predictable paths so the bundle finds its workers.\n // Override `MATHJAX_VENDOR_URL` to self-host.\n const VENDOR_URL = 'https://cdn.jsdelivr.net/npm/mathjax@4/tex-svg.js'\n await new Promise<void>((resolve, reject) => {\n const existing = document.querySelector(\n `script[src=\"${VENDOR_URL}\"]`,\n ) as HTMLScriptElement | null\n if (existing) {\n // Already injected by a previous call — wait for it to finish.\n existing.addEventListener('load', () => resolve(), { once: true })\n existing.addEventListener('error', () => reject(new Error('MathJax CDN load failed')), {\n once: true,\n })\n return\n }\n const script = document.createElement('script')\n script.src = VENDOR_URL\n script.async = true\n script.onload = () => resolve()\n script.onerror = () => reject(new Error('MathJax CDN load failed'))\n document.head.appendChild(script)\n })\n\n // MathJax's startup is a Promise; wait for it before returning.\n const mj = winAny.MathJax as (MathJaxLike & { startup?: { promise?: Promise<void> } }) | undefined\n if (!mj) throw new Error('MathJax did not install on window after import')\n if (typeof mj.tex2svgPromise !== 'function') {\n throw new Error('MathJax loaded but tex2svgPromise is missing — wrong bundle?')\n }\n await mj.startup?.promise\n return mj as MathJaxLike\n}\n\n/** Reset state — tests only. */\nexport const __resetMathLoader = (): void => {\n cached = null\n loadPromise = null\n loadFailed = false\n readyCallbacks.clear()\n}\n","/**\n * Math compile + raster cache.\n *\n * Pipeline per formula:\n * 1. LaTeX source → MathJax SVG string (sync once MathJax loaded)\n * 2. Inject the requested text color via `currentColor` substitution\n * 3. Rasterize to ImageBitmap at the requested on-device pixel size\n * 4. Cache by (source, color, sizeBucket)\n *\n * Compile work is queued and drained over rAF frames so a paste of\n * 100 math-heavy paragraphs doesn't block the main thread. Each\n * resolve bumps the math-epoch; the text bitmap cache reads the\n * epoch and invalidates only its math-bearing entries.\n */\nimport { getMathJax, onMathJaxReady } from './loader'\n\n// Round to integer to bound cache entries — math is keyed by\n// (source, color, sizePx). Font sizes in the library are a small\n// fixed set (14, 16, 24, 36), so no power-of-two bucketing needed;\n// integer rounding handles minor floating-point variance.\nconst normalizeSize = (px: number): number => Math.max(8, Math.round(px))\n\n/** Result of a successful math compile + raster. */\nexport type MathBitmap = {\n bitmap: ImageBitmap\n /** Width in logical CSS pixels at the requested font size. */\n width: number\n /** Height in logical CSS pixels at the requested font size. */\n height: number\n /**\n * Baseline offset in CSS pixels (positive = bitmap top sits ABOVE\n * the text baseline; the bottom dips below by `height - baseline`).\n * Parsed from MathJax's `vertical-align: -Nex` style attribute.\n */\n baselineOffset: number\n}\n\ntype Entry =\n | { state: 'pending' }\n | { state: 'ready'; bitmap: MathBitmap }\n | { state: 'error'; err: unknown }\n\nconst cache = new Map<string, Entry>()\nconst compileQueue: Array<{ key: string; source: string; color: string; sizePx: number }> = []\nlet compileScheduled = false\n\n// ---- epoch ----------------------------------------------------------\n// Bumped once per drained compile batch (not per formula), to amortize\n// text bitmap invalidation. Subscribed by the text bitmap cache.\n\nlet mathEpoch = 0\nconst epochSubscribers = new Set<() => void>()\n\nexport const getMathEpoch = (): number => mathEpoch\n\nexport const subscribeMathEpoch = (cb: () => void): (() => void) => {\n epochSubscribers.add(cb)\n return () => {\n epochSubscribers.delete(cb)\n }\n}\n\nconst bumpMathEpoch = (): void => {\n mathEpoch += 1\n for (const cb of epochSubscribers) cb()\n}\n\n// ---- public API ----------------------------------------------------\n\n/**\n * Look up a math bitmap or kick off compilation. Returns the cached\n * bitmap if ready, `null` if still loading / queued (caller should\n * paint a placeholder this frame). Triggers a math-epoch bump when\n * the formula resolves.\n *\n * `sizePx` is the on-screen height in logical px (typically the line\n * height of the surrounding text × DPR).\n */\nexport const getMathBitmap = (source: string, color: string, sizePx: number): MathBitmap | null => {\n const size = normalizeSize(sizePx)\n const key = `${size}:${color}:${source}`\n const existing = cache.get(key)\n if (existing) {\n if (existing.state === 'ready') return existing.bitmap\n return null\n }\n // Miss — enqueue for compile. The compile path triggers the lazy\n // MathJax load on its own; if it's not ready, we re-queue from\n // onMathJaxReady.\n cache.set(key, { state: 'pending' })\n compileQueue.push({ key, source, color, sizePx: size })\n scheduleCompile()\n return null\n}\n\nconst scheduleCompile = (): void => {\n if (compileScheduled) return\n compileScheduled = true\n if (typeof window === 'undefined' || typeof requestAnimationFrame === 'undefined') {\n // SSR / Node — drain synchronously so tests still progress.\n void drainQueue()\n return\n }\n requestAnimationFrame(() => {\n void drainQueue()\n })\n}\n\n/**\n * Compile loop. Time-sliced: each rAF tick spends up to 4ms on\n * compiles, then yields. After the queue drains, bumps the math\n * epoch once so text bitmaps containing math can invalidate in a\n * single pass.\n */\nconst drainQueue = async (): Promise<void> => {\n compileScheduled = false\n if (compileQueue.length === 0) return\n\n const mj = getMathJax()\n if (!mj) {\n // Not loaded yet — wait for the import, then resume.\n onMathJaxReady(() => scheduleCompile())\n return\n }\n\n const FRAME_BUDGET_MS = 4\n const start = performance.now()\n let didResolve = false\n\n while (compileQueue.length > 0 && performance.now() - start < FRAME_BUDGET_MS) {\n const item = compileQueue.shift()!\n if (cache.get(item.key)?.state !== 'pending') continue\n try {\n const bitmap = await compileOne(mj, item.source, item.color, item.sizePx)\n cache.set(item.key, { state: 'ready', bitmap })\n didResolve = true\n } catch (err) {\n cache.set(item.key, { state: 'error', err })\n console.warn(`[math] failed to compile \"${item.source}\":`, err)\n }\n }\n\n if (didResolve) bumpMathEpoch()\n if (compileQueue.length > 0) scheduleCompile()\n}\n\nconst compileOne = async (\n mj: NonNullable<ReturnType<typeof getMathJax>>,\n source: string,\n color: string,\n sizePx: number,\n): Promise<MathBitmap> => {\n // Step 1: LaTeX → SVG via MathJax. `em` controls the typesetting\n // scale; we pass the requested px so the SVG comes out at the right\n // intrinsic size.\n const svgElement = await mj.tex2svgPromise(source, { display: false, em: sizePx, ex: sizePx / 2 })\n // Prefer `serializeXML` (v4 canonical) so namespaces survive; fall\n // back to `outerHTML` for v3 compatibility.\n let markup = mj.startup.adaptor.serializeXML\n ? mj.startup.adaptor.serializeXML(svgElement)\n : mj.startup.adaptor.outerHTML(svgElement)\n // MathJax wraps the actual <svg> in a <mjx-container> element with\n // a sibling <mjx-speech> block for accessibility. We need just the\n // outer <svg>...</svg> for the blob.\n //\n // With `linebreaks.inline: false` set in the loader config, MathJax\n // produces exactly ONE <svg> per formula and no <mjx-break> markers.\n // We still defensively pick the FIRST <svg>...</svg> here (non-greedy)\n // in case the config doesn't fully prevent breaks for pathological\n // inputs — losing trailing fragments is preferable to a parse error\n // that kills the whole formula.\n const svgMatch = /<svg[\\s\\S]*?<\\/svg>/.exec(markup)\n if (svgMatch) markup = svgMatch[0]\n // Strip accessibility / semantic attributes. MathJax v4 emits a\n // huge set of data-semantic-*, data-speech-*, aria-*, role, and\n // focusable attributes whose values contain XML-encoded HTML. When\n // the SVG is loaded via a Blob URL into `<img>`, the strict XML\n // parser chokes on some of these (specifically the speech / braille\n // ones for certain formulas). We're rendering to canvas — no AT\n // consumes these — so dropping them is safe and shrinks the blob\n // ~70%.\n markup = markup\n .replace(/\\sdata-semantic-[a-z0-9-]+=\"[^\"]*\"/g, '')\n .replace(/\\sdata-speech-[a-z0-9-]+=\"[^\"]*\"/g, '')\n .replace(/\\sdata-mml-node=\"[^\"]*\"/g, '')\n .replace(/\\sdata-latex=\"[^\"]*\"/g, '')\n .replace(/\\sdata-braille[a-z0-9-]*=\"[^\"]*\"/g, '')\n .replace(/\\saria-[a-z0-9-]+=\"[^\"]*\"/g, '')\n .replace(/\\srole=\"[^\"]*\"/g, '')\n .replace(/\\sfocusable=\"[^\"]*\"/g, '')\n .replace(/\\stabindex=\"[^\"]*\"/g, '')\n .replace(/\\shas-speech=\"[^\"]*\"/g, '')\n // Ensure the xmlns is present (the lite-adaptor sometimes omits it,\n // which makes the <img> blob fail with a generic onerror).\n if (!markup.includes('xmlns=\"http://www.w3.org/2000/svg\"')) {\n markup = markup.replace(/^<svg\\b/, '<svg xmlns=\"http://www.w3.org/2000/svg\"')\n }\n\n // Step 2: tint. MathJax SVG output uses `currentColor` for glyph\n // fills; substitute the requested color.\n markup = markup.replace(/currentColor/gi, color)\n\n // Step 3: parse intrinsic dims + baseline offset from the SVG markup\n // before rasterizing. The outer <svg> carries `width` / `height` in\n // ex units and a `style=\"vertical-align: -Nex\"` for baseline.\n const dims = parseSvgDims(markup, sizePx)\n\n // Step 4: rasterize via Blob URL → Image → createImageBitmap.\n const blob = new Blob([markup], { type: 'image/svg+xml' })\n const url = URL.createObjectURL(blob)\n try {\n let img: HTMLImageElement\n try {\n img = await loadImage(url)\n } catch (e) {\n // Log the full markup so we can see WHY the SVG failed to load.\n console.warn(`[math] SVG failed to load for \"${source}\":\\n${markup}`)\n throw e\n }\n // Rasterize at 2x for crisp small glyphs without committing to a\n // full DPR-aware bucket key — sizes are already bucketed.\n const rasterW = Math.max(1, Math.ceil(dims.width * 2))\n const rasterH = Math.max(1, Math.ceil(dims.height * 2))\n const bitmap = await createImageBitmap(img, {\n resizeWidth: rasterW,\n resizeHeight: rasterH,\n resizeQuality: 'high',\n })\n return {\n bitmap,\n width: dims.width,\n height: dims.height,\n baselineOffset: dims.baselineOffset,\n }\n } finally {\n URL.revokeObjectURL(url)\n }\n}\n\nconst loadImage = (src: string): Promise<HTMLImageElement> =>\n new Promise((resolve, reject) => {\n const img = new Image()\n img.onload = () => resolve(img)\n img.onerror = e => reject(e)\n img.src = src\n })\n\n/**\n * Parse `<svg width=\"Nex\" height=\"Nex\" style=\"vertical-align: -Nex\">`\n * from the markup. Approximate `1 ex ≈ sizePx / 2`.\n */\nconst parseSvgDims = (\n markup: string,\n sizePx: number,\n): { width: number; height: number; baselineOffset: number } => {\n const exToPx = sizePx / 2\n const widthMatch = /<svg[^>]*\\bwidth=\"([0-9.]+)ex\"/.exec(markup)\n const heightMatch = /<svg[^>]*\\bheight=\"([0-9.]+)ex\"/.exec(markup)\n const vAlignMatch = /vertical-align:\\s*(-?[0-9.]+)ex/.exec(markup)\n\n const widthEx = widthMatch ? Number.parseFloat(widthMatch[1]!) : 2\n const heightEx = heightMatch ? Number.parseFloat(heightMatch[1]!) : 2\n const vAlignEx = vAlignMatch ? Number.parseFloat(vAlignMatch[1]!) : 0\n\n const width = widthEx * exToPx\n const height = heightEx * exToPx\n // vertical-align is negative = descend below baseline.\n // baselineOffset is the px from the bitmap top down to the text\n // baseline. If the bitmap descends `d` below baseline, baseline is\n // at `height - d` from the top.\n const descent = Math.abs(vAlignEx) * exToPx\n const baselineOffset = height - descent\n\n return { width, height, baselineOffset }\n}\n\n/** Test / debug aid. */\nexport const clearMathCache = (): void => {\n cache.clear()\n compileQueue.length = 0\n compileScheduled = false\n}\n\n/** Test / debug aid. */\nexport const getMathCacheSize = (): number => cache.size\n","import type { FontFamily, FontSize, TextStyle } from '../types'\n/**\n * Text measurement cache — ported from `canvas-lite-markdown.tsx`.\n *\n * `ctx.measureText` is the single most expensive operation in canvas text.\n * We memoize widths by (font, text) — a 5k-entry LRU keeps the working\n * set hot during pan/zoom and re-layouts.\n *\n * Cache is module-level so multiple Canvas instances share it. Eviction is\n * FIFO via Map iteration order (Maps preserve insertion order in JS).\n */\nimport { DEFAULT_TEXT_COLOR, FONT_FAMILY_MAP, FONT_SIZE_MAP } from './defaults'\nimport { getMathBitmap } from './math'\nimport type { InlineType } from './tokens'\n\nconst MAX_WIDTH_CACHE_SIZE = 5000\n\n// Shared one-off canvas used purely for measurement.\nconst measureCanvas: HTMLCanvasElement | null =\n typeof document !== 'undefined' ? document.createElement('canvas') : null\nconst measureCtx: CanvasRenderingContext2D | null = measureCanvas?.getContext('2d') ?? null\n\nconst widthCache = new Map<string, number>()\n\n/**\n * Returns the canvas `font` string for a given run.\n */\nexport const getCanvasFont = (opts: {\n type: InlineType\n fontFamily: FontFamily\n fontSize: FontSize\n textStyle: TextStyle\n}): string => {\n const weight = opts.type === 'bold' || opts.textStyle === 'bold' ? '700' : '400'\n const italic = opts.type === 'italic' || opts.textStyle === 'italic' ? 'italic' : 'normal'\n const family = opts.type === 'code' ? FONT_FAMILY_MAP.monospace : FONT_FAMILY_MAP[opts.fontFamily]\n return `${italic} ${weight} ${FONT_SIZE_MAP[opts.fontSize]}px ${family}`\n}\n\n/**\n * Memoized width measurement. Cache key includes font (so different\n * fonts/sizes/styles get separate entries).\n *\n * Falls back to a heuristic when no canvas is available (SSR / Node tests).\n */\nexport const measureText = (opts: {\n text: string\n type: InlineType\n fontFamily: FontFamily\n fontSize: FontSize\n textStyle: TextStyle\n}): number => {\n if (!opts.text) return 0\n // Math width comes from the bitmap cache (keyed by source + color +\n // size). Use DEFAULT_TEXT_COLOR so the lookup hits the SAME cache\n // entry that paint will later look up (paint's fallback is also\n // DEFAULT_TEXT_COLOR). Mismatch here = paint never finds the\n // bitmap layout compiled.\n if (opts.type === 'math') {\n const fontSizePx = FONT_SIZE_MAP[opts.fontSize]\n const bitmap = getMathBitmap(opts.text, DEFAULT_TEXT_COLOR, fontSizePx)\n if (bitmap) return bitmap.width\n return Math.max(8, opts.text.length * fontSizePx * 0.55 + fontSizePx)\n }\n const font = getCanvasFont(opts)\n const key = `${font}|${opts.text}`\n const cached = widthCache.get(key)\n if (cached !== undefined) return cached\n\n if (!measureCtx) {\n return opts.text.length * FONT_SIZE_MAP[opts.fontSize] * 0.55\n }\n\n measureCtx.font = font\n const width = measureCtx.measureText(opts.text).width\n widthCache.set(key, width)\n if (widthCache.size > MAX_WIDTH_CACHE_SIZE) {\n const oldestKey = widthCache.keys().next().value\n if (oldestKey !== undefined) widthCache.delete(oldestKey)\n }\n return width\n}\n\n/**\n * Clears all cached measurements. Called by the font-epoch system on\n * font load — fallback metrics returned before fonts settle would be\n * wrong, so we re-measure everything once they're ready.\n */\nexport const clearMeasureCache = (): void => {\n widthCache.clear()\n}\n","import type { FontFamily, FontSize, TextStyle } from '../types'\n/**\n * Wrap engine — ported from canvas-lite-markdown.tsx.\n *\n * Takes a stream of tokens + the wrap width + font settings; produces\n * an array of LayoutLines (text lines, code-block lines, rule lines).\n * Each text line is a sequence of StyledRuns (text + inline type).\n *\n * Code blocks wrap by character width using monospace metrics so they\n * fit precisely. Text lines wrap by word, falling back to char-wrap\n * for words longer than `width`.\n */\nimport { CODE_BLOCK_PADDING_X, DEFAULT_TEXT_COLOR, FONT_SIZE_MAP } from './defaults'\nimport { getMathBitmap } from './math'\nimport { measureText } from './measure'\nimport type { InlineType, Token } from './tokens'\n\nexport type StyledRun = {\n text: string\n type: InlineType\n}\n\nexport type LayoutLine =\n | { kind: 'text'; runs: StyledRun[] }\n | { kind: 'code-block'; runs: StyledRun[]; isFirst: boolean; isLast: boolean }\n | { kind: 'rule'; double: boolean }\n\nexport type LayoutOptions = {\n width: number\n fontFamily: FontFamily\n fontSize: FontSize\n textStyle: TextStyle\n /**\n * Used to key the math bitmap cache. Both layout (for measured dims)\n * and paint (for the actual bitmap) need to query the same cache\n * entry. Defaults to `#000000` for estimate-only callers.\n */\n textColor?: string\n}\n\nconst splitChunks = (text: string): string[] => text.split(/(\\s+)/g).filter(Boolean)\n\n/**\n * Wraps one fenced-code line by character width using monospace metrics.\n * Preserves whitespace and guarantees fit within `maxWidth`.\n */\nconst wrapCodeLine = (line: string, opts: LayoutOptions, maxWidth: number): string[] => {\n const normalized = line.replace(/\\t/g, ' ')\n if (!normalized) return ['']\n\n const wrapped: string[] = []\n let part = ''\n\n for (const ch of normalized) {\n const next = part + ch\n const nextWidth = measureText({\n text: next,\n type: 'code',\n fontFamily: opts.fontFamily,\n fontSize: opts.fontSize,\n textStyle: 'normal',\n })\n\n if (part && nextWidth > maxWidth) {\n wrapped.push(part)\n part = ch\n } else {\n part = next\n }\n }\n\n if (part) wrapped.push(part)\n return wrapped\n}\n\n/**\n * Turns tokens into drawable lines. Output consumed by the canvas paint pass.\n */\nexport const layoutTokens = (tokens: Token[], opts: LayoutOptions): LayoutLine[] => {\n const maxWidth = Math.max(40, opts.width)\n\n const lines: LayoutLine[] = []\n let currentRuns: StyledRun[] = []\n let cursorX = 0\n\n const pushLine = (): void => {\n lines.push({ kind: 'text', runs: currentRuns })\n currentRuns = []\n cursorX = 0\n }\n\n const pushRule = (double: boolean): void => {\n if (currentRuns.length > 0) pushLine()\n lines.push({ kind: 'rule', double })\n }\n\n const pushCodeBlock = (content: string): void => {\n if (currentRuns.length > 0) pushLine()\n const rawLines = content.split('\\n')\n const visualRuns: StyledRun[][] = []\n const codeMaxWidth = Math.max(20, maxWidth - CODE_BLOCK_PADDING_X * 2)\n\n for (const raw of rawLines) {\n for (const part of wrapCodeLine(raw, opts, codeMaxWidth)) {\n visualRuns.push([{ text: part, type: 'code' }])\n }\n }\n\n if (visualRuns.length === 0) {\n lines.push({ kind: 'code-block', runs: [], isFirst: true, isLast: true })\n return\n }\n\n for (let index = 0; index < visualRuns.length; index++) {\n const runs = visualRuns[index]!\n lines.push({\n kind: 'code-block',\n runs,\n isFirst: index === 0,\n isLast: index === visualRuns.length - 1,\n })\n }\n }\n\n const pushChunk = (chunk: string, type: InlineType): void => {\n if (!chunk) return\n\n const chunkWidth = measureText({\n text: chunk,\n type,\n fontFamily: opts.fontFamily,\n fontSize: opts.fontSize,\n textStyle: opts.textStyle,\n })\n\n if (!chunk.trim()) {\n if (cursorX === 0) return\n currentRuns.push({ text: chunk, type })\n cursorX += chunkWidth\n return\n }\n\n if (cursorX > 0 && cursorX + chunkWidth > maxWidth) {\n pushLine()\n }\n\n if (chunkWidth > maxWidth && chunk.length > 1) {\n let part = ''\n for (const ch of chunk) {\n const next = part + ch\n const nextWidth = measureText({\n text: next,\n type,\n fontFamily: opts.fontFamily,\n fontSize: opts.fontSize,\n textStyle: opts.textStyle,\n })\n if (cursorX > 0 && nextWidth > maxWidth) {\n if (part) {\n currentRuns.push({ text: part, type })\n cursorX += measureText({\n text: part,\n type,\n fontFamily: opts.fontFamily,\n fontSize: opts.fontSize,\n textStyle: opts.textStyle,\n })\n }\n pushLine()\n part = ch\n } else {\n part = next\n }\n }\n\n if (part) {\n currentRuns.push({ text: part, type })\n cursorX += measureText({\n text: part,\n type,\n fontFamily: opts.fontFamily,\n fontSize: opts.fontSize,\n textStyle: opts.textStyle,\n })\n }\n return\n }\n\n currentRuns.push({ text: chunk, type })\n cursorX += chunkWidth\n }\n\n const fontSizePx = FONT_SIZE_MAP[opts.fontSize]\n // Must match paint-canvas's fallback so the math cache lookup keys\n // align between layout (measuring) and paint (drawing). The cache\n // is keyed by (source, color, size); a mismatch means paint never\n // hits the bitmap layout compiled, and the placeholder sticks.\n const mathColor = opts.textColor || DEFAULT_TEXT_COLOR\n\n for (const token of tokens) {\n if (token.type === 'code-block') {\n pushCodeBlock(token.content)\n continue\n }\n if (token.type === 'br') {\n pushLine()\n continue\n }\n if (token.type === 'hr') {\n pushRule(false)\n continue\n }\n if (token.type === 'hr-double') {\n pushRule(true)\n continue\n }\n if (token.type === 'math') {\n // Math is an inline atom — never whitespace-split. Width comes\n // from the cached bitmap (if compiled) or a length-based\n // placeholder. When the cache resolves later, the math-epoch\n // bump invalidates this layout's bitmap cache entry.\n const bitmap = getMathBitmap(token.content, mathColor, fontSizePx)\n const width = bitmap\n ? bitmap.width\n : // Placeholder: roughly proportional to source length so wrap\n // doesn't dramatically shift on resolve. Capped at maxWidth.\n Math.min(maxWidth, token.content.length * fontSizePx * 0.55 + fontSizePx)\n if (cursorX > 0 && cursorX + width > maxWidth) pushLine()\n currentRuns.push({ text: token.content, type: 'math' })\n cursorX += width\n continue\n }\n for (const chunk of splitChunks(token.content)) pushChunk(chunk, token.type)\n }\n\n if (currentRuns.length > 0 || lines.length === 0) {\n lines.push({ kind: 'text', runs: currentRuns })\n }\n\n return lines\n}\n","/**\n * Font-load reactivity — ported from `canvas-lite-markdown.tsx`.\n *\n * Custom fonts (Architects Daughter, Inconsolata, etc.) load asynchronously\n * — `ctx.measureText` returns fallback metrics until they settle, which\n * means initial layouts would be wrong if we trusted them. The font-epoch\n * mechanism:\n *\n * 1. On first subscribe, attach listeners to document.fonts.ready and\n * 'loadingdone'.\n * 2. When fonts settle, bump an integer epoch and notify subscribers.\n * 3. Subscribers (measureCache + bitmap cache) clear themselves on bump.\n * 4. The renderer re-paints (one frame of \"jump\" as fonts settle, then\n * stable forever).\n */\nimport { clearMeasureCache } from './measure'\n\nconst fontEpochListeners = new Set<(epoch: number) => void>()\nlet fontEpoch = 0\nlet fontTrackingInitialized = false\n\nconst emitFontEpoch = (): void => {\n for (const listener of fontEpochListeners) listener(fontEpoch)\n}\n\n/**\n * Bumps the epoch and tells everyone. Caches (measure, bitmap) clear\n * themselves so the next paint pulls fresh metrics.\n */\nconst bumpFontEpoch = (): void => {\n fontEpoch += 1\n clearMeasureCache()\n emitFontEpoch()\n}\n\nconst initFontTracking = (): void => {\n if (fontTrackingInitialized) return\n fontTrackingInitialized = true\n\n if (typeof document === 'undefined' || !('fonts' in document)) return\n const fontSet = document.fonts\n let didSettleInitialFonts = false\n\n fontSet.ready\n .then(() => {\n if (didSettleInitialFonts) return\n didSettleInitialFonts = true\n bumpFontEpoch()\n })\n .catch(() => {\n /* ignore */\n })\n\n fontSet.addEventListener?.('loadingdone', () => {\n if (!didSettleInitialFonts) didSettleInitialFonts = true\n bumpFontEpoch()\n })\n}\n\n/**\n * Subscribe to font-epoch bumps. Lazy-initializes the document.fonts\n * listeners on first call. Returns an unsubscribe.\n */\nexport const subscribeFontEpoch = (listener: (epoch: number) => void): (() => void) => {\n initFontTracking()\n fontEpochListeners.add(listener)\n return () => {\n fontEpochListeners.delete(listener)\n }\n}\n\n/**\n * Current epoch — included in bitmap-cache keys so they invalidate when\n * custom fonts settle.\n */\nexport const getFontEpoch = (): number => fontEpoch\n","/**\n * Zoom + DPR quantization and moving-vs-idle render scale — ported\n * verbatim from canvas-lite-markdown.tsx.\n *\n * Bitmap-cache keys include `zoomBucket` and `dprBucket` instead of raw\n * camera.z and devicePixelRatio. Without quantization, tiny floating-\n * point drift on each wheel event would explode the cache. With it, a\n * zoom from 1.00 → 1.04 hits the same bucket and reuses the same bitmap.\n *\n * `resolveRenderScale` is the LOD selector: lower-quality rasterization\n * during pan/zoom motion, full quality on idle. Saves up to 60% of the\n * sample bitmap pixels when nothing's changing for the user anyway.\n */\nconst MIN_RENDER_SCALE = 0.15\nconst MAX_RENDER_SCALE = 1.5\nconst MAX_RENDER_WIDTH = 2000\nconst MAX_RENDER_HEIGHT = 1200\n\n/**\n * Buckets zoom to avoid cache churn from sub-1%-zoom changes.\n */\nexport const quantizeZoom = (value: number): number => {\n if (!Number.isFinite(value)) return 1\n return Math.max(0.1, Math.round(value * 10) / 10)\n}\n\n/**\n * Buckets DPR to keep cache keys stable across tiny devicePixelRatio\n * variance (e.g. when a window crosses a mixed-DPR monitor boundary).\n */\nexport const quantizeDpr = (value: number): number => {\n if (!Number.isFinite(value)) return 1\n const clamped = Math.max(1, Math.min(3, value))\n return Math.round(clamped * 4) / 4\n}\n\n/**\n * Chooses a render scale from a base scale, the current zoom bucket,\n * and whether the camera (or shape) is in motion. While moving, drop\n * quality for throughput; on idle, snap back to full quality.\n */\nexport const resolveRenderScale = (baseScale: number, zoom: number, isMoving: boolean): number => {\n const clampedBase = Math.max(MIN_RENDER_SCALE, Math.min(MAX_RENDER_SCALE, baseScale))\n let idleScale = clampedBase\n if (zoom <= 0.4) {\n idleScale = 0.45\n } else if (zoom <= 0.7) {\n idleScale = 0.85\n } else if (zoom <= 1) {\n idleScale = 1.15\n } else if (zoom <= 1.8) {\n idleScale = 1.35\n } else {\n idleScale = 1 + (zoom - 1.8) * 0.2\n }\n\n idleScale = Math.max(MIN_RENDER_SCALE, Math.min(MAX_RENDER_SCALE, idleScale))\n\n if (isMoving) {\n let movingScale = idleScale * (zoom >= 0.4 ? 0.72 : 0.6)\n if (zoom < 0.4) {\n movingScale = Math.min(movingScale, 0.22)\n } else if (zoom <= 0.7) {\n movingScale = Math.min(movingScale, 0.4)\n }\n return Math.max(MIN_RENDER_SCALE, Math.min(0.65, movingScale))\n }\n\n return idleScale\n}\n\n/**\n * Applies the absolute backing-store size cap so very-wide / very-tall\n * shapes don't blow up memory at high zoom.\n */\nexport const clampEffectiveScale = (baseScale: number, width: number, height: number): number => {\n const limiter = Math.min(\n 1,\n MAX_RENDER_WIDTH / Math.max(1, width * baseScale),\n MAX_RENDER_HEIGHT / Math.max(1, height * baseScale),\n )\n return baseScale * limiter\n}\n","import type { FontFamily, FontSize, TextStyle } from '../types'\n/**\n * Height-only probe for autosizing text shapes — ported from\n * canvas-lite-markdown.tsx.\n *\n * Same tokenize + layout pipeline as the paint pass; just skips the\n * actual draw. Used by the edit-mode autosize and by any consumer that\n * needs to compute the height a piece of markdown will take at a given\n * width.\n */\nimport { CODE_BLOCK_MARGIN_Y, CONTENT_HEIGHT_BUFFER, LINE_HEIGHT_MAP } from './defaults'\nimport { type LayoutLine, layoutTokens } from './layout'\nimport { tokenize } from './tokens'\n\nexport type EstimateOptions = {\n text: string\n width: number\n fontFamily?: FontFamily\n fontSize?: FontSize\n textStyle?: TextStyle\n}\n\nconst getLineAdvance = (line: LayoutLine, lineHeight: number): number => {\n if (line.kind !== 'code-block') return lineHeight\n let advance = lineHeight\n if (line.isFirst) advance += CODE_BLOCK_MARGIN_Y\n if (line.isLast) advance += CODE_BLOCK_MARGIN_Y\n return advance\n}\n\nexport const getContentHeight = (lines: LayoutLine[], lineHeight: number): number =>\n Math.max(\n lineHeight,\n lines.reduce((sum, line) => sum + getLineAdvance(line, lineHeight), 0),\n )\n\nexport const estimateMarkdownContentHeight = ({\n text,\n width,\n fontFamily = 'handwriting',\n fontSize = 'M',\n textStyle = 'normal',\n}: EstimateOptions): number => {\n const normalizedText = text.trim()\n if (!normalizedText) return 0\n\n const resolvedWidth = Math.max(40, Math.ceil(width))\n const lines = layoutTokens(tokenize(text), {\n width: resolvedWidth,\n fontFamily,\n fontSize,\n textStyle,\n })\n const lineHeight = LINE_HEIGHT_MAP[fontSize]\n return getContentHeight(lines, lineHeight) + CONTENT_HEIGHT_BUFFER\n}\n\nexport const getMarkdownLineHeightPx = (fontSize: FontSize): number => LINE_HEIGHT_MAP[fontSize]\n","import type { FontFamily, FontSize, TextAlign, TextStyle } from '../types'\n/**\n * Paints fully-laid-out markdown into a canvas context — ported from\n * canvas-lite-markdown.tsx with the output-stage simplification noted in\n * ARCHITECTURE.md §8.\n *\n * Caller is responsible for sizing the canvas + applying its own\n * transform. This function just paints content at (0, 0) into a rect of\n * the given (width, height).\n */\nimport {\n CODE_BG_COLOR,\n CODE_BLOCK_MARGIN_Y,\n CODE_BLOCK_PADDING_X,\n DEFAULT_HIGHLIGHT_COLOR,\n DEFAULT_TEXT_COLOR,\n FONT_SIZE_MAP,\n LINE_HEIGHT_MAP,\n LINK_COLOR,\n} from './defaults'\nimport { getContentHeight } from './estimate-height'\nimport { type LayoutLine, layoutTokens } from './layout'\nimport { getMathBitmap } from './math'\nimport { getCanvasFont, measureText } from './measure'\nimport { tokenize } from './tokens'\nimport type { InlineType } from './tokens'\n\nexport type DrawTextOptions = {\n text: string\n width: number\n height: number\n align: TextAlign\n fontFamily: FontFamily\n fontSize: FontSize\n textStyle: TextStyle\n textColor: string\n highlightColor: string\n}\n\nconst getLineAdvance = (line: LayoutLine, lineHeight: number): number => {\n if (line.kind !== 'code-block') return lineHeight\n let advance = lineHeight\n if (line.isFirst) advance += CODE_BLOCK_MARGIN_Y\n if (line.isLast) advance += CODE_BLOCK_MARGIN_Y\n return advance\n}\n\nconst getTextX = (opts: DrawTextOptions, lineWidth: number): number => {\n if (opts.align === 'center') return Math.floor((opts.width - lineWidth) / 2)\n if (opts.align === 'right') return Math.max(0, opts.width - lineWidth)\n return 0\n}\n\nconst drawRunDecoration = (\n ctx: CanvasRenderingContext2D,\n x: number,\n y: number,\n width: number,\n type: InlineType,\n fontSize: number,\n): void => {\n if (type === 'underline' || type === 'link') {\n const lineY = y + 2\n ctx.beginPath()\n ctx.moveTo(x, lineY)\n ctx.lineTo(x + width, lineY)\n ctx.lineWidth = 1\n ctx.stroke()\n }\n\n if (type === 'strike') {\n const lineY = y - Math.floor(fontSize * 0.35)\n ctx.beginPath()\n ctx.moveTo(x, lineY)\n ctx.lineTo(x + width, lineY)\n ctx.lineWidth = 1\n ctx.stroke()\n }\n}\n\n/**\n * Paints `text` (markdown) into the canvas at (0..width, 0..height) using\n * the laid-out lines and styled runs. Background chips for inline code +\n * highlight, vertical centering when content shorter than height, dashed\n * decorations for underline/strike/link.\n */\nexport const drawTextToCanvas = (ctx: CanvasRenderingContext2D, opts: DrawTextOptions): void => {\n const normalizedText = opts.text.trim()\n if (!normalizedText) return\n\n const lines = layoutTokens(tokenize(opts.text), {\n width: opts.width,\n fontFamily: opts.fontFamily,\n fontSize: opts.fontSize,\n textStyle: opts.textStyle,\n textColor: opts.textColor,\n })\n\n ctx.textBaseline = 'alphabetic'\n ctx.fillStyle = opts.textColor || DEFAULT_TEXT_COLOR\n ctx.strokeStyle = opts.textColor || DEFAULT_TEXT_COLOR\n\n const fontSizePx = FONT_SIZE_MAP[opts.fontSize]\n const lineHeight = LINE_HEIGHT_MAP[opts.fontSize]\n const contentHeight = getContentHeight(lines, lineHeight)\n const availableHeight = Math.max(0, opts.height)\n const shouldCenterVertically = contentHeight <= availableHeight\n const centeredTop = Math.floor((opts.height - contentHeight) / 2)\n const topInset = Math.ceil(fontSizePx * 0.92)\n const startBaseline = shouldCenterVertically\n ? Math.max(topInset, centeredTop + topInset)\n : topInset\n let y = startBaseline\n\n for (const line of lines) {\n const lineTop = y - fontSizePx\n const lineBottom = lineTop + getLineAdvance(line, lineHeight)\n\n if (lineBottom <= 0) {\n y += getLineAdvance(line, lineHeight)\n continue\n }\n if (lineTop >= opts.height) break\n\n if (line.kind === 'code-block') {\n if (line.isFirst) y += CODE_BLOCK_MARGIN_Y\n\n let lineWidth = 0\n for (const run of line.runs) {\n lineWidth += measureText({\n text: run.text,\n type: run.type,\n fontFamily: opts.fontFamily,\n fontSize: opts.fontSize,\n textStyle: 'normal',\n })\n }\n\n const blockX = 0\n const blockY = y - fontSizePx + 2\n const blockWidth = Math.max(10, opts.width)\n const blockHeight = lineHeight\n\n ctx.save()\n ctx.fillStyle = CODE_BG_COLOR\n ctx.fillRect(blockX, blockY, blockWidth, blockHeight)\n ctx.restore()\n\n let x = blockX + CODE_BLOCK_PADDING_X\n if (opts.align === 'center') {\n x = blockX + Math.max(CODE_BLOCK_PADDING_X, Math.floor((blockWidth - lineWidth) / 2))\n } else if (opts.align === 'right') {\n x = blockX + Math.max(CODE_BLOCK_PADDING_X, blockWidth - CODE_BLOCK_PADDING_X - lineWidth)\n }\n\n for (const run of line.runs) {\n const runWidth = measureText({\n text: run.text,\n type: run.type,\n fontFamily: opts.fontFamily,\n fontSize: opts.fontSize,\n textStyle: 'normal',\n })\n ctx.font = getCanvasFont({\n type: run.type,\n fontFamily: opts.fontFamily,\n fontSize: opts.fontSize,\n textStyle: 'normal',\n })\n ctx.fillStyle = opts.textColor || DEFAULT_TEXT_COLOR\n ctx.fillText(run.text, x, y)\n x += runWidth\n }\n\n y += lineHeight\n if (line.isLast) y += CODE_BLOCK_MARGIN_Y\n continue\n }\n\n if (line.kind === 'rule') {\n ctx.save()\n ctx.globalAlpha = 0.55\n ctx.beginPath()\n ctx.moveTo(0, y)\n ctx.lineTo(opts.width, y)\n ctx.lineWidth = 1\n ctx.stroke()\n if (line.double) {\n ctx.beginPath()\n ctx.moveTo(0, y + 3)\n ctx.lineTo(opts.width, y + 3)\n ctx.lineWidth = 1\n ctx.stroke()\n }\n ctx.restore()\n y += lineHeight\n continue\n }\n\n let lineWidth = 0\n for (const run of line.runs) {\n lineWidth += measureText({\n text: run.text,\n type: run.type,\n fontFamily: opts.fontFamily,\n fontSize: opts.fontSize,\n textStyle: opts.textStyle,\n })\n }\n\n let x = getTextX(opts, lineWidth)\n\n for (const run of line.runs) {\n const runWidth = measureText({\n text: run.text,\n type: run.type,\n fontFamily: opts.fontFamily,\n fontSize: opts.fontSize,\n textStyle: opts.textStyle,\n })\n\n // Math runs: blit the cached bitmap if ready, else paint a\n // subdued placeholder (light gray rectangle with `…`). The\n // math-epoch invalidates this bitmap on resolve so the next\n // paint picks up the real glyphs.\n if (run.type === 'math') {\n const mathColor = opts.textColor || DEFAULT_TEXT_COLOR\n const bitmap = getMathBitmap(run.text, mathColor, fontSizePx)\n if (bitmap) {\n // Align the bitmap's baseline to the text baseline `y`.\n // baselineOffset is px from the bitmap top down to baseline.\n ctx.drawImage(bitmap.bitmap, x, y - bitmap.baselineOffset, runWidth, bitmap.height)\n } else {\n ctx.save()\n ctx.fillStyle = 'rgba(148, 163, 184, 0.18)'\n ctx.fillRect(x, y - fontSizePx + 2, runWidth, fontSizePx)\n ctx.fillStyle = '#94a3b8'\n ctx.font = `italic ${Math.max(8, fontSizePx * 0.75)}px system-ui, sans-serif`\n ctx.textBaseline = 'alphabetic'\n ctx.fillText('…', x + runWidth / 2 - 4, y - 2)\n ctx.restore()\n }\n x += runWidth\n continue\n }\n\n if (run.type === 'highlight') {\n ctx.save()\n ctx.fillStyle = opts.highlightColor || DEFAULT_HIGHLIGHT_COLOR\n ctx.fillRect(x - 1, y - fontSizePx + 2, runWidth + 2, fontSizePx + 2)\n ctx.restore()\n }\n\n if (run.type === 'code') {\n ctx.save()\n ctx.fillStyle = CODE_BG_COLOR\n ctx.fillRect(x - 2, y - fontSizePx + 2, runWidth + 4, fontSizePx + 3)\n ctx.restore()\n }\n\n ctx.font = getCanvasFont({\n type: run.type,\n fontFamily: opts.fontFamily,\n fontSize: opts.fontSize,\n textStyle: opts.textStyle,\n })\n const runColor = run.type === 'link' ? LINK_COLOR : opts.textColor || DEFAULT_TEXT_COLOR\n ctx.fillStyle = runColor\n ctx.strokeStyle = runColor\n ctx.fillText(run.text, x, y)\n drawRunDecoration(ctx, x, y, runWidth, run.type, fontSizePx)\n\n x += runWidth\n }\n\n y += lineHeight\n }\n}\n","import type { FontFamily, FontSize, TextAlign, TextStyle } from '../types'\nimport { getFontEpoch, subscribeFontEpoch } from './font-epoch'\nimport { getMathEpoch, subscribeMathEpoch } from './math'\n/**\n * Bitmap cache for rendered markdown content — the architectural rewrite\n * called out in ARCHITECTURE.md §8.\n *\n * dim0's `canvas-lite-markdown.tsx` rendered into a private canvas, called\n * `canvas.toBlob('image/png')`, then wrapped the resulting Blob URL in an\n * `<img>` element. That made sense in a DOM-board context: each note was\n * already a React subtree, and swapping its text for one `<img>` cut DOM\n * paint cost. The async stage there required a queue + listener\n * coalescing + URL.revokeObjectURL lifecycle management — about 150 LOC.\n *\n * In the canvas-harness scene we render into a `<canvas>` already, so the\n * roundtrip to PNG and back is pure waste. This module caches to an\n * `OffscreenCanvas` (or detached `HTMLCanvasElement` fallback) keyed on\n * everything that affects pixel output. On a cache miss we draw\n * synchronously into the cached canvas; on hit we just blit via\n * `ctx.drawImage(cached, x, y, w, h)`.\n *\n * Cache scope is module-global; all `<Canvas>` instances share the same\n * LRU. ~1000-entry cap (configurable on init).\n */\nimport { drawTextToCanvas } from './paint-canvas'\nimport { clampEffectiveScale, quantizeDpr, quantizeZoom, resolveRenderScale } from './render-scale'\n\nconst MAX_CACHE_SIZE = 1000\n\nexport type BitmapCacheRequest = {\n /** Stable id for the source — typically the node id. */\n id: string\n text: string\n /** Logical CSS pixels of the destination rect. */\n width: number\n height: number\n zoom: number\n dpr: number\n isMoving: boolean\n align: TextAlign\n fontFamily: FontFamily\n fontSize: FontSize\n textStyle: TextStyle\n textColor: string\n highlightColor: string\n}\n\nexport type BitmapCacheEntry = {\n /** Backing-store canvas — pass to ctx.drawImage. */\n canvas: HTMLCanvasElement\n /** Logical (CSS) target width — what the caller should draw at. */\n width: number\n /** Logical (CSS) target height. */\n height: number\n}\n\ntype StoredEntry = {\n canvas: HTMLCanvasElement\n width: number\n height: number\n lastUsed: number\n}\n\nconst renderCache = new Map<string, StoredEntry>()\n\n/**\n * Memoize FNV-1a text hashes so the per-frame cache-key build doesn't\n * re-walk the content string for every visible node. Bounded; cleared on\n * font-epoch bump alongside the bitmap cache.\n */\nconst HASH_CACHE_MAX = 2000\nconst textHashCache = new Map<string, string>()\n\n/** Listen for font load → invalidate. */\nsubscribeFontEpoch(() => {\n renderCache.clear()\n textHashCache.clear()\n})\n\n/**\n * Listen for math compile resolves → cause math-bearing bitmaps to\n * miss the cache. We don't actively evict; the new key encodes the\n * bumped epoch so stale entries simply don't match. They LRU out.\n */\nsubscribeMathEpoch(() => {\n // No-op body — the epoch bump alone is enough since `makeKey` reads\n // `getMathEpoch()` for any text containing `$`. We still subscribe\n // to keep the hook active so consumer-side listeners (e.g. the\n // renderer triggering a repaint) can opt in via the same channel.\n})\n\n/**\n * Lookup-or-build. Always returns a non-null entry as long as `text` is\n * non-empty — on miss it draws synchronously and stores. Same call site\n * for hit and miss.\n *\n * Returns null only when the input is empty/whitespace.\n */\nexport const getOrRenderTextBitmap = (req: BitmapCacheRequest): BitmapCacheEntry | null => {\n const text = req.text\n if (!text || !text.trim()) return null\n\n const quantZoom = quantizeZoom(req.zoom)\n const quantDpr = quantizeDpr(req.dpr)\n const renderScale = resolveRenderScale(1, quantZoom, req.isMoving)\n const epoch = getFontEpoch()\n\n const key = makeKey(req, quantZoom, quantDpr, renderScale, epoch)\n\n const cached = renderCache.get(key)\n if (cached) {\n cached.lastUsed = Date.now()\n return { canvas: cached.canvas, width: cached.width, height: cached.height }\n }\n\n const entry = drawIntoNewCanvas(req, quantDpr, renderScale)\n if (!entry) return null\n\n renderCache.set(key, { ...entry, lastUsed: Date.now() })\n evictIfNeeded()\n return { canvas: entry.canvas, width: entry.width, height: entry.height }\n}\n\nconst makeKey = (\n req: BitmapCacheRequest,\n zoom: number,\n dpr: number,\n scale: number,\n epoch: number,\n): string => {\n // Cheap deterministic key — small string concat, no number formatting.\n // cachedTextHash memoizes the FNV-1a walk so a node's content is hashed\n // once across frames, not on every cache lookup.\n //\n // Math-epoch is folded in ONLY when the text contains `$` (cheap\n // includes check). Bitmaps without math never invalidate when math\n // compiles resolve; bitmaps with math get a new key on each epoch\n // bump and stale entries LRU out naturally.\n const mathSuffix = req.text.includes('$') ? `:m${getMathEpoch()}` : ''\n return `${epoch}:${cachedTextHash(req.text)}:${req.width}:${req.height}:${zoom}:${dpr}:${scale}:${req.align}:${req.fontFamily}:${req.fontSize}:${req.textStyle}:${req.textColor}:${req.highlightColor}${mathSuffix}`\n}\n\nconst cachedTextHash = (value: string): string => {\n const hit = textHashCache.get(value)\n if (hit !== undefined) return hit\n const hash = textHash(value)\n // Cap is a simple bound; on overflow clear the whole table rather than\n // pay LRU bookkeeping. The bitmap cache below it remains authoritative.\n if (textHashCache.size >= HASH_CACHE_MAX) textHashCache.clear()\n textHashCache.set(value, hash)\n return hash\n}\n\n/**\n * Fast non-cryptographic hash used to avoid putting full text in the key.\n */\nconst textHash = (value: string): string => {\n let hash = 2166136261\n for (let index = 0; index < value.length; index += 1) {\n hash ^= value.charCodeAt(index)\n hash = Math.imul(hash, 16777619)\n }\n return (hash >>> 0).toString(36)\n}\n\n/**\n * Draws the request into a fresh detached canvas at the resolved scale.\n * Synchronous; returns null if document is unavailable (SSR / Node).\n */\nconst drawIntoNewCanvas = (\n req: BitmapCacheRequest,\n dpr: number,\n baseScale: number,\n): BitmapCacheEntry | null => {\n if (typeof document === 'undefined') return null\n\n const effectiveScale = clampEffectiveScale(baseScale * dpr, req.width, req.height)\n const canvas = document.createElement('canvas')\n canvas.width = Math.max(1, Math.ceil(req.width * effectiveScale))\n canvas.height = Math.max(1, Math.ceil(req.height * effectiveScale))\n\n const ctx = canvas.getContext('2d')\n if (!ctx) return null\n\n // Draw in logical pixels (matches the request width/height) so\n // measureText / layout don't care about the backing-store scale.\n ctx.scale(effectiveScale, effectiveScale)\n\n drawTextToCanvas(ctx, {\n text: req.text,\n width: req.width,\n height: req.height,\n align: req.align,\n fontFamily: req.fontFamily,\n fontSize: req.fontSize,\n textStyle: req.textStyle,\n textColor: req.textColor,\n highlightColor: req.highlightColor,\n })\n\n return { canvas, width: req.width, height: req.height }\n}\n\n/**\n * LRU eviction. Sorts by lastUsed and trims to cap.\n */\nconst evictIfNeeded = (): void => {\n if (renderCache.size <= MAX_CACHE_SIZE) return\n const entries = [...renderCache.entries()].sort((a, b) => a[1].lastUsed - b[1].lastUsed)\n const toRemove = renderCache.size - MAX_CACHE_SIZE\n for (let i = 0; i < toRemove; i++) {\n const victim = entries[i]\n if (!victim) break\n renderCache.delete(victim[0])\n }\n}\n\n/** Test / debug aid. */\nexport const clearTextBitmapCache = (): void => {\n renderCache.clear()\n textHashCache.clear()\n}\n\n/** Test / debug aid. */\nexport const getTextBitmapCacheSize = (): number => renderCache.size\n","/**\n * Brushy edge bodies via perfect-freehand. Used for `solid` rough edges\n * — the dim0 \"Spider-Verse\" look: tapered ends, variable thickness,\n * filled polygon rather than a stroked line.\n *\n * Pipeline:\n * sample polyline → pressure-bell profile → getStroke() → Path2D\n *\n * Caching: the resulting Path2D is keyed on a coarse signature of the\n * sample points + strokeWidth + seed. Subsequent paints (stable scenes)\n * hit the cache and pay only one `ctx.fill()`.\n *\n * `dashed` / `dotted` strokes don't route here — they fall back to\n * `drawRoughEdge` (rough.js linearPath) since a filled polygon can't\n * dash naturally.\n */\nimport { getStroke } from 'perfect-freehand'\nimport type { Vec2 } from '../types'\n\n/**\n * LRU-ish cap on cached Path2Ds. Bigger payload per entry than rough\n * drawables (polygon vertices), so set lower than ROUGH_PATH_CACHE_MAX.\n */\nconst FREEHAND_CACHE_MAX = 500\nconst cache = new Map<string, Path2D>()\n\nconst remember = (key: string, path: Path2D): void => {\n cache.set(key, path)\n if (cache.size > FREEHAND_CACHE_MAX) {\n // Map iteration order is insertion order; evict oldest.\n const oldest = cache.keys().next().value\n if (oldest !== undefined) cache.delete(oldest)\n }\n}\n\n/**\n * Coarse signature: stride-sampled endpoints + length. Quantized to 1px\n * so sub-pixel jitter from camera math doesn't bust the cache every\n * frame. Length is the hash anchor.\n */\nconst signaturePoints = (samples: Vec2[]): string => {\n if (samples.length === 0) return 'e'\n const n = samples.length\n const step = Math.max(1, Math.floor(n / 6))\n const parts: string[] = [String(n)]\n for (let i = 0; i < n; i += step) {\n const p = samples[i]!\n parts.push(`${Math.round(p.x)},${Math.round(p.y)}`)\n }\n const last = samples[n - 1]!\n parts.push(`${Math.round(last.x)},${Math.round(last.y)}`)\n return parts.join('|')\n}\n\ntype StrokeOpts = {\n size: number\n thinning: number\n smoothing: number\n streamline: number\n simulatePressure: false\n last: true\n start: { taper: number; cap: true }\n end: { taper: number; cap: true }\n}\n\n/**\n * perfect-freehand expects `[x, y, pressure]`. Bell profile produces a\n * brush stroke that's thin at both ends and fatter in the middle —\n * matches dim0's signature look.\n */\nconst buildPressurePoints = (samples: Vec2[]): [number, number, number][] => {\n const n = samples.length\n if (n === 0) return []\n const out: [number, number, number][] = new Array(n)\n for (let i = 0; i < n; i++) {\n const t = n === 1 ? 0.5 : i / (n - 1)\n const bell = Math.sin(Math.PI * t)\n const pressure = 0.35 + 0.55 * bell\n const p = samples[i]!\n out[i] = [p.x, p.y, pressure]\n }\n return out\n}\n\n/**\n * Builds the outline polygon and emits a closed Path2D. Quadratic\n * midpoint smoothing on the polygon edges (the tldraw trick) gives\n * soft corners instead of faceted ones.\n */\nconst outlineToPath2D = (ring: number[][]): Path2D => {\n const path = new Path2D()\n const n = ring.length\n if (n === 0) return path\n if (n < 3) {\n path.moveTo(ring[0]![0]!, ring[0]![1]!)\n path.closePath()\n return path\n }\n path.moveTo(ring[0]![0]!, ring[0]![1]!)\n for (let i = 0; i < n; i++) {\n const a = ring[i]!\n const b = ring[(i + 1) % n]!\n const mx = (a[0]! + b[0]!) / 2\n const my = (a[1]! + b[1]!) / 2\n path.quadraticCurveTo(a[0]!, a[1]!, mx, my)\n }\n path.closePath()\n return path\n}\n\n/**\n * Returns a Path2D representing the brushy outline of `samples`. Cached\n * by sample-signature + strokeWidth + seed. Caller fills it with\n * `ctx.fillStyle = stroke; ctx.fill(path)`.\n *\n * `seed` exists to keep the cache key stable per-edge across frames\n * even though perfect-freehand itself is deterministic — different\n * edges produce different polygons because their inputs differ, not\n * because of any random source.\n */\nexport const getOrBuildFreehandPath = (\n samples: Vec2[],\n strokeWidth: number,\n seed: number,\n): Path2D | null => {\n if (samples.length < 2) return null\n const cacheKey = `${seed}|${strokeWidth.toFixed(2)}|${signaturePoints(samples)}`\n const hit = cache.get(cacheKey)\n if (hit) {\n // LRU touch: re-insert at tail.\n cache.delete(cacheKey)\n cache.set(cacheKey, hit)\n return hit\n }\n\n const pts = buildPressurePoints(samples)\n if (pts.length < 2) return null\n\n const size = Math.max(1.2, strokeWidth) * 1.3\n const taper = Math.min(24, size * 3)\n const strokeOpts: StrokeOpts = {\n size,\n thinning: 0.55,\n smoothing: 0.6,\n streamline: 0.55,\n simulatePressure: false,\n last: true,\n start: { taper, cap: true },\n end: { taper, cap: true },\n }\n const ring = getStroke(pts, strokeOpts)\n if (!ring || ring.length === 0) return null\n\n const path = outlineToPath2D(ring)\n remember(cacheKey, path)\n return path\n}\n\n/** Reset state — tests only. */\nexport const __resetFreehandCache = (): void => {\n cache.clear()\n}\n\n/** Diagnostic only. */\nexport const getFreehandCacheSize = (): number => cache.size\n","import { seedFromId } from '../render/rough/cache'\nimport { type ThemeResolver, dashPatternFor } from '../render/shapes/defaults'\nimport {\n DEFAULT_TEXT_COLOR,\n FONT_SIZE_MAP,\n LINE_HEIGHT_MAP,\n getOrRenderTextBitmap,\n measureText,\n subscribeFontEpoch,\n} from '../text'\nimport type { Edge, EdgeStyle, Node, Vec2 } from '../types'\n/**\n * Edge paint pipeline — see ARCHITECTURE.md §6.5–§6.7.\n *\n * Takes a precomputed EdgeGeometry (samples + AABB) and the attached\n * nodes, runs auto-clip, paints the visible polyline, draws arrowheads\n * at the clipped endpoints. World coords; caller already applied the\n * camera transform.\n */\nimport { getPointAndTangentAtArcLength } from './arc-length'\nimport { arrowheadLength, drawArrowhead } from './arrowhead'\nimport type { EdgeGeometry } from './cache'\nimport { clipSamples, fullVisibleClipResult } from './clip'\nimport { getOrBuildFreehandPath } from './freehand'\n\n/** Defaults for edge style — see ARCHITECTURE.md §3.4. */\nconst DEFAULT_EDGE_STYLE: Required<\n Pick<\n EdgeStyle,\n 'strokeColor' | 'strokeWidth' | 'strokeStyle' | 'sourceArrowhead' | 'targetArrowhead'\n >\n> = {\n strokeColor: '#475569',\n strokeWidth: 2,\n strokeStyle: 'solid',\n sourceArrowhead: 'none',\n targetArrowhead: 'arrow-filled',\n}\n\nconst STROKE_VISIBILITY_THRESHOLD_PX = 0.5\n\n/** Below this on-screen length, an arrowhead is invisible noise; skip it. */\nconst ARROWHEAD_VISIBILITY_THRESHOLD_PX = 2\n\n/**\n * How many polyline samples to skip per drawn segment when painting the\n * body. The cached sample array is 32 segments for visual smoothness at\n * full zoom, but at low zoom adjacent samples are within a fraction of a\n * pixel — drawing every-Nth is indistinguishable but cuts work N-fold.\n *\n * Hit-test, auto-clip, and arrowhead-tangent still walk the full sample\n * array — only the per-frame path build skips. So no correctness impact.\n */\nconst samplePaintStride = (scale: number): number => {\n if (scale < 0.15) return 8\n if (scale < 0.3) return 4\n if (scale < 0.7) return 2\n return 1\n}\n\n/**\n * Edge paint entry. `scale` is the world → device factor (camera.z ×\n * dpr) — kept for back-compat with PNG export and tests. `opts.zoom`,\n * `opts.dpr`, `opts.isMoving` control the label bitmap-cache LOD; if\n * omitted, derived from `scale` (zoom = scale, dpr = 1, idle).\n */\nexport const drawEdge = (\n ctx: CanvasRenderingContext2D,\n edge: Edge,\n geom: EdgeGeometry,\n sourceNode: Node | null,\n targetNode: Node | null,\n scale: number,\n theme?: ThemeResolver,\n opts?: { roughEnabled?: boolean; zoom?: number; dpr?: number; isMoving?: boolean },\n): void => {\n if (edge.hidden) return\n const samples = geom.samples\n if (samples.length < 2) return\n\n const style = edge.style\n const strokeWidth =\n typeof style?.strokeWidth === 'number'\n ? style.strokeWidth\n : ((theme?.('strokeWidth') as number | undefined) ?? DEFAULT_EDGE_STYLE.strokeWidth)\n if (strokeWidth * scale < STROKE_VISIBILITY_THRESHOLD_PX) return\n\n const strokeColor =\n typeof style?.strokeColor === 'string'\n ? style.strokeColor\n : ((theme?.('edge.strokeColor') as string | undefined) ?? DEFAULT_EDGE_STYLE.strokeColor)\n const sourceArrowhead = style?.sourceArrowhead ?? DEFAULT_EDGE_STYLE.sourceArrowhead\n const targetArrowhead = style?.targetArrowhead ?? DEFAULT_EDGE_STYLE.targetArrowhead\n\n // Self-loop doesn't get clipped (both endpoints are on the same node).\n const clip = geom.isSelfLoop\n ? fullVisibleClipResult(samples)\n : clipSamples(samples, sourceNode, targetNode)\n if (!clip.visible) return\n\n // Arrowheads vanish at sub-perceivable on-screen size; the line still\n // shows, just without the cap.\n const headStartWorld = arrowheadLength(sourceArrowhead, strokeWidth)\n const headEndWorld = arrowheadLength(targetArrowhead, strokeWidth)\n const drawSourceArrow =\n sourceArrowhead !== 'none' && headStartWorld * scale >= ARROWHEAD_VISIBILITY_THRESHOLD_PX\n const drawTargetArrow =\n targetArrowhead !== 'none' && headEndWorld * scale >= ARROWHEAD_VISIBILITY_THRESHOLD_PX\n\n // Pull the rendered polyline endpoints back by the arrowhead length so\n // the line tail doesn't poke through the arrow tip — only when actually\n // drawing the arrow.\n const lineStart = drawSourceArrow\n ? retreatFromPoint(samples, clip.startIndex, clip.startPoint, headStartWorld, +1)\n : clip.startPoint\n const lineEnd = drawTargetArrow\n ? retreatFromPoint(samples, clip.endIndex, clip.endPoint, headEndWorld, -1)\n : clip.endPoint\n\n // ---- body ----\n // Rough body when (a) gate from caller is on, (b) style.roughness > 0.\n // Two technique dispatch:\n // solid stroke → perfect-freehand brushy polygon (filled, tapered).\n // dashed/dotted → plain ctx.stroke below (rough.js's per-segment\n // wobble + bowing distorts each dash differently,\n // leaving the line fuzzy rather than reading as a\n // regular pattern). Drops the wobble for dashed\n // edges but the pattern stays cleanly visible.\n const isSolidStroke = (style?.strokeStyle ?? 'solid') === 'solid'\n const useRough = isSolidStroke && (opts?.roughEnabled ?? false) && (style?.roughness ?? 0) > 0\n if (useRough) {\n // Build a clipped sub-sample sequence so the rough body doesn't\n // extend past the visible portion (otherwise the wobble/brush pokes\n // into the node bodies). Re-uses the existing clip indices.\n const clipped: Vec2[] = [lineStart]\n for (let i = clip.startIndex + 1; i < clip.endIndex; i++) clipped.push(samples[i]!)\n clipped.push(lineEnd)\n\n const seed = edge.id ? (seedFromId(edge.id) % 2147483646) + 1 : 1337\n const path = getOrBuildFreehandPath(clipped, strokeWidth, seed)\n if (path) {\n ctx.save()\n ctx.fillStyle = strokeColor\n ctx.fill(path)\n ctx.restore()\n if (drawSourceArrow) {\n const tipDir = directionTowardTip(samples, clip.startIndex, clip.startPoint, +1)\n drawArrowhead(\n ctx,\n sourceArrowhead,\n clip.startPoint,\n negateVec(tipDir),\n strokeColor,\n strokeWidth,\n )\n }\n if (drawTargetArrow) {\n const tipDir = directionTowardTip(samples, clip.endIndex, clip.endPoint, -1)\n drawArrowhead(ctx, targetArrowhead, clip.endPoint, tipDir, strokeColor, strokeWidth)\n }\n if (edge.content?.trim()) drawEdgeLabel(ctx, edge, geom, scale, theme, opts)\n return\n }\n // freehand returned null (degenerate samples) — fall through to plain.\n }\n\n ctx.save()\n ctx.strokeStyle = strokeColor\n ctx.lineWidth = strokeWidth\n ctx.lineCap = 'round'\n ctx.lineJoin = 'round'\n ctx.setLineDash(dashPatternFor(style?.strokeStyle, strokeWidth))\n ctx.beginPath()\n ctx.moveTo(lineStart.x, lineStart.y)\n // Adaptive sampling: stride through the cached polyline at low zoom.\n // Hit-test / clip still use the full samples; only paint skips.\n const stride = samplePaintStride(scale)\n const limit = clip.endIndex - 1\n for (let i = clip.startIndex + stride; i <= limit; i += stride) {\n const p = samples[i]!\n ctx.lineTo(p.x, p.y)\n }\n ctx.lineTo(lineEnd.x, lineEnd.y)\n ctx.stroke()\n ctx.restore()\n\n // ---- arrowheads ----\n if (drawSourceArrow) {\n const tipDir = directionTowardTip(samples, clip.startIndex, clip.startPoint, +1)\n drawArrowhead(\n ctx,\n sourceArrowhead,\n clip.startPoint,\n negateVec(tipDir),\n strokeColor,\n strokeWidth,\n )\n }\n if (drawTargetArrow) {\n const tipDir = directionTowardTip(samples, clip.endIndex, clip.endPoint, -1)\n drawArrowhead(ctx, targetArrowhead, clip.endPoint, tipDir, strokeColor, strokeWidth)\n }\n\n // ---- label (§6.11) ----\n // Painted last so it sits on top of the body + arrowheads.\n if (edge.content?.trim()) {\n drawEdgeLabel(ctx, edge, geom, scale, theme, opts)\n }\n}\n\n/** Minimum on-screen font size — text smaller than this is unreadable\n * noise, skip the chip + blit. Same threshold the node-content paint uses. */\nconst LABEL_MIN_READABLE_FONT_PX = 3\nconst LABEL_MAX_WIDTH_PX = 240\nconst LABEL_PADDING_X = 6\nconst LABEL_PADDING_Y = 2\nconst LABEL_BORDER_RADIUS = 3\n\nconst DEFAULT_LABEL_BACKGROUND = '#ffffff'\n\ntype LabelDims = { width: number; height: number; fontPx: number }\n\n/**\n * Memoizes `computeLabelDims` per (content, font-family, font-size,\n * font-style) tuple. Many edges share labels in real graphs (\"yes\" /\n * \"no\" / \"depends on\"), so the hit rate is high. Cleared on font-epoch\n * bump because `measureText` depends on font load state.\n */\nconst labelDimsCache = new Map<string, LabelDims>()\nconst LABEL_DIMS_CACHE_MAX = 512\n\nsubscribeFontEpoch(() => {\n labelDimsCache.clear()\n})\n\n/**\n * Computes the label dimensions for an edge in world units. Heuristic:\n * - width: single-line measurement of the raw content, clamped to\n * [20, LABEL_MAX_WIDTH_PX]. Beyond the cap, the markdown layout\n * wraps to multiple lines.\n * - height: one line-height per wrap line, plus vertical padding.\n *\n * Returns null if dimensions are zero (empty content).\n */\nconst computeLabelDims = (edge: Edge): LabelDims | null => {\n const content = edge.content\n if (!content) return null\n const style = edge.style\n const fontFamily = style?.fontFamily ?? 'handwriting'\n const fontSize = style?.fontSize ?? 'M'\n const textStyle = style?.textStyle ?? 'normal'\n const cacheKey = `${content}|${fontFamily}|${fontSize}|${textStyle}`\n const hit = labelDimsCache.get(cacheKey)\n if (hit) return hit\n\n const fontPx = FONT_SIZE_MAP[fontSize]\n const naturalWidth = measureText({\n text: content,\n type: 'text',\n fontFamily,\n fontSize,\n textStyle,\n })\n const width = Math.min(LABEL_MAX_WIDTH_PX, Math.max(20, naturalWidth + LABEL_PADDING_X * 2))\n const lines = Math.max(1, Math.ceil(naturalWidth / Math.max(1, width - LABEL_PADDING_X * 2)))\n const height = lines * LINE_HEIGHT_MAP[fontSize] + LABEL_PADDING_Y * 2\n const dims: LabelDims = { width, height, fontPx }\n if (labelDimsCache.size >= LABEL_DIMS_CACHE_MAX) labelDimsCache.clear()\n labelDimsCache.set(cacheKey, dims)\n return dims\n}\n\n/**\n * Memoizes `getPointAndTangentAtArcLength` per (geometry, arcLength).\n * The geometry-cache returns the same object reference until any input\n * changes, so a WeakMap keyed on geometry auto-invalidates for free.\n *\n * Hot path: ~5-8µs / labeled edge saved per frame (the two-pass walk\n * over 32 samples per edge becomes a Map lookup).\n */\nconst anchorCache = new WeakMap<EdgeGeometry, Map<number, { point: Vec2; tangent: Vec2 }>>()\n\nconst getCachedLabelAnchor = (\n geom: EdgeGeometry,\n arcLength: number,\n): { point: Vec2; tangent: Vec2 } => {\n let bucket = anchorCache.get(geom)\n if (!bucket) {\n bucket = new Map()\n anchorCache.set(geom, bucket)\n }\n const hit = bucket.get(arcLength)\n if (hit) return hit\n const fresh = getPointAndTangentAtArcLength(geom.samples, arcLength)\n bucket.set(arcLength, fresh)\n return fresh\n}\n\nconst drawEdgeLabel = (\n ctx: CanvasRenderingContext2D,\n edge: Edge,\n geom: EdgeGeometry,\n scale: number,\n theme?: ThemeResolver,\n opts?: { zoom?: number; dpr?: number; isMoving?: boolean },\n): void => {\n const style = edge.style\n const fontSize = style?.fontSize ?? 'M'\n if (FONT_SIZE_MAP[fontSize] * scale < LABEL_MIN_READABLE_FONT_PX) return\n\n const dims = computeLabelDims(edge)\n if (!dims) return\n\n const t = clamp01(style?.labelArcLength ?? 0.5)\n const { point, tangent } = getCachedLabelAnchor(geom, t)\n const followTangent = style?.labelFollowsTangent === true\n\n // Per-edge override wins; falls through to theme, then to the\n // built-in white default.\n const bg =\n style?.labelBackground ??\n (theme?.('edge.label.background') as string | undefined) ??\n DEFAULT_LABEL_BACKGROUND\n\n ctx.save()\n ctx.translate(point.x, point.y)\n if (followTangent) {\n let angle = Math.atan2(tangent.y, tangent.x)\n // Keep text readable: flip upside-down labels so they read L→R.\n if (angle > Math.PI / 2) angle -= Math.PI\n if (angle < -Math.PI / 2) angle += Math.PI\n ctx.rotate(angle)\n }\n\n // Center the label rect on the anchor.\n const w = dims.width\n const h = dims.height\n const x = -w / 2\n const y = -h / 2\n\n // Chip background (rounded rect). Skipped when transparent so the\n // text renders directly over the edge line.\n if (bg !== 'none' && bg !== 'transparent') {\n ctx.fillStyle = bg\n drawRoundRect(ctx, x, y, w, h, LABEL_BORDER_RADIUS)\n ctx.fill()\n }\n\n // Text bitmap (reuses the Phase-6 cache). Matches the LOD args used\n // by node content paint — zoom = camera.z (not camera.z × dpr); dpr\n // = staticSurface.dpr (sharp on retina); isMoving threads through\n // from the renderer for the motion-LOD drop.\n const bitmap = getOrRenderTextBitmap({\n id: edge.id,\n text: edge.content ?? '',\n width: w,\n height: h,\n zoom: opts?.zoom ?? scale,\n dpr: opts?.dpr ?? 1,\n isMoving: opts?.isMoving ?? false,\n align: 'center',\n fontFamily: style?.fontFamily ?? 'handwriting',\n fontSize,\n textStyle: style?.textStyle ?? 'normal',\n textColor: style?.textColor ?? DEFAULT_TEXT_COLOR,\n highlightColor: '#fde047',\n })\n if (bitmap) ctx.drawImage(bitmap.canvas, x, y, w, h)\n ctx.restore()\n}\n\nconst clamp01 = (v: number): number => Math.max(0, Math.min(1, v))\n\nconst drawRoundRect = (\n ctx: CanvasRenderingContext2D,\n x: number,\n y: number,\n w: number,\n h: number,\n r: number,\n): void => {\n const radius = Math.min(r, w / 2, h / 2)\n ctx.beginPath()\n ctx.moveTo(x + radius, y)\n ctx.lineTo(x + w - radius, y)\n ctx.arcTo(x + w, y, x + w, y + radius, radius)\n ctx.lineTo(x + w, y + h - radius)\n ctx.arcTo(x + w, y + h, x + w - radius, y + h, radius)\n ctx.lineTo(x + radius, y + h)\n ctx.arcTo(x, y + h, x, y + h - radius, radius)\n ctx.lineTo(x, y + radius)\n ctx.arcTo(x, y, x + radius, y, radius)\n ctx.closePath()\n}\n\n/**\n * World-space label bounding box. Used by the hit-test (see\n * `hitTestEdge`). Returns `null` when the edge has no content.\n */\nexport const edgeLabelBoundsWorld = (\n edge: Edge,\n geom: EdgeGeometry,\n): { x: number; y: number; w: number; h: number } | null => {\n if (!edge.content || !edge.content.trim()) return null\n const dims = computeLabelDims(edge)\n if (!dims) return null\n const t = clamp01(edge.style?.labelArcLength ?? 0.5)\n const { point } = getCachedLabelAnchor(geom, t)\n return {\n x: point.x - dims.width / 2,\n y: point.y - dims.height / 2,\n w: dims.width,\n h: dims.height,\n }\n}\n\n/**\n * Returns a unit vector pointing along the curve toward the clipped tip.\n * `direction` = +1 walks samples forward (for source end), -1 backward.\n */\nconst directionTowardTip = (\n samples: Vec2[],\n clippedIndex: number,\n clipPoint: Vec2,\n direction: 1 | -1,\n): Vec2 => {\n const neighbor =\n direction === 1\n ? samples[Math.min(clippedIndex + 1, samples.length - 1)]!\n : samples[Math.max(clippedIndex - 1, 0)]!\n // tip direction = unit vector FROM neighbor TO tip\n const dx = clipPoint.x - neighbor.x\n const dy = clipPoint.y - neighbor.y\n const len = Math.hypot(dx, dy)\n if (len < 1e-6) return { x: direction, y: 0 }\n return { x: dx / len, y: dy / len }\n}\n\n/**\n * Returns the point `dist` along the curve back from `clipPoint`, toward\n * the curve interior. Used to retreat the line so the body doesn't poke\n * through the arrowhead tip.\n */\nconst retreatFromPoint = (\n samples: Vec2[],\n clippedIndex: number,\n clipPoint: Vec2,\n dist: number,\n direction: 1 | -1,\n): Vec2 => {\n if (dist <= 0) return clipPoint\n const neighbor =\n direction === 1\n ? samples[Math.min(clippedIndex + 1, samples.length - 1)]!\n : samples[Math.max(clippedIndex - 1, 0)]!\n const dx = clipPoint.x - neighbor.x\n const dy = clipPoint.y - neighbor.y\n const len = Math.hypot(dx, dy)\n if (len < 1e-6) return clipPoint\n const t = Math.min(1, dist / len)\n return {\n x: clipPoint.x - (dx / len) * dist * Math.min(1, t),\n y: clipPoint.y - (dy / len) * dist * Math.min(1, t),\n }\n}\n\nconst negateVec = (v: Vec2): Vec2 => ({ x: -v.x, y: -v.y })\n","/**\n * Custom node type definitions — see ARCHITECTURE.md §5.\n *\n * `defineNode` creates a registerable NodeTypeDef. The core doesn't know\n * about React; the `view` field is typed as `unknown` so the React layer\n * (or the playground for phase 5) can stash a component reference there\n * without coupling the core package to React.\n *\n * The library reads:\n * - kind: 'canvas' | 'react' — which render path applies\n * - renderCanvas / drawPlaceholder — canvas paint functions\n * - getSnapshot — optional bitmap fallback for LOD / motion\n * - hitTest / getOutline — interaction hooks\n * - lod — zoom thresholds\n * - lifecycle hooks\n *\n * Consumers register types via `createCanvasStore({ nodeTypes: [...] })`.\n */\nimport type { Node, Vec2 } from '../types'\n\nexport type RenderEnv = {\n zoom: number\n isMoving: boolean\n isSelected: boolean\n isHovered: boolean\n isEditing: boolean\n theme(token: string): string | number | undefined\n}\n\nexport type SnapshotEnv = {\n width: number\n height: number\n dpr: number\n}\n\nexport type NodeTypeDefOptions = {\n /** Unique type id, e.g. 'chart-card'. */\n type: string\n\n // ----- canvas paint paths (one of renderCanvas or react view required) -----\n /**\n * Canvas paint for the node body. Caller has already applied the\n * camera + node transform, so paint at `(0, 0, node.w, node.h)`.\n *\n * Context state contract:\n * - The renderer wraps this call in `ctx.save()` / `ctx.restore()`\n * so any state you change (fillStyle, strokeStyle, lineWidth,\n * setLineDash, globalAlpha, font, …) is automatically rolled\n * back before the next node draws — set whatever you need\n * without worrying about cleanup.\n * - Conversely, **do NOT assume default state on entry.** Always\n * set the styles you depend on; the previous node's values\n * may still be in effect.\n * - The transform is NOT save/restore-protected at this level\n * (it's managed one frame up by the renderer). Don't leave\n * `translate` / `rotate` / `scale` calls un-paired.\n */\n renderCanvas?: (ctx: CanvasRenderingContext2D, node: Node, env: RenderEnv) => void\n /**\n * Low-zoom / motion fallback paint — see ARCHITECTURE.md §5.3 LOD.\n * Same context-state contract as `renderCanvas`.\n */\n drawPlaceholder?: (ctx: CanvasRenderingContext2D, node: Node, env: RenderEnv) => void\n\n // ----- React view (opaque to core; the React layer / playground knows what to do) -----\n /**\n * The React view component reference. Stored as `unknown` here because the\n * core package is framework-agnostic. The React layer reads this field\n * when it needs to mount a custom node in the DOM overlay.\n */\n view?: unknown\n\n // ----- LOD config (defaults applied in normalizeNodeTypeDef) -----\n lod?: {\n /** Below this zoom, prefer drawPlaceholder over the React view. Default 0.7. */\n minZoomForReact?: number\n /** Below this zoom, skip the node entirely. Default 0.3. */\n minZoomForPlaceholder?: number\n /** ms; default Infinity. After this age, the snapshot is regenerated. */\n snapshotMaxAge?: number\n }\n\n /**\n * Author-provided rasterized fallback. Library calls this when it needs a\n * fast paint (motion, low zoom) and uses `drawImage` to blit. Returns null\n * to fall back to `drawPlaceholder`.\n */\n getSnapshot?: (\n node: Node,\n env: SnapshotEnv,\n ) => CanvasImageSource | null | Promise<CanvasImageSource | null>\n\n // ----- behavior -----\n /**\n * Custom hit-test. Receives the world point pre-transformed into the node's\n * pre-rotation local frame, origin top-left. Default: AABB.\n */\n hitTest?: (node: Node, localPoint: Vec2) => boolean\n /**\n * Custom outline polygon (in node-local coords). Default: rect AABB.\n * Used by the edge auto-clip system when an edge attaches to this node.\n */\n getOutline?: (node: Node) => Vec2[] | null\n\n // ----- lifecycle -----\n /** Called when the node enters the viewport / mounts a live React view. */\n onEnter?: (node: Node) => void\n /** Called when the node exits the viewport / unmounts. */\n onExit?: (node: Node) => void\n /**\n * If true, the React view stays mounted (hidden via visibility:hidden) when\n * off-screen instead of unmounting. Use sparingly — defeats viewport culling.\n * Default false.\n */\n keepMounted?: boolean\n\n /** Validation / migration on scene load. */\n parse?: (raw: unknown) => Node['data']\n migrate?: (data: unknown, fromVersion: number) => Node['data']\n}\n\n/**\n * Normalized form of a node type definition. The `kind` field is derived\n * from which render paths are provided so the renderer dispatch is one\n * `switch` away.\n */\nexport type NodeTypeDef = NodeTypeDefOptions & {\n kind: 'canvas-only' | 'react-only' | 'mixed' | 'invalid'\n lod: {\n minZoomForReact: number\n minZoomForPlaceholder: number\n snapshotMaxAge: number\n }\n}\n\nconst DEFAULT_LOD = {\n minZoomForReact: 0.7,\n minZoomForPlaceholder: 0.3,\n snapshotMaxAge: Number.POSITIVE_INFINITY,\n} as const\n\n/**\n * Defines a custom node type. Register the returned def via\n * `createCanvasStore({ nodeTypes: [myDef, ...] })`; then any `Node`\n * with `type === opts.type` will be dispatched to your renderers + hit\n * test + lifecycle hooks.\n *\n * A type must supply at least one render path: `renderCanvas` (paints\n * via the 2D context), `view` (React component reference — used by\n * `<Canvas renderCustomNodeView>`), or both (`mixed` — canvas at low\n * zoom, React at high zoom).\n *\n * @example\n * // Canvas-only — fastest path, paints with the 2D context.\n * export const sparklineDef = defineNode({\n * type: 'sparkline',\n * renderCanvas(ctx, node, env) {\n * ctx.strokeStyle = env.theme('node.stroke') as string ?? '#000'\n * // ...draw a sparkline...\n * },\n * hitTest: (node, p) => p.x >= 0 && p.x <= node.w && p.y >= 0 && p.y <= node.h,\n * })\n *\n * @example\n * // React view — full UI; library mounts it in the DOM overlay above\n * // the canvas at high zoom, falls back to drawPlaceholder below.\n * export const chartCardDef = defineNode({\n * type: 'chart-card',\n * view: ChartCardComponent,\n * drawPlaceholder(ctx, node) {\n * ctx.fillStyle = '#e0e7ff'\n * ctx.fillRect(0, 0, node.w, node.h)\n * },\n * lod: { minZoomForReact: 0.7, minZoomForPlaceholder: 0.3 },\n * })\n */\nexport const defineNode = (opts: NodeTypeDefOptions): NodeTypeDef => {\n const hasCanvas = !!opts.renderCanvas\n const hasView = !!opts.view\n let kind: NodeTypeDef['kind']\n if (hasCanvas && hasView) kind = 'mixed'\n else if (hasCanvas) kind = 'canvas-only'\n else if (hasView) kind = 'react-only'\n else kind = 'invalid'\n\n return {\n ...opts,\n kind,\n lod: {\n minZoomForReact: opts.lod?.minZoomForReact ?? DEFAULT_LOD.minZoomForReact,\n minZoomForPlaceholder: opts.lod?.minZoomForPlaceholder ?? DEFAULT_LOD.minZoomForPlaceholder,\n snapshotMaxAge: opts.lod?.snapshotMaxAge ?? DEFAULT_LOD.snapshotMaxAge,\n },\n }\n}\n","import { LINE_HEIGHT_MAP, estimateMarkdownContentHeight } from '../text'\nimport type { Node } from '../types'\n\n/**\n * Auto-fit policy — see ARCHITECTURE.md §8 and IMPLEMENTATION.md Phase 7.\n *\n * Height of a content-bearing node is recomputed on **commit boundaries**:\n * - `store.addNode` (when creating a node with content)\n * - `store.commitEdit` (when the user finishes editing)\n * - resize-commit (when a width-resize ends; new wrap → new height)\n *\n * NEVER per-keystroke. The textarea-editor grows its own DOM textarea\n * during typing; the canvas catches up once on commit.\n */\n\n/**\n * Should this node auto-fit its height to its content?\n *\n * Default: true for all node types — matches tldraw/excalidraw behavior\n * where a sticky / shape grows to fit whatever you type. Set\n * `style.autoFit: false` to opt out.\n */\nexport const shouldAutoFit = (node: Node): boolean => {\n return node.style?.autoFit !== false\n}\n\n/**\n * Returns the height this node *would* have if its content laid out at its\n * current width and style. For empty content, returns one line-height so a\n * shape with the empty-content placeholder isn't zero-sized.\n */\nexport const computeAutoFitHeight = (node: Node): number => {\n const fontSize = node.style?.fontSize ?? 'M'\n const oneLine = LINE_HEIGHT_MAP[fontSize]\n const content = node.content ?? ''\n if (!content.trim()) return oneLine\n return Math.max(\n oneLine,\n estimateMarkdownContentHeight({\n text: content,\n width: node.w,\n fontFamily: node.style?.fontFamily,\n fontSize,\n textStyle: node.style?.textStyle,\n }),\n )\n}\n\n/**\n * Pure: returns a copy of `node` with `h` adjusted to fit `content`, if\n * the node opts into autofit. Otherwise returns the input unchanged.\n *\n * Pure-by-design so it can run inside `addNode` before the op is enqueued\n * (avoids a double op: add + update-height).\n */\nexport const withAutoFitHeight = (node: Node): Node => {\n if (!shouldAutoFit(node)) return node\n // Empty content → no autofit; preserve the user's explicit h. Otherwise\n // we'd shrink every freshly-created shape to a single line.\n if (!node.content || !node.content.trim()) return node\n const fitted = computeAutoFitHeight(node)\n // Grow-only: never collapse a deliberately-tall node down to its\n // content height. tldraw / excalidraw behave the same way.\n if (fitted <= node.h) return node\n return { ...node, h: fitted }\n}\n","/**\n * Editor markdown shortcuts — see IMPLEMENTATION.md Phase 7.\n *\n * Pure string-transform helpers, framework-agnostic. The default DOM\n * textarea editor wires these to keyboard events; consumers using a\n * custom adapter (Lexical / ProseMirror) can ignore this module.\n *\n * Each transform takes `(value, selStart, selEnd)` and returns the new\n * value + new selection so the editor can update its DOM textarea in\n * one pass.\n */\n\nexport type Transform = {\n value: string\n selStart: number\n selEnd: number\n}\n\nconst wrapSelection = (\n value: string,\n selStart: number,\n selEnd: number,\n wrapper: string,\n): Transform => {\n const wrapLen = wrapper.length\n // Case 1: selection is immediately surrounded by the wrapper (selection\n // is the inner text). Strip the surrounding markers.\n if (\n selStart >= wrapLen &&\n value.slice(selStart - wrapLen, selStart) === wrapper &&\n value.slice(selEnd, selEnd + wrapLen) === wrapper\n ) {\n const next =\n value.slice(0, selStart - wrapLen) +\n value.slice(selStart, selEnd) +\n value.slice(selEnd + wrapLen)\n return {\n value: next,\n selStart: selStart - wrapLen,\n selEnd: selEnd - wrapLen,\n }\n }\n const middle = value.slice(selStart, selEnd)\n const before = value.slice(0, selStart)\n const after = value.slice(selEnd)\n // Case 2: selection itself starts and ends with the wrapper (user\n // selected the markers along with the content).\n if (middle.startsWith(wrapper) && middle.endsWith(wrapper) && middle.length >= wrapLen * 2) {\n const inner = middle.slice(wrapLen, middle.length - wrapLen)\n const next = before + inner + after\n return { value: next, selStart, selEnd: selStart + inner.length }\n }\n // Case 3: wrap the selection.\n const next = before + wrapper + middle + wrapper + after\n return {\n value: next,\n selStart: selStart + wrapLen,\n selEnd: selEnd + wrapLen,\n }\n}\n\nexport const toggleBold = (v: string, s: number, e: number): Transform =>\n wrapSelection(v, s, e, '**')\n\nexport const toggleItalic = (v: string, s: number, e: number): Transform =>\n wrapSelection(v, s, e, '*')\n\nexport const toggleUnderline = (v: string, s: number, e: number): Transform =>\n wrapSelection(v, s, e, '__')\n\nexport const toggleStrike = (v: string, s: number, e: number): Transform =>\n wrapSelection(v, s, e, '~~')\n\nexport const toggleCode = (v: string, s: number, e: number): Transform =>\n wrapSelection(v, s, e, '`')\n\n/**\n * Inserts `[selection](url)`. If `url` is empty the cursor lands inside\n * the parens so the user can type the URL.\n */\nexport const insertLink = (\n value: string,\n selStart: number,\n selEnd: number,\n url: string,\n): Transform => {\n const before = value.slice(0, selStart)\n const middle = value.slice(selStart, selEnd) || 'link'\n const after = value.slice(selEnd)\n const inserted = `[${middle}](${url})`\n const next = before + inserted + after\n // Place cursor inside the url parens if url is empty, else at end.\n if (url) {\n const newSel = selStart + inserted.length\n return { value: next, selStart: newSel, selEnd: newSel }\n }\n const newSel = before.length + middle.length + 3 // after \"](\"\n return { value: next, selStart: newSel, selEnd: newSel }\n}\n\n/**\n * Auto-list — when the user presses Enter inside a `- ` (or `* `, or\n * `1. ` etc.) line, the next line gets the same prefix prepended.\n * Two consecutive Enters on an empty list line exit the list.\n *\n * Returns a transform when an auto-list rule fires, else null. The\n * editor should fall back to the textarea's default Enter behavior in\n * the null case.\n */\nexport const handleEnter = (value: string, selStart: number, selEnd: number): Transform | null => {\n if (selStart !== selEnd) return null\n const lineStart = value.lastIndexOf('\\n', selStart - 1) + 1\n const lineText = value.slice(lineStart, selStart)\n const match = lineText.match(/^(\\s*)([-*]|\\d+\\.) (.*)$/)\n if (!match) return null\n const indent = match[1] ?? ''\n const bullet = match[2] ?? ''\n const rest = match[3] ?? ''\n // Empty list line + Enter → exit list (remove the bullet from current\n // line; produce a plain newline).\n if (rest.trim() === '') {\n const next = value.slice(0, lineStart) + value.slice(selStart)\n return { value: next, selStart: lineStart, selEnd: lineStart }\n }\n const nextBullet = /^\\d+\\.$/.test(bullet) ? `${Number.parseInt(bullet, 10) + 1}.` : bullet\n const insertion = `\\n${indent}${nextBullet} `\n const next = value.slice(0, selStart) + insertion + value.slice(selStart)\n const newSel = selStart + insertion.length\n return { value: next, selStart: newSel, selEnd: newSel }\n}\n","import { FONT_FAMILY_MAP, FONT_SIZE_MAP, LINE_HEIGHT_MAP } from '../text'\nimport type { EditorAdapter, EditorAdapterFactory } from './adapter'\nimport {\n handleEnter,\n insertLink,\n toggleBold,\n toggleCode,\n toggleItalic,\n toggleStrike,\n toggleUnderline,\n} from './markdown-shortcuts'\n\n/**\n * Default in-place editor — a plain `<textarea>` positioned over the\n * editing node. See Phase 7 plan.\n *\n * - Auto-sizes its height to its scrollHeight (DOM-native).\n * - Font matches the node's style so what you type roughly matches what\n * you'll see on commit.\n * - Cmd+B/I/U/Shift+X/E/K: bold/italic/underline/strike/code/link.\n * - Enter inside a `- ` line continues the bullet; double-Enter exits.\n * - Esc / Cmd+Enter / blur: commit. (cancel is wired by the renderer.)\n */\nexport const createDefaultTextareaEditor: EditorAdapterFactory = ({\n node,\n container,\n camera,\n onCommit,\n onCancel,\n}): EditorAdapter => {\n void onCancel\n const style = node.style ?? {}\n const fontSize = style.fontSize ?? 'M'\n const fontFamily = style.fontFamily ?? 'handwriting'\n const align = style.textAlign ?? 'center'\n const color = style.textColor ?? '#1f2937'\n\n const fontPx = FONT_SIZE_MAP[fontSize]\n const lineHeightPx = LINE_HEIGHT_MAP[fontSize]\n\n // Screen-space placement: node world-(x,y) → screen via camera.\n const screenX = (node.x - camera.x) * camera.z\n const screenY = (node.y - camera.y) * camera.z\n const screenW = node.w * camera.z\n const screenH = node.h * camera.z\n\n const alignToFlex: Record<string, string> = {\n left: 'flex-start',\n center: 'center',\n right: 'flex-end',\n }\n\n // Wrapper handles vertical centering so the textarea visually matches\n // the canvas paint (which centers when content fits within node.h).\n // When content grows past min-height, the wrapper grows with it.\n const wrap = document.createElement('div')\n wrap.style.position = 'absolute'\n wrap.style.left = `${screenX}px`\n wrap.style.top = `${screenY}px`\n wrap.style.width = `${screenW}px`\n wrap.style.minHeight = `${screenH}px`\n wrap.style.display = 'flex'\n wrap.style.flexDirection = 'column'\n wrap.style.justifyContent = 'center'\n wrap.style.alignItems = alignToFlex[align] ?? 'center'\n wrap.style.boxSizing = 'border-box'\n wrap.style.border = '1px solid #3b82f6'\n wrap.style.borderRadius = '4px'\n wrap.style.background = style.backgroundColor ?? '#ffffff'\n wrap.style.zIndex = '20'\n // EditorMount's host div is pointerEvents:'none' so clicks on the\n // canvas behind still pan/select. The editor itself MUST opt back in,\n // otherwise mouse clicks pass through and you can't position the\n // caret by clicking — only arrow keys move it.\n wrap.style.pointerEvents = 'auto'\n\n const ta = document.createElement('textarea')\n ta.value = node.content ?? ''\n ta.spellcheck = false\n ta.style.width = '100%'\n ta.style.padding = '6px'\n ta.style.margin = '0'\n ta.style.boxSizing = 'border-box'\n ta.style.border = 'none'\n ta.style.outline = 'none'\n ta.style.resize = 'none'\n ta.style.overflow = 'hidden'\n ta.style.background = 'transparent'\n ta.style.color = color\n ta.style.fontFamily = FONT_FAMILY_MAP[fontFamily]\n ta.style.fontSize = `${fontPx * camera.z}px`\n ta.style.lineHeight = `${lineHeightPx * camera.z}px`\n ta.style.textAlign = align\n ta.style.whiteSpace = 'pre-wrap'\n ta.style.wordBreak = 'break-word'\n\n const autosize = (): void => {\n ta.style.height = 'auto'\n ta.style.height = `${ta.scrollHeight}px`\n }\n\n const commitNow = (): void => {\n onCommit(ta.value)\n }\n\n const applyTransform = (t: { value: string; selStart: number; selEnd: number }): void => {\n ta.value = t.value\n ta.setSelectionRange(t.selStart, t.selEnd)\n autosize()\n }\n\n const onInput = (): void => {\n autosize()\n }\n const onBlur = (): void => {\n commitNow()\n }\n const onKeyDown = (e: KeyboardEvent): void => {\n if (e.key === 'Escape') {\n e.preventDefault()\n commitNow()\n return\n }\n const meta = e.metaKey || e.ctrlKey\n if (meta && e.key === 'Enter') {\n e.preventDefault()\n commitNow()\n return\n }\n if (meta && !e.shiftKey && (e.key === 'b' || e.key === 'B')) {\n e.preventDefault()\n applyTransform(toggleBold(ta.value, ta.selectionStart, ta.selectionEnd))\n return\n }\n if (meta && !e.shiftKey && (e.key === 'i' || e.key === 'I')) {\n e.preventDefault()\n applyTransform(toggleItalic(ta.value, ta.selectionStart, ta.selectionEnd))\n return\n }\n if (meta && !e.shiftKey && (e.key === 'u' || e.key === 'U')) {\n e.preventDefault()\n applyTransform(toggleUnderline(ta.value, ta.selectionStart, ta.selectionEnd))\n return\n }\n if (meta && e.shiftKey && (e.key === 'x' || e.key === 'X')) {\n e.preventDefault()\n applyTransform(toggleStrike(ta.value, ta.selectionStart, ta.selectionEnd))\n return\n }\n if (meta && !e.shiftKey && (e.key === 'e' || e.key === 'E')) {\n e.preventDefault()\n applyTransform(toggleCode(ta.value, ta.selectionStart, ta.selectionEnd))\n return\n }\n if (meta && !e.shiftKey && (e.key === 'k' || e.key === 'K')) {\n e.preventDefault()\n const url = window.prompt('URL') ?? ''\n applyTransform(insertLink(ta.value, ta.selectionStart, ta.selectionEnd, url))\n return\n }\n if (e.key === 'Enter' && !e.shiftKey && !meta) {\n const t = handleEnter(ta.value, ta.selectionStart, ta.selectionEnd)\n if (t) {\n e.preventDefault()\n applyTransform(t)\n }\n }\n }\n\n ta.addEventListener('input', onInput)\n ta.addEventListener('blur', onBlur)\n ta.addEventListener('keydown', onKeyDown)\n wrap.appendChild(ta)\n container.appendChild(wrap)\n // Defer focus until after mount to ensure layout settled.\n requestAnimationFrame(() => {\n ta.focus()\n ta.setSelectionRange(ta.value.length, ta.value.length)\n autosize()\n })\n\n return {\n focus: () => ta.focus(),\n getValue: () => ta.value,\n setValue: (text: string) => {\n ta.value = text\n autosize()\n },\n destroy: () => {\n ta.removeEventListener('input', onInput)\n ta.removeEventListener('blur', onBlur)\n ta.removeEventListener('keydown', onKeyDown)\n wrap.remove()\n },\n }\n}\n","/**\n * Raster image utilities used by `store.addImage` and the renderer's\n * asset cache.\n *\n * Inputs accepted: `File`, `Blob`, or a `data:image/(png|jpeg)` URI.\n * External URLs are rejected — scenes must be self-contained (no\n * out-of-document references, no CORS surprises).\n *\n * Anything larger than `MAX_IMAGE_BYTES` or not PNG/JPEG is rejected\n * up front with a clear error so consumers can show a useful message.\n */\n\nexport const MAX_IMAGE_BYTES = 2 * 1024 * 1024\nconst ACCEPTED_MIME = new Set<string>(['image/png', 'image/jpeg'])\n\n/**\n * Validates that the input is a PNG/JPEG within the size cap. Throws\n * on rejection — meant for the synchronous prologue of an async\n * `addImage` call so consumers see the failure immediately, not after\n * an in-flight load.\n */\nexport const validateImageInput = (input: File | Blob | string): void => {\n if (typeof input === 'string') {\n if (!input.startsWith('data:')) {\n throw new Error(\n 'addImage: external URL strings are not supported. Pass a File, Blob, or `data:image/(png|jpeg)` URI.',\n )\n }\n const mimeMatch = /^data:([^;,]+)/.exec(input)\n const mime = mimeMatch?.[1] ?? ''\n if (!ACCEPTED_MIME.has(mime)) {\n throw new Error(\n `addImage: unsupported MIME \"${mime || '(unknown)'}\". Only image/png and image/jpeg are supported.`,\n )\n }\n // base64-encoded payload ≈ 4/3 of decoded byte count\n const comma = input.indexOf(',')\n if (comma < 0) throw new Error('addImage: malformed data URI (missing payload separator)')\n const decodedBytes = Math.floor(((input.length - comma - 1) * 3) / 4)\n if (decodedBytes > MAX_IMAGE_BYTES) {\n throw new Error(\n `addImage: image exceeds the 2 MB limit (${Math.round(decodedBytes / 1024)} KB).`,\n )\n }\n return\n }\n if (!ACCEPTED_MIME.has(input.type)) {\n throw new Error(\n `addImage: unsupported file type \"${input.type || '(unknown)'}\". Only image/png and image/jpeg are supported.`,\n )\n }\n if (input.size > MAX_IMAGE_BYTES) {\n throw new Error(`addImage: file exceeds the 2 MB limit (${Math.round(input.size / 1024)} KB).`)\n }\n}\n\n/** Normalize any accepted `addImage` input to a `Blob`. */\nexport const toImageBlob = async (input: File | Blob | string): Promise<Blob> => {\n if (typeof input === 'string') {\n // data URIs round-trip through fetch reliably across browsers.\n const res = await fetch(input)\n return res.blob()\n }\n return input\n}\n\n/**\n * Downscales a blob's image if its longer side exceeds `maxDim`. Returns\n * the original blob unchanged when no downscale is needed. The output\n * MIME mirrors the input (PNG stays PNG to preserve alpha; JPEG stays\n * JPEG with q=0.9).\n *\n * `maxDim <= 0` disables downscaling entirely — useful when the caller\n * wants the original bytes (e.g. they're going to do their own\n * processing or they need full fidelity).\n */\nexport const downscaleImageBlob = async (\n blob: Blob,\n maxDim: number,\n): Promise<{ blob: Blob; naturalW: number; naturalH: number }> => {\n const bitmap = await createImageBitmap(blob)\n const naturalW = bitmap.width\n const naturalH = bitmap.height\n const maxSide = Math.max(naturalW, naturalH)\n if (maxDim <= 0 || maxSide <= maxDim) {\n bitmap.close?.()\n return { blob, naturalW, naturalH }\n }\n const scale = maxDim / maxSide\n const w = Math.max(1, Math.round(naturalW * scale))\n const h = Math.max(1, Math.round(naturalH * scale))\n const canvas = new OffscreenCanvas(w, h)\n const ctx = canvas.getContext('2d')\n if (!ctx) throw new Error('addImage: failed to acquire OffscreenCanvas 2d context')\n ctx.drawImage(bitmap, 0, 0, w, h)\n bitmap.close?.()\n const outType = blob.type === 'image/png' ? 'image/png' : 'image/jpeg'\n const outBlob = await canvas.convertToBlob({ type: outType, quality: 0.9 })\n return { blob: outBlob, naturalW: w, naturalH: h }\n}\n\n/**\n * Encodes a blob as a `data:` URI. The store persists this string on\n * `node.data.src` so the node round-trips through serialize/restore\n * without needing an external asset store.\n */\nexport const blobToDataUri = (blob: Blob): Promise<string> => {\n return new Promise((resolve, reject) => {\n const reader = new FileReader()\n reader.onload = () => {\n if (typeof reader.result === 'string') resolve(reader.result)\n else reject(new Error('FileReader returned non-string result'))\n }\n reader.onerror = () => reject(reader.error ?? new Error('FileReader failed'))\n reader.readAsDataURL(blob)\n })\n}\n","/**\n * SVG utilities used by `store.addSvg` and the renderer's asset cache.\n *\n * SVG is XML — it can carry `<script>` tags, `on*` event handlers, and\n * `javascript:` hrefs that execute when the markup is inlined into the\n * DOM. We rasterize SVGs (so the DOM is never asked to live-render\n * them as elements), but a defense-in-depth sanitize still runs since\n * the rasterization itself goes through `<img src=blob:>` and a stray\n * embedded `<foreignObject>` could host arbitrary HTML.\n */\n\nexport const MAX_SVG_BYTES = 2 * 1024 * 1024\nconst DEFAULT_SVG_SIZE = 24\n\n/**\n * Cheap \"is this plausibly SVG markup?\" check + size cap. Throws on\n * rejection so consumers see the error immediately.\n */\nexport const validateSvgMarkup = (markup: string): void => {\n if (typeof markup !== 'string') {\n throw new Error('addSvg: src must be a string of SVG markup')\n }\n // UTF-8 byte length, not character count.\n const byteLen = new Blob([markup]).size\n if (byteLen > MAX_SVG_BYTES) {\n throw new Error(`addSvg: SVG markup exceeds the 2 MB limit (${Math.round(byteLen / 1024)} KB).`)\n }\n if (!/<svg[\\s>]/i.test(markup)) {\n throw new Error('addSvg: src does not look like SVG markup (no <svg> tag found)')\n }\n}\n\n/**\n * Removes attack surfaces from SVG markup:\n * - `<script>` and `<foreignObject>` elements entirely\n * - `on*` event-handler attributes\n * - `href` / `xlink:href` / `src` attributes whose value starts with\n * `javascript:` (case-insensitive)\n * - External entity references (`<!DOCTYPE` / `<!ENTITY`) by parsing\n * in SVG mode (DOMParser ignores DTDs in SVG context)\n *\n * Returns the cleaned markup. Throws if the parser can't make sense\n * of the input.\n */\nexport const sanitizeSvg = (markup: string): string => {\n const parser = new DOMParser()\n const doc = parser.parseFromString(markup, 'image/svg+xml')\n const root = doc.documentElement\n if (root.nodeName === 'parsererror' || root.querySelector('parsererror')) {\n throw new Error('addSvg: malformed SVG (parser error)')\n }\n\n const removable: Element[] = []\n const walker = doc.createTreeWalker(doc, NodeFilter.SHOW_ELEMENT)\n let n: Node | null = walker.nextNode()\n while (n) {\n const el = n as Element\n const tag = el.tagName.toLowerCase()\n if (tag === 'script' || tag === 'foreignobject') {\n removable.push(el)\n } else {\n for (const attr of [...el.attributes]) {\n const name = attr.name.toLowerCase()\n const value = attr.value.trim().toLowerCase()\n if (name.startsWith('on')) {\n el.removeAttribute(attr.name)\n } else if (\n (name === 'href' || name === 'xlink:href' || name === 'src') &&\n value.startsWith('javascript:')\n ) {\n el.removeAttribute(attr.name)\n }\n }\n }\n n = walker.nextNode()\n }\n for (const el of removable) el.remove()\n return new XMLSerializer().serializeToString(doc)\n}\n\n/**\n * Resolves intended display dimensions for an SVG. Order of preference:\n * 1. explicit `width` + `height` attributes (numeric, units stripped)\n * 2. `viewBox` width/height\n * 3. fallback 24×24\n *\n * The result is the SVG's \"natural size\" — what `addSvg` uses as the\n * default node dimensions when caller omits `w`/`h`.\n */\nexport const extractSvgDimensions = (markup: string): { w: number; h: number } => {\n const parser = new DOMParser()\n const doc = parser.parseFromString(markup, 'image/svg+xml')\n const svg = doc.documentElement\n if (svg.nodeName.toLowerCase() !== 'svg') {\n return { w: DEFAULT_SVG_SIZE, h: DEFAULT_SVG_SIZE }\n }\n const widthAttr = svg.getAttribute('width')\n const heightAttr = svg.getAttribute('height')\n if (widthAttr && heightAttr) {\n const w = Number.parseFloat(widthAttr)\n const h = Number.parseFloat(heightAttr)\n if (Number.isFinite(w) && Number.isFinite(h) && w > 0 && h > 0) return { w, h }\n }\n const viewBox = svg.getAttribute('viewBox')\n if (viewBox) {\n const parts = viewBox.split(/[\\s,]+/).map(Number.parseFloat)\n if (parts.length === 4 && parts.every(Number.isFinite) && parts[2]! > 0 && parts[3]! > 0) {\n return { w: parts[2]!, h: parts[3]! }\n }\n }\n return { w: DEFAULT_SVG_SIZE, h: DEFAULT_SVG_SIZE }\n}\n\n/**\n * Substitutes every `currentColor` occurrence in the markup with the\n * given color literal. Case-insensitive. Used by the rasterizer cache\n * to bake the icon's tint into the rendered bitmap.\n *\n * Single-color recoloring covers ~95% of real icon libraries (Lucide,\n * Heroicons, Phosphor, Tabler, etc.) which are designed monochromatic.\n * Two-tone icons can pre-color their markup and skip this step.\n */\nexport const applySvgColor = (markup: string, color: string): string => {\n return markup.replace(/currentColor/gi, color)\n}\n","import type { Edge, Node, Op, OpBatch } from '../types'\n\n/**\n * LWW conflict detection — see ARCHITECTURE.md §10.6.\n *\n * For remote `node.update` / `edge.update` ops, the `prev` slice\n * captures what the *remote* client thought the value was before its\n * change. If our local current value differs, two clients touched the\n * same field concurrently: LWW says higher `batch.ts` wins (we still\n * apply the remote op), but we surface a 'conflict' event for\n * telemetry / consumer UX (e.g. \"your background color was just\n * overwritten by Alice\").\n */\nexport type ConflictRecord = { op: Op; field: string }\n\nexport type GetCurrentNode = (id: Node['id']) => Node | undefined\nexport type GetCurrentEdge = (id: Edge['id']) => Edge | undefined\n\n/**\n * Walks a remote OpBatch and returns the set of `(op, field)` pairs\n * where the local current value disagrees with the op's `prev` slice.\n * No state is mutated.\n */\nexport const detectConflicts = (\n batch: OpBatch,\n getNode: GetCurrentNode,\n getEdge: GetCurrentEdge,\n): ConflictRecord[] => {\n const out: ConflictRecord[] = []\n for (const op of batch.ops) {\n if (op.type === 'node.update') {\n const current = getNode(op.id)\n if (!current) continue\n for (const key of Object.keys(op.prev) as (keyof Node)[]) {\n if (!sameValue(current[key], op.prev[key])) {\n out.push({ op, field: String(key) })\n }\n }\n continue\n }\n if (op.type === 'edge.update') {\n const current = getEdge(op.id)\n if (!current) continue\n for (const key of Object.keys(op.prev) as (keyof Edge)[]) {\n if (!sameValue(current[key], op.prev[key])) {\n out.push({ op, field: String(key) })\n }\n }\n }\n }\n return out\n}\n\n/**\n * Field-equality used by the conflict check. Numbers / strings /\n * booleans by value; objects by JSON.stringify (small / bounded data).\n */\nconst sameValue = (a: unknown, b: unknown): boolean => {\n if (a === b) return true\n // null and undefined are equivalent for our wire/diff purposes —\n // they both mean \"field unset\" to the render and hit-test code.\n // Without this clause, JSON round-trips that turn undefined into\n // null (see normalizeUndefinedToNull in store.ts) would flag every\n // forward edit of a previously-unset field as a conflict.\n if (a == null && b == null) return true\n if (a == null || b == null) return false\n if (typeof a !== typeof b) return false\n if (typeof a === 'object') return JSON.stringify(a) === JSON.stringify(b)\n return false\n}\n","import type { ResizeHandle } from '../hit-test/handle'\n/**\n * InteractionState — see ARCHITECTURE.md §10.11.\n *\n * Per-client ephemeral state: what's the user doing right now. Drives the\n * interactive canvas paint, status bars, AI-mode gating, custom-node\n * `env.isMoving`. NOT in the op log; not synced; not in undo stack.\n *\n * Phase 3 ships dragging / resizing / marqueeing modes. Pan/zoom/edit\n * arrive later but the type covers them now to avoid breaking changes.\n */\nimport type { EdgeEnd, EdgeId, NodeId, Vec2, WorldRect } from '../types'\n\nexport type InteractionMode =\n | 'idle'\n | 'panning'\n | 'zooming'\n | 'dragging'\n | 'resizing'\n | 'rotating'\n | 'marqueeing'\n | 'creating-shape'\n | 'creating-edge'\n | 'reconnecting-edge'\n | 'editing'\n\nexport type PointerInfo = {\n worldX: number\n worldY: number\n screenX: number\n screenY: number\n pointerType: 'mouse' | 'touch' | 'pen'\n pressure?: number\n}\n\n/**\n * The frozen geometry of a node at drag-start, used to compute the\n * uncommitted display position during drag (= original + delta).\n */\nexport type DragOriginal = {\n id: NodeId\n x: number\n y: number\n w: number\n h: number\n angle: number\n}\n\nexport type InteractionState = {\n mode: InteractionMode\n pointer: PointerInfo | null\n\n // Drag state — populated when mode is 'dragging' or 'resizing'.\n draggedIds: NodeId[]\n dragOriginals: DragOriginal[]\n /** World-space delta from drag start; renderer applies this to draw the dragged set. */\n dragDelta: Vec2\n\n // Resize state — populated when mode is 'resizing'.\n resizeHandle: ResizeHandle | null\n /** Whether the user is holding Shift during a resize (aspect-lock). */\n resizeLockAspect: boolean\n /** Whether the user is holding Alt during a resize (resize from center). */\n resizeFromCenter: boolean\n /**\n * Live in-progress geometry of the resized node — written every\n * pointermove, committed to the store once on pointer-up. While\n * present, `store.getNode(id)` still returns the original geometry;\n * the renderer overlays this draft via `mapDragPositions` for the\n * interactive layer paint. Mirrors how `dragDelta` works for drag.\n */\n resizeDraft: { x: number; y: number; w: number; h: number; angle: number } | null\n\n // Marquee state — populated when mode is 'marqueeing'.\n marqueeRect: WorldRect | null\n /** Whether the marquee should add to (true, shift held) or replace selection. */\n marqueeAdditive: boolean\n\n /**\n * Live in-progress cubic controls of an edge being mid-point-dragged.\n * Written every pointermove, committed to the store once on\n * pointer-up. Same draft+commit model as `resizeDraft` and\n * `dragDelta` — keeps mid-gesture mutations off the 'change' bus.\n */\n midpointDraft: { edgeId: EdgeId; control: [Vec2, Vec2] } | null\n\n // Edge-creation state — populated when mode is 'creating-edge' or\n // 'reconnecting-edge'. `draftEdge` is the source/target the renderer\n // should paint as a preview.\n draftEdge: {\n source: EdgeEnd\n target: EdgeEnd\n /** When reconnecting an existing edge, the id; null for new edges. */\n reconnectingId: import('../types').EdgeId | null\n /** Snap candidate (a node id the target endpoint is hovering over). */\n snapTargetNodeId: NodeId | null\n } | null\n\n // Edit state — populated when mode is 'editing' (phase 7 + 12.5).\n // Phase 7 only edited node content; phase 12.5 generalizes to edge\n // labels too, so the field is `editingTarget: { kind, id } | null`.\n editingTarget: EditTarget | null\n\n // Drag-create state — populated while mode is 'creating-shape'.\n // The renderer paints `createDraftRect` as a preview on the\n // interactive canvas; `<Canvas onCreateDrag>` consumes the rect on\n // commit.\n createDraftRect: WorldRect | null\n createTool: string | null\n}\n\n/** Identifies what's currently being edited — a node (text content) or\n * an edge (label content). See `store.beginEdit`. */\nexport type EditTarget = { kind: 'node'; id: NodeId } | { kind: 'edge'; id: EdgeId }\n\nexport const idleInteractionState = (): InteractionState => ({\n mode: 'idle',\n pointer: null,\n draggedIds: [],\n dragOriginals: [],\n dragDelta: { x: 0, y: 0 },\n resizeHandle: null,\n resizeLockAspect: false,\n resizeFromCenter: false,\n resizeDraft: null,\n midpointDraft: null,\n marqueeRect: null,\n marqueeAdditive: false,\n draftEdge: null,\n editingTarget: null,\n createDraftRect: null,\n createTool: null,\n})\n\n/**\n * Convenience: any of panning/zooming/dragging/resizing/rotating is \"moving\".\n */\nexport const isMoving = (state: InteractionState): boolean => {\n const m = state.mode\n return (\n m === 'panning' || m === 'zooming' || m === 'dragging' || m === 'resizing' || m === 'rotating'\n )\n}\n","/**\n * Op inversion — see ARCHITECTURE.md §10.2.\n *\n * Every committed `Op` carries enough state (full snapshot for add/remove,\n * `prev` slice for updates) to derive its inverse with no diffing. Undo\n * applies `inverseBatch(batch)` with `origin: 'history'`; redo re-applies\n * the original batch.\n *\n * Inverse rules:\n * - add ↔ remove (full snapshot retained)\n * - update.patch ↔ update.prev\n * - group.upsert with `prev` ↔ group.upsert with prev fields swapped; if\n * `prev` is absent, the upsert was a fresh insert → invert to remove.\n */\nimport type { Op, OpBatch } from '../types'\n\nexport const inverseOp = (op: Op): Op => {\n switch (op.type) {\n case 'node.add':\n return { type: 'node.remove', node: op.node }\n case 'node.remove':\n return { type: 'node.add', node: op.node }\n case 'node.update':\n return { type: 'node.update', id: op.id, patch: op.prev, prev: op.patch }\n case 'edge.add':\n return { type: 'edge.remove', edge: op.edge }\n case 'edge.remove':\n return { type: 'edge.add', edge: op.edge }\n case 'edge.update':\n return { type: 'edge.update', id: op.id, patch: op.prev, prev: op.patch }\n case 'group.upsert':\n if (op.prev) return { type: 'group.upsert', group: op.prev, prev: op.group }\n return { type: 'group.remove', group: op.group }\n case 'group.remove':\n return { type: 'group.upsert', group: op.group }\n case 'frame.reorder':\n return { type: 'frame.reorder', ids: op.prev, prev: op.ids }\n }\n}\n\n/**\n * Inverse batch: reverse op order, invert each op. Reversing preserves\n * \"later ops depended on earlier ones\" semantics — e.g. a batch that\n * (1) adds a node and (2) updates it must undo (2) first, then (1).\n */\nexport const inverseBatch = (batch: OpBatch): Op[] => {\n const inv: Op[] = []\n for (let i = batch.ops.length - 1; i >= 0; i--) {\n inv.push(inverseOp(batch.ops[i]!))\n }\n return inv\n}\n","import type { ClientId, EdgeId, NodeId, Vec2 } from '../types'\n\n/**\n * Per-client awareness state that other clients see in real time.\n * Synced over the {@link SyncAdapter}; never in the op log; never\n * persisted by `toJSON`.\n *\n * Set the local copy via `store.presence.setLocal({...})`. Read the\n * remote copy via `usePresence()` / `usePresence(clientId)` (React) or\n * `store.presence.get(...)` / `store.presence.getAll()`.\n */\nexport type PresenceState = {\n /** Stable id of the owning client. */\n clientId: ClientId\n /** Cursor world position; null when the cursor has left the surface. */\n cursor: Vec2 | null\n /** Ids the remote client has selected — for shared-awareness highlights. */\n selection: (NodeId | EdgeId)[]\n /** Node id the remote client is currently editing (or null). */\n editing: NodeId | null\n /** Display color (hex). Used for remote cursors + selection outlines. */\n color: string\n /** Display name. */\n name: string\n}\n\nexport const emptyPresenceState = (clientId: ClientId): PresenceState => ({\n clientId,\n cursor: null,\n selection: [],\n editing: null,\n color: '#3b82f6',\n name: '',\n})\n\nexport type PresencePatch = Partial<Omit<PresenceState, 'clientId'>>\n\n/**\n * Returns true if any remote presence has this node currently open in\n * edit mode. Used to enforce the exclusive edit-lock when a SyncAdapter\n * is attached (see ARCHITECTURE.md §9 collab edit semantics).\n */\nexport const isNodeRemoteEditing = (\n remote: ReadonlyMap<ClientId, PresenceState>,\n nodeId: NodeId,\n): boolean => {\n for (const p of remote.values()) {\n if (p.editing === nodeId) return true\n }\n return false\n}\n","/**\n * CanvasStore implementation — see ARCHITECTURE.md §10.\n *\n * Phase 1: typed-Op-driven mutations, signia atoms for fine-grained reactivity,\n * spatial index kept in sync, framework-agnostic.\n *\n * NOT in phase 1 (added later):\n * - undo/redo (phase 8): the op log is built; the inverse machinery is not\n * - presence (phase 8)\n * - sync adapter (phase 8)\n * - signia-based React hooks (phase 9)\n */\nimport { type Atom, atom, transact } from 'signia'\n\nimport {\n blobToDataUri,\n downscaleImageBlob,\n extractSvgDimensions,\n sanitizeSvg,\n toImageBlob,\n validateImageInput,\n validateSvgMarkup,\n} from '../assets'\nimport { DEFAULT_CAMERA } from '../camera'\nimport { type EdgeGeometry, EdgeGeometryCache } from '../edges/cache'\nimport { shouldAutoFit, withAutoFitHeight } from '../edit/auto-fit'\nimport { type IdGenerator, makeIdGenerator, randomClientId } from '../ids'\nimport { UniformGrid, nodeAABB } from '../spatial'\nimport { SCHEMA_VERSION, asBatchId, asNodeId, isAttached } from '../types'\nimport type {\n CameraState,\n ClientId,\n Edge,\n EdgeId,\n Group,\n GroupId,\n IconNodeData,\n ImageNodeData,\n Node,\n NodeId,\n Op,\n OpBatch,\n Scene,\n Style,\n} from '../types'\nimport { detectConflicts } from './conflict'\nimport { type InteractionState, idleInteractionState } from './interaction'\nimport { inverseBatch } from './inverse-op'\nimport { type PresencePatch, type PresenceState, emptyPresenceState } from './presence'\nimport type {\n CanvasStore,\n OpOrigin,\n SpatialQuery,\n SpatialResult,\n StoreEventHandler,\n StoreEventName,\n StoreEvents,\n StoreOptions,\n Unsubscribe,\n} from './types'\n\nconst EMPTY_SCENE = (): Scene => ({\n schemaVersion: SCHEMA_VERSION,\n nodes: {},\n edges: {},\n groups: {},\n camera: DEFAULT_CAMERA,\n selection: [],\n})\n\n/**\n * Creates a new canvas store. One per scene / document. Pass into\n * `<CanvasProvider>` (React) or use the imperative API directly.\n *\n * @example\n * // Minimal\n * const store = createCanvasStore()\n *\n * @example\n * // With custom node types + a hydrated scene from JSON\n * const store = createCanvasStore({\n * nodeTypes: [chartCardDef, todoCardDef],\n * initial: fromSerialized(savedScene),\n * })\n */\n/**\n * Index of the first entry strictly greater than `target`, or -1 if\n * none. Assumes `arr` is sorted ascending. Used by bringForward to\n * find the immediate-above neighbour's z.\n */\nconst binaryFirstGreater = (arr: number[], target: number): number => {\n let lo = 0\n let hi = arr.length\n while (lo < hi) {\n const mid = (lo + hi) >>> 1\n if (arr[mid]! <= target) lo = mid + 1\n else hi = mid\n }\n return lo < arr.length ? lo : -1\n}\n\n/**\n * Index of the last entry strictly less than `target`, or -1 if none.\n * Used by sendBackward.\n */\nconst binaryLastLess = (arr: number[], target: number): number => {\n let lo = 0\n let hi = arr.length\n while (lo < hi) {\n const mid = (lo + hi) >>> 1\n if (arr[mid]! < target) lo = mid + 1\n else hi = mid\n }\n return lo > 0 ? lo - 1 : -1\n}\n\nexport const createCanvasStore = (opts: StoreOptions = {}): CanvasStore => {\n const clientId: ClientId = opts.clientId ?? randomClientId()\n const idGenerator: IdGenerator = opts.idGenerator ?? makeIdGenerator(clientId)\n const initial = opts.initial ?? EMPTY_SCENE()\n\n // ---- reactive state ----------------------------------------------------\n // One atom per entity gives us fine-grained subscriptions. The id-list\n // atoms drive iteration; the spatial index drives viewport queries.\n\n const nodeAtoms = new Map<NodeId, Atom<Node>>()\n const edgeAtoms = new Map<EdgeId, Atom<Edge>>()\n const groupAtoms = new Map<GroupId, Atom<Group>>()\n\n const nodeIdsAtom = atom<NodeId[]>('nodeIds', [])\n const edgeIdsAtom = atom<EdgeId[]>('edgeIds', [])\n const groupIdsAtom = atom<GroupId[]>('groupIds', [])\n\n const cameraAtom = atom<CameraState>('camera', initial.camera)\n const selectionAtom = atom<(NodeId | EdgeId)[]>('selection', initial.selection)\n // Presentation order for frame-typed nodes. Auto-maintained on\n // node.add (push) / node.remove (filter); explicitly mutated via the\n // `frame.reorder` op. See types/scene.ts.\n const frameOrderAtom = atom<NodeId[]>('frameOrder', initial.frameOrder ?? [])\n const interactionAtom = atom<InteractionState>('interaction', idleInteractionState())\n const localPresenceAtom = atom<PresenceState>('presence', emptyPresenceState(clientId))\n const remotePresence = new Map<ClientId, PresenceState>()\n\n const nodeIndex = new UniformGrid()\n const edgeIndex = new UniformGrid()\n const edgeGeoCache = new EdgeGeometryCache()\n\n // Custom node type registry — keyed by NodeTypeDef.type.\n const nodeTypeRegistry = new Map<string, import('../node-types').NodeTypeDef>()\n for (const def of opts.nodeTypes ?? []) {\n nodeTypeRegistry.set(def.type, def)\n }\n\n // Per-edge integer version. Bumped on edge.add/update and on node.update\n // for incident edges. Drives the EdgeGeometryCache invalidation without\n // having to compare full-state strings. See ARCHITECTURE.md §6.12.\n const edgeVersions = new Map<EdgeId, number>()\n const bumpEdgeVersion = (id: EdgeId): void => {\n edgeVersions.set(id, (edgeVersions.get(id) ?? 0) + 1)\n }\n\n // incidentEdges: nodeId -> set of edgeIds. Used by reindexEdge when a\n // node moves (to refresh all its edges' AABBs in the spatial index) and\n // by removeNode to cascade-delete attached edges.\n const incidentEdges = new Map<NodeId, Set<EdgeId>>()\n\n // Running extremes of node + edge z values. `topZ` only goes up\n // (++ on auto-create + bringToFront); `bottomZ` only goes down\n // (-- on sendToBack). New entities created without an explicit z\n // get `++topZ` (Figma / Excalidraw default — new on top); sendToBack\n // uses `--bottomZ`. Negative z is a first-class value: anything\n // sendToBack'd sits at z=-1, -2, … and z=0 is a neutral middle\n // position between front and back stacks.\n //\n // Both counters are tracked from every z-mutation centrally in\n // `applyOpInternal` so updateNode({ z: ... }) calls and remote ops\n // keep them in sync. Initialized from `initial` so hydration from\n // a saved scene preserves the high/low watermarks.\n let topZ = 0\n let bottomZ = 0\n for (const n of Object.values(initial.nodes) as Node[]) {\n if (n.z > topZ) topZ = n.z\n if (n.z < bottomZ) bottomZ = n.z\n }\n for (const e of Object.values(initial.edges) as Edge[]) {\n if (e.z > topZ) topZ = e.z\n if (e.z < bottomZ) bottomZ = e.z\n }\n\n const getNodeForGeo = (id: NodeId): Node | undefined => nodeAtoms.get(id)?.value\n\n // ---- batching ----------------------------------------------------------\n let currentBatchOps: Op[] | null = null\n let batchDepth = 0\n\n const startBatch = (): void => {\n if (batchDepth === 0) currentBatchOps = []\n batchDepth++\n }\n\n const endBatch = (): OpBatch | null => {\n batchDepth--\n if (batchDepth > 0) return null\n const ops = currentBatchOps ?? []\n currentBatchOps = null\n if (ops.length === 0) return null\n return {\n id: asBatchId(idGenerator()),\n clientId,\n ts: Date.now(),\n origin: 'local',\n ops,\n }\n }\n\n // ---- undo / redo stacks ------------------------------------------------\n // Local committed batches push onto undoStack; redoStack is cleared on\n // any fresh local op (the standard \"branching\" rule). Remote and history\n // batches do not push to undoStack — see emitChange below. Cap at 50.\n const UNDO_STACK_CAP = 50\n const undoStack: OpBatch[] = []\n const redoStack: OpBatch[] = []\n\n // ---- event bus ---------------------------------------------------------\n type Subscribers = { [E in StoreEventName]: Set<StoreEventHandler<E>> }\n const subscribers: Subscribers = {\n change: new Set(),\n camera: new Set(),\n selection: new Set(),\n interaction: new Set(),\n presence: new Set(),\n conflict: new Set(),\n }\n const emit = <E extends StoreEventName>(event: E, payload: StoreEvents[E]): void => {\n for (const cb of subscribers[event]) cb(payload)\n }\n\n /**\n * Single entry point for 'change' emission. Centralizes the undo-stack\n * bookkeeping so every call site (enqueueOp, removeNode cascade,\n * applyOp, applyBatch) gets it for free. Only `origin: 'local'`\n * batches enter the undo stack; remote and history batches don't.\n */\n const emitChange = (batch: OpBatch): void => {\n if (batch.origin === 'local') {\n undoStack.push(batch)\n if (undoStack.length > UNDO_STACK_CAP) undoStack.shift()\n // A fresh local op invalidates any redo branch.\n redoStack.length = 0\n }\n emit('change', batch)\n }\n\n // ---- spatial-index helpers --------------------------------------------\n const reindexNode = (node: Node): void => {\n nodeIndex.insert(node.id, nodeAABB(node))\n }\n const reindexEdge = (edge: Edge): void => {\n const version = edgeVersions.get(edge.id) ?? 0\n const geom = edgeGeoCache.get(edge, version, getNodeForGeo)\n if (geom) {\n edgeIndex.insert(edge.id, geom.aabb)\n } else {\n // Edge references a missing node; remove from index until things settle.\n edgeIndex.remove(edge.id)\n }\n }\n const unindexNode = (id: NodeId): void => {\n nodeIndex.remove(id)\n }\n const unindexEdge = (id: EdgeId): void => {\n edgeIndex.remove(id)\n edgeGeoCache.delete(id)\n }\n\n const trackIncidence = (edge: Edge): void => {\n for (const end of [edge.source, edge.target]) {\n if (isAttached(end)) {\n let s = incidentEdges.get(end.nodeId)\n if (!s) {\n s = new Set()\n incidentEdges.set(end.nodeId, s)\n }\n s.add(edge.id)\n }\n }\n }\n const untrackIncidence = (edge: Edge): void => {\n for (const end of [edge.source, edge.target]) {\n if (isAttached(end)) {\n incidentEdges.get(end.nodeId)?.delete(edge.id)\n }\n }\n }\n\n // ---- op application (internal, no event emission per-op) ---------------\n const applyOpInternal = (op: Op): void => {\n switch (op.type) {\n case 'node.add': {\n const a = atom<Node>(`node:${op.node.id}`, op.node)\n nodeAtoms.set(op.node.id, a)\n nodeIdsAtom.update(ids => [...ids, op.node.id])\n reindexNode(op.node)\n if (op.node.z > topZ) topZ = op.node.z\n if (op.node.z < bottomZ) bottomZ = op.node.z\n if (op.node.type === 'frame') {\n frameOrderAtom.update(ids => (ids.includes(op.node.id) ? ids : [...ids, op.node.id]))\n }\n break\n }\n case 'node.update': {\n const a = nodeAtoms.get(op.id)\n if (!a) return\n const next = { ...a.value, ...op.patch }\n a.set(next)\n reindexNode(next)\n if (op.patch.z !== undefined) {\n if (op.patch.z > topZ) topZ = op.patch.z\n if (op.patch.z < bottomZ) bottomZ = op.patch.z\n }\n // Edges whose endpoint is on this node now have stale geometry.\n // Bump each incident edge's version so the cache invalidates.\n const incident = incidentEdges.get(op.id)\n if (incident) {\n for (const eid of incident) {\n bumpEdgeVersion(eid)\n const e = edgeAtoms.get(eid)\n if (e) reindexEdge(e.value)\n }\n }\n break\n }\n case 'node.remove': {\n const id = op.node.id\n nodeAtoms.delete(id)\n nodeIdsAtom.update(ids => ids.filter(x => x !== id))\n unindexNode(id)\n incidentEdges.delete(id)\n if (op.node.type === 'frame') {\n frameOrderAtom.update(ids => ids.filter(x => x !== id))\n }\n break\n }\n case 'edge.add': {\n const a = atom<Edge>(`edge:${op.edge.id}`, op.edge)\n edgeAtoms.set(op.edge.id, a)\n edgeIdsAtom.update(ids => [...ids, op.edge.id])\n trackIncidence(op.edge)\n bumpEdgeVersion(op.edge.id)\n reindexEdge(op.edge)\n if (op.edge.z > topZ) topZ = op.edge.z\n if (op.edge.z < bottomZ) bottomZ = op.edge.z\n break\n }\n case 'edge.update': {\n const a = edgeAtoms.get(op.id)\n if (!a) return\n const prev = a.value\n const next = { ...prev, ...op.patch }\n untrackIncidence(prev)\n trackIncidence(next)\n a.set(next)\n bumpEdgeVersion(op.id)\n reindexEdge(next)\n if (op.patch.z !== undefined) {\n if (op.patch.z > topZ) topZ = op.patch.z\n if (op.patch.z < bottomZ) bottomZ = op.patch.z\n }\n break\n }\n case 'edge.remove': {\n const id = op.edge.id\n const a = edgeAtoms.get(id)\n if (a) untrackIncidence(a.value)\n edgeAtoms.delete(id)\n edgeIdsAtom.update(ids => ids.filter(x => x !== id))\n edgeVersions.delete(id)\n unindexEdge(id)\n break\n }\n case 'group.upsert': {\n const existing = groupAtoms.get(op.group.id)\n if (existing) {\n existing.set(op.group)\n } else {\n groupAtoms.set(op.group.id, atom(`group:${op.group.id}`, op.group))\n groupIdsAtom.update(ids => [...ids, op.group.id])\n }\n break\n }\n case 'group.remove': {\n const id = op.group.id\n groupAtoms.delete(id)\n groupIdsAtom.update(ids => ids.filter(x => x !== id))\n break\n }\n case 'frame.reorder': {\n frameOrderAtom.set([...op.ids])\n break\n }\n }\n }\n\n // ---- public surface ----------------------------------------------------\n const enqueueOp = (op: Op): void => {\n if (currentBatchOps === null) {\n // single-op outside batch — wrap in implicit batch for consistency\n startBatch()\n currentBatchOps!.push(op)\n applyOpInternal(op)\n const batch = endBatch()\n if (batch) emitChange(batch)\n } else {\n currentBatchOps.push(op)\n applyOpInternal(op)\n }\n }\n\n /**\n * Replaces `undefined` values with `null` in-place on the copied\n * object. `null` survives `JSON.stringify` (`undefined` keys get\n * dropped, breaking JSON-serialized sync adapters), and is\n * indistinguishable from `undefined` to the render / hit-test / text\n * code that reads node and edge fields. The TS cast is pragmatic —\n * field types rarely include `null`, but the value never escapes the\n * op/wire layer; downstream spreads it back into the record where\n * \"falsy\" is the only thing that matters.\n */\n const normalizeUndefinedToNull = <T extends object>(obj: T): T => {\n const out: Record<string, unknown> = {}\n for (const key of Object.keys(obj)) {\n const v = (obj as Record<string, unknown>)[key]\n out[key] = v === undefined ? null : v\n }\n return out as T\n }\n\n /**\n * Records the prev slice for an update op. Values that were\n * previously `undefined` are stored as `null` so the resulting\n * inverse op (which becomes the wire payload during undo) survives\n * a JSON round-trip — otherwise peers silently no-op on clears of\n * previously-unset fields.\n */\n const slicePrev = <T>(current: T, patch: Partial<T>): Partial<T> => {\n const prev: Partial<T> = {}\n for (const key of Object.keys(patch) as (keyof T)[]) {\n prev[key] = current[key]\n }\n return normalizeUndefinedToNull(prev)\n }\n\n // hoisted because applyOp/applyBatch and the public methods both need them\n const populateInitial = (scene: Scene): void => {\n // If the scene didn't carry an explicit frameOrder (older saves),\n // derive it from iteration order over frame-typed nodes so the\n // store has a usable order from the first frame the consumer asks\n // for. The explicit `scene.frameOrder` (when present) wins.\n const seededFrameOrder: NodeId[] = []\n for (const id of Object.keys(scene.nodes)) {\n const node = scene.nodes[id as NodeId]\n if (!node) continue\n const a = atom<Node>(`node:${node.id}`, node)\n nodeAtoms.set(node.id, a)\n nodeIdsAtom.update(ids => [...ids, node.id])\n reindexNode(node)\n if (node.type === 'frame') seededFrameOrder.push(node.id)\n }\n if (!scene.frameOrder) frameOrderAtom.set(seededFrameOrder)\n for (const id of Object.keys(scene.edges)) {\n const edge = scene.edges[id as EdgeId]\n if (!edge) continue\n const a = atom<Edge>(`edge:${edge.id}`, edge)\n edgeAtoms.set(edge.id, a)\n edgeIdsAtom.update(ids => [...ids, edge.id])\n trackIncidence(edge)\n bumpEdgeVersion(edge.id)\n reindexEdge(edge)\n }\n for (const id of Object.keys(scene.groups)) {\n const group = scene.groups[id as GroupId]\n if (!group) continue\n groupAtoms.set(group.id, atom(`group:${group.id}`, group))\n groupIdsAtom.update(ids => [...ids, group.id])\n }\n }\n\n populateInitial(initial)\n\n const store: CanvasStore = {\n clientId,\n generateId: () => idGenerator(),\n\n addNode(node) {\n // Auto-top z when the caller omits the field — newly created\n // nodes sit above everything else (Figma / Excalidraw default).\n // An explicit value (incl. 0 or negative) is honored as-is.\n // `topZ` is then tracked centrally in applyOpInternal.\n const z = node.z ?? ++topZ\n const fitted = withAutoFitHeight({ ...node, z })\n enqueueOp({ type: 'node.add', node: fitted })\n return fitted.id\n },\n updateNode(id, patch) {\n const current = nodeAtoms.get(id)?.value\n if (!current) return\n let resolvedPatch = patch\n // Auto-fit on commit-boundary fields: content (commitEdit) or font\n // style (StylePanel applies). Width changes from a resize stream\n // deliberately do NOT trigger autofit — that would override the\n // user's drag mid-stream. Resize-commit refits explicitly.\n const next = { ...current, ...patch }\n const styleChanged =\n patch.style &&\n (patch.style.fontFamily !== undefined ||\n patch.style.fontSize !== undefined ||\n patch.style.textStyle !== undefined)\n if (shouldAutoFit(next) && (patch.content !== undefined || styleChanged)) {\n const fitted = withAutoFitHeight(next)\n if (fitted.h !== next.h) {\n resolvedPatch = { ...patch, h: fitted.h }\n }\n }\n enqueueOp({\n type: 'node.update',\n id,\n // Normalize both halves so explicit-clear patches (e.g.\n // `updateNode(id, { content: undefined })`) and first-time-set\n // prev slices both survive a JSON-serialized sync transport.\n patch: normalizeUndefinedToNull(resolvedPatch),\n prev: slicePrev(current, resolvedPatch),\n })\n },\n removeNode(id) {\n const node = nodeAtoms.get(id)?.value\n if (!node) return\n transact(() => {\n startBatch()\n // cascade-remove incident edges first; phase 8 will surface a config knob\n const incident = incidentEdges.get(id)\n if (incident) {\n for (const eid of [...incident]) {\n const edge = edgeAtoms.get(eid)?.value\n if (edge) {\n currentBatchOps!.push({ type: 'edge.remove', edge })\n applyOpInternal({ type: 'edge.remove', edge })\n }\n }\n }\n currentBatchOps!.push({ type: 'node.remove', node })\n applyOpInternal({ type: 'node.remove', node })\n const batch = endBatch()\n if (batch) emitChange(batch)\n })\n },\n\n async addImage(opts) {\n validateImageInput(opts.src)\n const rawBlob = await toImageBlob(opts.src)\n const maxDim = opts.maxDimension ?? 2048\n const { blob, naturalW, naturalH } = await downscaleImageBlob(rawBlob, maxDim)\n const src = await blobToDataUri(blob)\n // Default sizing: natural dimensions clamped to 400 px on the\n // longer side so a screen-filling node isn't created from a big\n // image. Aspect ratio is preserved.\n const DEFAULT_MAX_NODE_SIDE = 400\n const aspectScale = Math.min(1, DEFAULT_MAX_NODE_SIDE / Math.max(naturalW, naturalH))\n const w = opts.w ?? Math.max(1, Math.round(naturalW * aspectScale))\n const h = opts.h ?? Math.max(1, Math.round(naturalH * aspectScale))\n const id = asNodeId(idGenerator())\n this.addNode({\n id,\n type: 'image',\n x: opts.x,\n y: opts.y,\n w,\n h,\n angle: 0,\n groups: [],\n style: opts.style,\n data: { src, naturalW, naturalH, alt: opts.alt } satisfies ImageNodeData,\n })\n return id\n },\n async addSvg(opts) {\n validateSvgMarkup(opts.src)\n const sanitized = sanitizeSvg(opts.src)\n const intrinsic = extractSvgDimensions(sanitized)\n const w = opts.w ?? intrinsic.w\n const h = opts.h ?? intrinsic.h\n const mergedStyle: Style | undefined =\n opts.color || opts.style\n ? { ...(opts.color ? { iconColor: opts.color } : {}), ...opts.style }\n : undefined\n const id = asNodeId(idGenerator())\n this.addNode({\n id,\n type: 'icon',\n x: opts.x,\n y: opts.y,\n w,\n h,\n angle: 0,\n groups: [],\n ...(mergedStyle ? { style: mergedStyle } : {}),\n data: { src: sanitized, alt: opts.alt } satisfies IconNodeData,\n })\n return id\n },\n\n addEdge(edge) {\n // Same auto-top behavior as addNode — omit z for \"on top\",\n // pass an explicit value (incl. 0 / negative) to override.\n const z = edge.z ?? ++topZ\n const withZ = { ...edge, z }\n enqueueOp({ type: 'edge.add', edge: withZ })\n return withZ.id\n },\n updateEdge(id, patch) {\n const current = edgeAtoms.get(id)?.value\n if (!current) return\n // Normalize both halves so an explicit-undefined clear and a\n // first-time-set prev both survive JSON-serialized transports.\n enqueueOp({\n type: 'edge.update',\n id,\n patch: normalizeUndefinedToNull(patch),\n prev: slicePrev(current, patch),\n })\n },\n removeEdge(id) {\n const edge = edgeAtoms.get(id)?.value\n if (!edge) return\n enqueueOp({ type: 'edge.remove', edge })\n },\n\n bringToFront(ids) {\n this.batch(() => {\n for (const id of ids) {\n if (nodeAtoms.has(id as NodeId)) this.updateNode(id as NodeId, { z: ++topZ })\n else if (edgeAtoms.has(id as EdgeId)) this.updateEdge(id as EdgeId, { z: ++topZ })\n }\n })\n },\n sendToBack(ids) {\n // O(1) per target via the monotonic `--bottomZ` counter. Multi-\n // select preserves relative order because each step decrements\n // (first selected lands one above the next).\n this.batch(() => {\n for (const id of ids) {\n if (nodeAtoms.has(id as NodeId)) this.updateNode(id as NodeId, { z: --bottomZ })\n else if (edgeAtoms.has(id as EdgeId)) this.updateEdge(id as EdgeId, { z: --bottomZ })\n }\n })\n },\n bringForward(ids) {\n // For each target, find the next-higher z among non-targets and\n // step the target above it. Self-stable: targets keep their\n // relative order if they're all moved past the same neighbour.\n const targets = new Set<string>(ids as string[])\n const allZ: number[] = []\n for (const a of nodeAtoms.values()) if (!targets.has(a.value.id)) allZ.push(a.value.z)\n for (const a of edgeAtoms.values()) if (!targets.has(a.value.id)) allZ.push(a.value.z)\n allZ.sort((a, b) => a - b)\n this.batch(() => {\n for (const id of ids) {\n const node = nodeAtoms.get(id as NodeId)?.value\n const edge = node ? null : edgeAtoms.get(id as EdgeId)?.value\n const currentZ = node?.z ?? edge?.z\n if (currentZ === undefined) continue\n // Smallest non-target z strictly greater than currentZ.\n // `applyOpInternal` keeps topZ in sync with the new value.\n const idx = binaryFirstGreater(allZ, currentZ)\n const nextZ = idx >= 0 ? allZ[idx]! + 1 : currentZ + 1\n if (node) this.updateNode(id as NodeId, { z: nextZ })\n else this.updateEdge(id as EdgeId, { z: nextZ })\n }\n })\n },\n sendBackward(ids) {\n const targets = new Set<string>(ids as string[])\n const allZ: number[] = []\n for (const a of nodeAtoms.values()) if (!targets.has(a.value.id)) allZ.push(a.value.z)\n for (const a of edgeAtoms.values()) if (!targets.has(a.value.id)) allZ.push(a.value.z)\n allZ.sort((a, b) => a - b)\n this.batch(() => {\n for (const id of ids) {\n const node = nodeAtoms.get(id as NodeId)?.value\n const edge = node ? null : edgeAtoms.get(id as EdgeId)?.value\n const currentZ = node?.z ?? edge?.z\n if (currentZ === undefined) continue\n // Largest non-target z strictly less than currentZ.\n const idx = binaryLastLess(allZ, currentZ)\n const nextZ = idx >= 0 ? allZ[idx]! - 1 : currentZ - 1\n if (node) this.updateNode(id as NodeId, { z: nextZ })\n else this.updateEdge(id as EdgeId, { z: nextZ })\n }\n })\n },\n\n upsertGroup(group) {\n const prev = groupAtoms.get(group.id)?.value\n enqueueOp({ type: 'group.upsert', group, prev })\n },\n removeGroup(id) {\n const group = groupAtoms.get(id)?.value\n if (!group) return\n enqueueOp({ type: 'group.remove', group })\n },\n\n batch(fn) {\n transact(() => {\n startBatch()\n try {\n fn()\n } finally {\n const batch = endBatch()\n if (batch) emitChange(batch)\n }\n })\n },\n\n applyOp(op, applyOpts) {\n const origin: OpOrigin = applyOpts?.origin ?? 'local'\n if (origin !== 'local') {\n // remote / history ops bypass the local batch buffer; emit their own\n applyOpInternal(op)\n emitChange({\n id: asBatchId(idGenerator()),\n clientId,\n ts: Date.now(),\n origin,\n ops: [op],\n })\n return\n }\n enqueueOp(op)\n },\n\n applyBatch(b) {\n transact(() => {\n // Conflict detection runs BEFORE apply — the remote op's `prev`\n // slice describes what the remote client expected; once we apply\n // we lose the chance to compare. LWW still wins (we apply\n // regardless), but consumers get a 'conflict' event for UX.\n if (b.origin === 'remote') {\n const conflicts = detectConflicts(\n b,\n id => nodeAtoms.get(id)?.value,\n id => edgeAtoms.get(id)?.value,\n )\n if (conflicts.length > 0) emit('conflict', { batch: b, conflicts })\n }\n for (const op of b.ops) applyOpInternal(op)\n emitChange(b)\n })\n },\n\n canUndo: () => undoStack.length > 0,\n canRedo: () => redoStack.length > 0,\n undo() {\n const batch = undoStack.pop()\n if (!batch) return false\n const ops = inverseBatch(batch)\n const inverseB: OpBatch = {\n id: asBatchId(idGenerator()),\n clientId,\n ts: Date.now(),\n origin: 'history',\n ops,\n }\n transact(() => {\n for (const op of ops) applyOpInternal(op)\n emit('change', inverseB) // bypass emitChange — history doesn't push\n })\n redoStack.push(batch)\n return true\n },\n redo() {\n const batch = redoStack.pop()\n if (!batch) return false\n // Replay with history origin so the inverse machinery stays clean,\n // and the redo batch goes back onto the undo stack so the user can\n // undo it again.\n const redoB: OpBatch = { ...batch, origin: 'history' }\n transact(() => {\n for (const op of redoB.ops) applyOpInternal(op)\n emit('change', redoB)\n })\n undoStack.push(batch)\n return true\n },\n clearHistory() {\n undoStack.length = 0\n redoStack.length = 0\n },\n\n // reads\n getNode: id => nodeAtoms.get(id)?.value,\n getEdge: id => edgeAtoms.get(id)?.value,\n getGroup: id => groupAtoms.get(id)?.value,\n getAllNodes: () => nodeIdsAtom.value.map(id => nodeAtoms.get(id)!.value),\n getAllEdges: () => edgeIdsAtom.value.map(id => edgeAtoms.get(id)!.value),\n getAllGroups: () => groupIdsAtom.value.map(id => groupAtoms.get(id)!.value),\n getNodeCount: () => nodeIdsAtom.value.length,\n getEdgeCount: () => edgeIdsAtom.value.length,\n getGroupCount: () => groupIdsAtom.value.length,\n\n getFrames: () => {\n const out: Node[] = []\n for (const id of frameOrderAtom.value) {\n const n = nodeAtoms.get(id)?.value\n if (n && n.type === 'frame') out.push(n)\n }\n return out\n },\n setFrameOrder(ids: NodeId[]) {\n const valid = new Set<NodeId>()\n for (const a of nodeAtoms.values()) {\n if (a.value.type === 'frame') valid.add(a.value.id)\n }\n // Drop ids that aren't (or no longer are) frames; append any\n // frames the caller forgot so the order remains a permutation\n // of the actual frame set.\n const filtered: NodeId[] = []\n const seen = new Set<NodeId>()\n for (const id of ids) {\n if (valid.has(id) && !seen.has(id)) {\n filtered.push(id)\n seen.add(id)\n }\n }\n for (const id of valid) {\n if (!seen.has(id)) filtered.push(id)\n }\n const prev = [...frameOrderAtom.value]\n // No-op short-circuit.\n if (filtered.length === prev.length && filtered.every((id, i) => id === prev[i])) {\n return\n }\n enqueueOp({ type: 'frame.reorder', ids: filtered, prev })\n },\n getNodesInFrame(id: NodeId) {\n const frame = nodeAtoms.get(id)?.value\n if (!frame || frame.type !== 'frame') return []\n const frameAabb = nodeAABB(frame)\n // Spatial broad-phase: any node intersecting the frame's AABB\n // is a candidate. Then filter to \"fully inside\" — node's AABB\n // entirely contained by the frame's AABB.\n const candidates = nodeIndex.queryRect(frameAabb) as NodeId[]\n const out: Node[] = []\n for (const cid of candidates) {\n if (cid === id) continue\n const node = nodeAtoms.get(cid)?.value\n if (!node || node.type === 'frame') continue\n const a = nodeAABB(node)\n if (\n a.x >= frameAabb.x &&\n a.y >= frameAabb.y &&\n a.x + a.w <= frameAabb.x + frameAabb.w &&\n a.y + a.h <= frameAabb.y + frameAabb.h\n ) {\n out.push(node)\n }\n }\n return out\n },\n\n getEdgeGeometry(id: EdgeId): EdgeGeometry | undefined {\n const edge = edgeAtoms.get(id)?.value\n if (!edge) return undefined\n const version = edgeVersions.get(id) ?? 0\n return edgeGeoCache.get(edge, version, getNodeForGeo) ?? undefined\n },\n getIncidentEdges(id: NodeId): EdgeId[] {\n const set = incidentEdges.get(id)\n return set ? [...set] : []\n },\n getNodeTypeDef(type: string) {\n return nodeTypeRegistry.get(type)\n },\n\n querySpatial(q: SpatialQuery): SpatialResult {\n const rect = q.rect ?? (q.point ? { x: q.point.x, y: q.point.y, w: 0, h: 0 } : null)\n if (!rect) return { nodes: [], edges: [] }\n return {\n nodes: nodeIndex.queryRect(rect) as NodeId[],\n edges: edgeIndex.queryRect(rect) as EdgeId[],\n }\n },\n\n getCamera: () => cameraAtom.value,\n setCamera(patch) {\n const next: CameraState = { ...cameraAtom.value, ...patch }\n cameraAtom.set(next)\n emit('camera', next)\n },\n\n getSelection: () => selectionAtom.value,\n setSelection(ids) {\n selectionAtom.set(ids)\n emit('selection', ids)\n },\n\n getInteractionState: () => interactionAtom.value,\n setInteractionState(patch) {\n const next: InteractionState = { ...interactionAtom.value, ...patch }\n interactionAtom.set(next)\n emit('interaction', next)\n },\n resetInteractionState() {\n const next = idleInteractionState()\n interactionAtom.set(next)\n emit('interaction', next)\n },\n\n beginEdit(id) {\n // Polymorphic: id may belong to a node or an edge. Resolve which.\n let target: import('./interaction').EditTarget | null = null\n if (nodeAtoms.has(id as NodeId)) target = { kind: 'node', id: id as NodeId }\n else if (edgeAtoms.has(id as EdgeId)) target = { kind: 'edge', id: id as EdgeId }\n if (!target) return\n const next: InteractionState = {\n ...interactionAtom.value,\n mode: 'editing',\n editingTarget: target,\n }\n interactionAtom.set(next)\n emit('interaction', next)\n },\n commitEdit(content) {\n const state = interactionAtom.value\n if (state.mode !== 'editing' || !state.editingTarget) return\n const target = state.editingTarget\n // Write content + autofit-derived height in one update so the\n // bitmap cache sees the final geometry on the next paint, not an\n // intermediate one.\n if (target.kind === 'node') this.updateNode(target.id, { content })\n else this.updateEdge(target.id, { content })\n const idleState = { ...interactionAtom.value, mode: 'idle' as const, editingTarget: null }\n interactionAtom.set(idleState)\n emit('interaction', idleState)\n },\n cancelEdit() {\n const state = interactionAtom.value\n if (state.mode !== 'editing') return\n const idleState = { ...state, mode: 'idle' as const, editingTarget: null }\n interactionAtom.set(idleState)\n emit('interaction', idleState)\n },\n\n presence: {\n setLocal(patch: PresencePatch) {\n const next: PresenceState = { ...localPresenceAtom.value, ...patch }\n localPresenceAtom.set(next)\n emit('presence', { state: next })\n },\n getLocal: () => localPresenceAtom.value,\n get: (id: ClientId) => remotePresence.get(id),\n getAll: () => remotePresence,\n applyRemote(id: ClientId, state: PresenceState | null) {\n if (state === null) {\n if (remotePresence.delete(id)) emit('presence', { clientId: id, removed: true })\n return\n }\n remotePresence.set(id, state)\n emit('presence', { state })\n },\n },\n\n subscribe<E extends StoreEventName>(event: E, cb: StoreEventHandler<E>): Unsubscribe {\n subscribers[event].add(cb)\n return () => {\n subscribers[event].delete(cb)\n }\n },\n }\n\n return store\n}\n","import type { ClientId, OpBatch } from '../types'\nimport type { PresencePatch, PresenceState } from './presence'\nimport type { CanvasStore, Unsubscribe } from './types'\n\n/**\n * SyncAdapter — see ARCHITECTURE.md §10.6.\n *\n * Pluggable transport contract for collab. The library never ships a\n * concrete adapter (transport is consumer territory: WebSocket, Yjs,\n * Automerge, BroadcastChannel, …). v1 ships:\n *\n * - This interface\n * - `attachSync(store, adapter)` — wires local commits → adapter and\n * remote batches → store with `origin: 'remote'`\n * - A separate package `@canvas-harness/sync-broadcast` providing a\n * BroadcastChannel-backed adapter for single-machine demos\n *\n * **v1 sync is experimental.** Conflict semantics assume causally-ordered\n * op delivery from the adapter. Adapters without causal ordering must\n * advertise `capabilities.crdt: true` and own merge themselves.\n */\nexport type SyncAdapterCapabilities = {\n /**\n * Adapter guarantees ops arrive in the same causal order all clients\n * see. Required for the default LWW path.\n */\n causalOrdering?: boolean\n /**\n * Adapter merges via CRDT (Yjs / Automerge / ...). Skips library-side\n * LWW because the adapter has already resolved conflicts.\n */\n crdt?: boolean\n}\n\n/**\n * Pluggable collab transport. Implementations forward op batches +\n * presence patches between peers. The library is transport-agnostic;\n * see `@canvas-harness/sync-broadcast` for a reference adapter using\n * `BroadcastChannel`.\n *\n * Authors typically wrap a WebSocket / Yjs / Automerge instance.\n *\n * @example\n * const myAdapter: SyncAdapter = {\n * capabilities: { causalOrdering: true },\n * sendBatch: b => ws.send(JSON.stringify({ kind: 'op', batch: b })),\n * sendPresence: p => ws.send(JSON.stringify({ kind: 'presence', patch: p })),\n * onBatch(cb) {\n * const h = (e: MessageEvent) => { const m = JSON.parse(e.data); if (m.kind === 'op') cb(m.batch) }\n * ws.addEventListener('message', h)\n * return () => ws.removeEventListener('message', h)\n * },\n * onPresence(cb) { … },\n * destroy() { ws.close() },\n * }\n * const detach = attachSync(store, myAdapter)\n */\nexport type SyncAdapter = {\n capabilities: SyncAdapterCapabilities\n\n /** Send a locally-committed (or history) batch to peers. */\n sendBatch(batch: OpBatch): void\n /** Send a local presence patch to peers. */\n sendPresence(patch: PresencePatch): void\n\n /** Receive remote batches. Subscription persists until `destroy()`. */\n onBatch(cb: (batch: OpBatch) => void): Unsubscribe\n /**\n * Receive remote presence patches. `state === null` means the remote\n * client has left and should be removed from the presence map.\n */\n onPresence(cb: (clientId: ClientId, state: PresenceState | null) => void): Unsubscribe\n\n /** Optional teardown — closes sockets, clears buffers, etc. */\n destroy?(): void\n}\n\n/**\n * Wires a {@link SyncAdapter} to a {@link CanvasStore}. Returns a\n * `detach()` function that disconnects everything (including the\n * adapter's own `destroy()`).\n *\n * Throws if the adapter advertises neither `causalOrdering` nor\n * `crdt` — the default LWW path requires causal order.\n *\n * After attach:\n * - Local + history batches forward to peers via `adapter.sendBatch`.\n * - Local presence updates forward via `adapter.sendPresence`.\n * - Remote batches apply to the store with `origin: 'remote'`\n * (don't enter undo stack; conflict event fires on `prev` mismatch).\n * - Remote presence updates merge into `store.presence`.\n *\n * @example\n * import { createBroadcastSyncAdapter } from '@canvas-harness/sync-broadcast'\n * const adapter = createBroadcastSyncAdapter({\n * channelName: 'my-board',\n * clientId: store.clientId,\n * })\n * const detach = attachSync(store, adapter)\n * // ...later, on unmount:\n * detach()\n */\nexport const attachSync = (store: CanvasStore, adapter: SyncAdapter): Unsubscribe => {\n if (!adapter.capabilities.causalOrdering && !adapter.capabilities.crdt) {\n throw new Error(\n 'SyncAdapter must advertise capabilities.causalOrdering or capabilities.crdt. ' +\n 'See ARCHITECTURE.md §10.6.',\n )\n }\n\n const unsubChange = store.subscribe('change', batch => {\n // Forward local mutations AND history batches (undo/redo). Remote\n // batches are echoes from peers and must not be re-broadcast.\n if (batch.origin !== 'remote') adapter.sendBatch(batch)\n })\n\n const unsubPresence = store.subscribe('presence', e => {\n if ('removed' in e && e.removed) return\n if (e.state.clientId !== store.clientId) return\n // Strip clientId from the patch — peers know who it's from from the channel.\n const { clientId: _id, ...patch } = e.state\n adapter.sendPresence(patch)\n })\n\n const unsubRemoteBatch = adapter.onBatch(batch => {\n // Bypass undo stack; apply with origin: 'remote' (origin is in the\n // batch itself for applyBatch). Conflict detection lives in\n // applyRemoteBatch (see conflict.ts).\n store.applyBatch({ ...batch, origin: 'remote' })\n })\n\n const unsubRemotePresence = adapter.onPresence((clientId, state) => {\n store.presence.applyRemote(clientId, state)\n })\n\n return () => {\n unsubChange()\n unsubPresence()\n unsubRemoteBatch()\n unsubRemotePresence()\n adapter.destroy?.()\n }\n}\n","/**\n * Palm-rejection helper — see IMPLEMENTATION.md Phase 11.\n *\n * When a stylus is actively touching the surface, mobile/tablet OSes\n * sometimes mis-route palm contacts as `pointerType: 'touch'`. The\n * heuristic: when a pen pointer is down (or has just lifted), drop all\n * incoming `touch` pointers for a short grace period.\n *\n * Pure state holder + helpers. The `<Canvas>` gesture hooks call\n * `notePenActive` / `notePenInactive` on pen pointer events, and\n * `shouldRejectTouch` before processing a touch event.\n */\n\nexport type PalmRejectionState = {\n /** True while at least one pen pointer is currently down. */\n penActive: boolean\n /** Timestamp (ms since epoch) at which the most recent pen pointer lifted. */\n lastPenUpAt: number\n}\n\nexport const PALM_REJECTION_GRACE_MS = 300\n\nexport const createPalmRejectionState = (): PalmRejectionState => ({\n penActive: false,\n lastPenUpAt: 0,\n})\n\nexport const notePenActive = (state: PalmRejectionState): void => {\n state.penActive = true\n}\n\nexport const notePenInactive = (state: PalmRejectionState, now: number): void => {\n state.penActive = false\n state.lastPenUpAt = now\n}\n\n/**\n * Returns true if this touch event should be ignored because a pen is\n * active (or just lifted within the grace window).\n */\nexport const shouldRejectTouch = (state: PalmRejectionState, now: number): boolean => {\n if (state.penActive) return true\n return now - state.lastPenUpAt < PALM_REJECTION_GRACE_MS\n}\n","import type { CanvasStore } from '../store'\n/**\n * Scene serialization codec — see ARCHITECTURE.md §3.8.\n *\n * In-memory uses Record<Id, T> for O(1) lookup; the wire format uses\n * arrays (smaller JSON, gzips better, deterministic iteration order).\n * Cost is one O(n) pass at the codec boundary, paid only on load/save.\n *\n * Schema migration: registered migrators run on `fromJSON` when the\n * incoming `schemaVersion` is lower than the current one.\n */\nimport { SCHEMA_VERSION, asEdgeId, asGroupId, asNodeId } from '../types'\nimport type { Scene, SerializedScene } from '../types'\n\nexport type Migrator = (raw: unknown) => unknown\n\nconst migrators = new Map<number, Migrator>()\n\n/**\n * Register a migrator that runs when loading data at version `fromVersion`.\n * The migrator should return data shaped for `fromVersion + 1`.\n */\nexport const registerMigrator = (fromVersion: number, fn: Migrator): void => {\n migrators.set(fromVersion, fn)\n}\n\n/**\n * Serializes a scene to its wire form.\n */\nexport const toSerialized = (scene: Scene): SerializedScene => ({\n schemaVersion: scene.schemaVersion,\n nodes: Object.values(scene.nodes),\n edges: Object.values(scene.edges),\n groups: Object.values(scene.groups),\n camera: scene.camera,\n selection: scene.selection,\n ...(scene.frameOrder && scene.frameOrder.length > 0 ? { frameOrder: scene.frameOrder } : {}),\n})\n\n/**\n * Deserializes from wire form into the in-memory Scene shape.\n * Runs migrators if the version is older than current.\n */\nexport const fromSerialized = (raw: SerializedScene | unknown): Scene => {\n let working: unknown = raw\n let version = (working as { schemaVersion?: number }).schemaVersion ?? 0\n\n while (version < SCHEMA_VERSION) {\n const fn = migrators.get(version)\n if (!fn) {\n throw new Error(\n `Cannot migrate scene from schemaVersion ${version} to ${SCHEMA_VERSION}; no migrator registered`,\n )\n }\n working = fn(working)\n version++\n }\n\n const ser = working as SerializedScene\n\n return {\n schemaVersion: SCHEMA_VERSION,\n nodes: Object.fromEntries(ser.nodes.map(n => [asNodeId(n.id), n])) as Scene['nodes'],\n edges: Object.fromEntries(ser.edges.map(e => [asEdgeId(e.id), e])) as Scene['edges'],\n groups: Object.fromEntries(ser.groups.map(g => [asGroupId(g.id), g])) as Scene['groups'],\n camera: ser.camera,\n selection: ser.selection,\n ...(ser.frameOrder ? { frameOrder: ser.frameOrder } : {}),\n }\n}\n\n/**\n * Convenience: dump a store's current state to wire form.\n */\nexport const storeToJSON = (store: CanvasStore): SerializedScene => ({\n schemaVersion: SCHEMA_VERSION,\n nodes: store.getAllNodes(),\n edges: store.getAllEdges(),\n groups: store.getAllGroups(),\n camera: store.getCamera(),\n selection: store.getSelection(),\n})\n","/**\n * DPR + size management for canvas elements.\n *\n * The backing-store size is `cssSize × dpr`, where `dpr` is clamped by\n * `maxDpr`. At native device-pixel-ratio on hi-DPI displays (Mac Retina\n * ≈ 2, Windows 4K @ 175% ≈ 1.75), the backing buffer can hit 8-25 MP —\n * every paint pays a proportional GPU-upload cost that often dominates\n * the frame budget.\n *\n * Default behavior when `maxDpr` is omitted: pick a cap from the\n * canvas's CSS-pixel area so the backing buffer stays in a healthy\n * 3-8 MP zone regardless of monitor / OS scaling. Tiered:\n *\n * - CSS canvas ≥ 2.5 MP (4K-ish, e.g. 4K Mac native, 4K Win @ 175%)\n * → cap at 1 (crispness sacrificed for perf, high-density makes\n * the softness less visible anyway)\n * - CSS canvas ≥ 1.5 MP (1440p / 2K-ish)\n * → cap at 1.5\n * - CSS canvas < 1.5 MP (1080p Retina laptops, embedded canvases)\n * → cap at 2 (DPR=2 is free at this size — keep crispness)\n *\n * Explicit `maxDpr={n}` always overrides the tier default. Text\n * remains crisp regardless of canvas DPR — the text bitmap cache\n * rasterizes glyphs at its own DPR-aware scale and blits.\n */\nconst HARD_MAX_DPR = 3 // anything above this just burns memory\n\n/**\n * Picks a sensible default `maxDpr` for the given CSS-pixel canvas\n * size. Targets ~3-8 MP backing buffer across the realistic hardware\n * spectrum. See module-level doc for the tier breakpoints.\n */\nexport const defaultMaxDprForSize = (cssW: number, cssH: number): number => {\n const cssPx = cssW * cssH\n if (cssPx >= 2_500_000) return 1\n if (cssPx >= 1_500_000) return 1.5\n return 2\n}\n\nexport type CanvasSurface = {\n canvas: HTMLCanvasElement\n ctx: CanvasRenderingContext2D\n /** Logical CSS pixels (the size you set in JS / read with getBoundingClientRect). */\n cssWidth: number\n cssHeight: number\n /** Device pixels — backing-store size. */\n dpr: number\n}\n\n/**\n * Resolved DPR for the canvas backing store. Clamped by `maxDpr`\n * (consumer-supplied) and the absolute `HARD_MAX_DPR` ceiling. When\n * `maxDpr` is omitted, the tier-based default (see\n * `defaultMaxDprForSize`) is used — pass `cssW`/`cssH` to enable it.\n */\nexport const getDpr = (maxDpr?: number, cssW = 0, cssH = 0): number => {\n if (typeof window === 'undefined') return 1\n const raw = window.devicePixelRatio || 1\n const resolvedMax =\n maxDpr === undefined && cssW > 0 && cssH > 0 ? defaultMaxDprForSize(cssW, cssH) : (maxDpr ?? 1)\n const cap = Math.max(1, Math.min(HARD_MAX_DPR, resolvedMax))\n return Math.max(1, Math.min(cap, raw))\n}\n\n/**\n * Builds a managed canvas surface. Caller pins the canvas element; we size\n * it and reset the 2d context's transform to logical-pixel space.\n *\n * Subsequent calls to `setSize` re-allocate the backing store if the new\n * `cssW × cssH × DPR` differs from the current.\n */\n// `maxDpr` is accepted but not yet used here — the actual DPR is\n// resolved in `sizeSurface` once we have the canvas dimensions for\n// the tier-default lookup. Kept on the signature for API symmetry.\nexport const setupSurface = (canvas: HTMLCanvasElement, _maxDpr?: number): CanvasSurface => {\n const ctx = canvas.getContext('2d')\n if (!ctx) throw new Error('Canvas 2d context unavailable')\n return {\n canvas,\n ctx,\n cssWidth: 0,\n cssHeight: 0,\n dpr: 1, // placeholder; `sizeSurface` writes the real value\n }\n}\n\n/**\n * Resizes the surface to a new CSS-pixel size, picking up the current DPR.\n * Returns true if anything changed (caller should redraw).\n */\nexport const sizeSurface = (\n surface: CanvasSurface,\n cssW: number,\n cssH: number,\n maxDpr?: number,\n): boolean => {\n const dpr = getDpr(maxDpr, cssW, cssH)\n if (surface.cssWidth === cssW && surface.cssHeight === cssH && surface.dpr === dpr) {\n return false\n }\n surface.cssWidth = cssW\n surface.cssHeight = cssH\n surface.dpr = dpr\n surface.canvas.width = Math.max(1, Math.round(cssW * dpr))\n surface.canvas.height = Math.max(1, Math.round(cssH * dpr))\n surface.canvas.style.width = `${cssW}px`\n surface.canvas.style.height = `${cssH}px`\n return true\n}\n\n/**\n * Clears the entire backing store. Call before setting the camera transform.\n */\nexport const clearSurface = (surface: CanvasSurface): void => {\n surface.ctx.setTransform(1, 0, 0, 1, 0, 0)\n surface.ctx.clearRect(0, 0, surface.canvas.width, surface.canvas.height)\n}\n","/**\n * rAF-driven frame loop — see ARCHITECTURE.md §4.3.\n *\n * The renderer marks layers dirty via `requestFrame()`; the loop coalesces\n * multiple requests into one paint per rAF tick. Idle frames cost nothing\n * because we only schedule when something is dirty.\n *\n * Per-frame timing is captured so consumers can drive perf overlays.\n */\nexport type FrameStats = {\n /** Most recent frame duration in ms (drawFn + overhead). */\n lastMs: number\n /** Running average over the last `historySize` frames. */\n avgMs: number\n /** Number of frames painted since start. */\n frames: number\n /** Frames drawn in the last 1000ms (FPS measurement). */\n fps: number\n}\n\nexport type FrameLoop = {\n start(): void\n stop(): void\n requestFrame(): void\n stats(): FrameStats\n}\n\ntype Opts = {\n draw: () => void\n historySize?: number\n}\n\nexport const createFrameLoop = ({ draw, historySize = 60 }: Opts): FrameLoop => {\n let running = false\n let scheduled = false\n let frameId = 0\n const history: number[] = []\n let frames = 0\n let lastMs = 0\n let avgMs = 0\n // rolling window of frame timestamps for FPS in the last second\n const fpsWindow: number[] = []\n let fps = 0\n\n const tick = (): void => {\n frameId = 0\n scheduled = false\n if (!running) return\n\n const t0 = performance.now()\n draw()\n const dur = performance.now() - t0\n\n history.push(dur)\n if (history.length > historySize) history.shift()\n let sum = 0\n for (const v of history) sum += v\n avgMs = sum / history.length\n lastMs = dur\n frames++\n\n fpsWindow.push(t0)\n const cutoff = t0 - 1000\n while (fpsWindow.length > 0 && fpsWindow[0]! < cutoff) fpsWindow.shift()\n fps = fpsWindow.length\n }\n\n const schedule = (): void => {\n if (scheduled || !running) return\n scheduled = true\n frameId = requestAnimationFrame(tick)\n }\n\n return {\n start() {\n if (running) return\n running = true\n schedule()\n },\n stop() {\n running = false\n if (frameId !== 0) {\n cancelAnimationFrame(frameId)\n frameId = 0\n }\n scheduled = false\n },\n requestFrame() {\n schedule()\n },\n stats: () => ({ lastMs, avgMs, frames, fps }),\n }\n}\n","/**\n * Renderer-side asset cache for `image` and `icon` node types.\n *\n * Why a cache: paint hot-path is sync; image / SVG decoding is async.\n * Each node carries its source on `node.data.src`; on first paint we\n * trigger an async decode and return a placeholder. When the decode\n * lands the cache fires `onReady`, which the renderer wires to a\n * static repaint so the next frame blits the real bitmap.\n *\n * Eviction: LRU bounded by `MAX_ENTRIES`. Entries hold either an\n * `HTMLImageElement` (raster) or an `ImageBitmap` (rasterized SVG).\n * Decoded images are GC-friendly — once the cache evicts the wrapper,\n * the browser frees the underlying pixel buffer.\n *\n * SVG raster cache keys by (markup, color, sizeBucket) so resizing an\n * icon node only rasterizes at the new size, leaving the previous\n * resolution available for siblings still at that size.\n */\nimport { applySvgColor } from '../../assets'\n\nconst MAX_ENTRIES = 256\n\ntype ImageEntry = {\n kind: 'image'\n state: 'pending' | 'ready' | 'error'\n bitmap: HTMLImageElement | null\n err?: unknown\n}\n\ntype IconEntry = {\n kind: 'icon'\n state: 'pending' | 'ready' | 'error'\n bitmap: ImageBitmap | null\n err?: unknown\n}\n\ntype Entry = ImageEntry | IconEntry\n\n/**\n * Bucket the requested icon raster size to a power-of-two step so\n * minor zoom changes don't churn the rasterizer. 32, 64, 128, 256,\n * 512. Above 512 the cache disables bucketing (one entry per exact\n * size) since fewer nodes hit those sizes.\n */\nconst bucketSize = (px: number): number => {\n if (px <= 32) return 32\n if (px <= 64) return 64\n if (px <= 128) return 128\n if (px <= 256) return 256\n if (px <= 512) return 512\n return Math.ceil(px / 256) * 256\n}\n\nexport type AssetCacheOptions = {\n /** Called when a pending entry transitions to ready or error. */\n onReady?: () => void\n}\n\nexport type AssetCache = {\n /** Returns a loaded HTMLImageElement or null if still loading. */\n getImage(src: string): HTMLImageElement | null\n /**\n * Returns a rasterized ImageBitmap for the given SVG markup at the\n * given on-device pixel size + tint color, or null if pending.\n */\n getIcon(markup: string, color: string | undefined, devicePixelSize: number): ImageBitmap | null\n /** Frees decoded bitmaps. Call from renderer.dispose(). */\n dispose(): void\n}\n\nexport const createAssetCache = (opts: AssetCacheOptions = {}): AssetCache => {\n const entries = new Map<string, Entry>()\n let disposed = false\n\n const notify = (): void => {\n if (disposed) return\n opts.onReady?.()\n }\n\n const touch = (key: string, entry: Entry): void => {\n entries.delete(key)\n entries.set(key, entry)\n if (entries.size > MAX_ENTRIES) {\n // Evict the oldest entry (insertion-order iteration on Map).\n const oldestKey = entries.keys().next().value\n if (oldestKey !== undefined) {\n const evicted = entries.get(oldestKey)\n if (evicted?.kind === 'icon' && evicted.bitmap) evicted.bitmap.close?.()\n entries.delete(oldestKey)\n }\n }\n }\n\n const startImageDecode = (key: string, src: string): void => {\n const entry: ImageEntry = { kind: 'image', state: 'pending', bitmap: null }\n touch(key, entry)\n const img = new Image()\n // Data URIs are same-origin; no crossorigin attribute needed.\n img.onload = () => {\n if (disposed) return\n entry.state = 'ready'\n entry.bitmap = img\n notify()\n }\n img.onerror = e => {\n if (disposed) return\n entry.state = 'error'\n entry.err = e\n notify()\n }\n img.src = src\n }\n\n const startIconRaster = (\n key: string,\n markup: string,\n color: string | undefined,\n sizePx: number,\n ): void => {\n const entry: IconEntry = { kind: 'icon', state: 'pending', bitmap: null }\n touch(key, entry)\n const colored = color ? applySvgColor(markup, color) : markup\n const blob = new Blob([colored], { type: 'image/svg+xml' })\n const url = URL.createObjectURL(blob)\n const img = new Image()\n img.onload = async () => {\n URL.revokeObjectURL(url)\n if (disposed) return\n try {\n // Use the intrinsic image dimensions but cap to the requested\n // bucket size; createImageBitmap with options gives a crisp\n // result at the target pixel grid without an OffscreenCanvas\n // dance in the simple cases.\n const bitmap = await createImageBitmap(img, {\n resizeWidth: sizePx,\n resizeHeight: sizePx,\n resizeQuality: 'high',\n })\n if (disposed) {\n bitmap.close?.()\n return\n }\n entry.state = 'ready'\n entry.bitmap = bitmap\n notify()\n } catch (e) {\n entry.state = 'error'\n entry.err = e\n notify()\n }\n }\n img.onerror = e => {\n URL.revokeObjectURL(url)\n if (disposed) return\n entry.state = 'error'\n entry.err = e\n notify()\n }\n img.src = url\n }\n\n return {\n getImage(src) {\n const key = `img:${src}`\n const existing = entries.get(key)\n if (existing && existing.kind === 'image') {\n if (existing.state === 'ready') {\n // Promote on access so LRU works.\n touch(key, existing)\n return existing.bitmap\n }\n return null\n }\n startImageDecode(key, src)\n return null\n },\n getIcon(markup, color, devicePixelSize) {\n const size = bucketSize(Math.max(1, Math.ceil(devicePixelSize)))\n const key = `icon:${size}:${color ?? ''}:${markup}`\n const existing = entries.get(key)\n if (existing && existing.kind === 'icon') {\n if (existing.state === 'ready') {\n touch(key, existing)\n return existing.bitmap\n }\n return null\n }\n startIconRaster(key, markup, color, size)\n return null\n },\n dispose() {\n disposed = true\n for (const entry of entries.values()) {\n if (entry.kind === 'icon' && entry.bitmap) entry.bitmap.close?.()\n }\n entries.clear()\n },\n }\n}\n","/**\n * Paint helpers for `image` and `icon` node types. Caller is already\n * inside `drawWithNodeTransform` (origin at the node's top-left,\n * rotation applied), so we paint into local space `(0, 0, w, h)`.\n *\n * Both helpers return true when a bitmap was blitted, false when the\n * bitmap is still loading (caller may paint a placeholder).\n */\nimport type { IconNodeData, ImageNodeData, Node } from '../../types'\nimport { resolveOpacity } from '../shapes/defaults'\nimport type { ThemeResolver } from '../shapes/defaults'\nimport type { AssetCache } from './cache'\n\n/** Cheap loading placeholder — light fill so the user sees a tile while we decode. */\nconst PLACEHOLDER_FILL = '#e5e7eb'\nconst PLACEHOLDER_TEXT_FILL = '#94a3b8'\n\nconst paintPlaceholder = (ctx: CanvasRenderingContext2D, w: number, h: number, label: string) => {\n ctx.fillStyle = PLACEHOLDER_FILL\n ctx.fillRect(0, 0, w, h)\n if (w >= 32 && h >= 16) {\n ctx.fillStyle = PLACEHOLDER_TEXT_FILL\n ctx.font = '11px system-ui, sans-serif'\n ctx.textAlign = 'center'\n ctx.textBaseline = 'middle'\n ctx.fillText(label, w / 2, h / 2)\n }\n}\n\nexport const paintImageNode = (\n ctx: CanvasRenderingContext2D,\n node: Node,\n cache: AssetCache,\n theme?: ThemeResolver,\n): void => {\n if (node.w <= 0 || node.h <= 0) return\n const data = node.data as ImageNodeData | undefined\n if (!data?.src) return\n const bitmap = cache.getImage(data.src)\n const opacity = resolveOpacity(node.style, theme)\n const needsScope = opacity !== 1\n if (needsScope) {\n ctx.save()\n ctx.globalAlpha = opacity\n }\n if (bitmap?.complete) {\n ctx.drawImage(bitmap, 0, 0, node.w, node.h)\n } else {\n paintPlaceholder(ctx, node.w, node.h, 'loading…')\n }\n if (needsScope) ctx.restore()\n}\n\nexport const paintIconNode = (\n ctx: CanvasRenderingContext2D,\n node: Node,\n cache: AssetCache,\n scale: number,\n theme?: ThemeResolver,\n): void => {\n if (node.w <= 0 || node.h <= 0) return\n const data = node.data as IconNodeData | undefined\n if (!data?.src) return\n // Bucket raster size by on-device pixels. We pass the longer side\n // so non-square nodes still render at their native quality on the\n // larger axis.\n const sizePx = Math.max(node.w, node.h) * scale\n const color = node.style?.iconColor\n const bitmap = cache.getIcon(data.src, color, sizePx)\n const opacity = resolveOpacity(node.style, theme)\n const needsScope = opacity !== 1\n if (needsScope) {\n ctx.save()\n ctx.globalAlpha = opacity\n }\n if (bitmap) {\n ctx.drawImage(bitmap, 0, 0, node.w, node.h)\n } else {\n paintPlaceholder(ctx, node.w, node.h, 'svg…')\n }\n if (needsScope) ctx.restore()\n}\n","import { type CanvasBackground, DEFAULT_BACKGROUND, type WorldRect } from '../types'\n\n/**\n * Page background + optional infinite dot / grid pattern.\n *\n * Called inside `paintStatic` after the camera transform is applied,\n * before nodes. Dots / grid lines are drawn in world coordinates so\n * they anchor to the world origin — panning moves the user *through*\n * the pattern, zooming changes visual density.\n *\n * LOD: when `gap × zoom` drops below `MIN_PATTERN_SCREEN_PX`, the\n * effective gap doubles in octaves so the pattern stays roughly the\n * same on-screen density. Below `MIN_VISIBLE_PATTERN_PX` the pattern\n * is omitted entirely (sub-pixel would be unreadable mush + waste).\n */\nexport type PaintBackgroundOptions = {\n /** Visible world rect (after viewport-overscan). */\n viewport: WorldRect\n /** camera.z — used for LOD octave selection + screen-px conversion. */\n zoom: number\n background?: CanvasBackground\n}\n\nconst MIN_PATTERN_SCREEN_PX = 8\nconst MIN_VISIBLE_PATTERN_PX = 2\n\nexport const paintBackground = (\n ctx: CanvasRenderingContext2D,\n opts: PaintBackgroundOptions,\n): void => {\n const bg = { ...DEFAULT_BACKGROUND, ...opts.background }\n\n // 1. Solid page color. Fill the visible world rect; the caller has\n // already applied the camera transform so we paint in world coords.\n ctx.save()\n ctx.fillStyle = bg.color\n ctx.fillRect(opts.viewport.x, opts.viewport.y, opts.viewport.w, opts.viewport.h)\n ctx.restore()\n\n if (bg.pattern === 'none') return\n\n // 2a. User-configured zoom cliffs — hide pattern outside [minZoom, maxZoom].\n if (opts.zoom < bg.minZoom) return\n if (opts.zoom > bg.maxZoom) return\n\n // 2b. LOD — densify the gap in octaves until each cell is at least\n // MIN_PATTERN_SCREEN_PX on-screen. Skip entirely when pattern\n // would be sub-visible.\n let effectiveGap = bg.gap\n while (effectiveGap * opts.zoom < MIN_PATTERN_SCREEN_PX) {\n effectiveGap *= 2\n if (effectiveGap > 1e6) return // runaway guard\n }\n if (effectiveGap * opts.zoom < MIN_VISIBLE_PATTERN_PX) return\n\n // 3. First grid line / dot inside the viewport — snap to the gap.\n const minX = Math.floor(opts.viewport.x / effectiveGap) * effectiveGap\n const minY = Math.floor(opts.viewport.y / effectiveGap) * effectiveGap\n const maxX = opts.viewport.x + opts.viewport.w\n const maxY = opts.viewport.y + opts.viewport.h\n\n if (bg.pattern === 'dots') {\n paintDots(ctx, minX, minY, maxX, maxY, effectiveGap, bg.patternColor, opts.zoom)\n } else if (bg.pattern === 'grid') {\n paintGrid(ctx, minX, minY, maxX, maxY, effectiveGap, bg.patternColor, opts.zoom)\n }\n}\n\nconst paintDots = (\n ctx: CanvasRenderingContext2D,\n minX: number,\n minY: number,\n maxX: number,\n maxY: number,\n gap: number,\n color: string,\n zoom: number,\n): void => {\n // Use a tiny `fillRect` per dot rather than `arc + fill`. At 1-2px\n // on-screen the corners aren't perceivable (antialiasing softens\n // them into something visually indistinguishable from a small\n // round dot), and one canvas2d call replaces three (beginPath /\n // arc / fill) plus the implicit curve approximation. ~3-5x faster\n // across thousands of dots/frame.\n const sizeWorld = Math.max(1, 1.6 / zoom)\n const half = sizeWorld / 2\n ctx.save()\n ctx.fillStyle = color\n for (let y = minY; y <= maxY; y += gap) {\n for (let x = minX; x <= maxX; x += gap) {\n ctx.fillRect(x - half, y - half, sizeWorld, sizeWorld)\n }\n }\n ctx.restore()\n}\n\nconst paintGrid = (\n ctx: CanvasRenderingContext2D,\n minX: number,\n minY: number,\n maxX: number,\n maxY: number,\n gap: number,\n color: string,\n zoom: number,\n): void => {\n const lineWidth = 1 / zoom // constant 1px on screen\n ctx.save()\n ctx.strokeStyle = color\n ctx.lineWidth = lineWidth\n ctx.beginPath()\n for (let x = minX; x <= maxX; x += gap) {\n ctx.moveTo(x, minY)\n ctx.lineTo(x, maxY)\n }\n for (let y = minY; y <= maxY; y += gap) {\n ctx.moveTo(minX, y)\n ctx.lineTo(maxX, y)\n }\n ctx.stroke()\n ctx.restore()\n}\n","/**\n * Resize-handle hit testing — see ARCHITECTURE.md §11.6.\n *\n * Handles are drawn at constant screen size (e.g. 8px), so their world-space\n * bounds change with camera zoom. They sit at the 8 cardinal points of the\n * node's bounding rect; for rotated nodes the handle positions rotate with\n * the node so a \"north-east\" handle is actually at the rotated NE corner.\n */\nimport type { Node, Vec2 } from '../types'\n\nexport type ResizeHandle = 'nw' | 'n' | 'ne' | 'e' | 'se' | 's' | 'sw' | 'w'\n\nexport const RESIZE_HANDLES: ResizeHandle[] = ['nw', 'n', 'ne', 'e', 'se', 's', 'sw', 'w']\n\n/**\n * Screen-pixel size of a resize-handle hit target. Visual size matches.\n * Sized for touch reach (~14px) without being intrusive on desktop;\n * tldraw uses a similar value.\n */\nexport const RESIZE_HANDLE_SIZE_PX = 14\n\n/**\n * Screen-pixel distance from the top edge of the node to the rotation\n * handle center. Visual + hit-target match.\n */\nexport const ROTATE_HANDLE_OFFSET_PX = 24\n\n/** Screen-pixel radius of the rotation-handle hit target. */\nexport const ROTATE_HANDLE_RADIUS_PX = 9\n\n/**\n * World-space centers of all 8 resize handles for the given node.\n * Rotation-aware: handles rotate with the node so they sit on the corners\n * and edge midpoints of the rotated rect (not the rotated AABB).\n */\nexport const handleWorldPositions = (node: Node): Record<ResizeHandle, Vec2> => {\n const localCenters: Record<ResizeHandle, Vec2> = {\n nw: { x: 0, y: 0 },\n n: { x: node.w / 2, y: 0 },\n ne: { x: node.w, y: 0 },\n e: { x: node.w, y: node.h / 2 },\n se: { x: node.w, y: node.h },\n s: { x: node.w / 2, y: node.h },\n sw: { x: 0, y: node.h },\n w: { x: 0, y: node.h / 2 },\n }\n if (node.angle === 0) {\n const offsetX = node.x\n const offsetY = node.y\n return {\n nw: { x: offsetX + localCenters.nw.x, y: offsetY + localCenters.nw.y },\n n: { x: offsetX + localCenters.n.x, y: offsetY + localCenters.n.y },\n ne: { x: offsetX + localCenters.ne.x, y: offsetY + localCenters.ne.y },\n e: { x: offsetX + localCenters.e.x, y: offsetY + localCenters.e.y },\n se: { x: offsetX + localCenters.se.x, y: offsetY + localCenters.se.y },\n s: { x: offsetX + localCenters.s.x, y: offsetY + localCenters.s.y },\n sw: { x: offsetX + localCenters.sw.x, y: offsetY + localCenters.sw.y },\n w: { x: offsetX + localCenters.w.x, y: offsetY + localCenters.w.y },\n }\n }\n\n const cx = node.x + node.w / 2\n const cy = node.y + node.h / 2\n const cos = Math.cos(node.angle)\n const sin = Math.sin(node.angle)\n const rotate = (p: Vec2): Vec2 => {\n // local coords (top-left origin) → center-origin → rotate → world\n const dx = p.x - node.w / 2\n const dy = p.y - node.h / 2\n return { x: cx + dx * cos - dy * sin, y: cy + dx * sin + dy * cos }\n }\n return {\n nw: rotate(localCenters.nw),\n n: rotate(localCenters.n),\n ne: rotate(localCenters.ne),\n e: rotate(localCenters.e),\n se: rotate(localCenters.se),\n s: rotate(localCenters.s),\n sw: rotate(localCenters.sw),\n w: rotate(localCenters.w),\n }\n}\n\n/**\n * Returns the handle hit by a world point, or null. `cameraZ` lets us map\n * the constant screen-size handle box to its current world-space footprint.\n */\nexport const hitTestHandles = (\n node: Node,\n worldPoint: Vec2,\n cameraZ: number,\n): ResizeHandle | null => {\n const halfWorld = RESIZE_HANDLE_SIZE_PX / 2 / cameraZ\n const positions = handleWorldPositions(node)\n for (const h of RESIZE_HANDLES) {\n const center = positions[h]\n if (\n Math.abs(worldPoint.x - center.x) <= halfWorld &&\n Math.abs(worldPoint.y - center.y) <= halfWorld\n ) {\n return h\n }\n }\n return null\n}\n\n/**\n * World-space position of the rotation handle — sits a constant 22px\n * (screen) above the node's top edge midpoint, perpendicular to the\n * rotated top edge.\n */\nexport const rotateHandleWorldPosition = (node: Node, cameraZ: number): Vec2 => {\n const offsetWorld = ROTATE_HANDLE_OFFSET_PX / cameraZ\n const cx = node.x + node.w / 2\n const cy = node.y + node.h / 2\n // Local coords (relative to node center, y-up): midpoint of top edge is\n // (0, -h/2 - offsetWorld). Apply rotation; node.angle is clockwise on\n // a y-down canvas.\n const localX = 0\n const localY = -node.h / 2 - offsetWorld\n const cos = Math.cos(node.angle)\n const sin = Math.sin(node.angle)\n return {\n x: cx + localX * cos - localY * sin,\n y: cy + localX * sin + localY * cos,\n }\n}\n\n/**\n * Returns true if `worldPoint` is over the rotation handle for the node.\n */\nexport const hitTestRotateHandle = (node: Node, worldPoint: Vec2, cameraZ: number): boolean => {\n const center = rotateHandleWorldPosition(node, cameraZ)\n const rWorld = ROTATE_HANDLE_RADIUS_PX / cameraZ\n const dx = worldPoint.x - center.x\n const dy = worldPoint.y - center.y\n return dx * dx + dy * dy <= rWorld * rWorld\n}\n","/**\n * Selection-overlay drawing — runs on the interactive canvas.\n *\n * Renders:\n * - selection outlines around selected node bounds\n * - 8 resize handles for a single-node or multi-select selection\n * - the marquee rect during marquee selection\n * - dragged nodes at their uncommitted (delta-offset) positions\n *\n * Visual sizes are constant in screen pixels — `scale` (camera.z × DPR)\n * is used to convert px → world for outline strokes and handle sizes.\n *\n * Color: every draw takes `color` so the renderer can thread its\n * `selectionColor` option through to all chrome. Marquee fill tints\n * via `globalAlpha = MARQUEE_FILL_ALPHA` so any color format works\n * (hex, rgb(), named) without parsing.\n */\nimport {\n RESIZE_HANDLE_SIZE_PX,\n ROTATE_HANDLE_RADIUS_PX,\n handleWorldPositions,\n rotateHandleWorldPosition,\n} from '../hit-test/handle'\nimport type { Node, Vec2, WorldRect } from '../types'\n\n/** Default selection chrome color when no override is provided. */\nexport const DEFAULT_SELECTION_COLOR = '#3b82f6'\nexport const SELECTION_OUTLINE_PX = 1.5\n/** Marquee fill = selection color at this alpha, applied via globalAlpha. */\nconst MARQUEE_FILL_ALPHA = 0.08\nconst MARQUEE_STROKE_PX = 1\n\n/**\n * Draws a 1.5px-on-screen outline around the node's (rotated) bounds.\n */\nexport const drawSelectionOutline = (\n ctx: CanvasRenderingContext2D,\n node: Node,\n scale: number,\n color: string,\n): void => {\n if (node.angle === 0) {\n ctx.save()\n ctx.strokeStyle = color\n ctx.lineWidth = SELECTION_OUTLINE_PX / scale\n ctx.beginPath()\n ctx.rect(node.x, node.y, node.w, node.h)\n ctx.stroke()\n ctx.restore()\n return\n }\n // Rotated: build the 4-corner path manually\n const cx = node.x + node.w / 2\n const cy = node.y + node.h / 2\n const cos = Math.cos(node.angle)\n const sin = Math.sin(node.angle)\n const corners: Vec2[] = [\n { x: -node.w / 2, y: -node.h / 2 },\n { x: node.w / 2, y: -node.h / 2 },\n { x: node.w / 2, y: node.h / 2 },\n { x: -node.w / 2, y: node.h / 2 },\n ].map(p => ({ x: cx + p.x * cos - p.y * sin, y: cy + p.x * sin + p.y * cos }))\n\n ctx.save()\n ctx.strokeStyle = color\n ctx.lineWidth = SELECTION_OUTLINE_PX / scale\n ctx.beginPath()\n const first = corners[0]!\n ctx.moveTo(first.x, first.y)\n for (let i = 1; i < corners.length; i++) {\n const c = corners[i]!\n ctx.lineTo(c.x, c.y)\n }\n ctx.closePath()\n ctx.stroke()\n ctx.restore()\n}\n\n/**\n * Draws the 8 resize handles for a node at constant screen size.\n */\nexport const drawResizeHandles = (\n ctx: CanvasRenderingContext2D,\n node: Node,\n scale: number,\n color: string,\n): void => {\n const halfPx = RESIZE_HANDLE_SIZE_PX / 2\n const halfWorld = halfPx / scale\n const positions = handleWorldPositions(node)\n\n ctx.save()\n ctx.fillStyle = '#fff'\n ctx.strokeStyle = color\n ctx.lineWidth = SELECTION_OUTLINE_PX / scale\n for (const key of Object.keys(positions) as (keyof typeof positions)[]) {\n const p = positions[key]\n ctx.beginPath()\n ctx.rect(p.x - halfWorld, p.y - halfWorld, halfWorld * 2, halfWorld * 2)\n ctx.fill()\n ctx.stroke()\n }\n ctx.restore()\n}\n\n/**\n * Draws the rotation handle — circle above the top edge midpoint,\n * connected by a tether line. Constant screen size; rotation-aware so\n * the handle stays \"above\" the rotated top edge.\n *\n * cameraZ is passed separately from `scale` because the handle's\n * world-space offset depends on plain zoom (not DPR-multiplied scale).\n */\nexport const drawRotateHandle = (\n ctx: CanvasRenderingContext2D,\n node: Node,\n scale: number,\n cameraZ: number,\n color: string,\n): void => {\n const center = rotateHandleWorldPosition(node, cameraZ)\n const radiusWorld = ROTATE_HANDLE_RADIUS_PX / scale\n\n // Tether: top edge midpoint → handle center, in the node's local frame.\n const cx = node.x + node.w / 2\n const cy = node.y + node.h / 2\n const cos = Math.cos(node.angle)\n const sin = Math.sin(node.angle)\n const topMidLocalY = -node.h / 2\n const topMidWorld = {\n x: cx + 0 * cos - topMidLocalY * sin,\n y: cy + 0 * sin + topMidLocalY * cos,\n }\n\n ctx.save()\n ctx.strokeStyle = color\n ctx.lineWidth = SELECTION_OUTLINE_PX / scale\n ctx.beginPath()\n ctx.moveTo(topMidWorld.x, topMidWorld.y)\n ctx.lineTo(center.x, center.y)\n ctx.stroke()\n\n ctx.fillStyle = '#fff'\n ctx.beginPath()\n ctx.arc(center.x, center.y, radiusWorld, 0, Math.PI * 2)\n ctx.fill()\n ctx.stroke()\n ctx.restore()\n}\n\n/**\n * Draws a single midpoint handle at the visual midpoint of a selected\n * bezier/polyline edge. Drag it to reshape the curve (the gesture in\n * `useInteractionGesture` converts the drag point into cubic controls\n * via `midpointToCubicControls`).\n */\nexport const drawEdgeMidpointHandle = (\n ctx: CanvasRenderingContext2D,\n midpoint: { x: number; y: number },\n scale: number,\n color: string,\n): void => {\n const radiusPx = 5\n const radiusWorld = radiusPx / scale\n ctx.save()\n ctx.fillStyle = '#fff'\n ctx.strokeStyle = color\n ctx.lineWidth = SELECTION_OUTLINE_PX / scale\n ctx.beginPath()\n ctx.arc(midpoint.x, midpoint.y, radiusWorld, 0, Math.PI * 2)\n ctx.fill()\n ctx.stroke()\n ctx.restore()\n}\n\n/**\n * Draws the endpoint handles for a selected edge at the source/target\n * world points. Used during edit/reconnection.\n */\nexport const drawEdgeEndpointHandles = (\n ctx: CanvasRenderingContext2D,\n source: { x: number; y: number },\n target: { x: number; y: number },\n scale: number,\n color: string,\n): void => {\n const radiusPx = 5\n const radiusWorld = radiusPx / scale\n ctx.save()\n ctx.fillStyle = '#fff'\n ctx.strokeStyle = color\n ctx.lineWidth = SELECTION_OUTLINE_PX / scale\n for (const p of [source, target]) {\n ctx.beginPath()\n ctx.arc(p.x, p.y, radiusWorld, 0, Math.PI * 2)\n ctx.fill()\n ctx.stroke()\n }\n ctx.restore()\n}\n\n/**\n * Draws the marquee selection rectangle.\n */\nexport const drawMarquee = (\n ctx: CanvasRenderingContext2D,\n rect: WorldRect,\n scale: number,\n color: string,\n): void => {\n ctx.save()\n // Fill via globalAlpha so any color literal (hex, rgb(), named) tints\n // correctly — no parsing needed.\n ctx.globalAlpha = MARQUEE_FILL_ALPHA\n ctx.fillStyle = color\n ctx.fillRect(rect.x, rect.y, rect.w, rect.h)\n ctx.globalAlpha = 1\n ctx.strokeStyle = color\n ctx.lineWidth = MARQUEE_STROKE_PX / scale\n ctx.setLineDash([4 / scale, 3 / scale])\n ctx.strokeRect(rect.x, rect.y, rect.w, rect.h)\n ctx.restore()\n}\n","/**\n * Paint for `type: 'frame'` nodes. Frames are slide regions that sit\n * visually behind content — see ARCHITECTURE.md §3.7 frames.\n *\n * Visual:\n * - Thin 1.5px-on-screen border in a subdued color\n * - Faint fill so the boundary reads even on textured backgrounds\n * - Name label above the top edge (`node.content`, fallback \"Frame\")\n *\n * Caller is already inside `drawWithNodeTransform` (origin at frame's\n * top-left, rotation applied). No rough.js — frames are organizational\n * chrome, not hand-drawn content.\n */\nimport type { Node } from '../types'\nimport { resolveColor, resolveOpacity } from './shapes/defaults'\nimport type { ThemeResolver } from './shapes/defaults'\n\nconst FRAME_BORDER_PX = 1.5\nconst FRAME_BORDER_COLOR_DEFAULT = '#94a3b8'\nconst FRAME_FILL_DEFAULT = 'rgba(148, 163, 184, 0.06)'\nconst FRAME_LABEL_FONT_PX = 12\nconst FRAME_LABEL_GAP_PX = 6\nconst FRAME_LABEL_COLOR = '#64748b'\n\nexport const paintFrameNode = (\n ctx: CanvasRenderingContext2D,\n node: Node,\n scale: number,\n theme?: ThemeResolver,\n): void => {\n if (node.w <= 0 || node.h <= 0) return\n const opacity = resolveOpacity(node.style, theme)\n const needsScope = opacity !== 1\n if (needsScope) {\n ctx.save()\n ctx.globalAlpha = opacity\n }\n\n // Fill\n const fill =\n node.style?.backgroundColor ??\n (theme ? (theme('frame.background') as string | undefined) : undefined) ??\n FRAME_FILL_DEFAULT\n ctx.fillStyle = fill\n ctx.fillRect(0, 0, node.w, node.h)\n\n // Border\n const stroke = resolveColor(node.style, 'strokeColor', FRAME_BORDER_COLOR_DEFAULT, theme)\n ctx.strokeStyle = stroke\n ctx.lineWidth = FRAME_BORDER_PX / scale\n ctx.setLineDash([])\n ctx.strokeRect(0, 0, node.w, node.h)\n\n // Label above the top edge. Drawn in screen-pixel sizes via\n // 1/scale so it stays constant across zoom levels.\n const labelPx = FRAME_LABEL_FONT_PX / scale\n const gapPx = FRAME_LABEL_GAP_PX / scale\n const label = node.content?.trim() || 'Frame'\n ctx.fillStyle = FRAME_LABEL_COLOR\n ctx.textBaseline = 'bottom'\n ctx.textAlign = 'left'\n ctx.font = `500 ${labelPx}px system-ui, -apple-system, sans-serif`\n ctx.fillText(label, 0, -gapPx)\n\n if (needsScope) ctx.restore()\n}\n","/**\n * Rough-rendering thresholds — see IMPROVEMENTS.md and dim0/rough.\n *\n * Below `ROUGH_MIN_ZOOM` or above `ROUGH_MAX_NODES` we fall back to\n * plain strokes; the wobble is invisible at low zoom and the per-shape\n * cost stacks up past the cap. These are the two cheap gates that\n * protect the frame budget without the consumer having to think about\n * it.\n */\nexport const ROUGH_MIN_ZOOM = 0.4\nexport const ROUGH_MAX_NODES = 800\n\n/**\n * Above this many simultaneously-dragged/resized/rotated nodes, we drop\n * rough rendering for the frame. Dragging a single node (or a small\n * group) keeps the hand-drawn look stable — only large marquee moves\n * fall back to plain. Pan/zoom always disables rough regardless.\n */\nexport const ROUGH_MAX_MOVING_NODES = 5\n\n/**\n * Path-cache hard cap. Keyed entries: per-shape `(type, w, h, stroke,\n * style, roughness, seed)` tuples. LRU eviction.\n */\nexport const ROUGH_PATH_CACHE_MAX = 1000\n\n/**\n * rough.js generator defaults. The combination of `disableMultiStroke`\n * + `preserveVertices` + `bowing: 2` is the one that yields the\n * excalidraw-feeling stroke without the 3-5× cost of multi-stroke.\n */\nexport const ROUGH_DEFAULTS = {\n bowing: 2,\n disableMultiStroke: true,\n preserveVertices: true,\n} as const\n\n/**\n * Print-misregistration offset — the fill is translated by this delta\n * before paint, while the rough stroke stays at the wrapper origin.\n * The resulting gap mimics an old CMYK plate that didn't quite line up.\n * Only applied when a shape opts into rough (`style.roughness > 0`).\n * Matches dim0's `--shape-misregister-x/y` (-3, -2) defaults.\n */\nexport const ROUGH_FILL_MISREGISTER_X = -3\nexport const ROUGH_FILL_MISREGISTER_Y = -2\n","/**\n * Small color utilities shared by the rendering pipeline. Pure\n * functions on hex strings — no canvas or DOM dependencies.\n */\n\nconst TONE_BLEND = 0.2\n\nconst parseHex = (hex: string): [number, number, number] | null => {\n if (!hex.startsWith('#')) return null\n const h = hex.slice(1)\n if (h.length === 3) {\n return [\n Number.parseInt(h[0]! + h[0]!, 16),\n Number.parseInt(h[1]! + h[1]!, 16),\n Number.parseInt(h[2]! + h[2]!, 16),\n ]\n }\n if (h.length === 6 || h.length === 8) {\n return [\n Number.parseInt(h.slice(0, 2), 16),\n Number.parseInt(h.slice(2, 4), 16),\n Number.parseInt(h.slice(4, 6), 16),\n ]\n }\n return null\n}\n\nconst toHexPair = (n: number): string =>\n Math.max(0, Math.min(255, Math.round(n)))\n .toString(16)\n .padStart(2, '0')\n\n/** Linear mix between two hex colors. `t = 0` returns `a`, `t = 1` returns `b`. */\nexport const mixHex = (a: string, b: string, t: number): string => {\n const A = parseHex(a)\n const B = parseHex(b)\n if (!A || !B) return a\n const p = Math.max(0, Math.min(1, t))\n return `#${toHexPair(A[0] * (1 - p) + B[0] * p)}${toHexPair(A[1] * (1 - p) + B[1] * p)}${toHexPair(A[2] * (1 - p) + B[2] * p)}`\n}\n\nconst darkenCache = new Map<string, string>()\n\n/**\n * Returns `hex` shifted 20% toward black. Memoized — colors used by\n * many layered nodes share a cache entry. Returns the input unchanged\n * if it isn't a parseable hex.\n */\nexport const darkenHex = (hex: string): string => {\n const cached = darkenCache.get(hex)\n if (cached !== undefined) return cached\n const result = mixHex(hex, '#000000', TONE_BLEND)\n darkenCache.set(hex, result)\n return result\n}\n","/**\n * Path-building helpers shared by shape draw functions.\n *\n * Each builds a path on the context using the node's local rect (0..w, 0..h);\n * the renderer has already applied translate(node.x, node.y) + rotation,\n * so shapes can think in pure local coordinates.\n */\nexport const buildRectPath = (\n ctx: CanvasRenderingContext2D,\n w: number,\n h: number,\n radius: number,\n): void => {\n ctx.beginPath()\n if (radius <= 0) {\n ctx.rect(0, 0, w, h)\n return\n }\n // Native roundRect — one C++ call per rect. The manual 4×\n // quadraticCurveTo + 4× lineTo build was 28k JS→native crossings\n // per frame at 7k visible rects and dominated paint on lower-end\n // GPUs (Windows 4K + integrated graphics). roundRect clamps the\n // radius to min(w/2, h/2) internally, matching the previous behavior.\n ctx.roundRect(0, 0, w, h, radius)\n}\n\nexport const buildEllipsePath = (ctx: CanvasRenderingContext2D, w: number, h: number): void => {\n const rx = w / 2\n const ry = h / 2\n ctx.beginPath()\n ctx.ellipse(rx, ry, rx, ry, 0, 0, Math.PI * 2)\n}\n\n/**\n * Diamond inscribed in `(0, 0, w, h)`. When `radius` > 0, each 45° edge is\n * trimmed by `radius * √2` and the corner vertex is replaced with a\n * quadratic curve — produces the \"soft diamond\" excalidraw look. At\n * radius 0 the corners are sharp.\n */\nexport const buildDiamondPath = (\n ctx: CanvasRenderingContext2D,\n w: number,\n h: number,\n radius = 0,\n): void => {\n ctx.beginPath()\n if (radius <= 0) {\n ctx.moveTo(w / 2, 0)\n ctx.lineTo(w, h / 2)\n ctx.lineTo(w / 2, h)\n ctx.lineTo(0, h / 2)\n ctx.closePath()\n return\n }\n const cx = w / 2\n const cy = h / 2\n const T = { x: cx, y: 0 }\n const R = { x: w, y: cy }\n const B = { x: cx, y: h }\n const L = { x: 0, y: cy }\n const edgeLen = Math.hypot(R.x - T.x, R.y - T.y)\n const sMax = Math.max(0, edgeLen / 2 - 0.01)\n const s = Math.min(radius * Math.SQRT2, sMax)\n if (s <= 0.0001) {\n ctx.moveTo(T.x, T.y)\n ctx.lineTo(R.x, R.y)\n ctx.lineTo(B.x, B.y)\n ctx.lineTo(L.x, L.y)\n ctx.closePath()\n return\n }\n const along = (a: { x: number; y: number }, b: { x: number; y: number }, d: number) => {\n const dx = b.x - a.x\n const dy = b.y - a.y\n const len = Math.hypot(dx, dy) || 1\n const t = d / len\n return { x: a.x + dx * t, y: a.y + dy * t }\n }\n const TR = along(T, R, s)\n const RT = along(R, T, s)\n const RB = along(R, B, s)\n const BR = along(B, R, s)\n const BL = along(B, L, s)\n const LB = along(L, B, s)\n const LT = along(L, T, s)\n const TL = along(T, L, s)\n ctx.moveTo(TR.x, TR.y)\n ctx.lineTo(RT.x, RT.y)\n ctx.quadraticCurveTo(R.x, R.y, RB.x, RB.y)\n ctx.lineTo(BR.x, BR.y)\n ctx.quadraticCurveTo(B.x, B.y, BL.x, BL.y)\n ctx.lineTo(LB.x, LB.y)\n ctx.quadraticCurveTo(L.x, L.y, LT.x, LT.y)\n ctx.lineTo(TL.x, TL.y)\n ctx.quadraticCurveTo(T.x, T.y, TR.x, TR.y)\n ctx.closePath()\n}\n\n/**\n * Compute thought-cloud geometry — used by both the canvas builder and\n * the SVG-path builder so the visible silhouette stays identical\n * between plain and rough rendering.\n */\nexport const thoughtCloudGeometry = (w: number, h: number) => {\n const domeW = Math.min(w * 0.4, h * 1.2)\n const domeH = Math.min(h * 0.45, domeW)\n const domeAnchorX = w * 0.3\n const domeX = Math.max(0, Math.min(w - domeW, domeAnchorX - domeW / 2))\n return {\n domeX,\n domeW,\n domeH,\n cx: domeX + domeW / 2,\n cy: domeH / 2,\n rx: domeW / 2,\n ry: domeH / 2,\n bodyY: domeH * 0.55,\n }\n}\n\n/**\n * Thought-cloud as a single union path — rect body with a dome that\n * merges seamlessly into the top edge. No internal border between\n * dome and rect; the silhouette reads as one continuous outline.\n */\nexport const buildThoughtCloudPath = (\n ctx: CanvasRenderingContext2D,\n w: number,\n h: number,\n radius: number,\n): void => {\n const g = thoughtCloudGeometry(w, h)\n const bodyH = h - g.bodyY\n const r = Math.max(0, Math.min(radius, bodyH / 2, w / 2))\n\n // Find where the dome's lower arc crosses the rect's top edge.\n const t = g.ry > 0 ? (g.bodyY - g.cy) / g.ry : 0\n const inRange = Math.abs(t) < 1\n let xL = g.domeX\n let xR = g.domeX + g.domeW\n if (inRange) {\n const xOffset = g.rx * Math.sqrt(1 - t * t)\n xL = g.cx - xOffset\n xR = g.cx + xOffset\n }\n // Clamp so the dome ends don't cross the rect's rounded corners.\n xL = Math.max(r, xL)\n xR = Math.min(w - r, xR)\n\n ctx.beginPath()\n ctx.moveTo(r, g.bodyY)\n ctx.lineTo(xL, g.bodyY)\n\n // Arc OVER the dome. Use ellipse parameter (not raw angle-from-center)\n // so non-circular domes start/end exactly on the rect top edge.\n const startAngle = Math.atan2((g.bodyY - g.cy) / g.ry, (xL - g.cx) / g.rx)\n let endAngle = Math.atan2((g.bodyY - g.cy) / g.ry, (xR - g.cx) / g.rx)\n // Canvas `anticlockwise=false` traces in the direction of increasing\n // angle (visually clockwise through the top of the dome). Wrap so the\n // arc takes the upper route, not the bottom.\n if (endAngle <= startAngle) endAngle += 2 * Math.PI\n ctx.ellipse(g.cx, g.cy, g.rx, g.ry, 0, startAngle, endAngle, false)\n\n ctx.lineTo(w - r, g.bodyY)\n ctx.quadraticCurveTo(w, g.bodyY, w, g.bodyY + r)\n ctx.lineTo(w, h - r)\n ctx.quadraticCurveTo(w, h, w - r, h)\n ctx.lineTo(r, h)\n ctx.quadraticCurveTo(0, h, 0, h - r)\n ctx.lineTo(0, g.bodyY + r)\n ctx.quadraticCurveTo(0, g.bodyY, r, g.bodyY)\n ctx.closePath()\n}\n\n/**\n * Tag shape — pointed notch on the left flowing into a rounded body.\n * `notch` is the horizontal distance from the tip to the body edge.\n * Ported from dim0/components/rough/paths.ts.\n */\nexport const buildTagPath = (\n ctx: CanvasRenderingContext2D,\n w: number,\n h: number,\n radius = 8,\n): void => {\n const notch = Math.min(h * 0.5, w * 0.3)\n const tipRadius = 6\n const tipX = 0\n const tipY = h / 2\n\n const bodyLeft = Math.max(0, Math.min(notch, w))\n const right = w\n const bottom = h\n const rBody = Math.min(radius, h / 2, (right - bodyLeft) / 2)\n const rJoin = Math.min(radius, h * 0.45, bodyLeft * 0.8)\n\n ctx.beginPath()\n if (bodyLeft <= 0.001) {\n const r = Math.min(radius, h / 2, w / 2)\n ctx.moveTo(r, 0)\n ctx.lineTo(w - r, 0)\n ctx.quadraticCurveTo(w, 0, w, r)\n ctx.lineTo(w, h - r)\n ctx.quadraticCurveTo(w, h, w - r, h)\n ctx.lineTo(r, h)\n ctx.quadraticCurveTo(0, h, 0, h - r)\n ctx.lineTo(0, r)\n ctx.quadraticCurveTo(0, 0, r, 0)\n ctx.closePath()\n return\n }\n\n const pTop = { x: bodyLeft, y: rJoin }\n const pBot = { x: bodyLeft, y: bottom - rJoin }\n const dirX = tipX - bodyLeft\n const dirYTop = tipY - rJoin\n const dirYBot = tipY - (bottom - rJoin)\n const lenTop = Math.hypot(dirX, dirYTop) || 1\n const lenBot = Math.hypot(dirX, dirYBot) || 1\n const maxTipRound = Math.min(lenTop, lenBot) * 0.49\n const t = Math.max(0, Math.min(tipRadius, maxTipRound))\n const tipEnter = { x: tipX - (dirX / lenBot) * t, y: tipY - (dirYBot / lenBot) * t }\n const tipExit = { x: tipX - (dirX / lenTop) * t, y: tipY - (dirYTop / lenTop) * t }\n const k = rJoin * 0.65\n const topStart = { x: bodyLeft + rBody, y: 0 }\n const botEnd = { x: bodyLeft + rBody, y: bottom }\n\n ctx.moveTo(topStart.x, topStart.y)\n ctx.lineTo(right - rBody, 0)\n ctx.quadraticCurveTo(right, 0, right, rBody)\n ctx.lineTo(right, bottom - rBody)\n ctx.quadraticCurveTo(right, bottom, right - rBody, bottom)\n ctx.lineTo(botEnd.x, botEnd.y)\n ctx.bezierCurveTo(\n botEnd.x - k,\n bottom,\n pBot.x - (dirX / lenBot) * k,\n pBot.y - (dirYBot / lenBot) * k,\n pBot.x,\n pBot.y,\n )\n ctx.lineTo(t > 0 ? tipEnter.x : tipX, t > 0 ? tipEnter.y : tipY)\n if (t > 0) ctx.quadraticCurveTo(tipX, tipY, tipExit.x, tipExit.y)\n ctx.lineTo(pTop.x, pTop.y)\n ctx.bezierCurveTo(\n pTop.x - (dirX / lenTop) * k,\n pTop.y - (dirYTop / lenTop) * k,\n topStart.x - k,\n 0,\n topStart.x,\n 0,\n )\n ctx.closePath()\n}\n","/**\n * Generic primitive paint pass.\n *\n * The renderer applies camera + node transforms (translate to node center,\n * rotate, translate back to top-left) before calling this. The drawer\n * just builds a local-space path and fills/strokes it with resolved style.\n *\n * `scale` is the current camera × DPR factor (world-units → device-pixels).\n * Callers compute it once per frame and pass it in so each drawShape call\n * doesn't allocate a DOMMatrix via ctx.getTransform().\n */\nimport type { Node, Style } from '../../types'\nimport { darkenHex } from '../color'\nimport {\n DEFAULT_STYLE,\n type ThemeResolver,\n dashPatternFor,\n isFullyTransparent,\n resolveColor,\n resolveOpacity,\n resolveStrokeWidth,\n} from './defaults'\nimport {\n buildDiamondPath,\n buildEllipsePath,\n buildRectPath,\n buildTagPath,\n buildThoughtCloudPath,\n} from './path-helpers'\n\n/**\n * Atomic single-path primitives. Composites paint multiple of these.\n * Thought-cloud is atomic — its union geometry is one continuous path\n * so the rough wobble unifies the silhouette.\n */\nexport type AtomicPrimitive = 'rect' | 'ellipse' | 'diamond' | 'tag' | 'thought-cloud'\n\n/**\n * Composite primitives built from multiple atomic sub-shapes. Capsule\n * is intentionally composite — the visible seam between the accent\n * circle and the rect body reads as two stacked hand-drawn shapes\n * (medicine-pill aesthetic), which we want to keep.\n */\ntype CompositePrimitive =\n | 'capsule'\n | 'layered-rect'\n | 'layered-ellipse'\n | 'layered-diamond'\n | 'soft-diamond'\n\nexport type PrimitiveType = AtomicPrimitive | CompositePrimitive\n\nconst ATOMIC: ReadonlySet<string> = new Set(['rect', 'ellipse', 'diamond', 'tag', 'thought-cloud'])\nconst COMPOSITE: ReadonlySet<string> = new Set([\n 'capsule',\n 'layered-rect',\n 'layered-ellipse',\n 'layered-diamond',\n 'soft-diamond',\n])\n\n/** Whether `type` is a composite primitive (paints multiple atomic sub-shapes). */\nexport const isCompositePrimitive = (type: string): boolean => COMPOSITE.has(type)\n\n/** Returns true if `node.type` is one of the built-ins drawShape can render. */\nexport const isDrawablePrimitive = (type: string): type is PrimitiveType =>\n ATOMIC.has(type) || COMPOSITE.has(type)\n\n/**\n * Below this threshold the rounded-rect path is visually indistinguishable\n * from a plain rect — at sub-pixel corner radius the difference disappears.\n */\nconst PLAIN_RECT_CORNER_THRESHOLD_PX = 1.5\n\n/** Offset for layered composites — back layer shifted down-right by this amount. */\nconst LAYERED_OFFSET = 12\n\nexport const drawShape = (\n ctx: CanvasRenderingContext2D,\n node: Node,\n scale: number,\n theme?: ThemeResolver,\n opts?: { skipStroke?: boolean },\n): void => {\n if (!isDrawablePrimitive(node.type)) return\n if (node.hidden) return\n if (node.w <= 0 || node.h <= 0) return\n\n if (COMPOSITE.has(node.type)) {\n drawComposite(ctx, node, scale, theme, opts)\n return\n }\n drawAtomic(ctx, node.type as AtomicPrimitive, node.w, node.h, node.style, scale, theme, opts)\n}\n\n/**\n * Paints a single atomic primitive at (0, 0, w, h) using the provided\n * `style`. Composites call this for each sub-shape with a translated ctx.\n */\nexport const drawAtomic = (\n ctx: CanvasRenderingContext2D,\n type: AtomicPrimitive,\n w: number,\n h: number,\n style: Style | undefined,\n scale: number,\n theme: ThemeResolver | undefined,\n opts?: { skipStroke?: boolean },\n): void => {\n if (w <= 0 || h <= 0) return\n const strokeWidth = resolveStrokeWidth(style, theme)\n const opacity = resolveOpacity(style, theme)\n const fill = resolveColor(style, 'backgroundColor', DEFAULT_STYLE.backgroundColor, theme)\n const stroke = resolveColor(style, 'strokeColor', DEFAULT_STYLE.strokeColor, theme)\n const fillVisible = !isFullyTransparent(fill)\n const strokeVisible = strokeWidth > 0 && !isFullyTransparent(stroke)\n if (!fillVisible && !strokeVisible) return\n\n const cornerRadius = (style?.roundness ?? DEFAULT_STYLE.roundness) * 4\n\n switch (type) {\n case 'rect': {\n if (cornerRadius * scale < PLAIN_RECT_CORNER_THRESHOLD_PX) {\n ctx.beginPath()\n ctx.rect(0, 0, w, h)\n } else {\n buildRectPath(ctx, w, h, cornerRadius)\n }\n break\n }\n case 'ellipse':\n buildEllipsePath(ctx, w, h)\n break\n case 'diamond':\n buildDiamondPath(ctx, w, h, cornerRadius)\n break\n case 'tag':\n buildTagPath(ctx, w, h, cornerRadius)\n break\n case 'thought-cloud':\n buildThoughtCloudPath(ctx, w, h, cornerRadius)\n break\n }\n\n const needsScope = opacity !== 1\n if (needsScope) {\n ctx.save()\n ctx.globalAlpha = opacity\n }\n if (fillVisible) {\n ctx.fillStyle = fill\n ctx.fill()\n }\n if (strokeVisible && !opts?.skipStroke) {\n ctx.strokeStyle = stroke\n // Clamp lineWidth so the on-screen stroke is at least 1 device\n // pixel. At low zoom this keeps the shape silhouette visible\n // (the alternative — skipping the stroke — made big nodes look\n // like featureless colored blobs at fit-all). The scene cache\n // makes this affordable: pan reuses the rendered border, only\n // zoom/edit pays the per-frame cost.\n ctx.lineWidth = Math.max(strokeWidth, 1 / scale)\n // Dash pattern stays keyed to the natural strokeWidth — at low\n // zoom sub-pixel dashes collapse visually into a near-solid line,\n // matching what the user would perceive anyway.\n ctx.setLineDash(dashPatternFor(style?.strokeStyle, strokeWidth))\n ctx.stroke()\n }\n if (needsScope) ctx.restore()\n}\n\n/**\n * Layout each composite type as a list of `{ x, y, w, h, atomic }` sub-shapes\n * in the node's local frame. Paint order is back-to-front.\n *\n * For `layered-*`, the back layer's style is darkened to set it apart from\n * the front; the front uses the node's resolved style as-is.\n */\nconst drawComposite = (\n ctx: CanvasRenderingContext2D,\n node: Node,\n scale: number,\n theme: ThemeResolver | undefined,\n opts?: { skipStroke?: boolean },\n): void => {\n const subs = compositeLayout(node)\n for (const s of subs) {\n ctx.save()\n ctx.translate(s.x, s.y)\n drawAtomic(ctx, s.atomic, s.w, s.h, s.style ?? node.style, scale, theme, opts)\n ctx.restore()\n }\n}\n\ntype SubShape = {\n atomic: AtomicPrimitive\n x: number\n y: number\n w: number\n h: number\n style?: Style\n}\n\n/** Builds the back-to-front sub-shape list for a composite node. Exported for rough. */\nexport const compositeLayout = (node: Node): SubShape[] => {\n const { w, h } = node\n switch (node.type) {\n case 'capsule': {\n // Medicine-pill: small accent circle on the left + rect body.\n // Kept composite (vs. a single union path) so the visible seam\n // between circle and rect reads as two stacked hand-drawn shapes.\n const circ = Math.min(h * 0.55, w * 0.28, 56)\n const overlap = circ * 0.15\n const rectX = circ - overlap\n const rectW = Math.max(0, w - rectX)\n const circY = (h - circ) / 2\n return [\n { atomic: 'ellipse', x: 0, y: circY, w: circ, h: circ },\n { atomic: 'rect', x: rectX, y: 0, w: rectW, h },\n ]\n }\n case 'layered-rect':\n case 'layered-ellipse':\n case 'layered-diamond': {\n const atomic: AtomicPrimitive =\n node.type === 'layered-rect'\n ? 'rect'\n : node.type === 'layered-ellipse'\n ? 'ellipse'\n : 'diamond'\n // Match dim0: front fills the bbox exactly, back is a same-sized\n // copy translated past the bbox by `LAYERED_OFFSET`. The back\n // reads as a \"shadow\" peeking out bottom-right rather than as\n // a distinct second shape. Clamped on small nodes so the offset\n // stays visually proportional.\n const off = Math.min(LAYERED_OFFSET, w * 0.15, h * 0.15)\n const back: SubShape = {\n atomic,\n x: off,\n y: off,\n w,\n h,\n style: darkenedStyle(node.style),\n }\n const front: SubShape = { atomic, x: 0, y: 0, w, h }\n return [back, front]\n }\n case 'soft-diamond': {\n // Concentric scale-layered diamond — matches dim0's SoftDiamond.\n // Back is 108% of the bbox centered (slight overshoot reads as a\n // tinted outer outline); front is 96% centered (slight inset).\n // No offset like `layered-diamond` — both centered on the same\n // point. Reads as a soft-outlined / double-stroked diamond.\n const backScale = 1.08\n const frontScale = 0.96\n const bw = w * backScale\n const bh = h * backScale\n const fw = w * frontScale\n const fh = h * frontScale\n const back: SubShape = {\n atomic: 'diamond',\n x: (w - bw) / 2,\n y: (h - bh) / 2,\n w: bw,\n h: bh,\n style: darkenedStyle(node.style),\n }\n const front: SubShape = {\n atomic: 'diamond',\n x: (w - fw) / 2,\n y: (h - fh) / 2,\n w: fw,\n h: fh,\n }\n return [back, front]\n }\n }\n return []\n}\n\n/**\n * Returns a clone of `style` with both fill and stroke shifted 20%\n * toward black — the \"back layer\" tone used by layered composites.\n *\n * Memoized via WeakMap on the parent style reference. The store\n * replaces (not mutates) `node.style` on updates, so refs are stable\n * across paints for nodes whose style hasn't changed — meaning a 1k\n * layered scene that's idle hits the cache 100% of the time instead\n * of allocating a fresh Style object per node per frame.\n */\nconst DARKENED_NO_STYLE: Style = {}\nconst darkenedStyleCache = new WeakMap<Style, Style>()\nconst darkenedStyle = (style: Style | undefined): Style => {\n if (!style) return DARKENED_NO_STYLE\n const hit = darkenedStyleCache.get(style)\n if (hit) return hit\n const fill = style.backgroundColor\n const stroke = style.strokeColor\n const next: Style = {\n ...style,\n ...(fill ? { backgroundColor: darkenHex(fill) } : {}),\n ...(stroke ? { strokeColor: darkenHex(stroke) } : {}),\n }\n darkenedStyleCache.set(style, next)\n return next\n}\n","/**\n * Lazy-loader for `roughjs` — avoids inlining its ~30KB gzip into core\n * for users who never set `roughness > 0`.\n *\n * First caller triggers `import('roughjs/bin/canvas')`. Until the\n * promise resolves, `getRoughCanvas` returns `null` and the renderer\n * falls back to plain strokes. Once loaded, subsequent calls return\n * the cached factory synchronously.\n */\ntype RoughCanvasCtor = new (canvas: HTMLCanvasElement) => RoughCanvasLike\n\nexport type RoughCanvasLike = {\n generator: {\n path(d: string, options?: object): RoughDrawableLike\n linearPath(points: [number, number][], options?: object): RoughDrawableLike\n ellipse(x: number, y: number, w: number, h: number, options?: object): RoughDrawableLike\n }\n draw(drawable: RoughDrawableLike): void\n}\n\nexport type RoughDrawableLike = unknown\n\nlet cachedCtor: RoughCanvasCtor | null = null\nlet loadPromise: Promise<RoughCanvasCtor | null> | null = null\nconst readyCallbacks = new Set<() => void>()\n\n/**\n * Returns the `RoughCanvas` constructor if ready. Triggers the lazy\n * import on first call. Returns `null` until the module resolves;\n * callers should fall back to plain stroke that frame and call\n * `onRoughReady(cb)` to repaint when rough.js becomes available.\n */\nexport const getRoughCanvasCtor = (): RoughCanvasCtor | null => {\n if (cachedCtor) return cachedCtor\n if (!loadPromise) {\n loadPromise = import('roughjs/bin/canvas')\n .then(mod => {\n cachedCtor = mod.RoughCanvas as unknown as RoughCanvasCtor\n for (const cb of readyCallbacks) cb()\n readyCallbacks.clear()\n return cachedCtor\n })\n .catch(err => {\n console.warn('[rough] failed to load roughjs:', err)\n return null\n })\n }\n return null\n}\n\n/**\n * Registers a callback that fires once when rough.js becomes\n * available. No-op when rough is already loaded — caller should check\n * `getRoughCanvasCtor() !== null` first. Used by the renderer to\n * trigger a repaint after the first opt-in to `roughness > 0`.\n */\nexport const onRoughReady = (cb: () => void): void => {\n if (cachedCtor) return\n readyCallbacks.add(cb)\n}\n\n/** Reset state — tests only. */\nexport const __resetRoughLoader = (): void => {\n cachedCtor = null\n loadPromise = null\n readyCallbacks.clear()\n}\n","/**\n * SVG-path builders for our shape primitives. Designed to feed\n * `rough.generator.path(d, ...)`.\n *\n * Rounded rect / diamond follow the excalidraw style — quadratic\n * curves at the corners that, combined with rough.js jitter, look\n * organically imperfect.\n */\n\nexport const rectPath = (x: number, y: number, w: number, h: number): string => {\n return `M${x} ${y} L${x + w} ${y} L${x + w} ${y + h} L${x} ${y + h} Z`\n}\n\n/**\n * Excalidraw-style rounded rect — corners use quadratic curves rather\n * than perfect arcs. Slight asymmetry under rough.js jitter looks\n * hand-drawn instead of CAD-clean.\n */\nexport const excalidrawRoundedRectPath = (\n x: number,\n y: number,\n w: number,\n h: number,\n radius: number,\n): string => {\n const r = Math.max(0, Math.min(radius, w / 2, h / 2))\n if (r === 0) return rectPath(x, y, w, h)\n const x2 = x + w\n const y2 = y + h\n return [\n `M${x + r} ${y}`,\n `L${x2 - r} ${y}`,\n `Q${x2} ${y}, ${x2} ${y + r}`,\n `L${x2} ${y2 - r}`,\n `Q${x2} ${y2}, ${x2 - r} ${y2}`,\n `L${x + r} ${y2}`,\n `Q${x} ${y2}, ${x} ${y2 - r}`,\n `L${x} ${y + r}`,\n `Q${x} ${y}, ${x + r} ${y}`,\n 'Z',\n ].join(' ')\n}\n\n/**\n * Diamond inscribed in `(x, y, w, h)`. At `radius = 0` the corners are\n * sharp; positive radius produces the soft-diamond excalidraw look —\n * each edge trimmed by r·√2, corners replaced with quadratic curves.\n */\nexport const diamondPath = (x: number, y: number, w: number, h: number, radius = 0): string => {\n const cx = x + w / 2\n const cy = y + h / 2\n if (radius <= 0) {\n return `M${cx} ${y} L${x + w} ${cy} L${cx} ${y + h} L${x} ${cy} Z`\n }\n const T = { x: cx, y }\n const R = { x: x + w, y: cy }\n const B = { x: cx, y: y + h }\n const L = { x, y: cy }\n const edgeLen = Math.hypot(R.x - T.x, R.y - T.y)\n const sMax = Math.max(0, edgeLen / 2 - 0.01)\n const s = Math.min(radius * Math.SQRT2, sMax)\n if (s <= 0.0001) {\n return `M${T.x} ${T.y} L${R.x} ${R.y} L${B.x} ${B.y} L${L.x} ${L.y} Z`\n }\n const along = (a: { x: number; y: number }, b: { x: number; y: number }, d: number) => {\n const dx = b.x - a.x\n const dy = b.y - a.y\n const len = Math.hypot(dx, dy) || 1\n const t = d / len\n return { x: a.x + dx * t, y: a.y + dy * t }\n }\n const TR = along(T, R, s)\n const RT = along(R, T, s)\n const RB = along(R, B, s)\n const BR = along(B, R, s)\n const BL = along(B, L, s)\n const LB = along(L, B, s)\n const LT = along(L, T, s)\n const TL = along(T, L, s)\n return [\n `M${TR.x} ${TR.y}`,\n `L${RT.x} ${RT.y}`,\n `Q${R.x} ${R.y}, ${RB.x} ${RB.y}`,\n `L${BR.x} ${BR.y}`,\n `Q${B.x} ${B.y}, ${BL.x} ${BL.y}`,\n `L${LB.x} ${LB.y}`,\n `Q${L.x} ${L.y}, ${LT.x} ${LT.y}`,\n `L${TL.x} ${TL.y}`,\n `Q${T.x} ${T.y}, ${TR.x} ${TR.y}`,\n 'Z',\n ].join(' ')\n}\n\n/**\n * Ellipse as an SVG path. rough.js has its own `ellipse` primitive\n * but using a single path keeps the rough cache key compact.\n */\nexport const ellipsePath = (x: number, y: number, w: number, h: number): string => {\n const cx = x + w / 2\n const rx = w / 2\n const ry = h / 2\n return [\n `M${cx} ${y}`,\n `A${rx} ${ry} 0 1 0 ${cx} ${y + h}`,\n `A${rx} ${ry} 0 1 0 ${cx} ${y}`,\n 'Z',\n ].join(' ')\n}\n\n/**\n * Thought-cloud — rect body with a dome that merges seamlessly into\n * the top edge. Single continuous outline, no internal seam between\n * dome and rect.\n */\nexport const thoughtCloudPath = (\n x: number,\n y: number,\n w: number,\n h: number,\n radius: number,\n): string => {\n const domeW = Math.min(w * 0.4, h * 1.2)\n const domeH = Math.min(h * 0.45, domeW)\n const domeAnchorX = w * 0.3\n const domeX = Math.max(0, Math.min(w - domeW, domeAnchorX - domeW / 2))\n const cx = x + domeX + domeW / 2\n const cy = y + domeH / 2\n const rx = domeW / 2\n const ry = domeH / 2\n const bodyY = y + domeH * 0.55\n const bodyH = y + h - bodyY\n const r = Math.max(0, Math.min(radius, bodyH / 2, w / 2))\n\n const t = ry > 0 ? (bodyY - cy) / ry : 0\n let xL = x + domeX\n let xR = x + domeX + domeW\n if (Math.abs(t) < 1) {\n const xOffset = rx * Math.sqrt(1 - t * t)\n xL = cx - xOffset\n xR = cx + xOffset\n }\n xL = Math.max(x + r, xL)\n xR = Math.min(x + w - r, xR)\n\n // Large-arc=1 (longer arc, through top), sweep=1 (clockwise / positive\n // angle direction in SVG, i.e. up over the dome).\n return [\n `M${x + r} ${bodyY}`,\n `L${xL} ${bodyY}`,\n `A${rx} ${ry} 0 1 1 ${xR} ${bodyY}`,\n `L${x + w - r} ${bodyY}`,\n `Q${x + w} ${bodyY}, ${x + w} ${bodyY + r}`,\n `L${x + w} ${y + h - r}`,\n `Q${x + w} ${y + h}, ${x + w - r} ${y + h}`,\n `L${x + r} ${y + h}`,\n `Q${x} ${y + h}, ${x} ${y + h - r}`,\n `L${x} ${bodyY + r}`,\n `Q${x} ${bodyY}, ${x + r} ${bodyY}`,\n 'Z',\n ].join(' ')\n}\n\n/**\n * Tag — pointed notch on the left flowing into a rounded body.\n * Ported from dim0. `radius` controls both the body corner radius and\n * the join smoothness.\n */\nexport const tagPath = (x: number, y: number, w: number, h: number, radius = 8): string => {\n const notch = Math.min(h * 0.5, w * 0.3)\n const tipRadius = 6\n const tipX = x\n const tipY = y + h / 2\n const bodyLeft = x + Math.max(0, Math.min(notch, w))\n const right = x + w\n const bottom = y + h\n const rBody = Math.min(radius, h / 2, (right - bodyLeft) / 2)\n const rJoin = Math.min(radius, h * 0.45, (bodyLeft - x) * 0.8)\n\n if (bodyLeft - x <= 0.001) {\n return excalidrawRoundedRectPath(x, y, w, h, Math.min(radius, h / 2, w / 2))\n }\n\n const pTop = { x: bodyLeft, y: y + rJoin }\n const pBot = { x: bodyLeft, y: bottom - rJoin }\n const dirX = tipX - bodyLeft\n const dirYTop = tipY - pTop.y\n const dirYBot = tipY - pBot.y\n const lenTop = Math.hypot(dirX, dirYTop) || 1\n const lenBot = Math.hypot(dirX, dirYBot) || 1\n const maxTipRound = Math.min(lenTop, lenBot) * 0.49\n const t = Math.max(0, Math.min(tipRadius, maxTipRound))\n const tipEnter = { x: tipX - (dirX / lenBot) * t, y: tipY - (dirYBot / lenBot) * t }\n const tipExit = { x: tipX - (dirX / lenTop) * t, y: tipY - (dirYTop / lenTop) * t }\n const k = rJoin * 0.65\n const topStart = { x: bodyLeft + rBody, y }\n const botEnd = { x: bodyLeft + rBody, y: bottom }\n\n const parts: string[] = [\n `M${topStart.x} ${topStart.y}`,\n `L${right - rBody} ${y}`,\n `Q${right} ${y}, ${right} ${y + rBody}`,\n `L${right} ${bottom - rBody}`,\n `Q${right} ${bottom}, ${right - rBody} ${bottom}`,\n `L${botEnd.x} ${botEnd.y}`,\n `C${botEnd.x - k} ${bottom}, ${pBot.x - (dirX / lenBot) * k} ${pBot.y - (dirYBot / lenBot) * k}, ${pBot.x} ${pBot.y}`,\n `L${t > 0 ? tipEnter.x : tipX} ${t > 0 ? tipEnter.y : tipY}`,\n ]\n if (t > 0) parts.push(`Q${tipX} ${tipY}, ${tipExit.x} ${tipExit.y}`)\n parts.push(\n `L${pTop.x} ${pTop.y}`,\n `C${pTop.x - (dirX / lenTop) * k} ${pTop.y - (dirYTop / lenTop) * k}, ${topStart.x - k} ${y}, ${topStart.x} ${topStart.y}`,\n 'Z',\n )\n return parts.join(' ')\n}\n","/**\n * Derive a visible border color for rough shapes whose `strokeColor` is\n * transparent — without this, the rough.js pass paints nothing and the\n * misregistration effect (offset fill vs. stroke) has nothing to show.\n *\n * Mirrors dim0's `resolveEdgeRender` + tonal-shift mix:\n * light mode: `mixHex(fill, '#fff', 0.2)` → lighter than fill\n * dark mode: `mixHex(fill, '#000', 0.2)` → darker than fill\n *\n * Result is memoized per `(fill, isDark)` pair so the rough drawable\n * cache key stays stable across renders.\n */\nimport { mixHex } from '../color'\nimport { isFullyTransparent } from '../shapes/defaults'\n\nconst TONE_BLEND = 0.2\nconst cache = new Map<string, string>()\n\n/**\n * If `stroke` is transparent and `fill` is a visible color, returns a\n * tonally-shifted variant of `fill` suitable for drawing a soft border.\n * Otherwise returns `stroke` unchanged. Memoized.\n */\nexport const deriveRoughStrokeColor = (stroke: string, fill: string, isDark: boolean): string => {\n if (!isFullyTransparent(stroke)) return stroke\n if (isFullyTransparent(fill)) return stroke\n const key = `${fill}|${isDark ? 'd' : 'l'}`\n const hit = cache.get(key)\n if (hit) return hit\n const next = mixHex(fill, isDark ? '#000000' : '#ffffff', TONE_BLEND)\n cache.set(key, next)\n return next\n}\n\n/** Reset state — tests only. */\nexport const __resetToneDownCache = (): void => {\n cache.clear()\n}\n","/**\n * Per-shape rough stroke pass.\n *\n * Caller (renderer) decides whether to call this (via the gate). Fill\n * has already been painted by the regular `drawShape` pipeline — we\n * paint only the wobbly outline on top.\n *\n * Returns false when the rough.js module hasn't loaded yet; caller\n * should fall back to plain stroke.\n *\n * For composite nodes (capsule, thought-cloud, layered-*), the rough\n * pass walks `compositeLayout` and paints each sub-shape's outline as\n * its own rough drawable. Each sub-shape gets its own cache entry so\n * scrubbing one node attribute only invalidates the affected subset.\n */\nimport type { Edge, Node, Style, Vec2 } from '../../types'\nimport {\n DEFAULT_STYLE,\n type ThemeResolver,\n dashPatternFor,\n isFullyTransparent,\n resolveColor,\n resolveStrokeWidth,\n} from '../shapes/defaults'\nimport { compositeLayout, drawAtomic } from '../shapes/draw-shape'\nimport { getOrBuildDrawable, seedFromId } from './cache'\nimport { ROUGH_DEFAULTS, ROUGH_FILL_MISREGISTER_X, ROUGH_FILL_MISREGISTER_Y } from './constants'\nimport { type RoughCanvasLike, getRoughCanvasCtor } from './loader'\nimport {\n diamondPath,\n ellipsePath,\n excalidrawRoundedRectPath,\n rectPath,\n tagPath,\n thoughtCloudPath,\n} from './paths'\nimport { deriveRoughStrokeColor } from './tone-down'\n\ntype AtomicRoughPrimitive = 'rect' | 'ellipse' | 'diamond' | 'tag' | 'thought-cloud'\n\nconst apparentDetail = (\n maxSide: number,\n zoom: number,\n): { curveStepCount: number; maxRandomnessOffset: number } => {\n const apparent = maxSide * Math.min(1, zoom)\n if (apparent >= 800) return { curveStepCount: 3, maxRandomnessOffset: 0.9 }\n if (apparent >= 400) return { curveStepCount: 4, maxRandomnessOffset: 1.1 }\n return { curveStepCount: 5, maxRandomnessOffset: 1.3 }\n}\n\n/**\n * Paints the rough stroke for an ATOMIC primitive at the node's local\n * origin. Caller (renderer) decides whether to call this. Returns\n * false if rough.js isn't loaded yet. Composites use\n * `drawCompositeRough` instead — they need interleaved fill+stroke\n * painting per sub-shape, not the two-pass model used for atomics.\n */\nexport const drawRoughShape = (\n ctx: CanvasRenderingContext2D,\n node: Node,\n scale: number,\n theme?: ThemeResolver,\n): boolean => {\n const Ctor = getRoughCanvasCtor()\n if (!Ctor) return false\n const rc = ensureRoughCanvas(ctx, Ctor)\n if (!rc) return false\n\n const seed = node.id ? (seedFromId(node.id) % 2147483646) + 1 : 1337\n paintAtomicRough(\n rc,\n ctx,\n node.type as AtomicRoughPrimitive,\n node.w,\n node.h,\n node.style,\n scale,\n theme,\n seed,\n )\n return true\n}\n\n/**\n * Composite-aware rough paint. Walks the composite layout and for\n * each sub-shape paints fill (misregistered) + rough stroke before\n * moving to the next sub. This interleaving is critical: if all fills\n * paint first and all strokes after, the back layer's stroke ends up\n * sitting on top of the front layer's fill in the overlap region.\n *\n * Returns false if rough.js isn't loaded yet (caller should fall back\n * to the plain `drawShape` path).\n */\nexport const drawCompositeRough = (\n ctx: CanvasRenderingContext2D,\n node: Node,\n scale: number,\n theme?: ThemeResolver,\n): boolean => {\n const Ctor = getRoughCanvasCtor()\n if (!Ctor) return false\n const rc = ensureRoughCanvas(ctx, Ctor)\n if (!rc) return false\n\n const subs = compositeLayout(node)\n const baseSeed = node.id ? (seedFromId(node.id) % 2147483646) + 1 : 1337\n for (let i = 0; i < subs.length; i++) {\n const s = subs[i]!\n const subStyle = s.style ?? node.style\n ctx.save()\n ctx.translate(s.x, s.y)\n // Misregister this sub's fill — same printing-press offset effect\n // as atomic shapes, applied per sub so the back's fill and stroke\n // misalign just like the front's do.\n ctx.translate(ROUGH_FILL_MISREGISTER_X, ROUGH_FILL_MISREGISTER_Y)\n drawAtomic(ctx, s.atomic, s.w, s.h, subStyle, scale, theme, { skipStroke: true })\n ctx.translate(-ROUGH_FILL_MISREGISTER_X, -ROUGH_FILL_MISREGISTER_Y)\n // Rough stroke for this sub. Painted before the next sub's fill so\n // the front layer's fill correctly covers the back's stroke in\n // the overlap region.\n paintAtomicRough(\n rc,\n ctx,\n s.atomic as AtomicRoughPrimitive,\n s.w,\n s.h,\n subStyle,\n scale,\n theme,\n ((baseSeed + i * 7919) % 2147483646) + 1,\n )\n ctx.restore()\n }\n return true\n}\n\n/** Paints a single atomic primitive at (0, 0, w, h) using the given style. */\nconst paintAtomicRough = (\n rc: RoughCanvasLike,\n ctx: CanvasRenderingContext2D,\n type: AtomicRoughPrimitive,\n w: number,\n h: number,\n style: Style | undefined,\n scale: number,\n theme: ThemeResolver | undefined,\n seed: number,\n): void => {\n if (w <= 0 || h <= 0) return\n const rawStroke = resolveColor(style, 'strokeColor', '#1f2937', theme)\n const isDark = theme?.('mode') === 'dark'\n const fill = resolveColor(style, 'backgroundColor', DEFAULT_STYLE.backgroundColor, theme)\n const strokeColor = deriveRoughStrokeColor(rawStroke, fill, isDark)\n const rawStrokeWidth = resolveStrokeWidth(style, theme)\n if (rawStrokeWidth <= 0) return\n\n const roughness = style?.roughness ?? 0\n if (roughness <= 0) return\n\n // When the user picked \"no border\" (transparent stroke), rough still\n // paints a soft fill-derived outline for the misregistration effect\n // — but the user's strokeStyle (dashed/dotted) and strokeWidth were\n // *border* choices they didn't make, so don't apply them to the soft\n // outline. Force the system baseline so every no-border node renders\n // a uniform subtle outline regardless of the panel's current values.\n // Nodes with a real strokeColor keep the user's chosen style + width.\n const isNoBorderIntent = isFullyTransparent(rawStroke)\n const effectiveStrokeStyle = isNoBorderIntent ? 'solid' : (style?.strokeStyle ?? 'solid')\n const strokeWidth = isNoBorderIntent ? DEFAULT_STYLE.strokeWidth : rawStrokeWidth\n\n const cornerRadius = (style?.roundness ?? DEFAULT_STYLE.roundness) * 4\n const radius = Math.max(0, Math.min(cornerRadius, w / 2, h / 2))\n const dash = dashPatternFor(effectiveStrokeStyle, strokeWidth)\n const detail = apparentDetail(Math.max(w, h), scale)\n\n const cacheKey = [\n type,\n w.toFixed(1),\n h.toFixed(1),\n radius.toFixed(1),\n strokeColor,\n strokeWidth.toFixed(2),\n effectiveStrokeStyle,\n roughness.toFixed(2),\n seed,\n detail.curveStepCount,\n detail.maxRandomnessOffset.toFixed(2),\n ].join('|')\n\n const drawable = getOrBuildDrawable(cacheKey, () => {\n const pathData = buildPath(type, 0, 0, w, h, radius)\n return rc.generator.path(pathData, {\n ...ROUGH_DEFAULTS,\n stroke: strokeColor,\n strokeWidth,\n roughness,\n seed,\n // Always pass an explicit array (empty = solid) so rough.js calls\n // ctx.setLineDash() to a known state. Passing `undefined` makes\n // rough skip that call, and the canvas inherits whatever the\n // previous draw left behind — a transparent-stroke node's\n // fill-derived outline would pick up the dash from an earlier\n // dashed node in the same paint pass.\n strokeLineDash: dash,\n curveStepCount: detail.curveStepCount,\n maxRandomnessOffset: detail.maxRandomnessOffset,\n })\n })\n\n ctx.save()\n ctx.lineJoin = 'round'\n rc.draw(drawable)\n ctx.restore()\n}\n\n/**\n * Paints a rough stroke for an edge body. `samples` is the cached\n * polyline. We use rough's `linearPath` because it preserves the\n * shape exactly (excalidraw connectors). Arrowheads + clip stay plain\n * — wobble on arrowheads doesn't add visual value.\n */\nexport const drawRoughEdge = (\n ctx: CanvasRenderingContext2D,\n edge: Edge,\n samples: Vec2[],\n scale: number,\n theme?: ThemeResolver,\n): boolean => {\n const Ctor = getRoughCanvasCtor()\n if (!Ctor) return false\n if (samples.length < 2) return true\n\n const style = edge.style\n const strokeColor = resolveColor(style, 'strokeColor', '#475569', theme)\n const strokeWidth = resolveStrokeWidth(style, theme)\n if (strokeWidth <= 0) return true\n\n const roughness = style?.roughness ?? 0\n if (roughness <= 0) return true\n\n const seed = edge.id ? (seedFromId(edge.id) % 2147483646) + 1 : 1337\n const dash = dashPatternFor(style?.strokeStyle, strokeWidth)\n let minX = samples[0]!.x\n let maxX = samples[0]!.x\n let minY = samples[0]!.y\n let maxY = samples[0]!.y\n for (const p of samples) {\n if (p.x < minX) minX = p.x\n if (p.x > maxX) maxX = p.x\n if (p.y < minY) minY = p.y\n if (p.y > maxY) maxY = p.y\n }\n const detail = apparentDetail(Math.max(maxX - minX, maxY - minY), scale)\n\n const cacheKey = [\n 'edge',\n edge.id,\n samples.length,\n Math.round(minX),\n Math.round(minY),\n Math.round(maxX),\n Math.round(maxY),\n strokeColor,\n strokeWidth.toFixed(2),\n style?.strokeStyle ?? 'solid',\n roughness.toFixed(2),\n seed,\n detail.curveStepCount,\n detail.maxRandomnessOffset.toFixed(2),\n ].join('|')\n\n const rc = ensureRoughCanvas(ctx, Ctor)\n if (!rc) return false\n\n const drawable = getOrBuildDrawable(cacheKey, () => {\n const points: [number, number][] = samples.map(s => [s.x, s.y])\n return rc.generator.linearPath(points, {\n ...ROUGH_DEFAULTS,\n stroke: strokeColor,\n strokeWidth,\n roughness,\n seed,\n // See paintAtomicRough — pass an explicit array (empty = solid)\n // so rough resets the canvas dash; `undefined` lets stale state\n // from a previous draw leak through.\n strokeLineDash: dash,\n curveStepCount: detail.curveStepCount,\n maxRandomnessOffset: detail.maxRandomnessOffset,\n })\n })\n\n ctx.save()\n ctx.lineJoin = 'round'\n rc.draw(drawable)\n ctx.restore()\n return true\n}\n\n/**\n * Reuses one `RoughCanvas` per CanvasRenderingContext2D — building it\n * is cheap (~5µs) but per-frame stacks up. Stored on the context as\n * a hidden property.\n */\nconst ROUGH_CANVAS_KEY = '__roughCanvas'\nconst ensureRoughCanvas = (\n ctx: CanvasRenderingContext2D,\n Ctor: NonNullable<ReturnType<typeof getRoughCanvasCtor>>,\n): RoughCanvasLike | null => {\n const ctxWithCache = ctx as CanvasRenderingContext2D & {\n [ROUGH_CANVAS_KEY]?: RoughCanvasLike\n }\n if (ctxWithCache[ROUGH_CANVAS_KEY]) return ctxWithCache[ROUGH_CANVAS_KEY]\n const rc = new Ctor(ctx.canvas) as RoughCanvasLike\n ctxWithCache[ROUGH_CANVAS_KEY] = rc\n return rc\n}\n\nconst buildPath = (\n type: AtomicRoughPrimitive,\n x: number,\n y: number,\n w: number,\n h: number,\n radius: number,\n): string => {\n switch (type) {\n case 'rect':\n return radius > 0 ? excalidrawRoundedRectPath(x, y, w, h, radius) : rectPath(x, y, w, h)\n case 'ellipse':\n return ellipsePath(x, y, w, h)\n case 'diamond':\n return diamondPath(x, y, w, h, radius)\n case 'tag':\n return tagPath(x, y, w, h, radius)\n case 'thought-cloud':\n return thoughtCloudPath(x, y, w, h, radius)\n }\n}\n","/**\n * Per-shape content bounds — the rect within a node where text content\n * is laid out and painted. Defaults to the full node bbox; shapes with\n * non-rectangular interiors override so text doesn't bleed into the\n * non-content areas (capsule's accent circle, diamond's narrow tips,\n * thought-cloud's dome, tag's notch, etc.).\n *\n * Returned in node-local coords. Renderer's `paintNodeContent` already\n * applies the node transform before drawing — bounds are relative to\n * (0, 0) inside the node.\n */\nimport type { Node } from '../../types'\n\nexport type ContentBounds = { x: number; y: number; w: number; h: number }\n\nconst SQRT2_INV = 1 / Math.SQRT2\n\nexport const contentBounds = (node: Node): ContentBounds => {\n const { w, h } = node\n switch (node.type) {\n case 'capsule': {\n // Skip the accent circle — text fills the rect body to its right.\n // Must mirror compositeLayout's capsule geometry.\n const circ = Math.min(h * 0.55, w * 0.28, 56)\n const overlap = circ * 0.15\n const rectX = circ - overlap\n return { x: rectX, y: 0, w: Math.max(0, w - rectX), h }\n }\n case 'diamond':\n case 'layered-diamond':\n case 'soft-diamond': {\n // Inscribed rectangle of a square rotated 45° = bbox × (1/√2).\n // For `soft-diamond` the inner (front) diamond is 96% of bbox so\n // its inscribed rect is slightly tighter, but the bbox-relative\n // formula reads well enough without a separate case.\n const cw = w * SQRT2_INV\n const ch = h * SQRT2_INV\n return { x: (w - cw) / 2, y: (h - ch) / 2, w: cw, h: ch }\n }\n case 'ellipse':\n case 'layered-ellipse': {\n // True ellipse-inscribed rect is bbox × (1/√2). Using 0.7 gives a\n // tiny safety margin so text doesn't kiss the curve at the edges.\n const f = 0.7\n const cw = w * f\n const ch = h * f\n return { x: (w - cw) / 2, y: (h - ch) / 2, w: cw, h: ch }\n }\n case 'thought-cloud': {\n // Rect body only — skip the dome area at the top. Must mirror\n // the geometry in `path-helpers.ts thoughtCloudGeometry`.\n const domeW = Math.min(w * 0.4, h * 1.2)\n const domeH = Math.min(h * 0.45, domeW)\n const bodyY = domeH * 0.55\n return { x: 0, y: bodyY, w, h: Math.max(0, h - bodyY) }\n }\n case 'tag': {\n // Skip the left notch — text fills the body to the right.\n const notch = Math.min(h * 0.5, w * 0.3)\n return { x: notch, y: 0, w: Math.max(0, w - notch), h }\n }\n default:\n return { x: 0, y: 0, w, h }\n }\n}\n","/**\n * Camera transform application + viewport math.\n *\n * The trick: instead of transforming each shape's coordinates by hand,\n * we set the canvas matrix once per frame and draw every shape in world\n * coordinates. The DPR factor is folded into the matrix so logical-pixel\n * stroke widths come out crisp.\n */\nimport { viewportWorldRect } from '../camera'\nimport type { CameraState, Node, WorldRect } from '../types'\nimport type { CanvasSurface } from './canvas-setup'\n\n/**\n * Sets the 2d transform so subsequent draw calls take world coords.\n *\n * screen.x = (world.x - camera.x) * camera.z * dpr\n * screen.y = (world.y - camera.y) * camera.z * dpr\n */\nexport const applyCameraTransform = (surface: CanvasSurface, camera: CameraState): void => {\n const sx = camera.z * surface.dpr\n const sy = camera.z * surface.dpr\n const tx = -camera.x * sx\n const ty = -camera.y * sy\n surface.ctx.setTransform(sx, 0, 0, sy, tx, ty)\n}\n\n/**\n * The world rect currently visible inside the surface.\n */\nexport const worldViewport = (surface: CanvasSurface, camera: CameraState): WorldRect =>\n viewportWorldRect(camera, surface.cssWidth, surface.cssHeight)\n\n/**\n * Wraps a draw callback in the local-frame transform for one node:\n * translates to the node's center, rotates by node.angle, then translates\n * back to the node's top-left so the drawer can build paths in (0..w, 0..h).\n *\n * Fast path: when `node.angle === 0` (the common case) we skip the\n * canvas2d save/restore pair entirely and manually un-translate after\n * the callback. `save()`/`restore()` allocate + swap a full graphics\n * state record; at 10k+ nodes/frame that's ~1ms of the paint budget.\n * The callback is responsible for not leaking transform state — all\n * built-in drawers (drawShape, drawCompositeRough, paintFrameNode,\n * paintImageNode, paintIconNode) honor this contract by either\n * leaving the transform untouched or restoring their own inner pushes.\n */\nexport const drawWithNodeTransform = (\n ctx: CanvasRenderingContext2D,\n node: Node,\n fn: () => void,\n): void => {\n if (node.angle === 0) {\n ctx.translate(node.x, node.y)\n fn()\n ctx.translate(-node.x, -node.y)\n return\n }\n // Rotated path keeps the save/restore — un-doing translate + rotate\n // + translate manually is error-prone and rotated nodes are rare.\n ctx.save()\n const cx = node.x + node.w / 2\n const cy = node.y + node.h / 2\n ctx.translate(cx, cy)\n ctx.rotate(node.angle)\n ctx.translate(-node.w / 2, -node.h / 2)\n fn()\n ctx.restore()\n}\n","import { computeEdgeGeometry, drawEdge } from '../edges'\n/**\n * Renderer — see ARCHITECTURE.md §4.\n *\n * Owns two canvases (static + interactive) and one DOM overlay div; reads\n * from a CanvasStore; redraws in response to store changes, camera changes,\n * interaction-state changes, and viewport resizes.\n *\n * static — every committed primitive at its committed position. Redraws\n * only when committed scene state, camera, or selection changes.\n * interactive — selection outlines, resize handles, marquee rect, and any\n * shape currently being dragged at its uncommitted position.\n * Redrawn every rAF tick while interaction.mode !== 'idle'.\n */\nimport { getPointAndTangentAtArcLength } from '../edges/arc-length'\nimport type { NodeTypeDef, RenderEnv } from '../node-types'\nimport { inflateRect, nodeAABB } from '../spatial'\nimport type { CanvasStore, InteractionState } from '../store'\nimport {\n DEFAULT_HIGHLIGHT_COLOR,\n DEFAULT_TEXT_COLOR,\n FONT_SIZE_MAP,\n getOrRenderTextBitmap,\n subscribeFontEpoch,\n subscribeMathEpoch,\n} from '../text'\nimport type { CameraState, CanvasBackground, Edge, EdgeId, Node, NodeId, WorldRect } from '../types'\nimport { type AssetCache, createAssetCache, paintIconNode, paintImageNode } from './assets'\nimport { paintBackground } from './background'\nimport { type CanvasSurface, clearSurface, setupSurface, sizeSurface } from './canvas-setup'\nimport { type FrameLoop, type FrameStats, createFrameLoop } from './frame-loop'\nimport {\n DEFAULT_SELECTION_COLOR,\n drawEdgeEndpointHandles,\n drawEdgeMidpointHandle,\n drawMarquee,\n drawResizeHandles,\n drawRotateHandle,\n drawSelectionOutline,\n} from './overlay'\nimport { paintFrameNode } from './paint-frame'\nimport { ROUGH_MAX_NODES, ROUGH_MIN_ZOOM, drawCompositeRough, drawRoughShape } from './rough'\nimport {\n ROUGH_FILL_MISREGISTER_X,\n ROUGH_FILL_MISREGISTER_Y,\n ROUGH_MAX_MOVING_NODES,\n} from './rough/constants'\nimport { getRoughCanvasCtor, onRoughReady } from './rough/loader'\nimport {\n type ThemeResolver,\n contentBounds,\n drawShape,\n isCompositePrimitive,\n isDrawablePrimitive,\n} from './shapes'\nimport { applyCameraTransform, drawWithNodeTransform, worldViewport } from './transform'\n\n/**\n * The static scene is rendered into an offscreen cache sized to the\n * viewport plus this margin (CSS px) on every side. The on-screen\n * canvas is presented from that cache: a sub-margin pan blits, a pan\n * past the margin shifts + repaints only the exposed strip, and only a\n * content/zoom change re-renders the whole scene. The margin is the\n * pan distance reused before a strip extend is needed. See\n * ARCHITECTURE.md §4.4.\n */\nconst SCENE_CACHE_MARGIN_PX = 256\n\n/**\n * Minimum on-screen size (in logical CSS pixels) for a shape to be worth drawing.\n * Below this both dimensions, the shape can't be perceived anyway; skipping it\n * saves the entire path build + fill/stroke for that node.\n */\nconst MIN_ON_SCREEN_SIZE_PX = 1.5\n\n/**\n * Minimum on-screen font size (in logical CSS pixels) for text to be worth\n * rasterizing. Below ~3px nothing is readable; skipping the bitmap lookup +\n * blit saves several μs/node and matters at extreme zoom-out with thousands\n * of content-bearing nodes visible.\n */\nconst MIN_READABLE_FONT_PX = 3\n\nexport type RendererOptions = {\n store: CanvasStore\n staticCanvas: HTMLCanvasElement\n interactiveCanvas: HTMLCanvasElement\n theme?: ThemeResolver\n /** Initial CSS-pixel size. Use `setSize()` to update on resize. */\n width: number\n height: number\n /**\n * Optional page background + dot/grid pattern. Local-only (not in\n * the synced scene). Update at runtime via `Renderer.setBackground`.\n */\n background?: CanvasBackground\n /**\n * Color for all selection chrome: selection outlines, resize +\n * rotate handles, edge endpoint + midpoint handles, marquee rect,\n * and the drag-create preview. Defaults to `#3b82f6` (the standard\n * canvas-app blue). Update at runtime via `Renderer.setSelectionColor`.\n *\n * Accepts any CSS color literal (hex, rgb(), named). The marquee\n * fill tints via globalAlpha — no parsing needed.\n */\n selectionColor?: string\n /**\n * Cap on the canvas backing-store DPR (device-pixel ratio). At\n * native DPR on hi-DPI displays, the backing buffer can hit\n * 20-30 megapixels per frame; the GPU-upload step alone dominates\n * the frame budget. Defaults to `1` for consistent perf across\n * hardware. Bump to `2` (or `window.devicePixelRatio`) for\n * pixel-crisp rendering at the cost of FPS on hi-DPI displays.\n *\n * Text is unaffected — the text bitmap cache renders glyphs at\n * its own DPR-aware scale.\n */\n maxDpr?: number\n /**\n * Fires when the set of custom nodes that should be rendered in the DOM\n * overlay changes. Consumers use this to mount/unmount React subtrees\n * (or whatever framework). See ARCHITECTURE.md §5.2 lifecycle.\n *\n * The callback receives the FULL current set, not a delta — consumers\n * compute the mount/unmount diff themselves.\n */\n onOverlayChange?: (mountedIds: NodeId[]) => void\n}\n\nexport type Renderer = {\n /** Begin the rAF loop. Idempotent. */\n start(): void\n /** Stop the rAF loop. Idempotent. */\n stop(): void\n /** Force a static repaint on the next rAF tick. */\n invalidate(): void\n /** Resize both canvases to a new CSS-pixel viewport. */\n setSize(cssW: number, cssH: number): void\n /** Update the page background / pattern. Triggers a static repaint. */\n setBackground(bg: CanvasBackground | undefined): void\n /** Update the selection chrome color. Triggers an interactive repaint. */\n setSelectionColor(color: string): void\n /**\n * Toggle frame-node paint. Use during a presentation flow to drop\n * the slide border + label so only the frame contents are visible.\n * Triggers a static repaint.\n */\n setHideFrames(hidden: boolean): void\n /** Per-frame timing (FPS, lastMs, avgMs, frames). */\n stats(): FrameStats\n /** Number of items the most recent paint actually drew. */\n lastDrawCount(): number\n /** Current overlay-mounted custom-node ids. */\n getOverlaySet(): NodeId[]\n /**\n * Renderer-owned asset cache (decoded image bitmaps + rasterized\n * SVG icons). Pass to {@link exportSelection} / {@link exportViewport}\n * so PNG export paints image + icon nodes from the same bitmaps the\n * live canvas uses.\n */\n getAssetCache(): AssetCache\n /** Detach event listeners. The store is left untouched. */\n dispose(): void\n}\n\nexport const createRenderer = (opts: RendererOptions): Renderer => {\n const { store, theme, onOverlayChange } = opts\n const maxDpr = opts.maxDpr\n const staticSurface = setupSurface(opts.staticCanvas, maxDpr)\n const interactiveSurface = setupSurface(opts.interactiveCanvas, maxDpr)\n let background: CanvasBackground | undefined = opts.background\n let selectionColor: string = opts.selectionColor ?? DEFAULT_SELECTION_COLOR\n let hideFrames = false\n sizeSurface(staticSurface, opts.width, opts.height, maxDpr)\n sizeSurface(interactiveSurface, opts.width, opts.height, maxDpr)\n\n let staticDirty = true\n let interactiveDirty = false\n /** Custom nodes whose React view is currently mounted in the overlay. */\n let overlaySet: ReadonlySet<NodeId> = new Set()\n let lastDrawn = 0\n\n // Offscreen scene cache (viewport + margin). Rendered by\n // `renderFullCache`, blitted to the on-screen static surface by\n // `presentStatic`. `cacheCam*` records the camera the cache is valid\n // for — used by the present blit to compute the source offset (and,\n // from Phase 2 on, to decide whether a re-render is needed at all).\n let cacheSurface: CanvasSurface | null = null\n let cacheCamX = 0\n let cacheCamY = 0\n let cacheCamZ = 1\n // True when the cache's *content* is stale (a scene/zoom/size change,\n // anything but a pure pan). Pan leaves it false so `paintStatic` can\n // present by blitting alone. `renderFullCache` clears it.\n let cacheStale = true\n\n /**\n * Lazily allocates / resizes the offscreen cache to `viewport + 2·margin`\n * at the static surface's DPR. The DPR is copied from `staticSurface`\n * (not recomputed from the cache's larger size) so the cache↔screen blit\n * stays a 1:1 device-pixel copy.\n */\n const ensureCacheSurface = (): CanvasSurface => {\n const dpr = staticSurface.dpr\n const cssW = staticSurface.cssWidth + 2 * SCENE_CACHE_MARGIN_PX\n const cssH = staticSurface.cssHeight + 2 * SCENE_CACHE_MARGIN_PX\n if (!cacheSurface) {\n const canvas = document.createElement('canvas')\n const ctx = canvas.getContext('2d')\n if (!ctx) throw new Error('Canvas 2d context unavailable')\n cacheSurface = { canvas, ctx, cssWidth: 0, cssHeight: 0, dpr: 1 }\n }\n if (\n cacheSurface.cssWidth !== cssW ||\n cacheSurface.cssHeight !== cssH ||\n cacheSurface.dpr !== dpr\n ) {\n cacheSurface.cssWidth = cssW\n cacheSurface.cssHeight = cssH\n cacheSurface.dpr = dpr\n cacheSurface.canvas.width = Math.max(1, Math.round(cssW * dpr))\n cacheSurface.canvas.height = Math.max(1, Math.round(cssH * dpr))\n }\n return cacheSurface\n }\n\n // Sorted-by-(z, id) caches of ALL scene nodes / edges. Rebuilt\n // lazily on first access and invalidated on every `'change'` op.\n // Lets `visibleNodes` / `visibleEdges` skip per-frame Array.sort —\n // during pan, the scene doesn't mutate so these stay valid for the\n // whole gesture. At 10k nodes this saves ~1ms / frame.\n let sortedNodeIdsCache: NodeId[] | null = null\n let sortedEdgeIdsCache: EdgeId[] | null = null\n const invalidateSortedCaches = (): void => {\n sortedNodeIdsCache = null\n sortedEdgeIdsCache = null\n }\n\n // Asset cache for image + icon node types. The `onReady` hook fires\n // when a pending decode lands so the next frame blits the bitmap.\n // `loop` is created later in this scope, so we wrap the request in a\n // closure that resolves it at call time.\n const requestRepaint = (): void => {\n staticDirty = true\n cacheStale = true\n loop.requestFrame()\n }\n const assetCache = createAssetCache({ onReady: requestRepaint })\n\n const isInteractive = (state: InteractionState): boolean =>\n state.mode !== 'idle' || store.getSelection().length > 0\n\n const drawFrame = (): void => {\n if (staticDirty) {\n paintStatic()\n staticDirty = false\n }\n if (interactiveDirty) {\n paintInteractive()\n interactiveDirty = false\n }\n }\n\n /**\n * Paints the full static scene (background + frames + nodes + edges)\n * into `surface` in world coordinates. The caller is responsible for\n * having cleared the surface and applied the world→device transform;\n * `viewport` is the world rect to cull against (it may extend beyond\n * the on-screen viewport when painting into the oversized cache).\n */\n const paintSceneBody = (\n surface: CanvasSurface,\n camera: CameraState,\n viewport: WorldRect,\n // Strip renders (Phase 3 cache extension) paint only a sliver of\n // the scene, so they must NOT publish the draw count or the\n // React-overlay mount set — those describe the whole viewport and\n // are owned by full renders. Same contract as the blit-only path,\n // which doesn't run this body at all.\n fullRender = true,\n ): void => {\n const scale = camera.z * surface.dpr\n const interaction = store.getInteractionState()\n // Per ARCHITECTURE.md §4.2: nodes currently being dragged or resized,\n // AND edges incident to them, are excluded from static and drawn on\n // the interactive canvas at their uncommitted positions instead.\n const excludedNodes =\n interaction.mode === 'dragging' || interaction.mode === 'resizing'\n ? new Set(interaction.draggedIds)\n : null\n // An edge being mid-point-dragged is excluded too — the interactive\n // layer paints it with the in-progress control from `midpointDraft`.\n const baseExcludedEdges = excludedNodes ? incidentEdgeIds(excludedNodes) : null\n const midpointEdgeId = interaction.midpointDraft?.edgeId ?? null\n const excludedEdges: ReadonlySet<EdgeId> | null =\n midpointEdgeId !== null\n ? new Set<EdgeId>([...(baseExcludedEdges ?? []), midpointEdgeId])\n : baseExcludedEdges\n\n // ---- background (page color + dot/grid pattern) ----\n paintBackground(surface.ctx, { viewport, zoom: camera.z, background })\n\n // ---- nodes ----\n const visible = visibleNodes(camera, viewport)\n const isMoving =\n interaction.mode === 'panning' ||\n interaction.mode === 'zooming' ||\n interaction.mode === 'dragging' ||\n interaction.mode === 'resizing' ||\n interaction.mode === 'rotating'\n const minOnScreen = MIN_ON_SCREEN_SIZE_PX\n const nextOverlaySet = new Set<NodeId>()\n let drawn = 0\n\n // Render env shared by built-in content rendering + custom-node dispatch.\n const renderEnv: RenderEnv = {\n zoom: camera.z,\n isMoving,\n isSelected: false,\n isHovered: false,\n isEditing: false,\n theme: token => (theme ? theme(token) : undefined),\n }\n const editingNodeId =\n interaction.editingTarget?.kind === 'node' ? interaction.editingTarget.id : null\n\n // Rough-stroke gate — paint the wobbly outline only when ALL hold:\n // - pan/zoom is NOT in progress (whole viewport in motion would\n // blow the frame budget),\n // - any drag/resize/rotate affects <= ROUGH_MAX_MOVING_NODES (so a\n // single-node drag keeps the rough look on its neighbours; a\n // big marquee move falls back to plain),\n // - zoom is high enough that the wobble is perceptible,\n // - visible node count is below the cap.\n // Per-node `style.roughness > 0` is the final per-shape gate inside\n // `drawRoughShape`. When the gate is false, plain strokes only.\n const cameraIsMoving = interaction.mode === 'panning' || interaction.mode === 'zooming'\n const movingNodeCount = excludedNodes?.size ?? 0\n const roughEnabled =\n !cameraIsMoving &&\n movingNodeCount <= ROUGH_MAX_MOVING_NODES &&\n camera.z >= ROUGH_MIN_ZOOM &&\n visible.length <= ROUGH_MAX_NODES\n\n // First pass: frames. They render behind everything else so the\n // slide chrome reads as a background region. The main loop below\n // skips `type === 'frame'`. `hideFrames` (set by a present-mode\n // flow) skips painting them entirely.\n if (!hideFrames) {\n for (const node of visible) {\n if (node.type !== 'frame') continue\n if (excludedNodes?.has(node.id)) continue\n drawWithNodeTransform(surface.ctx, node, () => {\n paintFrameNode(surface.ctx, node, scale, theme)\n })\n drawn++\n }\n }\n\n for (const node of visible) {\n if (node.type === 'frame') continue\n if (excludedNodes?.has(node.id)) continue\n\n // The editing node's content is occluded by the textarea overlay —\n // skip its bitmap paint so the canvas underneath doesn't show stale\n // pixels through the textarea's translucent edges.\n const isEditingThis = editingNodeId === node.id\n\n // Built-in primitive path: shape paint + optional content paint.\n if (isDrawablePrimitive(node.type)) {\n const useRough = roughEnabled && (node.style?.roughness ?? 0) > 0\n // Peek (and trigger lazy import) — null means rough.js hasn't\n // resolved yet this session.\n const roughReady = useRough ? getRoughCanvasCtor() !== null : false\n const composite = isCompositePrimitive(node.type)\n drawWithNodeTransform(surface.ctx, node, () => {\n if (useRough && roughReady) {\n if (composite) {\n // Composites paint each sub fully (misregistered fill +\n // rough stroke) before moving to the next sub. Crucial\n // so the back layer's stroke is covered by the front\n // layer's fill in the overlap region.\n drawCompositeRough(surface.ctx, node, camera.z, theme)\n } else {\n // Atomic: misregistered fill in one pass, rough stroke\n // in a second pass. Print-misregistration shifts fill\n // up-and-left a few pixels from the rough stroke. See\n // ROUGH_FILL_MISREGISTER_X/Y in rough/constants.\n surface.ctx.translate(ROUGH_FILL_MISREGISTER_X, ROUGH_FILL_MISREGISTER_Y)\n drawShape(surface.ctx, node, scale, theme, { skipStroke: true })\n surface.ctx.translate(-ROUGH_FILL_MISREGISTER_X, -ROUGH_FILL_MISREGISTER_Y)\n drawRoughShape(surface.ctx, node, camera.z, theme)\n }\n } else {\n // Plain fill + stroke at native origin — also the fallback\n // for the one frame before rough.js finishes loading.\n // Rough auto-disable during pan/zoom (via the interaction\n // mode propagation set up in `use-pan-zoom`) is what keeps\n // layered shapes smooth here; no special LOD fast-path\n // needed for composites at the count cap.\n drawShape(surface.ctx, node, scale, theme)\n if (useRough && !roughReady) {\n onRoughReady(() => {\n staticDirty = true\n cacheStale = true\n loop.requestFrame()\n })\n }\n }\n if (!isEditingThis) paintNodeContent(surface.ctx, node, renderEnv)\n })\n drawn++\n continue\n }\n // Image node: blit cached bitmap (or placeholder if still loading).\n if (node.type === 'image') {\n drawWithNodeTransform(surface.ctx, node, () => {\n paintImageNode(surface.ctx, node, assetCache, theme)\n })\n drawn++\n continue\n }\n // Icon node: rasterized SVG with optional `style.iconColor` tint.\n if (node.type === 'icon') {\n drawWithNodeTransform(surface.ctx, node, () => {\n paintIconNode(surface.ctx, node, assetCache, scale, theme)\n })\n drawn++\n continue\n }\n // Text-only shape: no fill/stroke, just content (or placeholder).\n if (node.type === 'text') {\n drawWithNodeTransform(surface.ctx, node, () => {\n if (isEditingThis) return\n const hasContent = node.content && node.content.trim().length > 0\n if (hasContent) {\n paintNodeContent(surface.ctx, node, renderEnv)\n } else {\n paintEmptyTextPlaceholder(surface.ctx, node, camera.z)\n }\n })\n drawn++\n continue\n }\n\n // Custom-node dispatch (§5.3 LOD ladder).\n const def = store.getNodeTypeDef(node.type)\n if (!def) continue\n // Sub-pixel skip — same threshold as built-ins.\n if (node.w * camera.z < minOnScreen && node.h * camera.z < minOnScreen) continue\n if (camera.z < def.lod.minZoomForPlaceholder) continue\n\n // Below the React threshold OR currently moving: prefer cheap canvas\n // paths. Order: getSnapshot → drawPlaceholder → renderCanvas → skip.\n const preferCanvas = camera.z < def.lod.minZoomForReact || isMoving\n if (preferCanvas) {\n if (paintCustomCanvasFallback(surface.ctx, node, def, scale, renderEnv)) {\n drawn++\n }\n continue\n }\n\n // Full quality: prefer React overlay; else renderCanvas; else skip.\n if (def.view) {\n nextOverlaySet.add(node.id)\n continue\n }\n if (def.renderCanvas) {\n // Custom-node drawers get a save/restore scope: built-in\n // drawers honor the \"set every state you depend on\" contract\n // (see drawWithNodeTransform), but consumer code can't be\n // assumed to. Cost is one extra save/restore per visible\n // custom node — negligible since custom nodes are rare.\n drawWithNodeTransform(surface.ctx, node, () => {\n surface.ctx.save()\n def.renderCanvas!(surface.ctx, node, renderEnv)\n surface.ctx.restore()\n })\n drawn++\n }\n }\n\n // ---- edges ----\n const visEdges = visibleEdges(viewport)\n // Edges share the same gate as nodes — extra cap protects against\n // mass-labeled scenes where edge counts dominate the budget.\n const edgeRoughEnabled =\n !cameraIsMoving &&\n movingNodeCount <= ROUGH_MAX_MOVING_NODES &&\n camera.z >= ROUGH_MIN_ZOOM &&\n visEdges.length <= ROUGH_MAX_NODES\n for (const edge of visEdges) {\n if (excludedEdges?.has(edge.id)) continue\n paintOneEdge(surface.ctx, edge, scale, edgeRoughEnabled, camera.z, isMoving)\n drawn++\n }\n if (!fullRender) return\n lastDrawn = drawn\n\n // Emit overlay event if the React-mount set changed.\n if (!setsEqual(nextOverlaySet, overlaySet)) {\n overlaySet = nextOverlaySet\n onOverlayChange?.([...overlaySet])\n }\n }\n\n /**\n * Renders the whole scene into the offscreen cache at `camera`, with a\n * margin offset so the cache covers the viewport inflated by\n * SCENE_CACHE_MARGIN_PX on every side. Records `cacheCam*` so a\n * subsequent `presentStatic` knows where the viewport sits inside it.\n */\n /**\n * Sets the cache's world→device transform centered on (`centerX`,\n * `centerY`) at zoom `z`, shifted by the margin so the world point at\n * screen (-margin, -margin) maps to cache device (0, 0).\n */\n const applyCacheTransform = (\n cache: CanvasSurface,\n centerX: number,\n centerY: number,\n z: number,\n ): void => {\n const s = z * cache.dpr\n const m = SCENE_CACHE_MARGIN_PX * cache.dpr\n cache.ctx.setTransform(s, 0, 0, s, -centerX * s + m, -centerY * s + m)\n }\n\n const renderFullCache = (camera: CameraState): void => {\n const cache = ensureCacheSurface()\n clearSurface(cache)\n applyCacheTransform(cache, camera.x, camera.y, camera.z)\n const marginWorld = SCENE_CACHE_MARGIN_PX / camera.z\n const viewport = inflateRect(worldViewport(staticSurface, camera), marginWorld)\n paintSceneBody(cache, camera, viewport)\n cacheCamX = camera.x\n cacheCamY = camera.y\n cacheCamZ = camera.z\n cacheStale = false\n }\n\n /**\n * True when a pan past the margin still overlaps the cache enough to\n * be worth extending (vs a full re-render). False on big jumps\n * (minimap click, programmatic teleport) where nothing can be reused.\n */\n const canExtend = (camera: CameraState): boolean => {\n if (!cacheSurface) return false\n const s = camera.z * staticSurface.dpr\n const dx = Math.abs((cacheCamX - camera.x) * s)\n const dy = Math.abs((cacheCamY - camera.y) * s)\n return dx < cacheSurface.canvas.width && dy < cacheSurface.canvas.height\n }\n\n /**\n * Repaints one device-space strip of the cache: clip + clear it, then\n * render the scene clipped to that strip under the cache transform\n * centered on (`centerX`, `centerY`).\n */\n const renderCacheStrip = (\n cache: CanvasSurface,\n centerX: number,\n centerY: number,\n z: number,\n px: number,\n py: number,\n pw: number,\n ph: number,\n ): void => {\n const ctx = cache.ctx\n const s = z * cache.dpr\n const m = SCENE_CACHE_MARGIN_PX * cache.dpr\n ctx.save()\n // Clip + clear in device space; the clip persists across setTransform.\n ctx.setTransform(1, 0, 0, 1, 0, 0)\n ctx.beginPath()\n ctx.rect(px, py, pw, ph)\n ctx.clip()\n ctx.clearRect(px, py, pw, ph)\n applyCacheTransform(cache, centerX, centerY, z)\n // device → world for the strip rect (inverse of the cache transform).\n const viewport: WorldRect = {\n x: (px - m) / s + centerX,\n y: (py - m) / s + centerY,\n w: pw / s,\n h: ph / s,\n }\n paintSceneBody(cache, { x: centerX, y: centerY, z }, viewport, false)\n ctx.restore()\n }\n\n /**\n * Reuses the cache across a pan that left the margin: shifts the\n * existing pixels to recenter on `camera` (integer device-px copy, so\n * no resample / no accumulating blur), then repaints only the\n * L-shaped strip the shift exposed. Pre: cache valid, same zoom,\n * `canExtend(camera)` true.\n */\n const extendCache = (camera: CameraState): void => {\n const cache = ensureCacheSurface()\n const s = camera.z * cache.dpr\n const cacheW = cache.canvas.width\n const cacheH = cache.canvas.height\n // Integer device-px shift that recenters old content on `camera`,\n // and the exact world center that integer shift implies (keeps the\n // transform consistent with the rounded copy).\n const dx = Math.round((cacheCamX - camera.x) * s)\n const dy = Math.round((cacheCamY - camera.y) * s)\n const newCamX = cacheCamX - dx / s\n const newCamY = cacheCamY - dy / s\n\n // 1. Shift existing pixels. Self-copy is spec-safe (source snapshot).\n cache.ctx.setTransform(1, 0, 0, 1, 0, 0)\n cache.ctx.drawImage(cache.canvas, 0, 0, cacheW, cacheH, dx, dy, cacheW, cacheH)\n cacheCamX = newCamX\n cacheCamY = newCamY\n cacheCamZ = camera.z\n\n // 2. Repaint the vacated L-shape as two disjoint rects. Horizontal\n // strip spans full height; vertical strip takes the remaining\n // width so the corner is painted exactly once.\n const hw = Math.abs(dx)\n const vh = Math.abs(dy)\n const hx = dx > 0 ? 0 : cacheW - hw\n const vy = dy > 0 ? 0 : cacheH - vh\n const vx = dx > 0 ? hw : 0\n const vw = cacheW - hw\n if (hw > 0) renderCacheStrip(cache, newCamX, newCamY, camera.z, hx, 0, hw, cacheH)\n if (vh > 0 && vw > 0) renderCacheStrip(cache, newCamX, newCamY, camera.z, vx, vy, vw, vh)\n }\n\n /**\n * The viewport's top-left offset inside the cache, in cache device\n * pixels, given the pan since `cacheCam*`. Rounded so the present blit\n * and the fits-in-cache test agree on the same integer rect.\n */\n const cacheSourceOffset = (camera: CameraState): { x: number; y: number } => {\n const dpr = staticSurface.dpr\n return {\n x: Math.round(((camera.x - cacheCamX) * cacheCamZ + SCENE_CACHE_MARGIN_PX) * dpr),\n y: Math.round(((camera.y - cacheCamY) * cacheCamZ + SCENE_CACHE_MARGIN_PX) * dpr),\n }\n }\n\n /**\n * True when the current viewport lies entirely within the cached\n * region — i.e. the pan since the last full render stayed inside the\n * margin, so we can present by blitting alone.\n */\n const viewportFitsInCache = (camera: CameraState): boolean => {\n if (!cacheSurface) return false\n const { x, y } = cacheSourceOffset(camera)\n return (\n x >= 0 &&\n y >= 0 &&\n x + staticSurface.canvas.width <= cacheSurface.canvas.width &&\n y + staticSurface.canvas.height <= cacheSurface.canvas.height\n )\n }\n\n /**\n * Blits the viewport-sized sub-rect of the cache onto the on-screen\n * static surface. The source offset is the viewport's position inside\n * the cache, derived from the pan since `cacheCam*`.\n */\n const presentStatic = (camera: CameraState): void => {\n const cache = ensureCacheSurface()\n const w = staticSurface.canvas.width\n const h = staticSurface.canvas.height\n const { x: srcX, y: srcY } = cacheSourceOffset(camera)\n staticSurface.ctx.setTransform(1, 0, 0, 1, 0, 0)\n staticSurface.ctx.clearRect(0, 0, w, h)\n staticSurface.ctx.drawImage(cache.canvas, srcX, srcY, w, h, 0, 0, w, h)\n }\n\n /**\n * Static-layer paint entry point. Three tiers, cheapest first:\n * 1. cache valid + viewport inside the margin → blit only (Phase 2)\n * 2. cache valid + panned past the margin but still overlapping →\n * shift + repaint the exposed strip, then blit (Phase 3)\n * 3. otherwise (stale content, zoom, big jump) → full re-render\n */\n const paintStatic = (): void => {\n const camera = store.getCamera()\n if (!cacheStale && camera.z === cacheCamZ) {\n if (viewportFitsInCache(camera)) {\n presentStatic(camera)\n return\n }\n if (canExtend(camera)) {\n extendCache(camera)\n presentStatic(camera)\n return\n }\n }\n renderFullCache(camera)\n presentStatic(camera)\n }\n\n /**\n * Tries the cheap canvas paths in order; returns true if anything was\n * painted. Order: getSnapshot → drawPlaceholder → renderCanvas.\n * Async snapshot returns are treated as \"no snapshot ready\"; consumer's\n * own caching is responsible for the eventual blit.\n */\n const paintCustomCanvasFallback = (\n ctx: CanvasRenderingContext2D,\n node: Node,\n def: NodeTypeDef,\n drawScale: number,\n env: RenderEnv,\n ): boolean => {\n void drawScale\n if (def.getSnapshot) {\n const snap = def.getSnapshot(node, {\n width: node.w,\n height: node.h,\n dpr: staticSurface.dpr,\n })\n // Phase 5 ships sync-only snapshot handling; promise-returning\n // authors get a no-op until v2 adds the cache layer.\n if (snap && !(snap instanceof Promise)) {\n drawWithNodeTransform(ctx, node, () => {\n ctx.drawImage(snap as CanvasImageSource, 0, 0, node.w, node.h)\n })\n return true\n }\n }\n if (def.drawPlaceholder) {\n // Consumer-supplied drawer — wrap in save/restore so any state\n // it leaves behind doesn't bleed into the next node.\n drawWithNodeTransform(ctx, node, () => {\n ctx.save()\n def.drawPlaceholder!(ctx, node, env)\n ctx.restore()\n })\n return true\n }\n if (def.renderCanvas) {\n drawWithNodeTransform(ctx, node, () => {\n ctx.save()\n def.renderCanvas!(ctx, node, env)\n ctx.restore()\n })\n return true\n }\n return false\n }\n\n /**\n * Paints node.content (lite markdown) via the bitmap cache. Caller is\n * already inside drawWithNodeTransform (origin at node's top-left,\n * rotation applied). No-op when content is empty.\n */\n const paintNodeContent = (ctx: CanvasRenderingContext2D, node: Node, env: RenderEnv): void => {\n const content = node.content\n if (!content || !content.trim()) return\n const style = node.style\n const fontSize = style?.fontSize ?? 'M'\n // Readability skip — text below ~3px on-screen is unreadable noise.\n // Bypasses cache lookup (FNV walk + concat) and the drawImage blit.\n if (FONT_SIZE_MAP[fontSize] * env.zoom < MIN_READABLE_FONT_PX) return\n // Layout the text within the shape's visible interior (capsule's\n // rect body excluding the accent circle, diamond's inscribed rect,\n // ellipse's inscribed rect, thought-cloud's body below the dome,\n // tag's body past the notch). Rect/text fall through to full bbox.\n const bounds = contentBounds(node)\n if (bounds.w <= 0 || bounds.h <= 0) return\n const bitmap = getOrRenderTextBitmap({\n id: node.id,\n text: content,\n width: bounds.w,\n height: bounds.h,\n zoom: env.zoom,\n dpr: staticSurface.dpr,\n isMoving: env.isMoving,\n align: style?.textAlign ?? 'center',\n fontFamily: style?.fontFamily ?? 'handwriting',\n fontSize,\n textStyle: style?.textStyle ?? 'normal',\n textColor: style?.textColor ?? DEFAULT_TEXT_COLOR,\n highlightColor: DEFAULT_HIGHLIGHT_COLOR,\n })\n if (!bitmap) return\n ctx.drawImage(bitmap.canvas, bounds.x, bounds.y, bounds.w, bounds.h)\n }\n\n /**\n * Paints \"Type to edit…\" centered in a text-typed node that has no\n * content. Hidden during edit (the textarea covers the rect).\n */\n const paintEmptyTextPlaceholder = (\n ctx: CanvasRenderingContext2D,\n node: Node,\n zoom: number,\n ): void => {\n const fontSize = node.style?.fontSize ?? 'M'\n const fontPx = FONT_SIZE_MAP[fontSize]\n if (fontPx * zoom < MIN_READABLE_FONT_PX) return\n ctx.save()\n ctx.fillStyle = '#94a3b8'\n ctx.textBaseline = 'middle'\n ctx.textAlign = 'center'\n ctx.font = `italic ${fontPx}px ${node.style?.fontFamily ?? 'sans-serif'}`\n ctx.fillText('Type to edit…', node.w / 2, node.h / 2)\n ctx.restore()\n }\n\n const setsEqual = (a: ReadonlySet<NodeId>, b: ReadonlySet<NodeId>): boolean => {\n if (a.size !== b.size) return false\n for (const v of a) if (!b.has(v)) return false\n return true\n }\n\n /**\n * Union of edge ids incident to any of the given node ids. Used by the\n * \"exclude from static during drag\" rule (§4.2). O(node count) via the\n * store's internal incidentEdges map.\n */\n const incidentEdgeIds = (nodeIds: ReadonlySet<NodeId>): ReadonlySet<EdgeId> => {\n const result = new Set<EdgeId>()\n for (const nid of nodeIds) {\n for (const eid of store.getIncidentEdges(nid)) result.add(eid)\n }\n return result\n }\n\n /**\n * Helper: paint a single edge using its cached geometry from the store.\n * `roughEnabled` mirrors the same gate used for nodes — caller threads it in.\n */\n const paintOneEdge = (\n ctx: CanvasRenderingContext2D,\n edge: Edge,\n scale: number,\n roughEnabled: boolean,\n zoom: number,\n isMoving: boolean,\n ): void => {\n const geom = store.getEdgeGeometry(edge.id)\n if (!geom) return\n const sourceNode = geom.sourceNodeId ? (store.getNode(geom.sourceNodeId) ?? null) : null\n const targetNode = geom.targetNodeId ? (store.getNode(geom.targetNodeId) ?? null) : null\n drawEdge(ctx, edge, geom, sourceNode, targetNode, scale, theme, {\n roughEnabled,\n zoom,\n dpr: staticSurface.dpr,\n isMoving,\n })\n }\n\n const getSortedEdgeIds = (): EdgeId[] => {\n if (sortedEdgeIdsCache) return sortedEdgeIdsCache\n const all = store.getAllEdges()\n sortedEdgeIdsCache = all\n .slice()\n .sort((a, b) => a.z - b.z || (a.id < b.id ? -1 : 1))\n .map(e => e.id)\n return sortedEdgeIdsCache\n }\n\n const visibleEdges = (viewport: WorldRect): Edge[] => {\n const ids = store.querySpatial({ rect: viewport }).edges as EdgeId[]\n if (ids.length === 0) return []\n const visibleSet = new Set<EdgeId>(ids)\n const sorted = getSortedEdgeIds()\n const result: Edge[] = []\n for (const id of sorted) {\n if (!visibleSet.has(id)) continue\n const e = store.getEdge(id)\n if (e) result.push(e)\n }\n return result\n }\n\n const paintInteractive = (): void => {\n const camera = store.getCamera()\n clearSurface(interactiveSurface)\n applyCameraTransform(interactiveSurface, camera)\n const scale = camera.z * interactiveSurface.dpr\n const interaction = store.getInteractionState()\n const ctx = interactiveSurface.ctx\n\n // 1. Dragged / resizing nodes at their uncommitted positions.\n if (interaction.mode === 'dragging' || interaction.mode === 'resizing') {\n const inDragMap = mapDragPositions(interaction)\n const dragEnv: RenderEnv = {\n zoom: camera.z,\n isMoving: true,\n isSelected: true,\n isHovered: false,\n isEditing: false,\n theme: token => (theme ? theme(token) : undefined),\n }\n // Mirror the static-surface rough gate so the dragged node keeps\n // its hand-drawn look on small drags. Pan/zoom can't be active in\n // this branch (we're inside dragging/resizing), so the only knobs\n // are the moving-count cap and the zoom floor.\n const dragRoughEnabled =\n inDragMap.size <= ROUGH_MAX_MOVING_NODES && camera.z >= ROUGH_MIN_ZOOM\n for (const node of inDragMap.values()) {\n if (\n !isDrawablePrimitive(node.type) &&\n node.type !== 'text' &&\n node.type !== 'image' &&\n node.type !== 'icon' &&\n node.type !== 'frame'\n )\n continue\n drawWithNodeTransform(ctx, node, () => {\n if (node.type === 'frame') {\n paintFrameNode(ctx, node, scale, theme)\n return\n }\n if (node.type === 'image') {\n paintImageNode(ctx, node, assetCache, theme)\n return\n }\n if (node.type === 'icon') {\n paintIconNode(ctx, node, assetCache, scale, theme)\n return\n }\n if (isDrawablePrimitive(node.type)) {\n const useRough = dragRoughEnabled && (node.style?.roughness ?? 0) > 0\n const roughReady = useRough ? getRoughCanvasCtor() !== null : false\n if (useRough && roughReady) {\n if (isCompositePrimitive(node.type)) {\n drawCompositeRough(ctx, node, camera.z, theme)\n } else {\n ctx.translate(ROUGH_FILL_MISREGISTER_X, ROUGH_FILL_MISREGISTER_Y)\n drawShape(ctx, node, scale, theme, { skipStroke: true })\n ctx.translate(-ROUGH_FILL_MISREGISTER_X, -ROUGH_FILL_MISREGISTER_Y)\n drawRoughShape(ctx, node, camera.z, theme)\n }\n } else {\n drawShape(ctx, node, scale, theme)\n }\n }\n paintNodeContent(ctx, node, dragEnv)\n })\n }\n\n // Edges incident to a dragged node redraw with the offset applied.\n // We wrap getNode so endpoint projection sees the dragged position.\n const wrapGetNode = (id: NodeId): Node | undefined => inDragMap.get(id) ?? store.getNode(id)\n const drawnEdgeIds = new Set<EdgeId>()\n for (const nodeId of inDragMap.keys()) {\n for (const eid of store.getIncidentEdges(nodeId)) {\n if (drawnEdgeIds.has(eid)) continue\n drawnEdgeIds.add(eid)\n const edge = store.getEdge(eid)\n if (!edge) continue\n // Compute geometry directly — bypass the cache so we get the\n // uncommitted positions. Cheap; samples-per-frame is bounded\n // by drag size, not scene size.\n const geom = computeEdgeGeometry(edge, wrapGetNode)\n if (!geom) continue\n const sourceNode = geom.sourceNodeId ? (wrapGetNode(geom.sourceNodeId) ?? null) : null\n const targetNode = geom.targetNodeId ? (wrapGetNode(geom.targetNodeId) ?? null) : null\n drawEdge(ctx, edge, geom, sourceNode, targetNode, scale, theme, {\n zoom: camera.z,\n dpr: interactiveSurface.dpr,\n isMoving: true,\n })\n }\n }\n }\n\n // 1b. Edge being mid-point-dragged. Excluded from the static layer\n // via excludedEdges; painted here with the draft cubic controls.\n // Bypasses the edge-geometry cache (keyed on edge.version, which\n // doesn't bump during the gesture).\n if (interaction.midpointDraft) {\n const { edgeId, control } = interaction.midpointDraft\n const edge = store.getEdge(edgeId)\n if (edge) {\n const draftEdge: Edge = { ...edge, control }\n const geom = computeEdgeGeometry(draftEdge, id => store.getNode(id))\n if (geom) {\n const sourceNode = geom.sourceNodeId ? (store.getNode(geom.sourceNodeId) ?? null) : null\n const targetNode = geom.targetNodeId ? (store.getNode(geom.targetNodeId) ?? null) : null\n drawEdge(ctx, draftEdge, geom, sourceNode, targetNode, scale, theme, {\n zoom: camera.z,\n dpr: interactiveSurface.dpr,\n isMoving: true,\n })\n }\n }\n }\n\n // 2. Selection outlines + handles for selected nodes (uses current /\n // in-progress geometry).\n const selection = store.getSelection()\n const selectedNodeIds: NodeId[] = []\n const selectedEdgeIds: EdgeId[] = []\n for (const id of selection) {\n if (store.getNode(id as NodeId)) selectedNodeIds.push(id as NodeId)\n else if (store.getEdge(id as EdgeId)) selectedEdgeIds.push(id as EdgeId)\n }\n if (selectedNodeIds.length > 0) {\n const inDragMap = mapDragPositions(interaction)\n for (const id of selectedNodeIds) {\n const node = inDragMap.get(id) ?? store.getNode(id)\n if (!node) continue\n drawSelectionOutline(ctx, node, scale, selectionColor)\n }\n // Resize + rotate handles only for non-dragging selection. (During\n // a drag, the handles would jitter with the dragged geometry —\n // Excalidraw hides them mid-drag for the same reason.)\n if (interaction.mode !== 'dragging' && selectedNodeIds.length === 1) {\n const node = inDragMap.get(selectedNodeIds[0]!) ?? store.getNode(selectedNodeIds[0]!)\n if (node) {\n drawResizeHandles(ctx, node, scale, selectionColor)\n drawRotateHandle(ctx, node, scale, camera.z, selectionColor)\n }\n }\n }\n // Edge endpoint handles on selected edges.\n for (const id of selectedEdgeIds) {\n const geom = store.getEdgeGeometry(id)\n if (geom) {\n drawEdgeEndpointHandles(ctx, geom.source, geom.target, scale, selectionColor)\n // Midpoint handle — drag to reshape (Phase 12.6). Only on\n // bezier; polyline / straight don't have a meaningful curve to\n // sculpt with one drag point.\n const edge = store.getEdge(id)\n if (edge && edge.pathStyle === 'bezier') {\n const mid = getPointAndTangentAtArcLength(geom.samples, 0.5).point\n drawEdgeMidpointHandle(ctx, mid, scale, selectionColor)\n }\n }\n }\n\n // 3. Marquee rect.\n if (interaction.mode === 'marqueeing' && interaction.marqueeRect) {\n drawMarquee(ctx, interaction.marqueeRect, scale, selectionColor)\n }\n\n // 3.5 Drag-create preview — dashed outline matching the active\n // shape tool's intended footprint.\n if (interaction.mode === 'creating-shape' && interaction.createDraftRect) {\n drawMarquee(ctx, interaction.createDraftRect, scale, selectionColor)\n }\n\n // 4. Draft edge during creation / reconnection.\n if (\n (interaction.mode === 'creating-edge' || interaction.mode === 'reconnecting-edge') &&\n interaction.draftEdge\n ) {\n const draft: Edge = {\n id: 'draft' as EdgeId,\n source: interaction.draftEdge.source,\n target: interaction.draftEdge.target,\n pathStyle: 'bezier',\n z: 0,\n groups: [],\n style: { strokeColor: selectionColor },\n }\n const geom = computeEdgeGeometry(draft, id => store.getNode(id))\n if (geom) {\n const sNode = geom.sourceNodeId ? (store.getNode(geom.sourceNodeId) ?? null) : null\n const tNode = geom.targetNodeId ? (store.getNode(geom.targetNodeId) ?? null) : null\n drawEdge(ctx, draft, geom, sNode, tNode, scale, theme, {\n zoom: camera.z,\n dpr: interactiveSurface.dpr,\n isMoving: true,\n })\n }\n }\n }\n\n const mapDragPositions = (interaction: InteractionState): Map<NodeId, Node> => {\n const m = new Map<NodeId, Node>()\n if (interaction.mode !== 'dragging' && interaction.mode !== 'resizing') return m\n for (const orig of interaction.dragOriginals) {\n const live = store.getNode(orig.id)\n if (!live) continue\n if (interaction.mode === 'dragging') {\n m.set(orig.id, {\n ...live,\n x: orig.x + interaction.dragDelta.x,\n y: orig.y + interaction.dragDelta.y,\n })\n } else {\n // Resize: the store still holds the original geometry until\n // pointer-up. Overlay the in-progress geometry from resizeDraft\n // so the interactive layer (and incident-edge re-routing\n // through this same map) paints the live shape.\n const d = interaction.resizeDraft\n if (d) {\n m.set(orig.id, { ...live, x: d.x, y: d.y, w: d.w, h: d.h, angle: d.angle })\n } else {\n m.set(orig.id, live)\n }\n }\n }\n return m\n }\n\n const getSortedNodeIds = (): NodeId[] => {\n if (sortedNodeIdsCache) return sortedNodeIdsCache\n const all = store.getAllNodes()\n sortedNodeIdsCache = all\n .slice()\n .sort((a, b) => a.z - b.z || (a.id < b.id ? -1 : 1))\n .map(n => n.id)\n return sortedNodeIdsCache\n }\n\n const visibleNodes = (camera: CameraState, viewport: WorldRect): Node[] => {\n const ids = store.querySpatial({ rect: viewport }).nodes as NodeId[]\n if (ids.length === 0) return []\n // Build a Set of broad-phase-visible ids (the spatial query is\n // bucket-based, so this is a superset of the true visible set).\n const visibleSet = new Set<NodeId>(ids)\n // Walk the cached sorted list in order and emit those in the\n // visible set after the exact-AABB intersection check. No\n // per-frame Array.sort.\n const sorted = getSortedNodeIds()\n const result: Node[] = []\n const minWorldSize = MIN_ON_SCREEN_SIZE_PX / camera.z\n for (const id of sorted) {\n if (!visibleSet.has(id)) continue\n const n = store.getNode(id)\n if (!n) continue\n if (n.w < minWorldSize && n.h < minWorldSize) continue\n if (intersectsViewport(n, viewport)) result.push(n)\n }\n return result\n }\n\n const loop: FrameLoop = createFrameLoop({ draw: drawFrame })\n\n const onStoreChange = (): void => {\n // Any commit may have added / removed / re-z-ordered an entity,\n // so the sorted caches must rebuild on next paint. Camera /\n // selection / interaction events do NOT invalidate (z-order is\n // independent of viewport + selection state).\n invalidateSortedCaches()\n staticDirty = true\n cacheStale = true\n interactiveDirty = true\n loop.requestFrame()\n }\n // Camera is the one static-dirtying event that does NOT stale the\n // cache content: a pure pan reuses the cache (blit-only), and a zoom\n // is caught by the `z !== cacheCamZ` check in `paintStatic`.\n const onCameraChange = (): void => {\n staticDirty = true\n interactiveDirty = true\n loop.requestFrame()\n }\n const onSelectionChange = (): void => {\n interactiveDirty = true\n loop.requestFrame()\n }\n const onInteractionChange = (state: InteractionState): void => {\n interactiveDirty = true\n // Mode transitions that affect what the static surface paints:\n // - dragging/resizing toggle the excluded set\n // - rotating/panning/zooming flip motion-LOD on for layered\n // - idle restores full-quality after any of the above\n // Any of these need a static repaint at the transition boundary\n // so the LOD changes (motion fast-path, rough auto-disable, text\n // bitmap downscale) take effect on the very next frame.\n if (\n state.mode === 'dragging' ||\n state.mode === 'resizing' ||\n state.mode === 'rotating' ||\n state.mode === 'panning' ||\n state.mode === 'zooming' ||\n state.mode === 'idle'\n ) {\n staticDirty = true\n // A mode transition changes the excluded set and/or motion-LOD,\n // so the cache content must be rebuilt. This also guarantees the\n // first frame of a pan does a full render — which is what swaps\n // custom-node React overlays to their canvas fallback.\n cacheStale = true\n }\n loop.requestFrame()\n }\n\n const unsubChange = store.subscribe('change', onStoreChange)\n const unsubCamera = store.subscribe('camera', onCameraChange)\n const unsubSelection = store.subscribe('selection', onSelectionChange)\n const unsubInteraction = store.subscribe('interaction', onInteractionChange)\n // Custom-font load → bitmap cache clears itself; we just need a repaint.\n const unsubFontEpoch = subscribeFontEpoch(() => {\n staticDirty = true\n cacheStale = true\n loop.requestFrame()\n })\n // Math formula compile → math-bearing bitmaps get a new cache key\n // via the math-epoch; repaint to pick up the real glyphs.\n const unsubMathEpoch = subscribeMathEpoch(() => {\n staticDirty = true\n cacheStale = true\n loop.requestFrame()\n })\n\n return {\n start() {\n loop.start()\n staticDirty = true\n cacheStale = true\n interactiveDirty = isInteractive(store.getInteractionState())\n loop.requestFrame()\n },\n stop() {\n loop.stop()\n },\n invalidate() {\n staticDirty = true\n cacheStale = true\n interactiveDirty = true\n loop.requestFrame()\n },\n setSize(cssW, cssH) {\n const a = sizeSurface(staticSurface, cssW, cssH, maxDpr)\n const b = sizeSurface(interactiveSurface, cssW, cssH, maxDpr)\n if (a || b) {\n staticDirty = true\n cacheStale = true\n interactiveDirty = true\n loop.requestFrame()\n }\n },\n setBackground(bg) {\n background = bg\n staticDirty = true\n cacheStale = true\n loop.requestFrame()\n },\n setSelectionColor(color) {\n selectionColor = color\n // Selection chrome lives on the interactive surface; static doesn't\n // need to repaint. The draft-edge stroke is also interactive-only.\n interactiveDirty = true\n loop.requestFrame()\n },\n setHideFrames(hidden) {\n hideFrames = hidden\n staticDirty = true\n cacheStale = true\n loop.requestFrame()\n },\n stats: () => loop.stats(),\n lastDrawCount: () => lastDrawn,\n getOverlaySet: () => [...overlaySet],\n getAssetCache: () => assetCache,\n dispose() {\n loop.stop()\n unsubChange()\n unsubCamera()\n unsubSelection()\n unsubInteraction()\n unsubFontEpoch()\n unsubMathEpoch()\n assetCache.dispose()\n if (cacheSurface) {\n // Drop the backing store so the GPU buffer is freed promptly.\n cacheSurface.canvas.width = 0\n cacheSurface.canvas.height = 0\n cacheSurface = null\n }\n },\n }\n}\n\n/**\n * Narrow-phase check: does the (rotation-aware) node AABB intersect the viewport?\n */\nconst intersectsViewport = (\n node: Node,\n viewport: { x: number; y: number; w: number; h: number },\n) => {\n const a = nodeAABB(node)\n return (\n a.x < viewport.x + viewport.w &&\n a.x + a.w > viewport.x &&\n a.y < viewport.y + viewport.h &&\n a.y + a.h > viewport.y\n )\n}\n","import { nodeAABB } from '../spatial'\nimport type { CanvasStore } from '../store'\nimport type { CameraState, WorldRect } from '../types'\n\n/**\n * Minimap rendering — see IMPROVEMENTS.md (UX) and the React layer's\n * `<Minimap />` component.\n *\n * Splits into two paths consumers can compose independently:\n *\n * - `renderMinimapContent(ctx, store, ...)` — paints every node as a\n * plain `fillRect` at its scaled AABB. Edge bodies are skipped\n * (not useful at this scale and would multiply cost). Run on\n * committed scene change ONLY; cache the result as an\n * OffscreenCanvas/HTMLCanvasElement and blit.\n *\n * - `drawMinimapViewport(ctx, camera, sceneBounds, mapSize)` — paints\n * a tiny rectangle showing the visible viewport. Cheap; run on\n * every camera change.\n *\n * Cost model:\n * - content render: O(N) — only fires on committed mutations.\n * - viewport overlay: O(1) per frame.\n *\n * Hard cap (`maxNodes`) — above which the content render skips\n * entirely and the consumer is expected to show a \"minimap disabled\"\n * placeholder. Default 5000.\n */\n\nexport const DEFAULT_MINIMAP_MAX_NODES = 5000\n\nexport type MinimapContentOptions = {\n /** Hard upper bound on node count; above this, content is skipped. */\n maxNodes?: number\n /** Override fill color for nodes (used when node has no style.backgroundColor). */\n defaultNodeColor?: string\n /** Background color drawn first inside the minimap rect. */\n backgroundColor?: string\n}\n\n/**\n * Returns the world-space bounding rect that encloses every visible\n * node, or `null` if the scene is empty. Used to scale the minimap so\n * the entire scene fits inside it.\n */\nexport const sceneBounds = (store: CanvasStore): WorldRect | null => {\n const nodes = store.getAllNodes()\n if (nodes.length === 0) return null\n let minX = Number.POSITIVE_INFINITY\n let minY = Number.POSITIVE_INFINITY\n let maxX = Number.NEGATIVE_INFINITY\n let maxY = Number.NEGATIVE_INFINITY\n for (const n of nodes) {\n if (n.hidden) continue\n // Frames are excluded from minimap content paint; exclude them\n // from the bounds calculation too, otherwise an off-canvas frame\n // would scale the minimap to mostly-empty space.\n if (n.type === 'frame') continue\n const r = nodeAABB(n)\n if (r.x < minX) minX = r.x\n if (r.y < minY) minY = r.y\n if (r.x + r.w > maxX) maxX = r.x + r.w\n if (r.y + r.h > maxY) maxY = r.y + r.h\n }\n if (!Number.isFinite(minX)) return null\n return { x: minX, y: minY, w: maxX - minX, h: maxY - minY }\n}\n\n/**\n * Paints the scene's nodes into the minimap canvas's logical pixel\n * space. Caller has already cleared the target. Returns true on\n * success, false when skipped (empty scene or over the node cap).\n */\nexport const renderMinimapContent = (\n ctx: CanvasRenderingContext2D,\n store: CanvasStore,\n mapWidth: number,\n mapHeight: number,\n opts: MinimapContentOptions = {},\n): boolean => {\n const cap = opts.maxNodes ?? DEFAULT_MINIMAP_MAX_NODES\n const count = store.getNodeCount()\n if (count === 0 || count > cap) return false\n\n const bounds = sceneBounds(store)\n if (!bounds || bounds.w === 0 || bounds.h === 0) return false\n\n // Pad the bounds so shapes near the edges aren't clipped.\n const pad = Math.max(bounds.w, bounds.h) * 0.05\n const bx = bounds.x - pad\n const by = bounds.y - pad\n const bw = bounds.w + pad * 2\n const bh = bounds.h + pad * 2\n const scale = Math.min(mapWidth / bw, mapHeight / bh)\n // Center the scaled content in the map rect.\n const offX = (mapWidth - bw * scale) / 2\n const offY = (mapHeight - bh * scale) / 2\n\n if (opts.backgroundColor) {\n ctx.fillStyle = opts.backgroundColor\n ctx.fillRect(0, 0, mapWidth, mapHeight)\n }\n\n const defaultColor = opts.defaultNodeColor ?? '#94a3b8'\n for (const node of store.getAllNodes()) {\n if (node.hidden) continue\n // Frames are slide chrome, not content — skip them so the minimap\n // shows content density rather than slide boundaries.\n if (node.type === 'frame') continue\n const r = nodeAABB(node)\n const x = offX + (r.x - bx) * scale\n const y = offY + (r.y - by) * scale\n const w = Math.max(1, r.w * scale)\n const h = Math.max(1, r.h * scale)\n ctx.fillStyle = node.style?.backgroundColor ?? defaultColor\n ctx.fillRect(x, y, w, h)\n }\n return true\n}\n\n/**\n * Paints the camera viewport rectangle on top of the cached minimap\n * content. Cheap; consumers call this on every camera tick.\n *\n * `sceneRect` should be the same bounds used by `renderMinimapContent`\n * for the current cache. `viewportWorld` is the visible world rect\n * (caller derives from camera + screen size).\n */\nexport const drawMinimapViewport = (\n ctx: CanvasRenderingContext2D,\n viewportWorld: WorldRect,\n sceneRect: WorldRect,\n mapWidth: number,\n mapHeight: number,\n color = '#3b82f6',\n): void => {\n // Same scaling math as renderMinimapContent — keeps the viewport\n // overlay perfectly registered with the cached content.\n const pad = Math.max(sceneRect.w, sceneRect.h) * 0.05\n const bx = sceneRect.x - pad\n const by = sceneRect.y - pad\n const bw = sceneRect.w + pad * 2\n const bh = sceneRect.h + pad * 2\n const scale = Math.min(mapWidth / bw, mapHeight / bh)\n const offX = (mapWidth - bw * scale) / 2\n const offY = (mapHeight - bh * scale) / 2\n\n const x = offX + (viewportWorld.x - bx) * scale\n const y = offY + (viewportWorld.y - by) * scale\n const w = viewportWorld.w * scale\n const h = viewportWorld.h * scale\n\n ctx.save()\n ctx.strokeStyle = color\n ctx.lineWidth = 1.5\n ctx.strokeRect(x, y, w, h)\n ctx.restore()\n}\n\n/**\n * Inverse mapping for click-to-pan: a screen point inside the minimap\n * rect → the world point it corresponds to. Returns null when the\n * scene is empty (no bounds to scale against).\n */\nexport const minimapScreenToWorld = (\n store: CanvasStore,\n screenX: number,\n screenY: number,\n mapWidth: number,\n mapHeight: number,\n): { x: number; y: number } | null => {\n const bounds = sceneBounds(store)\n if (!bounds || bounds.w === 0 || bounds.h === 0) return null\n const pad = Math.max(bounds.w, bounds.h) * 0.05\n const bx = bounds.x - pad\n const by = bounds.y - pad\n const bw = bounds.w + pad * 2\n const bh = bounds.h + pad * 2\n const scale = Math.min(mapWidth / bw, mapHeight / bh)\n const offX = (mapWidth - bw * scale) / 2\n const offY = (mapHeight - bh * scale) / 2\n return {\n x: (screenX - offX) / scale + bx,\n y: (screenY - offY) / scale + by,\n }\n}\n\n/**\n * World-space viewport rect from the camera + a screen size. Pass to\n * `drawMinimapViewport`. Caller's responsibility to supply the\n * canvas/CSS pixel dimensions.\n */\nexport const worldViewportFromCamera = (\n camera: CameraState,\n screenW: number,\n screenH: number,\n): WorldRect => ({\n x: camera.x,\n y: camera.y,\n w: screenW / camera.z,\n h: screenH / camera.z,\n})\n","/**\n * Node hit testing — see ARCHITECTURE.md §6.9 (parallels edge hit testing\n * structure for phase 4).\n *\n * For axis-aligned nodes: a fast AABB check.\n * For rotated nodes: transform the world point into node-local pre-rotation\n * coords (collapsing the rotation problem to AABB).\n */\nimport type { Node, Vec2, WorldRect } from '../types'\n\n/**\n * Returns true if the world-space point is inside the (possibly rotated) node.\n */\nexport const pointInNode = (point: Vec2, node: Node): boolean => {\n if (node.hidden) return false\n if (node.w <= 0 || node.h <= 0) return false\n\n if (node.angle === 0) {\n return (\n point.x >= node.x &&\n point.x <= node.x + node.w &&\n point.y >= node.y &&\n point.y <= node.y + node.h\n )\n }\n\n const cx = node.x + node.w / 2\n const cy = node.y + node.h / 2\n const cos = Math.cos(-node.angle)\n const sin = Math.sin(-node.angle)\n const dx = point.x - cx\n const dy = point.y - cy\n // localCoord = rotate(point - center, -angle) + (w/2, h/2)\n const localX = dx * cos - dy * sin + node.w / 2\n const localY = dx * sin + dy * cos + node.h / 2\n return localX >= 0 && localX <= node.w && localY >= 0 && localY <= node.h\n}\n\n/**\n * Returns true if the node's rotated rect intersects the given AABB.\n * For axis-aligned nodes this collapses to two AABB ranges; for rotated\n * nodes we test all 4 corners + 4 axis projections (SAT).\n */\nexport const nodeIntersectsRect = (node: Node, rect: WorldRect): boolean => {\n if (node.hidden) return false\n if (node.w <= 0 || node.h <= 0) return false\n\n if (node.angle === 0) {\n return (\n node.x < rect.x + rect.w &&\n node.x + node.w > rect.x &&\n node.y < rect.y + rect.h &&\n node.y + node.h > rect.y\n )\n }\n\n // SAT against the rotated rect — cheap enough that this is fine for marquee.\n const cx = node.x + node.w / 2\n const cy = node.y + node.h / 2\n const cos = Math.cos(node.angle)\n const sin = Math.sin(node.angle)\n const localCorners: Vec2[] = [\n { x: -node.w / 2, y: -node.h / 2 },\n { x: node.w / 2, y: -node.h / 2 },\n { x: node.w / 2, y: node.h / 2 },\n { x: -node.w / 2, y: node.h / 2 },\n ]\n const worldCorners: Vec2[] = localCorners.map(p => ({\n x: cx + p.x * cos - p.y * sin,\n y: cy + p.x * sin + p.y * cos,\n }))\n const rectCorners: Vec2[] = [\n { x: rect.x, y: rect.y },\n { x: rect.x + rect.w, y: rect.y },\n { x: rect.x + rect.w, y: rect.y + rect.h },\n { x: rect.x, y: rect.y + rect.h },\n ]\n const axes: Vec2[] = [\n { x: 1, y: 0 },\n { x: 0, y: 1 },\n { x: cos, y: sin },\n { x: -sin, y: cos },\n ]\n for (const a of axes) {\n let minA = Number.POSITIVE_INFINITY\n let maxA = Number.NEGATIVE_INFINITY\n for (const p of worldCorners) {\n const v = p.x * a.x + p.y * a.y\n if (v < minA) minA = v\n if (v > maxA) maxA = v\n }\n let minB = Number.POSITIVE_INFINITY\n let maxB = Number.NEGATIVE_INFINITY\n for (const p of rectCorners) {\n const v = p.x * a.x + p.y * a.y\n if (v < minB) minB = v\n if (v > maxB) maxB = v\n }\n if (maxA < minB || maxB < minA) return false\n }\n return true\n}\n","/**\n * Edge hit testing — see ARCHITECTURE.md §6.9.\n *\n * Broad-phase via the spatial index; narrow-phase via point-to-polyline\n * distance over the cached samples. Sub-region detection: arrowhead tips\n * and (when selected) endpoint handles are tested before the body.\n */\nimport { getPointAndTangentAtArcLength } from '../edges/arc-length'\nimport { edgeLabelBoundsWorld } from '../edges/draw'\nimport type { CanvasStore, EdgeGeometry } from '../store'\nimport type { Edge, EdgeId, Vec2 } from '../types'\n\n/** Hit-slop in screen pixels for the edge body. */\nexport const EDGE_HIT_SLOP_PX = 8\n/** Hit-slop in screen pixels for endpoint / arrowhead handles. */\nexport const EDGE_HANDLE_SLOP_PX = 12\n/** Hit-slop in screen pixels for the midpoint handle (Phase 12.6). */\nexport const EDGE_MIDPOINT_SLOP_PX = 10\n\nexport type EdgeHit =\n | { kind: 'body'; edgeId: EdgeId; distance: number; arcLength: number }\n | { kind: 'source-handle'; edgeId: EdgeId; distance: number }\n | { kind: 'target-handle'; edgeId: EdgeId; distance: number }\n | { kind: 'midpoint-handle'; edgeId: EdgeId }\n | { kind: 'label'; edgeId: EdgeId }\n\n/**\n * Returns the topmost edge hit by a world point, or null.\n * `selectedEdges` enables endpoint-handle detection (handles only show\n * when the edge is selected).\n */\nexport const hitTestEdge = (\n store: CanvasStore,\n worldPoint: Vec2,\n cameraZ: number,\n selectedEdges: ReadonlySet<EdgeId> = new Set(),\n): EdgeHit | null => {\n const slopWorld = EDGE_HIT_SLOP_PX / cameraZ\n const handleSlopWorld = EDGE_HANDLE_SLOP_PX / cameraZ\n\n // Endpoint handles win over body (interactive-over-background rule).\n // Midpoint handle slots between endpoint handles and the body.\n const midpointSlopWorld = EDGE_MIDPOINT_SLOP_PX / cameraZ\n for (const id of selectedEdges) {\n const geom = store.getEdgeGeometry(id)\n if (!geom) continue\n const dSource = distance(worldPoint, geom.source)\n if (dSource <= handleSlopWorld) {\n return { kind: 'source-handle', edgeId: id, distance: dSource }\n }\n const dTarget = distance(worldPoint, geom.target)\n if (dTarget <= handleSlopWorld) {\n return { kind: 'target-handle', edgeId: id, distance: dTarget }\n }\n const mid = getPointAndTangentAtArcLength(geom.samples, 0.5).point\n if (distance(worldPoint, mid) <= midpointSlopWorld) {\n return { kind: 'midpoint-handle', edgeId: id }\n }\n }\n\n // Body hits — broad-phase via spatial index, narrow via polyline.\n const queryRect = {\n x: worldPoint.x - slopWorld,\n y: worldPoint.y - slopWorld,\n w: slopWorld * 2,\n h: slopWorld * 2,\n }\n const candidates = store.querySpatial({ rect: queryRect }).edges\n\n // Label hits — checked before body so a click on a label doesn't\n // accidentally select the edge body underneath. Iterates candidates\n // again because labels can extend slightly beyond the body slop.\n for (const id of candidates) {\n const edge = store.getEdge(id)\n if (!edge || edge.hidden || !edge.content || !edge.content.trim()) continue\n const geom = store.getEdgeGeometry(id)\n if (!geom) continue\n const bounds = edgeLabelBoundsWorld(edge, geom)\n if (!bounds) continue\n if (\n worldPoint.x >= bounds.x &&\n worldPoint.x <= bounds.x + bounds.w &&\n worldPoint.y >= bounds.y &&\n worldPoint.y <= bounds.y + bounds.h\n ) {\n return { kind: 'label', edgeId: id }\n }\n }\n\n type BodyHit = Extract<EdgeHit, { kind: 'body' }>\n let best: { hit: BodyHit; z: number; edge: Edge } | null = null\n for (const id of candidates) {\n const edge = store.getEdge(id)\n if (!edge || edge.hidden) continue\n const geom = store.getEdgeGeometry(id)\n if (!geom) continue\n const result = nearestSampleDistance(worldPoint, geom)\n if (result.distance > slopWorld) continue\n if (\n !best ||\n edge.z > best.edge.z ||\n (edge.z === best.edge.z && result.distance < best.hit.distance)\n ) {\n best = {\n hit: { kind: 'body', edgeId: id, distance: result.distance, arcLength: result.arcLength },\n z: edge.z,\n edge,\n }\n }\n }\n\n return best ? best.hit : null\n}\n\n/**\n * Walks the polyline samples and finds the nearest segment to the point.\n * Returns the perpendicular distance + the arc-length parameter (0..1)\n * of the foot of perpendicular along the polyline. Callers use arcLength\n * to insert midpoints or anchor labels.\n */\nconst nearestSampleDistance = (\n p: Vec2,\n geom: EdgeGeometry,\n): { distance: number; arcLength: number } => {\n const samples = geom.samples\n if (samples.length < 2) return { distance: Number.POSITIVE_INFINITY, arcLength: 0 }\n\n const segmentLengths: number[] = []\n let totalLen = 0\n for (let i = 1; i < samples.length; i++) {\n const a = samples[i - 1]!\n const b = samples[i]!\n const len = Math.hypot(b.x - a.x, b.y - a.y)\n segmentLengths.push(len)\n totalLen += len\n }\n if (totalLen === 0) return { distance: distance(p, samples[0]!), arcLength: 0 }\n\n let bestD2 = Number.POSITIVE_INFINITY\n let bestArc = 0\n let cumLen = 0\n for (let i = 1; i < samples.length; i++) {\n const a = samples[i - 1]!\n const b = samples[i]!\n const segLen = segmentLengths[i - 1]!\n const { d2, t } = pointSegmentDistanceSq(p, a, b)\n if (d2 < bestD2) {\n bestD2 = d2\n bestArc = (cumLen + t * segLen) / totalLen\n }\n cumLen += segLen\n }\n return { distance: Math.sqrt(bestD2), arcLength: bestArc }\n}\n\nconst distance = (a: Vec2, b: Vec2): number => Math.hypot(b.x - a.x, b.y - a.y)\n\n/**\n * Squared distance from point p to segment ab, plus parametric t along ab.\n * Squared to avoid the sqrt in the inner loop.\n */\nconst pointSegmentDistanceSq = (p: Vec2, a: Vec2, b: Vec2): { d2: number; t: number } => {\n const dx = b.x - a.x\n const dy = b.y - a.y\n const len2 = dx * dx + dy * dy\n if (len2 === 0) {\n const ex = p.x - a.x\n const ey = p.y - a.y\n return { d2: ex * ex + ey * ey, t: 0 }\n }\n let t = ((p.x - a.x) * dx + (p.y - a.y) * dy) / len2\n t = Math.max(0, Math.min(1, t))\n const fx = a.x + dx * t\n const fy = a.y + dy * t\n const ex = p.x - fx\n const ey = p.y - fy\n return { d2: ex * ex + ey * ey, t }\n}\n","/**\n * Higher-level hit queries that combine the spatial index with per-shape\n * narrow-phase tests. Returns the topmost hit by z, or all hits inside a\n * marquee rect.\n */\nimport type { CanvasStore } from '../store'\nimport type { EdgeId, Node, NodeId, Vec2, WorldRect } from '../types'\nimport { type EdgeHit, hitTestEdge } from './edge'\nimport { type ResizeHandle, hitTestHandles, hitTestRotateHandle } from './handle'\nimport { nodeIntersectsRect, pointInNode } from './node'\n\nexport type NodeHit =\n | { kind: 'body'; nodeId: NodeId }\n | { kind: 'resize-handle'; nodeId: NodeId; handle: ResizeHandle }\n | { kind: 'rotate-handle'; nodeId: NodeId }\n\n/** A hit covers either a node or an edge sub-region. */\nexport type Hit = NodeHit | EdgeHit\n\n/**\n * Returns the topmost node hit by a world-space point, plus the part hit\n * (body or resize handle). Handles are tested before bodies (interactive\n * elements always win over background — see ARCHITECTURE.md §7).\n *\n * If `selectedIds` is provided, only those nodes' handles are considered\n * — handles only display when the node is selected.\n */\nexport const hitTestPoint = (\n store: CanvasStore,\n worldPoint: Vec2,\n cameraZ: number,\n selectedIds: ReadonlySet<NodeId> = new Set(),\n): NodeHit | null => {\n // First try rotation + resize handles on selected nodes (drawn above\n // bodies). Rotate handle sits OUTSIDE the node bounds so it gets\n // priority over neighboring bodies underneath.\n for (const id of selectedIds) {\n const n = store.getNode(id)\n if (!n) continue\n if (hitTestRotateHandle(n, worldPoint, cameraZ)) {\n return { kind: 'rotate-handle', nodeId: id }\n }\n const h = hitTestHandles(n, worldPoint, cameraZ)\n if (h) return { kind: 'resize-handle', nodeId: id, handle: h }\n }\n\n // Then bodies, topmost-z first. Tiebreak on id (lexically greater id\n // is painted later → sits on top → wins the hit) so hit-test matches\n // paint order exactly.\n const candidates = store.querySpatial({ point: worldPoint }).nodes\n let best: Node | null = null\n for (const id of candidates) {\n const n = store.getNode(id)\n if (!n) continue\n if (!pointInNode(worldPoint, n)) continue\n if (!best || n.z > best.z || (n.z === best.z && n.id > best.id)) {\n best = n\n }\n }\n return best ? { kind: 'body', nodeId: best.id } : null\n}\n\n/**\n * Combined node + edge hit testing. Order: node handles > edge endpoint\n * handles > visually-topmost body (node or edge, compared by z).\n *\n * For bodies, the rule is paint-order: whichever of (node body, edge\n * body) has the higher z wins, with ties going to edges (edges paint\n * over nodes by convention). This lets users click an edge that runs\n * visually over a large background-style node — the 8px polyline slop\n * keeps the edge's hit zone narrow, so clicks far from the polyline\n * still land on the node underneath.\n */\nexport const hitTestAny = (\n store: CanvasStore,\n worldPoint: Vec2,\n cameraZ: number,\n selectedNodes: ReadonlySet<NodeId> = new Set(),\n selectedEdges: ReadonlySet<EdgeId> = new Set(),\n): Hit | null => {\n // 1. node rotate + resize handles (selected only)\n for (const id of selectedNodes) {\n const n = store.getNode(id)\n if (!n) continue\n if (hitTestRotateHandle(n, worldPoint, cameraZ)) {\n return { kind: 'rotate-handle', nodeId: id }\n }\n const h = hitTestHandles(n, worldPoint, cameraZ)\n if (h) return { kind: 'resize-handle', nodeId: id, handle: h }\n }\n\n // 2. edge handles (selected only) — endpoint reconnect handles and\n // the midpoint reshape handle.\n for (const id of selectedEdges) {\n const partial = hitTestEdge(store, worldPoint, cameraZ, new Set([id]))\n if (\n partial &&\n (partial.kind === 'source-handle' ||\n partial.kind === 'target-handle' ||\n partial.kind === 'midpoint-handle')\n ) {\n return partial\n }\n }\n\n // 3. bodies — visually topmost wins. Edge body / label both expose\n // an `edgeId` field; either competes with the node body via z.\n const nodeHit = hitTestPoint(store, worldPoint, cameraZ, selectedNodes)\n const edgeHit = hitTestEdge(store, worldPoint, cameraZ)\n if (nodeHit && edgeHit && 'edgeId' in edgeHit) {\n const nodeZ = store.getNode(nodeHit.nodeId)?.z ?? 0\n const edgeZ = store.getEdge(edgeHit.edgeId)?.z ?? 0\n return edgeZ >= nodeZ ? edgeHit : nodeHit\n }\n return nodeHit ?? edgeHit\n}\n\n/**\n * Returns ids of all nodes whose (rotated) rect intersects the given rect.\n * Used for marquee selection.\n */\nexport const marqueeNodes = (store: CanvasStore, rect: WorldRect): NodeId[] => {\n const candidates = store.querySpatial({ rect }).nodes\n const result: NodeId[] = []\n for (const id of candidates) {\n const n = store.getNode(id)\n if (!n) continue\n if (nodeIntersectsRect(n, rect)) result.push(id)\n }\n return result\n}\n","import type { CanvasStore } from '../store'\nimport { SCHEMA_VERSION, asEdgeId, asNodeId, isAttached } from '../types'\nimport type { Edge, EdgeEnd, EdgeId, Node, NodeId, Vec2 } from '../types'\n\n/**\n * Clipboard serialization — see ARCHITECTURE.md §13 (copy/paste).\n *\n * Captures the selected nodes plus the edges *between* them (edges\n * crossing the selection are dropped — same rule as tldraw/excalidraw).\n * Pure functions; no clipboard-API I/O. The store wraps these with\n * `navigator.clipboard.{write,read}` calls.\n */\n\nexport type SerializedClipboard = {\n /** Schema version stamped at copy time. */\n v: number\n /** Source clientId — diagnostic only; not used for paste. */\n clientId: string\n /** Tagged so we can tell our payload apart from arbitrary JSON. */\n kind: 'canvas-harness/clipboard'\n nodes: Node[]\n edges: Edge[]\n}\n\n/**\n * Builds a clipboard payload from the store's current selection. Pure\n * — no I/O, no clipboard API. Useful for programmatic copy-paste\n * (snapshots, AI-driven duplication, drag-from-sidebar, ...).\n *\n * Edges crossing the selection boundary (only one endpoint in the\n * selection) are dropped. Edges with `worldPoint` endpoints are kept.\n *\n * @example\n * const clip = serializeSelection(store)\n * localStorage.setItem('clipboard', JSON.stringify(clip))\n */\nexport const serializeSelection = (store: CanvasStore): SerializedClipboard => {\n const selectedIds = store.getSelection()\n const selectedNodeIds = new Set<NodeId>()\n for (const id of selectedIds) {\n if (store.getNode(id as NodeId)) selectedNodeIds.add(id as NodeId)\n }\n const nodes: Node[] = []\n for (const id of selectedNodeIds) {\n const n = store.getNode(id)\n if (n) nodes.push(n)\n }\n // Edges: include if either both endpoints are in the selection (or\n // free-floating). Drop edges that cross the selection boundary.\n const edges: Edge[] = []\n for (const id of selectedIds) {\n const e = store.getEdge(id as EdgeId)\n if (e && bothEndsInsideSelection(e, selectedNodeIds)) edges.push(e)\n }\n // Also include any edges *between* selected nodes, even if not in the\n // selection itself — matches user expectation: \"copy this cluster\".\n for (const e of store.getAllEdges()) {\n if (edges.includes(e)) continue\n if (bothEndsInsideSelection(e, selectedNodeIds)) edges.push(e)\n }\n return {\n v: SCHEMA_VERSION,\n clientId: store.clientId,\n kind: 'canvas-harness/clipboard',\n nodes,\n edges,\n }\n}\n\nconst bothEndsInsideSelection = (edge: Edge, ids: ReadonlySet<NodeId>): boolean => {\n return endInside(edge.source, ids) && endInside(edge.target, ids)\n}\nconst endInside = (end: EdgeEnd, ids: ReadonlySet<NodeId>): boolean => {\n if (!isAttached(end)) return true // free-floating endpoint paste-safe\n return ids.has(end.nodeId)\n}\n\nexport type DeserializeOptions = {\n /**\n * Relative world-space offset added to every pasted node's `x/y`\n * (and to free-floating edge endpoints). Takes precedence over\n * `at` when both are passed. Default `(20, 20)` when neither is\n * given.\n */\n offset?: Vec2\n /**\n * Absolute world-space target — the *center* of the pasted bbox\n * lands here. Used by `paste()` to place the paste at the cursor;\n * pass directly for programmatic absolute placement. Ignored if\n * `offset` is also set.\n */\n at?: Vec2\n /** Override the selection on the store after applying. Default true. */\n select?: boolean\n}\n\n/**\n * Bounding-box center of a clip's node rects (pre-offset). Used to\n * translate an absolute `at` target into the per-node offset that\n * lands the paste's visual center on that point.\n */\nconst clipBboxCenter = (nodes: Node[]): Vec2 => {\n if (nodes.length === 0) return { x: 0, y: 0 }\n let minX = Number.POSITIVE_INFINITY\n let minY = Number.POSITIVE_INFINITY\n let maxX = Number.NEGATIVE_INFINITY\n let maxY = Number.NEGATIVE_INFINITY\n for (const n of nodes) {\n if (n.x < minX) minX = n.x\n if (n.y < minY) minY = n.y\n if (n.x + n.w > maxX) maxX = n.x + n.w\n if (n.y + n.h > maxY) maxY = n.y + n.h\n }\n return { x: (minX + maxX) / 2, y: (minY + maxY) / 2 }\n}\n\n/**\n * Applies a clipboard payload to the store. New ids are minted; edge\n * endpoints are rewired; the resulting nodes + edges become the new\n * selection by default. Positioning precedence:\n *\n * 1. `opts.offset` (relative) — used as-is.\n * 2. `opts.at` (absolute) — offset computed so the clip's bbox\n * center lands on this point.\n * 3. Default — relative `(20, 20)` offset.\n *\n * Free-floating edge endpoints (`{ worldPoint }`) also receive the\n * offset so an edge with an unattached end stays connected to the\n * surrounding nodes after the paste.\n *\n * One `store.batch` — one undo step.\n *\n * @example\n * // Restore from localStorage:\n * const clip = JSON.parse(localStorage.getItem('clipboard')!)\n * if (isCanvasHarnessClipboard(clip)) deserializeClipboard(store, clip)\n */\nexport const deserializeClipboard = (\n store: CanvasStore,\n clip: SerializedClipboard,\n opts: DeserializeOptions = {},\n): NodeId[] => {\n let offset: Vec2\n if (opts.offset) {\n offset = opts.offset\n } else if (opts.at && clip.nodes.length > 0) {\n const center = clipBboxCenter(clip.nodes)\n offset = { x: opts.at.x - center.x, y: opts.at.y - center.y }\n } else {\n offset = { x: 20, y: 20 }\n }\n const select = opts.select ?? true\n\n // Old → new id maps.\n const nodeMap = new Map<NodeId, NodeId>()\n const edgeMap = new Map<EdgeId, EdgeId>()\n for (const n of clip.nodes) nodeMap.set(n.id, asNodeId(store.generateId()))\n for (const e of clip.edges) edgeMap.set(e.id, asEdgeId(store.generateId()))\n\n const remappedNodes: Node[] = clip.nodes.map(n => ({\n ...n,\n id: nodeMap.get(n.id)!,\n x: n.x + offset.x,\n y: n.y + offset.y,\n }))\n const remapEnd = (end: EdgeEnd): EdgeEnd => {\n if (!isAttached(end)) {\n // Free-floating endpoint — keep it visually attached to the\n // pasted neighbourhood by applying the same offset the nodes\n // got. Without this, the edge end stays at the original world\n // point and the connection visually stretches.\n return { worldPoint: { x: end.worldPoint.x + offset.x, y: end.worldPoint.y + offset.y } }\n }\n const newId = nodeMap.get(end.nodeId)\n return newId ? { nodeId: newId, localOffset: end.localOffset } : end\n }\n const remappedEdges: Edge[] = clip.edges.map(e => ({\n ...e,\n id: edgeMap.get(e.id)!,\n source: remapEnd(e.source),\n target: remapEnd(e.target),\n }))\n\n store.batch(() => {\n for (const n of remappedNodes) store.addNode(n)\n for (const e of remappedEdges) store.addEdge(e)\n })\n\n const ids = remappedNodes.map(n => n.id)\n if (select) store.setSelection([...ids, ...remappedEdges.map(e => e.id)])\n return ids\n}\n\n/**\n * Type guard — verifies a parsed JSON blob is a clipboard payload from\n * this library, not arbitrary JSON pasted from elsewhere.\n */\nexport const isCanvasHarnessClipboard = (raw: unknown): raw is SerializedClipboard => {\n if (!raw || typeof raw !== 'object') return false\n const r = raw as Record<string, unknown>\n return r.kind === 'canvas-harness/clipboard' && Array.isArray(r.nodes) && Array.isArray(r.edges)\n}\n","import type { CanvasStore } from '../store'\nimport type { EdgeId, NodeId } from '../types'\nimport {\n type DeserializeOptions,\n type SerializedClipboard,\n deserializeClipboard,\n isCanvasHarnessClipboard,\n serializeSelection,\n} from './serialize'\n\nexport type {\n DeserializeOptions,\n SerializedClipboard,\n} from './serialize'\nexport { deserializeClipboard, isCanvasHarnessClipboard, serializeSelection } from './serialize'\n\nconst MIME_NATIVE = 'application/x-canvas-harness+json'\nconst MIME_TEXT = 'text/plain'\n\n/**\n * Copies the current selection to the system clipboard. Writes both a\n * native MIME (`application/x-canvas-harness+json`) and a `text/plain`\n * fallback (concatenated node contents) so paste works in non-canvas\n * destinations too.\n *\n * The `<Canvas>` component already wires this to Cmd/Ctrl+C — call\n * directly only if you're building a custom copy button.\n *\n * @example\n * <button onClick={() => copy(store)}>Copy</button>\n */\nexport const copy = async (store: CanvasStore): Promise<SerializedClipboard> => {\n const clip = serializeSelection(store)\n await writeClipboard(clip)\n return clip\n}\n\n/**\n * Copy + remove the selection in one undoable batch. Same as\n * Cmd/Ctrl+X.\n *\n * @example\n * <button onClick={() => cut(store)}>Cut</button>\n */\nexport const cut = async (store: CanvasStore): Promise<SerializedClipboard> => {\n const clip = await copy(store)\n store.batch(() => {\n for (const n of clip.nodes) store.removeNode(n.id)\n for (const e of clip.edges) store.removeEdge(e.id)\n })\n return clip\n}\n\n/**\n * Paste from the system clipboard (or a supplied payload). Every node\n * + edge gets a fresh id; edge endpoints rewire to the new ids; the\n * resulting nodes + edges become the new selection. Wrapped in one\n * undoable batch.\n *\n * Positioning, in precedence order:\n * 1. `opts.offset` — relative offset, used as-is.\n * 2. `opts.at` — absolute target; the paste's bbox center lands here.\n * 3. The store's current cursor (`interactionState.pointer`) — the\n * paste lands centered under the cursor. This is the default\n * `paste(store)` behavior on a Cmd+V keybind.\n * 4. Fallback `(20, 20)` relative offset when nothing else is known\n * (e.g. fresh session with no pointermove yet).\n *\n * Returns the new node ids on success, or `null` if the clipboard\n * didn't contain a canvas-harness payload.\n *\n * @example\n * <button onClick={() => paste(store)}>Paste</button>\n *\n * @example\n * // Programmatic paste at a specific world point:\n * paste(store, savedClip, { at: { x: 300, y: 200 }, select: false })\n */\nexport const paste = async (\n store: CanvasStore,\n payload?: SerializedClipboard,\n opts?: DeserializeOptions,\n): Promise<(NodeId | EdgeId)[] | null> => {\n const clip = payload ?? (await readClipboard())\n if (!clip) return null\n // Cursor-as-default: when the caller didn't specify positioning,\n // and the store has tracked the pointer at least once, paste at\n // the cursor's world position. deserializeClipboard handles the\n // bbox-center math.\n let effective = opts\n if (!opts?.offset && !opts?.at) {\n const pointer = store.getInteractionState().pointer\n if (pointer) {\n effective = { ...opts, at: { x: pointer.worldX, y: pointer.worldY } }\n }\n }\n const ids = deserializeClipboard(store, clip, effective)\n return ids\n}\n\nconst writeClipboard = async (clip: SerializedClipboard): Promise<void> => {\n if (typeof navigator === 'undefined' || !navigator.clipboard) return\n const json = JSON.stringify(clip)\n const text = clip.nodes\n .map(n => n.content ?? '')\n .filter(s => s.length > 0)\n .join('\\n')\n // navigator.clipboard.write expects ClipboardItem; not all engines\n // support arbitrary mime types. We dual-write best-effort.\n type ClipboardItemCtor = new (data: Record<string, Blob>) => ClipboardItem\n const W = (globalThis as { ClipboardItem?: ClipboardItemCtor }).ClipboardItem\n if (W && navigator.clipboard.write) {\n try {\n const item = new W({\n [MIME_NATIVE]: new Blob([json], { type: MIME_NATIVE }),\n [MIME_TEXT]: new Blob([text], { type: MIME_TEXT }),\n })\n await navigator.clipboard.write([item])\n return\n } catch {\n // Fall through to text-only writeText.\n }\n }\n if (navigator.clipboard.writeText) await navigator.clipboard.writeText(json)\n}\n\nconst readClipboard = async (): Promise<SerializedClipboard | null> => {\n if (typeof navigator === 'undefined' || !navigator.clipboard) return null\n // Prefer the native MIME via clipboard.read; fall back to readText.\n if (navigator.clipboard.read) {\n try {\n const items = await navigator.clipboard.read()\n for (const item of items) {\n if (item.types.includes(MIME_NATIVE)) {\n const blob = await item.getType(MIME_NATIVE)\n const text = await blob.text()\n const parsed = JSON.parse(text)\n if (isCanvasHarnessClipboard(parsed)) return parsed\n }\n }\n } catch {\n // Fall through to readText.\n }\n }\n if (navigator.clipboard.readText) {\n try {\n const text = await navigator.clipboard.readText()\n if (!text.trim().startsWith('{')) return null\n const parsed = JSON.parse(text)\n if (isCanvasHarnessClipboard(parsed)) return parsed\n } catch {\n return null\n }\n }\n return null\n}\n","import { computeEdgeGeometry } from '../edges'\nimport { drawEdge } from '../edges/draw'\nimport type { AssetCache } from '../render/assets'\nimport { paintIconNode, paintImageNode } from '../render/assets'\nimport { drawShape, isDrawablePrimitive } from '../render/shapes'\nimport type { ThemeResolver } from '../render/shapes'\nimport { drawWithNodeTransform } from '../render/transform'\nimport { nodeAABB } from '../spatial'\nimport type { CanvasStore } from '../store'\nimport {\n DEFAULT_HIGHLIGHT_COLOR,\n DEFAULT_TEXT_COLOR,\n FONT_SIZE_MAP,\n getOrRenderTextBitmap,\n} from '../text'\nimport type { Edge, Node, NodeId } from '../types'\n\n/**\n * PNG export — see ARCHITECTURE.md §13. Paints the requested set of\n * nodes + edges into an offscreen canvas at logical coords; returns a\n * Blob (image/png).\n */\nexport type ExportOptions = {\n /** Bitmap scale multiplier — defaults to 2 for retina-ish output. */\n scale?: number\n /** Padding (logical px) around the bounding rect. Default 16. */\n padding?: number\n /** Skip the background fill. Default false. */\n transparentBackground?: boolean\n /** Background color when not transparent. Default white. */\n backgroundColor?: string\n /** Theme resolver, same one passed to the live renderer. */\n theme?: ThemeResolver\n /**\n * Renderer-owned asset cache. When provided, `image` and `icon`\n * nodes paint from the same decoded bitmaps the live canvas uses.\n * When omitted, those node types are skipped (back-compat).\n *\n * Usage: `exportSelection(store, { assetCache: renderer.getAssetCache() })`.\n */\n assetCache?: AssetCache\n}\n\nconst DEFAULT_SCALE = 2\nconst DEFAULT_PADDING = 16\nconst DEFAULT_BACKGROUND = '#ffffff'\nconst MIN_READABLE_FONT_PX = 3\n\n/**\n * Renders the current selection to a PNG. Returns a `Blob` you can\n * download, upload, or paste somewhere.\n *\n * Bounding rect is computed from the selected nodes; edges between\n * selected nodes are included, edges crossing the boundary are\n * dropped.\n *\n * @example\n * // Download the selection as a PNG file.\n * const blob = await exportSelection(store, { scale: 2 })\n * const url = URL.createObjectURL(blob)\n * Object.assign(document.createElement('a'), {\n * href: url, download: 'scene.png',\n * }).click()\n * URL.revokeObjectURL(url)\n *\n * @example\n * // Transparent PNG for slide-deck overlays.\n * const blob = await exportSelection(store, { transparentBackground: true })\n */\nexport const exportSelection = async (\n store: CanvasStore,\n opts: ExportOptions = {},\n): Promise<Blob> => {\n const ids = store.getSelection()\n const nodeIds = new Set<NodeId>()\n for (const id of ids) {\n if (store.getNode(id as NodeId)) nodeIds.add(id as NodeId)\n }\n return exportNodeSet(store, nodeIds, opts)\n}\n\n/**\n * Renders an arbitrary world-space viewport to a PNG. Use to capture\n * the current screen, a minimap, or a specific region.\n *\n * @example\n * const viewport = worldViewport(staticSurface, store.getCamera())\n * const blob = await exportViewport(store, viewport)\n */\nexport const exportViewport = async (\n store: CanvasStore,\n viewport: { x: number; y: number; w: number; h: number },\n opts: ExportOptions = {},\n): Promise<Blob> => {\n const scale = opts.scale ?? DEFAULT_SCALE\n const padding = opts.padding ?? 0\n const ctx = makeContext(viewport.w + padding * 2, viewport.h + padding * 2, scale, opts)\n ctx.translate(-viewport.x + padding, -viewport.y + padding)\n paintScene(\n ctx,\n store,\n store.getAllNodes().filter((n: Node) => intersects(n, viewport)),\n scale,\n opts,\n )\n return toBlob(ctx.canvas)\n}\n\nconst exportNodeSet = async (\n store: CanvasStore,\n nodeIds: ReadonlySet<NodeId>,\n opts: ExportOptions,\n): Promise<Blob> => {\n if (nodeIds.size === 0) {\n // Empty selection — emit a 1×1 transparent png so callers don't crash.\n const c = document.createElement('canvas')\n c.width = 1\n c.height = 1\n return toBlob(c)\n }\n const nodes: Node[] = []\n for (const id of nodeIds) {\n const n = store.getNode(id)\n if (n) nodes.push(n)\n }\n const padding = opts.padding ?? DEFAULT_PADDING\n const scale = opts.scale ?? DEFAULT_SCALE\n const bbox = unionBounds(nodes)\n const w = bbox.w + padding * 2\n const h = bbox.h + padding * 2\n\n const ctx = makeContext(w, h, scale, opts)\n ctx.translate(-bbox.x + padding, -bbox.y + padding)\n\n // Edges that connect two selected nodes.\n const edges: Edge[] = []\n for (const e of store.getAllEdges()) {\n if (bothEndsInside(e, nodeIds)) edges.push(e)\n }\n paintScene(ctx, store, nodes, scale, opts, edges)\n return toBlob(ctx.canvas)\n}\n\nconst makeContext = (\n cssW: number,\n cssH: number,\n scale: number,\n opts: ExportOptions,\n): CanvasRenderingContext2D => {\n const canvas = document.createElement('canvas')\n canvas.width = Math.max(1, Math.ceil(cssW * scale))\n canvas.height = Math.max(1, Math.ceil(cssH * scale))\n const ctx = canvas.getContext('2d')\n if (!ctx) throw new Error('Canvas 2D context unavailable')\n if (!opts.transparentBackground) {\n ctx.fillStyle = opts.backgroundColor ?? DEFAULT_BACKGROUND\n ctx.fillRect(0, 0, canvas.width, canvas.height)\n }\n ctx.scale(scale, scale)\n return ctx\n}\n\n/**\n * Walks the node + edge set and paints them. Uses the same primitives\n * as the live renderer so output matches the canvas.\n */\nconst paintScene = (\n ctx: CanvasRenderingContext2D,\n store: CanvasStore,\n nodes: Node[],\n scale: number,\n opts: ExportOptions,\n edges?: Edge[],\n): void => {\n const theme = opts.theme\n const assetCache = opts.assetCache\n for (const node of nodes) {\n drawWithNodeTransform(ctx, node, () => {\n if (isDrawablePrimitive(node.type)) drawShape(ctx, node, scale, theme)\n if (assetCache) {\n if (node.type === 'image') paintImageNode(ctx, node, assetCache, theme)\n else if (node.type === 'icon') paintIconNode(ctx, node, assetCache, scale, theme)\n }\n paintContent(ctx, node)\n })\n }\n const edgeList = edges ?? store.getAllEdges()\n const getNode = (id: NodeId): Node | undefined => store.getNode(id)\n for (const edge of edgeList) {\n const geom = computeEdgeGeometry(edge, getNode)\n if (!geom) continue\n const sourceNode = geom.sourceNodeId ? (getNode(geom.sourceNodeId) ?? null) : null\n const targetNode = geom.targetNodeId ? (getNode(geom.targetNodeId) ?? null) : null\n drawEdge(ctx, edge, geom, sourceNode, targetNode, scale, theme)\n }\n}\n\nconst paintContent = (ctx: CanvasRenderingContext2D, node: Node): void => {\n if (!node.content || !node.content.trim()) return\n const style = node.style\n const fontSize = style?.fontSize ?? 'M'\n // Same readability skip as the live renderer.\n if (FONT_SIZE_MAP[fontSize] * 1 < MIN_READABLE_FONT_PX) return\n const bitmap = getOrRenderTextBitmap({\n id: node.id,\n text: node.content,\n width: node.w,\n height: node.h,\n zoom: 1,\n dpr: 2,\n isMoving: false,\n align: style?.textAlign ?? 'center',\n fontFamily: style?.fontFamily ?? 'handwriting',\n fontSize,\n textStyle: style?.textStyle ?? 'normal',\n textColor: style?.textColor ?? DEFAULT_TEXT_COLOR,\n highlightColor: DEFAULT_HIGHLIGHT_COLOR,\n })\n if (!bitmap) return\n ctx.drawImage(bitmap.canvas, 0, 0, node.w, node.h)\n}\n\nconst toBlob = (canvas: HTMLCanvasElement): Promise<Blob> =>\n new Promise((resolve, reject) => {\n canvas.toBlob(b => (b ? resolve(b) : reject(new Error('toBlob returned null'))), 'image/png')\n })\n\nconst unionBounds = (nodes: Node[]): { x: number; y: number; w: number; h: number } => {\n let minX = Number.POSITIVE_INFINITY\n let minY = Number.POSITIVE_INFINITY\n let maxX = Number.NEGATIVE_INFINITY\n let maxY = Number.NEGATIVE_INFINITY\n for (const n of nodes) {\n const r = nodeAABB(n)\n if (r.x < minX) minX = r.x\n if (r.y < minY) minY = r.y\n if (r.x + r.w > maxX) maxX = r.x + r.w\n if (r.y + r.h > maxY) maxY = r.y + r.h\n }\n return { x: minX, y: minY, w: maxX - minX, h: maxY - minY }\n}\n\nconst intersects = (n: Node, vp: { x: number; y: number; w: number; h: number }): boolean => {\n const a = nodeAABB(n)\n return a.x < vp.x + vp.w && a.x + a.w > vp.x && a.y < vp.y + vp.h && a.y + a.h > vp.y\n}\n\nconst bothEndsInside = (e: Edge, ids: ReadonlySet<NodeId>): boolean => {\n const inEnd = (end: typeof e.source): boolean => 'nodeId' in end && ids.has(end.nodeId)\n return inEnd(e.source) && inEnd(e.target)\n}\n","import { applySvgColor, extractSvgDimensions } from '../assets'\nimport { computeEdgeGeometry } from '../edges'\nimport { nodeAABB } from '../spatial'\nimport type { CanvasStore } from '../store'\nimport { FONT_FAMILY_MAP, FONT_SIZE_MAP } from '../text'\nimport type { Edge, IconNodeData, ImageNodeData, Node, NodeId } from '../types'\n\n/**\n * SVG export — see ARCHITECTURE.md §13.\n *\n * **Scope**: matches PNG export for shape geometry + edge geometry.\n * Image nodes are inlined as `<image href=\"…\">` (data URI passes\n * through verbatim). Icon nodes nest their sanitized SVG markup inside\n * a `<g transform>`, preserving vector quality and the `iconColor`\n * recolor knob.\n *\n * Markdown content is emitted as **plain text** (no inline bold /\n * italic / highlight). SVG `<text>` doesn't support our markdown\n * dialect without tspan positioning math; deferred to v2. PNG export\n * preserves all markdown styling via the bitmap pipeline.\n */\nexport type SvgExportOptions = {\n padding?: number\n transparentBackground?: boolean\n backgroundColor?: string\n}\n\nconst DEFAULT_PADDING = 16\nconst DEFAULT_BACKGROUND = '#ffffff'\n\n/**\n * Renders the current selection to an SVG string. Synchronous —\n * unlike PNG, no canvas roundtrip needed.\n *\n * **Caveat:** SVG `<text>` doesn't support our markdown dialect, so\n * `**bold**` / `==hl==` etc. render as plain text with the syntax\n * stripped. PNG export preserves all markdown via the bitmap pipeline.\n *\n * @example\n * const svg = exportSelectionSvg(store)\n * const blob = new Blob([svg], { type: 'image/svg+xml' })\n */\nexport const exportSelectionSvg = (store: CanvasStore, opts: SvgExportOptions = {}): string => {\n const ids = store.getSelection()\n const nodeIds = new Set<NodeId>()\n for (const id of ids) {\n if (store.getNode(id as NodeId)) nodeIds.add(id as NodeId)\n }\n return exportNodeSetSvg(store, nodeIds, opts)\n}\n\nconst exportNodeSetSvg = (\n store: CanvasStore,\n nodeIds: ReadonlySet<NodeId>,\n opts: SvgExportOptions,\n): string => {\n const padding = opts.padding ?? DEFAULT_PADDING\n if (nodeIds.size === 0) {\n return `<svg xmlns=\"http://www.w3.org/2000/svg\" width=\"1\" height=\"1\" />`\n }\n const nodes: Node[] = []\n for (const id of nodeIds) {\n const n = store.getNode(id)\n if (n) nodes.push(n)\n }\n const bbox = unionBounds(nodes)\n const w = Math.ceil(bbox.w + padding * 2)\n const h = Math.ceil(bbox.h + padding * 2)\n const tx = -bbox.x + padding\n const ty = -bbox.y + padding\n\n const bgRect = opts.transparentBackground\n ? ''\n : `<rect width=\"100%\" height=\"100%\" fill=\"${escapeAttr(opts.backgroundColor ?? DEFAULT_BACKGROUND)}\" />`\n\n const edges: Edge[] = []\n for (const e of store.getAllEdges()) {\n if (bothEndsInside(e, nodeIds)) edges.push(e)\n }\n\n const parts: string[] = []\n parts.push(\n `<svg xmlns=\"http://www.w3.org/2000/svg\" width=\"${w}\" height=\"${h}\" viewBox=\"0 0 ${w} ${h}\">`,\n )\n parts.push(bgRect)\n parts.push(`<g transform=\"translate(${tx} ${ty})\">`)\n for (const node of nodes) parts.push(renderNodeSvg(node))\n for (const edge of edges) parts.push(renderEdgeSvg(edge, store))\n parts.push('</g>')\n parts.push('</svg>')\n return parts.join('')\n}\n\nconst renderNodeSvg = (node: Node): string => {\n const fill = node.style?.backgroundColor ?? '#ffffff'\n const stroke = node.style?.strokeColor ?? '#0f172a'\n const strokeWidth = node.style?.strokeWidth ?? 1.5\n const opacity = node.style?.opacity ?? 1\n const rotate =\n node.angle !== 0\n ? ` transform=\"rotate(${(node.angle * 180) / Math.PI} ${node.x + node.w / 2} ${node.y + node.h / 2})\"`\n : ''\n\n const text = renderTextSvg(node)\n if (node.type === 'image') {\n return `<g${rotate}>${renderImageNodeSvg(node, opacity)}${text}</g>`\n }\n if (node.type === 'icon') {\n return `<g${rotate}>${renderIconNodeSvg(node, opacity)}${text}</g>`\n }\n\n const shape = renderShapeSvg(node, fill, stroke, strokeWidth, opacity)\n return `<g${rotate}>${shape}${text}</g>`\n}\n\nconst renderImageNodeSvg = (node: Node, opacity: number): string => {\n const data = node.data as ImageNodeData | undefined\n if (!data?.src) return ''\n // `<image href>` accepts data URIs directly; `preserveAspectRatio=\"none\"`\n // mirrors the live renderer's drawImage(0, 0, w, h) which stretches\n // the bitmap to the node rect (matches the no-default-aspect-lock\n // policy for image/icon resize).\n return `<image href=\"${escapeAttr(data.src)}\" x=\"${node.x}\" y=\"${node.y}\" width=\"${node.w}\" height=\"${node.h}\" preserveAspectRatio=\"none\" opacity=\"${opacity}\" />`\n}\n\nconst renderIconNodeSvg = (node: Node, opacity: number): string => {\n const data = node.data as IconNodeData | undefined\n if (!data?.src) return ''\n // Apply the same `currentColor` substitution the live renderer does\n // via getIcon(src, color, …). The sanitized markup is already\n // script-free (add-time guarantee).\n const colored = node.style?.iconColor ? applySvgColor(data.src, node.style.iconColor) : data.src\n // Nest the source <svg> inside a <g translate+scale>. The inner SVG\n // keeps its viewBox so vector content scales cleanly to the node\n // rect. extractSvgDimensions falls back to 24×24 if width/height/\n // viewBox are missing — same fallback the addSvg path uses.\n const dim = extractSvgDimensions(colored)\n const sx = node.w / dim.w\n const sy = node.h / dim.h\n return `<g transform=\"translate(${node.x} ${node.y}) scale(${sx} ${sy})\" opacity=\"${opacity}\">${colored}</g>`\n}\n\nconst renderShapeSvg = (\n node: Node,\n fill: string,\n stroke: string,\n strokeWidth: number,\n opacity: number,\n): string => {\n const attrs = (extra: string): string =>\n `fill=\"${escapeAttr(fill)}\" stroke=\"${escapeAttr(stroke)}\" stroke-width=\"${strokeWidth}\" opacity=\"${opacity}\"${extra}`\n switch (node.type) {\n case 'rect': {\n const r = (node.style?.roundness ?? 0) * 4\n return `<rect x=\"${node.x}\" y=\"${node.y}\" width=\"${node.w}\" height=\"${node.h}\" rx=\"${r}\" ry=\"${r}\" ${attrs('')} />`\n }\n case 'ellipse':\n return `<ellipse cx=\"${node.x + node.w / 2}\" cy=\"${node.y + node.h / 2}\" rx=\"${node.w / 2}\" ry=\"${node.h / 2}\" ${attrs('')} />`\n case 'diamond': {\n const cx = node.x + node.w / 2\n const cy = node.y + node.h / 2\n const pts = `${cx},${node.y} ${node.x + node.w},${cy} ${cx},${node.y + node.h} ${node.x},${cy}`\n return `<polygon points=\"${pts}\" ${attrs('')} />`\n }\n case 'tag': {\n // Approximate — emit the bounding rect. Full tag geometry is not\n // worth porting to the SVG export path.\n return `<rect x=\"${node.x}\" y=\"${node.y}\" width=\"${node.w}\" height=\"${node.h}\" rx=\"6\" ry=\"6\" ${attrs('')} />`\n }\n case 'capsule':\n case 'thought-cloud':\n case 'layered-rect':\n case 'layered-ellipse':\n case 'layered-diamond': {\n // Composites: emit a bounding rect placeholder. PNG export uses\n // the canvas renderer directly and renders these correctly.\n return `<rect x=\"${node.x}\" y=\"${node.y}\" width=\"${node.w}\" height=\"${node.h}\" rx=\"4\" ry=\"4\" ${attrs('')} />`\n }\n case 'text':\n return ''\n default:\n return `<rect x=\"${node.x}\" y=\"${node.y}\" width=\"${node.w}\" height=\"${node.h}\" fill=\"none\" stroke=\"${escapeAttr(stroke)}\" stroke-dasharray=\"4 4\" stroke-width=\"1\" opacity=\"0.5\" />`\n }\n}\n\nconst renderTextSvg = (node: Node): string => {\n if (!node.content || !node.content.trim()) return ''\n const fontSize = FONT_SIZE_MAP[node.style?.fontSize ?? 'M']\n const family = FONT_FAMILY_MAP[node.style?.fontFamily ?? 'handwriting']\n const color = node.style?.textColor ?? '#1f2937'\n const align = node.style?.textAlign ?? 'center'\n const anchor = align === 'left' ? 'start' : align === 'right' ? 'end' : 'middle'\n // Plain text — see header doc. Strip markdown syntax for legibility\n // (so '**bold**' renders as 'bold' not '**bold**').\n const lines = node.content.split('\\n').map(stripMarkdown)\n const cx = node.x + (align === 'left' ? 8 : align === 'right' ? node.w - 8 : node.w / 2)\n const totalH = lines.length * fontSize * 1.25\n const startY = node.y + (node.h - totalH) / 2 + fontSize * 0.8\n const tspans = lines\n .map(\n (line, i) =>\n `<tspan x=\"${cx}\" y=\"${startY + i * fontSize * 1.25}\">${escapeText(line)}</tspan>`,\n )\n .join('')\n return `<text fill=\"${escapeAttr(color)}\" font-family=\"${escapeAttr(family)}\" font-size=\"${fontSize}\" text-anchor=\"${anchor}\">${tspans}</text>`\n}\n\nconst renderEdgeSvg = (edge: Edge, store: CanvasStore): string => {\n const getNode = (id: NodeId): Node | undefined => store.getNode(id)\n const geom = computeEdgeGeometry(edge, getNode)\n if (!geom) return ''\n const samples = geom.samples\n if (samples.length < 2) return ''\n const d = samples\n .map((p, i) => `${i === 0 ? 'M' : 'L'}${p.x.toFixed(1)} ${p.y.toFixed(1)}`)\n .join(' ')\n const stroke = edge.style?.strokeColor ?? '#0f172a'\n const strokeWidth = edge.style?.strokeWidth ?? 1.5\n return `<path d=\"${d}\" fill=\"none\" stroke=\"${escapeAttr(stroke)}\" stroke-width=\"${strokeWidth}\" />`\n}\n\nconst stripMarkdown = (s: string): string =>\n s\n .replace(/\\*\\*(.*?)\\*\\*/g, '$1')\n .replace(/__(.*?)__/g, '$1')\n .replace(/~~(.*?)~~/g, '$1')\n .replace(/==(.*?)==/g, '$1')\n .replace(/`(.*?)`/g, '$1')\n .replace(/\\*(.*?)\\*/g, '$1')\n .replace(/\\[(.*?)\\]\\(.*?\\)/g, '$1')\n\nconst escapeText = (s: string): string =>\n s.replace(/&/g, '&amp;').replace(/</g, '&lt;').replace(/>/g, '&gt;')\nconst escapeAttr = (s: string): string => escapeText(s).replace(/\"/g, '&quot;')\n\nconst unionBounds = (nodes: Node[]): { x: number; y: number; w: number; h: number } => {\n let minX = Number.POSITIVE_INFINITY\n let minY = Number.POSITIVE_INFINITY\n let maxX = Number.NEGATIVE_INFINITY\n let maxY = Number.NEGATIVE_INFINITY\n for (const n of nodes) {\n const r = nodeAABB(n)\n if (r.x < minX) minX = r.x\n if (r.y < minY) minY = r.y\n if (r.x + r.w > maxX) maxX = r.x + r.w\n if (r.y + r.h > maxY) maxY = r.y + r.h\n }\n return { x: minX, y: minY, w: maxX - minX, h: maxY - minY }\n}\n\nconst bothEndsInside = (e: Edge, ids: ReadonlySet<NodeId>): boolean => {\n const inEnd = (end: typeof e.source): boolean => 'nodeId' in end && ids.has(end.nodeId)\n return inEnd(e.source) && inEnd(e.target)\n}\n","import type { CanvasStore } from '../store'\nimport { isAttached } from '../types'\nimport type { Edge, EdgeEnd, EdgeId, Node, NodeId } from '../types'\n\n/**\n * AI scene context — see ARCHITECTURE.md §13.\n *\n * Returns a human- or machine-readable snapshot of the scene for use\n * as a system-prompt payload or AI tool-call argument. **Markdown is\n * the prose form** (better for LLM comprehension token-per-token);\n * JSON is the structured form for downstream automation.\n *\n * Output keeps it tight: each node + edge becomes one line, with\n * truncation when the scene is large.\n */\nexport type GetContextOptions = {\n format?: 'markdown' | 'json'\n /** Restrict to the current selection. Default: include the whole scene. */\n selectionOnly?: boolean\n /** Truncate node list at this count. Default 500. */\n maxNodes?: number\n}\n\nconst DEFAULT_MAX_NODES = 500\n\n/**\n * Returns a snapshot of the scene suitable for an LLM system prompt or\n * a tool-call argument.\n *\n * - `format: 'markdown'` (default) — full-text prose summary. Better\n * for LLM token economy.\n * - `format: 'json'` — structured `SceneContextJson` shape; lighter\n * than `SerializedScene` (no internal fields).\n *\n * @example\n * // System prompt\n * const ctx = getContext(store) as string\n * await anthropic.messages.create({\n * system: `Current scene:\\n${ctx}`,\n * ...\n * })\n *\n * @example\n * // JSON for downstream automation\n * const ctx = getContext(store, { format: 'json', selectionOnly: true })\n */\nexport const getContext = (\n store: CanvasStore,\n opts: GetContextOptions = {},\n): string | SceneContextJson => {\n const format = opts.format ?? 'markdown'\n const maxNodes = opts.maxNodes ?? DEFAULT_MAX_NODES\n\n let nodes: Node[]\n let edges: Edge[]\n if (opts.selectionOnly) {\n const ids = new Set(store.getSelection())\n nodes = []\n edges = []\n for (const id of ids) {\n const n = store.getNode(id as NodeId)\n if (n) nodes.push(n)\n else {\n const e = store.getEdge(id as EdgeId)\n if (e) edges.push(e)\n }\n }\n } else {\n nodes = store.getAllNodes()\n edges = store.getAllEdges()\n }\n\n const truncated = nodes.length > maxNodes\n if (truncated) nodes = nodes.slice(0, maxNodes)\n\n if (format === 'json') return toJsonContext(nodes, edges, store, truncated)\n return toMarkdownContext(nodes, edges, store, truncated)\n}\n\n// ----- JSON output ------------------------------------------------------\n\nexport type SceneContextJson = {\n camera: { x: number; y: number; z: number }\n nodes: ContextNode[]\n edges: ContextEdge[]\n truncated: boolean\n}\n\nexport type ContextNode = {\n id: string\n type: string\n x: number\n y: number\n w: number\n h: number\n angle?: number\n content?: string\n style?: Record<string, unknown>\n}\n\nexport type ContextEdge = {\n id: string\n source: string | { x: number; y: number }\n target: string | { x: number; y: number }\n pathStyle?: string\n}\n\nconst toJsonContext = (\n nodes: Node[],\n edges: Edge[],\n store: CanvasStore,\n truncated: boolean,\n): SceneContextJson => {\n const camera = store.getCamera()\n return {\n camera: { x: camera.x, y: camera.y, z: camera.z },\n nodes: nodes.map(n => {\n const out: ContextNode = { id: n.id, type: n.type, x: n.x, y: n.y, w: n.w, h: n.h }\n if (n.angle !== 0) out.angle = n.angle\n if (n.content) out.content = n.content\n if (n.style && Object.keys(n.style).length > 0) out.style = n.style as Record<string, unknown>\n return out\n }),\n edges: edges.map(e => ({\n id: e.id,\n source: serializeEnd(e.source),\n target: serializeEnd(e.target),\n pathStyle: e.pathStyle,\n })),\n truncated,\n }\n}\n\nconst serializeEnd = (end: EdgeEnd): string | { x: number; y: number } => {\n if (isAttached(end)) return end.nodeId\n return { x: end.worldPoint.x, y: end.worldPoint.y }\n}\n\n// ----- Markdown output --------------------------------------------------\n\nconst toMarkdownContext = (\n nodes: Node[],\n edges: Edge[],\n store: CanvasStore,\n truncated: boolean,\n): string => {\n const lines: string[] = []\n const camera = store.getCamera()\n\n lines.push('# Canvas scene')\n lines.push('')\n lines.push(\n `camera at (${formatNumber(camera.x)}, ${formatNumber(camera.y)}) zoom ${formatNumber(camera.z)}`,\n )\n lines.push(`${nodes.length} node(s), ${edges.length} edge(s)`)\n if (truncated) lines.push(`_(truncated to first ${nodes.length} nodes)_`)\n lines.push('')\n\n if (nodes.length > 0) {\n lines.push('## Nodes')\n lines.push('')\n for (const n of nodes) lines.push(`- ${formatNode(n)}`)\n lines.push('')\n }\n\n if (edges.length > 0) {\n lines.push('## Edges')\n lines.push('')\n for (const e of edges) lines.push(`- ${formatEdge(e)}`)\n }\n\n return lines.join('\\n')\n}\n\nconst formatNode = (n: Node): string => {\n const pos = `at (${formatNumber(n.x)}, ${formatNumber(n.y)}) size ${formatNumber(n.w)}×${formatNumber(n.h)}`\n const angle = n.angle !== 0 ? ` rotated ${formatNumber((n.angle * 180) / Math.PI)}°` : ''\n const id = `\\`${n.id}\\``\n const type = `**${n.type}**`\n const content = n.content ? ` — \"${truncateText(n.content, 80)}\"` : ''\n return `${id} ${type} ${pos}${angle}${content}`\n}\n\nconst formatEdge = (e: Edge): string => {\n const id = `\\`${e.id}\\``\n const src = describeEnd(e.source)\n const tgt = describeEnd(e.target)\n const style = e.pathStyle !== 'bezier' ? ` (${e.pathStyle})` : ''\n return `${id} ${src} → ${tgt}${style}`\n}\n\nconst describeEnd = (end: EdgeEnd): string => {\n if (isAttached(end)) return `\\`${end.nodeId}\\``\n return `(${formatNumber(end.worldPoint.x)}, ${formatNumber(end.worldPoint.y)})`\n}\n\nconst formatNumber = (n: number): string => (Number.isInteger(n) ? String(n) : n.toFixed(1))\n\nconst truncateText = (s: string, max: number): string =>\n s.length <= max ? s.replace(/\\n/g, ' ↵ ') : `${s.slice(0, max - 1).replace(/\\n/g, ' ↵ ')}…`\n","/**\n * Op schemas — see ARCHITECTURE.md §13.\n *\n * Hand-written JSON-Schema definitions for the `Op` discriminated\n * union. AI agents use these to validate generated ops before calling\n * `store.applyOp`; tool-use frameworks (Anthropic, OpenAI, Vertex)\n * advertise the schemas as callable tool definitions.\n *\n * Hand-written (not derived from TS) so the schemas survive when the\n * runtime shape evolves without an explicit schema update.\n */\n\nconst Vec2 = {\n type: 'object',\n required: ['x', 'y'],\n properties: { x: { type: 'number' }, y: { type: 'number' } },\n} as const\n\nconst NodeBase = {\n type: 'object',\n required: ['id', 'type', 'x', 'y', 'w', 'h', 'angle', 'z', 'groups'],\n properties: {\n id: {\n type: 'string',\n description: 'Stable id (typically generated via `store.generateId()`).',\n },\n type: {\n type: 'string',\n description:\n 'Node type — rect / ellipse / diamond / tag / capsule / thought-cloud / layered-rect / layered-ellipse / layered-diamond / text / a registered custom type.',\n },\n x: { type: 'number' },\n y: { type: 'number' },\n w: { type: 'number', minimum: 0 },\n h: { type: 'number', minimum: 0 },\n angle: { type: 'number', description: 'Rotation in radians (clockwise).' },\n z: { type: 'number' },\n groups: { type: 'array', items: { type: 'string' } },\n content: { type: 'string', description: 'Markdown content (for text-bearing shapes).' },\n style: { type: 'object', description: 'Style bag — see ARCHITECTURE.md §3.4 (Style type).' },\n hidden: { type: 'boolean' },\n },\n} as const\n\nconst EdgeEnd = {\n oneOf: [\n {\n type: 'object',\n required: ['nodeId', 'localOffset'],\n properties: { nodeId: { type: 'string' }, localOffset: Vec2 },\n },\n {\n type: 'object',\n required: ['worldPoint'],\n properties: { worldPoint: Vec2 },\n },\n ],\n} as const\n\nconst EdgeBase = {\n type: 'object',\n required: ['id', 'source', 'target', 'pathStyle', 'z', 'groups'],\n properties: {\n id: { type: 'string' },\n source: EdgeEnd,\n target: EdgeEnd,\n pathStyle: { type: 'string', enum: ['bezier', 'straight', 'polyline'] },\n z: { type: 'number' },\n groups: { type: 'array', items: { type: 'string' } },\n style: { type: 'object' },\n hidden: { type: 'boolean' },\n },\n} as const\n\nconst GroupBase = {\n type: 'object',\n required: ['id', 'memberIds'],\n properties: {\n id: { type: 'string' },\n memberIds: { type: 'array', items: { type: 'string' } },\n name: { type: 'string' },\n },\n} as const\n\n/**\n * JSON-Schema definitions for every `Op` variant. Use to validate\n * agent-generated ops before calling `store.applyOp`, or to feed into\n * an LLM tool-use loop.\n *\n * @example\n * import Ajv from 'ajv'\n * const ajv = new Ajv()\n * const validate = ajv.compile(opSchemas.nodeAdd)\n * if (validate(generatedOp)) store.applyOp(generatedOp)\n */\nexport const opSchemas = {\n nodeAdd: {\n type: 'object',\n required: ['type', 'node'],\n properties: { type: { const: 'node.add' }, node: NodeBase },\n },\n nodeUpdate: {\n type: 'object',\n required: ['type', 'id', 'patch', 'prev'],\n properties: {\n type: { const: 'node.update' },\n id: { type: 'string' },\n patch: { type: 'object' },\n prev: { type: 'object' },\n },\n },\n nodeRemove: {\n type: 'object',\n required: ['type', 'node'],\n properties: { type: { const: 'node.remove' }, node: NodeBase },\n },\n edgeAdd: {\n type: 'object',\n required: ['type', 'edge'],\n properties: { type: { const: 'edge.add' }, edge: EdgeBase },\n },\n edgeUpdate: {\n type: 'object',\n required: ['type', 'id', 'patch', 'prev'],\n properties: {\n type: { const: 'edge.update' },\n id: { type: 'string' },\n patch: { type: 'object' },\n prev: { type: 'object' },\n },\n },\n edgeRemove: {\n type: 'object',\n required: ['type', 'edge'],\n properties: { type: { const: 'edge.remove' }, edge: EdgeBase },\n },\n groupUpsert: {\n type: 'object',\n required: ['type', 'group'],\n properties: { type: { const: 'group.upsert' }, group: GroupBase, prev: GroupBase },\n },\n groupRemove: {\n type: 'object',\n required: ['type', 'group'],\n properties: { type: { const: 'group.remove' }, group: GroupBase },\n },\n} as const\n\n/**\n * Tool definition in the Anthropic Messages API shape.\n */\nexport type AnthropicToolDef = {\n name: string\n description: string\n input_schema: object\n}\n\n/**\n * Returns op schemas wrapped as Anthropic Messages-API tool\n * definitions. Drop into the `tools` field of a `messages.create`\n * request to let an agent mutate the canvas directly.\n *\n * @example\n * const response = await anthropic.messages.create({\n * model: 'claude-opus-4-7',\n * tools: opSchemasAsAnthropicTools(),\n * messages: [{ role: 'user', content: 'Add a red sticky note' }],\n * })\n * for (const block of response.content) {\n * if (block.type === 'tool_use' && block.name.startsWith('canvas_')) {\n * const op = toOp(block.name, block.input)\n * store.applyOp(op)\n * }\n * }\n */\nexport const opSchemasAsAnthropicTools = (): AnthropicToolDef[] => [\n {\n name: 'canvas_node_add',\n description: 'Add a new node to the canvas.',\n input_schema: opSchemas.nodeAdd,\n },\n {\n name: 'canvas_node_update',\n description: 'Update fields on an existing node.',\n input_schema: opSchemas.nodeUpdate,\n },\n {\n name: 'canvas_node_remove',\n description: 'Remove an existing node (the previous snapshot must be supplied for undo).',\n input_schema: opSchemas.nodeRemove,\n },\n {\n name: 'canvas_edge_add',\n description: 'Add a new edge connecting two nodes (or free world points).',\n input_schema: opSchemas.edgeAdd,\n },\n {\n name: 'canvas_edge_update',\n description: 'Update fields on an existing edge.',\n input_schema: opSchemas.edgeUpdate,\n },\n {\n name: 'canvas_edge_remove',\n description: 'Remove an existing edge.',\n input_schema: opSchemas.edgeRemove,\n },\n]\n","import type { CanvasStore, StoreEventHandler, StoreEventName, Unsubscribe } from '../store'\n\n/**\n * Extension system — see ARCHITECTURE.md §13.9.\n *\n * The escape hatch for features the core won't ship: snap-to-grid,\n * alignment guides, minimap, autosave, AI plugins. Extensions get a\n * store handle + event subscription helper; they can mutate the store\n * (via the regular API), subscribe to events, and clean up on uninstall.\n *\n * Bare-bones by design — anything more (paint hooks, custom handles,\n * shortcut registration) is a v2 concern. Authors who need those today\n * can compose them inside `onInstall` against the store directly.\n */\nexport type ExtensionApi = {\n /** The store the extension is attached to. */\n store: CanvasStore\n /**\n * Subscribe to a store event with automatic cleanup on uninstall —\n * authors don't have to thread their own teardown.\n */\n on<E extends StoreEventName>(event: E, cb: StoreEventHandler<E>): Unsubscribe\n}\n\nexport type Extension = {\n /** Unique name; one extension per name per store. */\n name: string\n /**\n * Called when the extension is installed. May return a cleanup\n * function that runs on uninstall (in addition to auto-unsubscribed\n * listeners registered via `api.on`).\n *\n * `void` in the union is deliberate — extensions whose installer\n * does its work via `api.on` (auto-cleaned-up) don't need to return\n * anything. `undefined | (() => void)` would require an explicit\n * `return undefined`, which is noise. Biome's noConfusingVoidType\n * fires on this pattern; the suppression below is intentional.\n */\n // biome-ignore lint/suspicious/noConfusingVoidType: see comment above\n onInstall(api: ExtensionApi): void | (() => void)\n}\n\n/**\n * Defines an extension. Pure identity — exists for symmetry with\n * `defineNode` and to make call sites read nicely.\n *\n * @example\n * export const snapToGrid = defineExtension({\n * name: 'snap-to-grid',\n * onInstall: api => {\n * api.on('interaction', state => {\n * if (state.mode !== 'dragging') return\n * const snapped = {\n * x: Math.round(state.dragDelta.x / 20) * 20,\n * y: Math.round(state.dragDelta.y / 20) * 20,\n * }\n * api.store.setInteractionState({ dragDelta: snapped })\n * })\n * },\n * })\n */\nexport const defineExtension = (ext: Extension): Extension => ext\n\nconst installed = new WeakMap<CanvasStore, Map<string, () => void>>()\n\n/**\n * Installs an extension against a store. Returns an `uninstall()`\n * function. Re-installing the same name replaces the previous\n * instance.\n *\n * @example\n * useEffect(() => {\n * if (snapEnabled) return installExtension(store, snapToGrid)\n * }, [store, snapEnabled])\n */\nexport const installExtension = (store: CanvasStore, ext: Extension): Unsubscribe => {\n let registry = installed.get(store)\n if (!registry) {\n registry = new Map()\n installed.set(store, registry)\n }\n // Replace existing.\n const existing = registry.get(ext.name)\n if (existing) existing()\n\n const teardownFns: (() => void)[] = []\n const api: ExtensionApi = {\n store,\n on(event, cb) {\n const unsub = store.subscribe(event, cb)\n teardownFns.push(unsub)\n return unsub\n },\n }\n const userTeardown = ext.onInstall(api)\n if (typeof userTeardown === 'function') teardownFns.push(userTeardown)\n\n const teardown = (): void => {\n for (const fn of teardownFns) fn()\n teardownFns.length = 0\n registry?.delete(ext.name)\n }\n registry.set(ext.name, teardown)\n return teardown\n}\n\n/** Test / debug aid: list installed extension names for a store. */\nexport const installedExtensions = (store: CanvasStore): string[] => {\n const registry = installed.get(store)\n return registry ? [...registry.keys()] : []\n}\n","/**\n * @canvas-harness/core\n *\n * Framework-agnostic core for the canvas-harness library.\n * See ARCHITECTURE.md and IMPLEMENTATION.md at the repo root.\n *\n * Phase 1 ships: types, ids, camera, spatial index, store skeleton, codec.\n */\nexport const VERSION = '0.0.0'\n\nexport * from './types'\nexport * from './ids'\nexport * from './camera'\nexport * from './spatial'\nexport * from './edges'\nexport * from './node-types'\nexport * from './text'\nexport * from './edit'\nexport * from './store'\nexport * from './codec'\nexport * from './render'\nexport * from './hit-test'\nexport * from './clipboard'\nexport * from './export'\nexport * from './ai'\nexport * from './assets'\nexport * from './extension'\n"]}
1
+ {"version":3,"sources":["../src/types/primitives.ts","../src/types/edge.ts","../src/types/background.ts","../src/ids/index.ts","../src/camera/index.ts","../src/spatial/aabb.ts","../src/spatial/grid.ts","../src/spatial/node-aabb.ts","../src/edges/project.ts","../src/edges/auto-route.ts","../src/edges/clip.ts","../src/edges/aabb.ts","../src/edges/samples.ts","../src/edges/self-loop.ts","../src/edges/cache.ts","../src/edges/arc-length.ts","../src/edges/midpoint.ts","../src/edges/arrowhead.ts","../src/render/rough/cache.ts","../src/render/shapes/defaults.ts","../src/text/tokens.ts","../src/text/defaults.ts","../src/text/math/loader.ts","../src/text/math/cache.ts","../src/text/measure.ts","../src/text/layout.ts","../src/text/font-epoch.ts","../src/text/render-scale.ts","../src/text/estimate-height.ts","../src/text/paint-canvas.ts","../src/text/bitmap-cache.ts","../src/edges/freehand.ts","../src/edges/draw.ts","../src/node-types/define-node.ts","../src/edit/auto-fit.ts","../src/edit/markdown-shortcuts.ts","../src/edit/textarea-editor.ts","../src/assets/image.ts","../src/assets/svg.ts","../src/store/conflict.ts","../src/store/interaction.ts","../src/store/inverse-op.ts","../src/store/presence.ts","../src/store/store.ts","../src/store/sync.ts","../src/store/palm-rejection.ts","../src/codec/index.ts","../src/render/canvas-setup.ts","../src/render/frame-loop.ts","../src/render/assets/cache.ts","../src/render/assets/paint.ts","../src/render/background.ts","../src/hit-test/handle.ts","../src/render/overlay.ts","../src/render/paint-frame.ts","../src/render/rough/constants.ts","../src/render/color.ts","../src/render/shapes/path-helpers.ts","../src/render/shapes/draw-shape.ts","../src/render/rough/loader.ts","../src/render/rough/paths.ts","../src/render/rough/tone-down.ts","../src/render/rough/draw.ts","../src/render/shapes/content-bounds.ts","../src/render/transform.ts","../src/render/renderer.ts","../src/render/minimap.ts","../src/hit-test/node.ts","../src/hit-test/edge.ts","../src/hit-test/store-query.ts","../src/clipboard/serialize.ts","../src/clipboard/index.ts","../src/export/png.ts","../src/export/svg.ts","../src/ai/context.ts","../src/ai/op-schemas.ts","../src/extension/index.ts","../src/index.ts"],"names":["a","b","samples","cached","segLen","cache","isMoving","getLineAdvance","lineWidth","x","next","newSel","opts","MAX_ENTRIES","loadPromise","readyCallbacks","TONE_BLEND","ex","ey","DEFAULT_BACKGROUND","MIN_READABLE_FONT_PX","DEFAULT_PADDING","unionBounds","bothEndsInside"],"mappings":"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","file":"index.js","sourcesContent":["/**\n * Branded ID types so node/edge/group ids never accidentally cross.\n */\nexport type NodeId = string & { readonly __brand: 'NodeId' }\nexport type EdgeId = string & { readonly __brand: 'EdgeId' }\nexport type GroupId = string & { readonly __brand: 'GroupId' }\nexport type ClientId = string & { readonly __brand: 'ClientId' }\nexport type BatchId = string & { readonly __brand: 'BatchId' }\n\nexport const asNodeId = (s: string): NodeId => s as NodeId\nexport const asEdgeId = (s: string): EdgeId => s as EdgeId\nexport const asGroupId = (s: string): GroupId => s as GroupId\nexport const asClientId = (s: string): ClientId => s as ClientId\nexport const asBatchId = (s: string): BatchId => s as BatchId\n\n/**\n * A point in world coordinates.\n */\nexport type Vec2 = { x: number; y: number }\n\n/**\n * An axis-aligned rectangle in world coordinates.\n * x/y is the top-left; w/h extend toward +x/+y.\n */\nexport type WorldRect = { x: number; y: number; w: number; h: number }\n\nexport const SCHEMA_VERSION = 1 as const\nexport type SchemaVersion = typeof SCHEMA_VERSION\n","import type { EdgeId, GroupId, NodeId, Vec2 } from './primitives'\nimport type { EdgeStyle } from './style'\n\nexport type PathStyle = 'straight' | 'bezier' | 'polyline'\n\n/**\n * Edge endpoint — see ARCHITECTURE.md §6.1.\n *\n * Attached: `localOffset` is in the node's pre-rotation local frame,\n * top-left origin, absolute pixels. Endpoint follows the node\n * automatically via projection at render time.\n * Free-floating: `worldPoint` is in world coordinates.\n */\nexport type EdgeEnd = { nodeId: NodeId; localOffset: Vec2 } | { worldPoint: Vec2 }\n\nexport const isAttached = (e: EdgeEnd): e is { nodeId: NodeId; localOffset: Vec2 } => 'nodeId' in e\n\n/**\n * Scene edge — see ARCHITECTURE.md §3.3.\n */\nexport type Edge = {\n id: EdgeId\n\n source: EdgeEnd\n target: EdgeEnd\n pathStyle: PathStyle\n control?: Vec2[]\n\n z: number\n groups: GroupId[]\n locked?: boolean\n hidden?: boolean\n\n content?: string\n style?: EdgeStyle\n data?: unknown\n}\n","/**\n * Canvas background — see ARCHITECTURE.md §4 (rendering pipeline).\n *\n * Local-only render-time config (not part of the synced scene). Drives\n * the page color plus an optional infinite dot / grid pattern that\n * helps spatial orientation while panning.\n *\n * Patterns are world-space: dots/lines are anchored to the world\n * origin, so panning moves *through* them rather than dragging them\n * along.\n */\nexport type CanvasBackgroundPattern = 'none' | 'dots' | 'grid'\n\nexport type CanvasBackground = {\n /** Page background color. Default `'#f8fafc'`. */\n color?: string\n /** Pattern overlay on top of the color. Default `'none'`. */\n pattern?: CanvasBackgroundPattern\n /** World units between adjacent dots / grid lines. Default `20`. */\n gap?: number\n /** Color of the dots / grid lines. Default `'#cbd5e1'`. */\n patternColor?: string\n /**\n * Hide the pattern when `camera.z < minZoom`. Useful to declutter\n * zoomed-out views and skip the per-frame pattern paint cost. Default\n * `0` (no minimum — pattern shows at any zoom, subject to the LOD\n * skip when individual cells would be sub-2px).\n */\n minZoom?: number\n /**\n * Hide the pattern when `camera.z > maxZoom`. Default `Infinity` (no\n * maximum). Most consumers won't need this; useful if you want the\n * pattern to disappear when zoomed in past a \"detail\" threshold.\n */\n maxZoom?: number\n}\n\nexport const DEFAULT_BACKGROUND: Required<CanvasBackground> = {\n color: '#f8fafc',\n pattern: 'none',\n gap: 20,\n patternColor: '#cbd5e1',\n minZoom: 0,\n maxZoom: Number.POSITIVE_INFINITY,\n}\n","/**\n * ID generation — see ARCHITECTURE.md §10.8.\n *\n * Default scheme: `${clientId}-${counter}`. Collision-free across clients\n * without coordination, human-readable in dev tools, monotonic per client.\n *\n * Consumers may override via `createCanvasStore({ idGenerator })`.\n */\nimport type { ClientId } from '../types'\n\nexport type IdGenerator = () => string\n\n/**\n * Generates a random short client id like \"u-7f3a\".\n * Used when no `clientId` is passed and no `sync` adapter is attached.\n */\nexport const randomClientId = (): ClientId => {\n const hex = Math.floor(Math.random() * 0xffff)\n .toString(16)\n .padStart(4, '0')\n return `u-${hex}` as ClientId\n}\n\n/**\n * Builds an id generator that prefixes a stable client id with an\n * incrementing counter. Each call returns a fresh, never-recycled id.\n */\nexport const makeIdGenerator = (clientId: ClientId): IdGenerator => {\n let counter = 0\n return () => `${clientId}-${counter++}`\n}\n","/**\n * Camera math — see ARCHITECTURE.md §4.3 and §13.4.\n *\n * The camera maps world coordinates to screen coordinates via:\n * screen = (world - camera.{x,y}) * camera.z\n * world = screen / camera.z + camera.{x,y}\n *\n * camera.{x,y} is the world-space point shown at screen (0,0).\n * camera.z is the zoom factor (1 = identity).\n */\nimport type { CameraState, Vec2, WorldRect } from '../types'\n\nexport const DEFAULT_CAMERA: CameraState = { x: 0, y: 0, z: 1 }\n\nexport const MIN_ZOOM = 0.05\nexport const MAX_ZOOM = 16\n\n/**\n * Converts a screen-space point to world coords given the current camera.\n */\nexport const screenToWorld = (screen: Vec2, camera: CameraState): Vec2 => ({\n x: screen.x / camera.z + camera.x,\n y: screen.y / camera.z + camera.y,\n})\n\n/**\n * Converts a world-space point to screen coords given the current camera.\n */\nexport const worldToScreen = (world: Vec2, camera: CameraState): Vec2 => ({\n x: (world.x - camera.x) * camera.z,\n y: (world.y - camera.y) * camera.z,\n})\n\n/**\n * Computes the world-space rect currently visible inside a viewport of the\n * given screen-space size. Used for viewport culling queries.\n */\nexport const viewportWorldRect = (\n camera: CameraState,\n viewportW: number,\n viewportH: number,\n): WorldRect => ({\n x: camera.x,\n y: camera.y,\n w: viewportW / camera.z,\n h: viewportH / camera.z,\n})\n\n/**\n * Clamps a zoom factor to the supported range.\n */\nexport const clampZoom = (z: number): number => {\n if (!Number.isFinite(z)) return 1\n return Math.max(MIN_ZOOM, Math.min(MAX_ZOOM, z))\n}\n\n/**\n * Applies a zoom delta keeping the world point under `screenAnchor` stationary.\n * Useful for wheel-zoom and pinch-zoom — keeps focus where the user looks.\n */\nexport const zoomAtScreenPoint = (\n camera: CameraState,\n newZoom: number,\n screenAnchor: Vec2,\n): CameraState => {\n const z = clampZoom(newZoom)\n const worldAnchor = screenToWorld(screenAnchor, camera)\n // Solve for new x/y so that worldToScreen(worldAnchor, new) === screenAnchor.\n return {\n x: worldAnchor.x - screenAnchor.x / z,\n y: worldAnchor.y - screenAnchor.y / z,\n z,\n }\n}\n\n/**\n * Pans the camera by a screen-space delta (e.g. from a drag gesture).\n */\nexport const panByScreen = (camera: CameraState, deltaScreen: Vec2): CameraState => ({\n x: camera.x - deltaScreen.x / camera.z,\n y: camera.y - deltaScreen.y / camera.z,\n z: camera.z,\n})\n","import type { Vec2, WorldRect } from '../types'\n\n/**\n * AABB utilities. Rectangles are { x, y, w, h } in world space.\n */\n\nexport const rectContainsPoint = (r: WorldRect, p: Vec2): boolean =>\n p.x >= r.x && p.x <= r.x + r.w && p.y >= r.y && p.y <= r.y + r.h\n\nexport const rectsIntersect = (a: WorldRect, b: WorldRect): boolean =>\n a.x < b.x + b.w && a.x + a.w > b.x && a.y < b.y + b.h && a.y + a.h > b.y\n\n/**\n * Inflate rect by a uniform world-space amount on all sides.\n */\nexport const inflateRect = (r: WorldRect, amount: number): WorldRect => ({\n x: r.x - amount,\n y: r.y - amount,\n w: r.w + amount * 2,\n h: r.h + amount * 2,\n})\n\n/**\n * Smallest AABB containing two points.\n */\nexport const rectFromPoints = (a: Vec2, b: Vec2): WorldRect => {\n const x = Math.min(a.x, b.x)\n const y = Math.min(a.y, b.y)\n return { x, y, w: Math.abs(b.x - a.x), h: Math.abs(b.y - a.y) }\n}\n\n/**\n * Smallest AABB containing all given rects. Returns null for empty input.\n */\nexport const unionRects = (rects: WorldRect[]): WorldRect | null => {\n if (rects.length === 0) return null\n let minX = Number.POSITIVE_INFINITY\n let minY = Number.POSITIVE_INFINITY\n let maxX = Number.NEGATIVE_INFINITY\n let maxY = Number.NEGATIVE_INFINITY\n for (const r of rects) {\n if (r.x < minX) minX = r.x\n if (r.y < minY) minY = r.y\n if (r.x + r.w > maxX) maxX = r.x + r.w\n if (r.y + r.h > maxY) maxY = r.y + r.h\n }\n return { x: minX, y: minY, w: maxX - minX, h: maxY - minY }\n}\n","import type { Vec2, WorldRect } from '../types'\n/**\n * Uniform-grid spatial index — see ARCHITECTURE.md §7.\n *\n * Stores ids by their AABB, with each AABB occupying one or more grid cells.\n * Insert / remove / query are O(1) per cell touched; total per query is\n * O(cells × items-per-cell), which for our 256-unit cell size and\n * typical scene density is well under 1ms even at 50k items.\n *\n * Sized ~256 world units by default. Tune via the constructor.\n */\nimport { rectsIntersect } from './aabb'\n\nexport type SpatialId = string\n\nexport class UniformGrid {\n private readonly cellSize: number\n // cell key -> set of ids whose AABB intersects this cell\n private readonly cells = new Map<string, Set<SpatialId>>()\n // id -> AABB (cached so remove() can find which cells to clear)\n private readonly bounds = new Map<SpatialId, WorldRect>()\n\n constructor(cellSize = 256) {\n if (cellSize <= 0) throw new Error('cellSize must be positive')\n this.cellSize = cellSize\n }\n\n get size(): number {\n return this.bounds.size\n }\n\n /**\n * Inserts or replaces an entry. Removes previous cell membership if the id existed.\n */\n insert(id: SpatialId, aabb: WorldRect): void {\n const existing = this.bounds.get(id)\n if (existing) this.removeFromCells(id, existing)\n this.bounds.set(id, aabb)\n for (const key of this.cellKeysFor(aabb)) {\n let cell = this.cells.get(key)\n if (!cell) {\n cell = new Set()\n this.cells.set(key, cell)\n }\n cell.add(id)\n }\n }\n\n /**\n * Removes an entry. No-op if id is unknown.\n */\n remove(id: SpatialId): void {\n const aabb = this.bounds.get(id)\n if (!aabb) return\n this.removeFromCells(id, aabb)\n this.bounds.delete(id)\n }\n\n /**\n * Returns the stored AABB for an id, if any.\n */\n getAABB(id: SpatialId): WorldRect | undefined {\n return this.bounds.get(id)\n }\n\n /**\n * Returns ids whose AABB intersects the query rect.\n * Broad-phase only — callers do narrow-phase per id.\n */\n queryRect(rect: WorldRect): SpatialId[] {\n const result = new Set<SpatialId>()\n for (const key of this.cellKeysFor(rect)) {\n const cell = this.cells.get(key)\n if (!cell) continue\n for (const id of cell) {\n const aabb = this.bounds.get(id)\n if (aabb && rectsIntersect(aabb, rect)) result.add(id)\n }\n }\n return [...result]\n }\n\n /**\n * Returns ids whose AABB contains the point.\n */\n queryPoint(p: Vec2): SpatialId[] {\n return this.queryRect({ x: p.x, y: p.y, w: 0, h: 0 })\n }\n\n /**\n * Empties the index. O(1) on the bookkeeping; the GC handles the rest.\n */\n clear(): void {\n this.cells.clear()\n this.bounds.clear()\n }\n\n /**\n * Yields the cell keys that an AABB covers.\n */\n private *cellKeysFor(aabb: WorldRect): IterableIterator<string> {\n const cs = this.cellSize\n const x0 = Math.floor(aabb.x / cs)\n const y0 = Math.floor(aabb.y / cs)\n const x1 = Math.floor((aabb.x + aabb.w) / cs)\n const y1 = Math.floor((aabb.y + aabb.h) / cs)\n for (let cy = y0; cy <= y1; cy++) {\n for (let cx = x0; cx <= x1; cx++) {\n yield `${cx},${cy}`\n }\n }\n }\n\n private removeFromCells(id: SpatialId, aabb: WorldRect): void {\n for (const key of this.cellKeysFor(aabb)) {\n const cell = this.cells.get(key)\n if (!cell) continue\n cell.delete(id)\n if (cell.size === 0) this.cells.delete(key)\n }\n }\n}\n","/**\n * Compute world-space AABB for a (possibly rotated) node.\n *\n * For axis-aligned nodes (angle === 0): the AABB is the node rect itself.\n * For rotated nodes: enclose the 4 rotated corners.\n */\nimport type { Node, Vec2, WorldRect } from '../types'\n\nexport const nodeAABB = (node: Node): WorldRect => {\n if (node.angle === 0) {\n return { x: node.x, y: node.y, w: node.w, h: node.h }\n }\n\n const cx = node.x + node.w / 2\n const cy = node.y + node.h / 2\n const cos = Math.cos(node.angle)\n const sin = Math.sin(node.angle)\n\n const corners: Vec2[] = [\n rotatePoint(node.x, node.y, cx, cy, cos, sin),\n rotatePoint(node.x + node.w, node.y, cx, cy, cos, sin),\n rotatePoint(node.x + node.w, node.y + node.h, cx, cy, cos, sin),\n rotatePoint(node.x, node.y + node.h, cx, cy, cos, sin),\n ]\n\n let minX = corners[0]!.x\n let minY = corners[0]!.y\n let maxX = minX\n let maxY = minY\n for (let i = 1; i < corners.length; i++) {\n const c = corners[i]!\n if (c.x < minX) minX = c.x\n if (c.x > maxX) maxX = c.x\n if (c.y < minY) minY = c.y\n if (c.y > maxY) maxY = c.y\n }\n return { x: minX, y: minY, w: maxX - minX, h: maxY - minY }\n}\n\nconst rotatePoint = (\n px: number,\n py: number,\n cx: number,\n cy: number,\n cos: number,\n sin: number,\n): Vec2 => {\n const dx = px - cx\n const dy = py - cy\n return { x: cx + dx * cos - dy * sin, y: cy + dx * sin + dy * cos }\n}\n","/**\n * Edge endpoint projection — see ARCHITECTURE.md §6.1.\n *\n * An EdgeEnd is either { nodeId, localOffset } (attached) or\n * { worldPoint } (free-floating). This module computes the current\n * world-space position of an endpoint by reading the latest node\n * state — no caching, no sync code; the projection is the truth.\n */\nimport { isAttached } from '../types'\nimport type { EdgeEnd, Node, NodeId, Vec2 } from '../types'\n\n/**\n * Resolves an EdgeEnd to its current world coordinates.\n * Returns null when the endpoint is attached to a node that no longer exists.\n */\nexport const projectEndToWorld = (\n end: EdgeEnd,\n getNode: (id: NodeId) => Node | undefined,\n): Vec2 | null => {\n if (!isAttached(end)) return end.worldPoint\n const node = getNode(end.nodeId)\n if (!node) return null\n return nodeLocalToWorld(end.localOffset, node)\n}\n\n/**\n * Transforms a point in a node's pre-rotation local frame (top-left origin)\n * into world coordinates.\n */\nexport const nodeLocalToWorld = (local: Vec2, node: Node): Vec2 => {\n if (node.angle === 0) {\n return { x: node.x + local.x, y: node.y + local.y }\n }\n const cx = node.x + node.w / 2\n const cy = node.y + node.h / 2\n const cos = Math.cos(node.angle)\n const sin = Math.sin(node.angle)\n const dx = local.x - node.w / 2\n const dy = local.y - node.h / 2\n return { x: cx + dx * cos - dy * sin, y: cy + dx * sin + dy * cos }\n}\n\n/**\n * Transforms a world point into the node's pre-rotation local frame.\n * Used by auto-clip and by edge-creation snap-to-boundary logic.\n */\nexport const worldToNodeLocal = (world: Vec2, node: Node): Vec2 => {\n if (node.angle === 0) {\n return { x: world.x - node.x, y: world.y - node.y }\n }\n const cx = node.x + node.w / 2\n const cy = node.y + node.h / 2\n const cos = Math.cos(-node.angle)\n const sin = Math.sin(-node.angle)\n const dx = world.x - cx\n const dy = world.y - cy\n return { x: dx * cos - dy * sin + node.w / 2, y: dx * sin + dy * cos + node.h / 2 }\n}\n\n/**\n * Given a world point and a node, returns the local-frame coords of the\n * nearest point on the node's rect boundary. If the world point is inside\n * the rect, projects to the nearest edge; if outside, clamps to the\n * containing edge / corner.\n *\n * Used by the edge-creation gesture to snap endpoints to the node boundary.\n */\nexport const projectToNodeBoundary = (world: Vec2, node: Node): Vec2 => {\n const local = worldToNodeLocal(world, node)\n const clampedX = Math.max(0, Math.min(node.w, local.x))\n const clampedY = Math.max(0, Math.min(node.h, local.y))\n\n const isOutside = local.x < 0 || local.x > node.w || local.y < 0 || local.y > node.h\n if (isOutside) return { x: clampedX, y: clampedY }\n\n // Inside: project to the nearest edge.\n const distLeft = local.x\n const distRight = node.w - local.x\n const distTop = local.y\n const distBottom = node.h - local.y\n const minDist = Math.min(distLeft, distRight, distTop, distBottom)\n if (minDist === distLeft) return { x: 0, y: clampedY }\n if (minDist === distRight) return { x: node.w, y: clampedY }\n if (minDist === distTop) return { x: clampedX, y: 0 }\n return { x: clampedX, y: node.h }\n}\n","/**\n * Auto-routing for bezier edges — see ARCHITECTURE.md §6.6.\n *\n * Unified rule: for each attached endpoint, cast a ray from the node\n * center toward the other endpoint and pick the side the ray exits\n * through. The bezier's control point at that end leaves along that\n * side's outward normal. Endpoints themselves stay at the user-supplied\n * localOffset; the renderer's clipSamples trims any inside-rect portion.\n *\n * Rotation-aware: side selection happens in each node's pre-rotation\n * local frame, then the normal is rotated back into world.\n */\nimport type { Node, Vec2 } from '../types'\nimport { worldToNodeLocal } from './project'\n\n/** Max world-space distance a control point can sit from its endpoint. */\nconst CONTROL_MAX = 200\n/** Fraction of endpoint-to-endpoint distance used for the control offset. */\nconst CONTROL_FRACTION = 0.4\n\nexport type Side = 'n' | 's' | 'e' | 'w'\n\n/**\n * Picks the side of a node's local rect closest to the given local offset.\n * Used to determine which way a bezier should leave the node.\n */\nexport const sideOf = (node: Node, localX: number, localY: number): Side => {\n const distLeft = localX\n const distRight = node.w - localX\n const distTop = localY\n const distBottom = node.h - localY\n const minDist = Math.min(distLeft, distRight, distTop, distBottom)\n if (minDist === distLeft) return 'w'\n if (minDist === distRight) return 'e'\n if (minDist === distTop) return 'n'\n return 's'\n}\n\n/**\n * Outward-pointing unit vector for a given side, in the node's pre-rotation\n * local frame.\n */\nexport const sideNormalLocal = (side: Side): Vec2 => {\n switch (side) {\n case 'n':\n return { x: 0, y: -1 }\n case 's':\n return { x: 0, y: 1 }\n case 'e':\n return { x: 1, y: 0 }\n case 'w':\n return { x: -1, y: 0 }\n }\n}\n\n/**\n * Rotates a local-frame vector into world coordinates by the node's angle.\n */\nexport const rotateVecByAngle = (v: Vec2, angle: number): Vec2 => {\n if (angle === 0) return v\n const cos = Math.cos(angle)\n const sin = Math.sin(angle)\n return { x: v.x * cos - v.y * sin, y: v.x * sin + v.y * cos }\n}\n\n/**\n * Computes auto-routed control points for a cubic bezier between\n * sourceWorld and targetWorld. Each control point is offset along the\n * outward normal of its endpoint's attached node (if any).\n *\n * For free-floating endpoints (no node), the control aligns with the\n * source→target direction so the curve degenerates gracefully toward a\n * straight line.\n */\nexport const autoRouteControls = (\n sourceWorld: Vec2,\n targetWorld: Vec2,\n sourceNormalWorld: Vec2 | null,\n targetNormalWorld: Vec2 | null,\n): { c1: Vec2; c2: Vec2 } => {\n const dx = targetWorld.x - sourceWorld.x\n const dy = targetWorld.y - sourceWorld.y\n const dist = Math.hypot(dx, dy)\n const offset = Math.min(CONTROL_MAX, CONTROL_FRACTION * dist)\n\n // Fallback direction when no node attached.\n const fallbackSource = dist > 0 ? { x: dx / dist, y: dy / dist } : { x: 1, y: 0 }\n const fallbackTarget = dist > 0 ? { x: -dx / dist, y: -dy / dist } : { x: -1, y: 0 }\n\n const ns = sourceNormalWorld ?? fallbackSource\n const nt = targetNormalWorld ?? fallbackTarget\n\n return {\n c1: { x: sourceWorld.x + ns.x * offset, y: sourceWorld.y + ns.y * offset },\n c2: { x: targetWorld.x + nt.x * offset, y: targetWorld.y + nt.y * offset },\n }\n}\n\n/**\n * Picks which side of {@link node}'s rect the line from the node's\n * center to {@link towardWorld} exits through. The bezier auto-route\n * uses this to choose each endpoint's outgoing direction: the control\n * leaves along the chosen side's outward normal.\n *\n * Rotation-aware: the ray is computed in the node's pre-rotation local\n * frame so a rotated rect still picks its locally-correct side.\n */\nexport const sideToward = (node: Node, towardWorld: Vec2): Side => {\n const local = worldToNodeLocal(towardWorld, node)\n const halfW = node.w / 2\n const halfH = node.h / 2\n const dx = local.x - halfW\n const dy = local.y - halfH\n if (dx === 0 && dy === 0) return 'e'\n const tx = dx === 0 ? Number.POSITIVE_INFINITY : (dx > 0 ? halfW : -halfW) / dx\n const ty = dy === 0 ? Number.POSITIVE_INFINITY : (dy > 0 ? halfH : -halfH) / dy\n if (tx <= ty) return dx > 0 ? 'e' : 'w'\n return dy > 0 ? 's' : 'n'\n}\n","import type { Node, Vec2 } from '../types'\n/**\n * Auto-clip: hide the part of an edge that's inside its attached nodes.\n * See ARCHITECTURE.md §6.5.\n *\n * For each end, transform the polyline samples into the attached node's\n * pre-rotation local frame (collapsing the rotated-rect problem to\n * axis-aligned). Walk samples from that endpoint outward; the first\n * sample outside the rect is the exit. Sub-pixel interpolate between\n * the last-inside and first-outside samples for a clean clip point.\n */\nimport { nodeLocalToWorld, worldToNodeLocal } from './project'\n\n/**\n * Result of clipping the polyline against the two attached-node rects.\n * `startIndex` / `endIndex` are sample indices; the visible polyline is\n * `[startPoint, samples[startIndex+1..endIndex-1], endPoint]`.\n * If both ends are free-floating (no attached node), returns the full range.\n */\nexport type ClipResult = {\n startIndex: number\n endIndex: number\n startPoint: Vec2\n endPoint: Vec2\n visible: boolean\n}\n\nexport const fullVisibleClipResult = (samples: Vec2[]): ClipResult => ({\n startIndex: 0,\n endIndex: samples.length - 1,\n startPoint: samples[0] ?? { x: 0, y: 0 },\n endPoint: samples[samples.length - 1] ?? { x: 0, y: 0 },\n visible: samples.length >= 2,\n})\n\n/**\n * Clips a polyline against (up to) two attached-node rects.\n * `sourceNode` / `targetNode` are the nodes the source/target endpoints\n * attach to (null for free-floating endpoints).\n */\nexport const clipSamples = (\n samples: Vec2[],\n sourceNode: Node | null,\n targetNode: Node | null,\n): ClipResult => {\n if (samples.length < 2) return fullVisibleClipResult(samples)\n\n let startIndex = 0\n let startPoint = samples[0]!\n if (sourceNode) {\n const trimmed = trimFromStart(samples, sourceNode)\n if (!trimmed) return { ...fullVisibleClipResult(samples), visible: false }\n startIndex = trimmed.index\n startPoint = trimmed.point\n }\n\n let endIndex = samples.length - 1\n let endPoint = samples[endIndex]!\n if (targetNode) {\n const trimmed = trimFromEnd(samples, targetNode)\n if (!trimmed) return { ...fullVisibleClipResult(samples), visible: false }\n endIndex = trimmed.index\n endPoint = trimmed.point\n }\n\n // Source clip is strictly after target clip → nothing visible (clips\n // crossed over each other; happens when nodes overlap and edge ends\n // are inside both).\n if (startIndex > endIndex) {\n return {\n startIndex,\n endIndex,\n startPoint,\n endPoint,\n visible: false,\n }\n }\n\n return { startIndex, endIndex, startPoint, endPoint, visible: true }\n}\n\n/**\n * Walks samples from index 0 outward, returns the exit point where the\n * polyline first leaves the node's local rect. Returns null if every\n * sample is inside the rect (edge fully consumed by the node).\n */\nconst trimFromStart = (samples: Vec2[], node: Node): { index: number; point: Vec2 } | null => {\n const localSamples = samples.map(p => worldToNodeLocal(p, node))\n // Find first \"outside\" sample after we've seen at least one \"inside\".\n let lastInside = -1\n for (let i = 0; i < localSamples.length; i++) {\n const p = localSamples[i]!\n if (isInsideLocalRect(p, node.w, node.h)) {\n lastInside = i\n } else if (lastInside >= 0) {\n // Transition: lastInside → i is the crossing segment.\n const crossingLocal = segmentRectExit(localSamples[lastInside]!, p, node.w, node.h)\n return {\n index: i,\n point: nodeLocalToWorld(crossingLocal, node),\n }\n }\n // First sample already outside → the source endpoint is outside its node.\n // That's normal for free-floating endpoints; for attached endpoints it\n // happens when the node is small and the endpoint is exactly on the edge.\n if (i === 0 && !isInsideLocalRect(p, node.w, node.h)) {\n return { index: 0, point: samples[0]! }\n }\n }\n // Every sample inside → nothing visible.\n return null\n}\n\n/**\n * Mirror of trimFromStart: walk from the end backwards.\n */\nconst trimFromEnd = (samples: Vec2[], node: Node): { index: number; point: Vec2 } | null => {\n const localSamples = samples.map(p => worldToNodeLocal(p, node))\n let lastInside = -1\n for (let i = localSamples.length - 1; i >= 0; i--) {\n const p = localSamples[i]!\n if (isInsideLocalRect(p, node.w, node.h)) {\n lastInside = i\n } else if (lastInside >= 0) {\n const crossingLocal = segmentRectExit(localSamples[lastInside]!, p, node.w, node.h)\n return {\n index: i,\n point: nodeLocalToWorld(crossingLocal, node),\n }\n }\n if (i === localSamples.length - 1 && !isInsideLocalRect(p, node.w, node.h)) {\n return { index: i, point: samples[i]! }\n }\n }\n return null\n}\n\n/**\n * Boolean: is a local-frame point inside the rect [0..w, 0..h]?\n * Allows a tiny inset epsilon so the \"first sample on the boundary\"\n * case behaves consistently.\n */\nconst isInsideLocalRect = (p: Vec2, w: number, h: number): boolean => {\n const eps = 1e-6\n return p.x >= -eps && p.x <= w + eps && p.y >= -eps && p.y <= h + eps\n}\n\n/**\n * Given a local-frame segment from `inside` to `outside`, find the exact\n * point where it exits the rect [0..w, 0..h]. Tests against all 4 edges\n * and picks the smallest t in (0, 1].\n */\nconst segmentRectExit = (inside: Vec2, outside: Vec2, w: number, h: number): Vec2 => {\n let bestT = 1\n const ts: number[] = []\n if (outside.x !== inside.x) {\n ts.push(crossEdge(inside.x, outside.x, 0, inside, outside, h, /* checkY */ true))\n ts.push(crossEdge(inside.x, outside.x, w, inside, outside, h, true))\n }\n if (outside.y !== inside.y) {\n ts.push(crossEdgeY(inside.y, outside.y, 0, inside, outside, w))\n ts.push(crossEdgeY(inside.y, outside.y, h, inside, outside, w))\n }\n for (const t of ts) {\n if (t > 0 && t <= 1 && t < bestT) bestT = t\n }\n return {\n x: inside.x + bestT * (outside.x - inside.x),\n y: inside.y + bestT * (outside.y - inside.y),\n }\n}\n\n/**\n * Tests crossing of a segment with a vertical edge at x=edgeX.\n * Returns the parametric t along the segment, or Infinity if the\n * y at that t is outside [0..h].\n */\nconst crossEdge = (\n ax: number,\n bx: number,\n edgeX: number,\n a: Vec2,\n b: Vec2,\n h: number,\n _checkY: boolean,\n): number => {\n if (ax === bx) return Number.POSITIVE_INFINITY\n const t = (edgeX - ax) / (bx - ax)\n if (t < 0 || t > 1) return Number.POSITIVE_INFINITY\n const y = a.y + t * (b.y - a.y)\n if (y < -1e-6 || y > h + 1e-6) return Number.POSITIVE_INFINITY\n return t\n}\n\n/**\n * Tests crossing of a segment with a horizontal edge at y=edgeY.\n */\nconst crossEdgeY = (ay: number, by: number, edgeY: number, a: Vec2, b: Vec2, w: number): number => {\n if (ay === by) return Number.POSITIVE_INFINITY\n const t = (edgeY - ay) / (by - ay)\n if (t < 0 || t > 1) return Number.POSITIVE_INFINITY\n const x = a.x + t * (b.x - a.x)\n if (x < -1e-6 || x > w + 1e-6) return Number.POSITIVE_INFINITY\n return t\n}\n","/**\n * Edge AABB from samples — see ARCHITECTURE.md §6.12.\n *\n * Phase-1 had a crude AABB based on raw endpoint positions. Phase 4\n * computes the actual sample bounds + padding for arrowheads and labels,\n * which is what the spatial index needs for correct hit-testing.\n */\nimport type { Vec2, WorldRect } from '../types'\n\n/** Extra padding around sample bounds to cover arrowhead tips. */\nconst SAMPLE_PADDING = 12\n\nexport const edgeAABBFromSamples = (samples: Vec2[]): WorldRect => {\n if (samples.length === 0) return { x: 0, y: 0, w: 0, h: 0 }\n let minX = Number.POSITIVE_INFINITY\n let minY = Number.POSITIVE_INFINITY\n let maxX = Number.NEGATIVE_INFINITY\n let maxY = Number.NEGATIVE_INFINITY\n for (const p of samples) {\n if (p.x < minX) minX = p.x\n if (p.x > maxX) maxX = p.x\n if (p.y < minY) minY = p.y\n if (p.y > maxY) maxY = p.y\n }\n return {\n x: minX - SAMPLE_PADDING,\n y: minY - SAMPLE_PADDING,\n w: maxX - minX + SAMPLE_PADDING * 2,\n h: maxY - minY + SAMPLE_PADDING * 2,\n }\n}\n","/**\n * Curve sampling — see ARCHITECTURE.md §6.6 / §6.9.\n *\n * The polyline samples are the load-bearing data for everything edge-related:\n * paint, auto-clip, hit testing all walk the same array. Caching is in\n * cache.ts; this module is pure geometry.\n */\nimport type { PathStyle, Vec2 } from '../types'\n\n/** Default number of intermediate samples for a bezier (cubic). 32 is\n * indistinguishable from 64 at typical zoom; halve the array size. */\nexport const BEZIER_SEGMENTS = 32\n\n/**\n * Evaluates a cubic bezier at parameter t ∈ [0, 1].\n */\nexport const cubicBezier = (p0: Vec2, c1: Vec2, c2: Vec2, p1: Vec2, t: number): Vec2 => {\n const it = 1 - t\n const it2 = it * it\n const it3 = it2 * it\n const t2 = t * t\n const t3 = t2 * t\n return {\n x: it3 * p0.x + 3 * it2 * t * c1.x + 3 * it * t2 * c2.x + t3 * p1.x,\n y: it3 * p0.y + 3 * it2 * t * c1.y + 3 * it * t2 * c2.y + t3 * p1.y,\n }\n}\n\n/**\n * Tangent (unit vector) to a cubic bezier at parameter t.\n * Used for arrowhead orientation.\n */\nexport const cubicBezierTangent = (p0: Vec2, c1: Vec2, c2: Vec2, p1: Vec2, t: number): Vec2 => {\n const it = 1 - t\n const it2 = it * it\n const t2 = t * t\n // derivative of cubic bezier\n const dx = 3 * (it2 * (c1.x - p0.x) + 2 * it * t * (c2.x - c1.x) + t2 * (p1.x - c2.x))\n const dy = 3 * (it2 * (c1.y - p0.y) + 2 * it * t * (c2.y - c1.y) + t2 * (p1.y - c2.y))\n const len = Math.hypot(dx, dy)\n if (len === 0) return { x: 1, y: 0 }\n return { x: dx / len, y: dy / len }\n}\n\n/**\n * Samples a cubic bezier into BEZIER_SEGMENTS+1 evenly-spaced points\n * (in parameter space — not arc-length).\n */\nexport const sampleBezier = (\n p0: Vec2,\n c1: Vec2,\n c2: Vec2,\n p1: Vec2,\n segments: number = BEZIER_SEGMENTS,\n): Vec2[] => {\n const points: Vec2[] = new Array(segments + 1)\n for (let i = 0; i <= segments; i++) {\n const t = i / segments\n points[i] = cubicBezier(p0, c1, c2, p1, t)\n }\n return points\n}\n\n/**\n * Returns the polyline sample list for an edge given its path style,\n * world-projected endpoints, and (for bezier) control points or (for\n * polyline) midpoints. Straight = 2-point polyline.\n */\nexport const samplesFor = (\n pathStyle: PathStyle,\n source: Vec2,\n target: Vec2,\n controls: Vec2[] | undefined,\n): Vec2[] => {\n switch (pathStyle) {\n case 'straight':\n return [source, target]\n case 'polyline':\n return [source, ...(controls ?? []), target]\n case 'bezier': {\n const c1 = controls?.[0] ?? source\n const c2 = controls?.[1] ?? target\n return sampleBezier(source, c1, c2, target)\n }\n }\n}\n\n/**\n * Tangent at parameter t along the sampled polyline (arc-length-ish).\n * Used for arrowhead orientation when we don't have analytic curve info.\n * For straight/polyline this returns the segment direction; for bezier\n * we approximate by the direction between adjacent samples around the\n * target t.\n */\nexport const tangentAtArcLength = (samples: Vec2[], t: number): Vec2 => {\n if (samples.length < 2) return { x: 1, y: 0 }\n // Walk arc length to find the segment containing the target distance.\n const totalLengths: number[] = [0]\n let total = 0\n for (let i = 1; i < samples.length; i++) {\n const a = samples[i - 1]!\n const b = samples[i]!\n total += Math.hypot(b.x - a.x, b.y - a.y)\n totalLengths.push(total)\n }\n const target = total * Math.max(0, Math.min(1, t))\n let segIndex = 1\n for (; segIndex < totalLengths.length; segIndex++) {\n if (totalLengths[segIndex]! >= target) break\n }\n segIndex = Math.min(segIndex, samples.length - 1)\n const a = samples[segIndex - 1]!\n const b = samples[segIndex]!\n const dx = b.x - a.x\n const dy = b.y - a.y\n const len = Math.hypot(dx, dy)\n if (len === 0) return { x: 1, y: 0 }\n return { x: dx / len, y: dy / len }\n}\n","import type { Node, Vec2 } from '../types'\n/**\n * Self-loop case — see ARCHITECTURE.md §6.8.\n *\n * When source.nodeId === target.nodeId, the regular bezier between two\n * coincident points collapses. Generate a small loop on the top-right\n * corner instead: exit the top edge, arc outward, re-enter via the\n * right edge.\n */\nimport { autoRouteControls, rotateVecByAngle, sideNormalLocal } from './auto-route'\nimport { nodeLocalToWorld } from './project'\nimport { sampleBezier } from './samples'\n\n/** World-space loop radius factor based on max(w, h). */\nconst LOOP_SIZE_FRACTION = 0.6\n\n/**\n * Returns world-space (source, target, control1, control2) for a self-loop\n * on the given node. The loop exits from the top edge and re-enters via\n * the right edge.\n */\nexport const selfLoopGeometry = (\n node: Node,\n): { source: Vec2; target: Vec2; controls: [Vec2, Vec2] } => {\n const topAnchor = nodeLocalToWorld({ x: node.w / 2, y: 0 }, node)\n const rightAnchor = nodeLocalToWorld({ x: node.w, y: node.h / 2 }, node)\n const sourceNormal = rotateVecByAngle(sideNormalLocal('n'), node.angle)\n const targetNormal = rotateVecByAngle(sideNormalLocal('e'), node.angle)\n const offset = LOOP_SIZE_FRACTION * Math.max(node.w, node.h)\n const { c1, c2 } = autoRouteControlsAtOffset(\n topAnchor,\n rightAnchor,\n sourceNormal,\n targetNormal,\n offset,\n )\n return { source: topAnchor, target: rightAnchor, controls: [c1, c2] }\n}\n\n/**\n * Samples a self-loop given its node. Convenience wrapper that produces\n * the polyline samples auto-clip/hit-test/paint all consume.\n */\nexport const sampleSelfLoop = (node: Node): Vec2[] => {\n const { source, target, controls } = selfLoopGeometry(node)\n return sampleBezier(source, controls[0], controls[1], target)\n}\n\n/**\n * Like autoRouteControls but with an explicit offset; the loop wants a\n * larger control distance than the natural endpoint-distance formula\n * (which would be near-zero for coincident endpoints).\n */\nconst autoRouteControlsAtOffset = (\n source: Vec2,\n target: Vec2,\n sourceNormal: Vec2,\n targetNormal: Vec2,\n offset: number,\n): { c1: Vec2; c2: Vec2 } => {\n void autoRouteControls // (keep type linker happy if the helper isn't used)\n return {\n c1: { x: source.x + sourceNormal.x * offset, y: source.y + sourceNormal.y * offset },\n c2: { x: target.x + targetNormal.x * offset, y: target.y + targetNormal.y * offset },\n }\n}\n","/**\n * Edge geometry cache — see ARCHITECTURE.md §6.12.\n *\n * Stores per-edge sampled polylines + AABB, indexed by an opaque \"version\"\n * string derived from inputs (endpoints, controls, pathStyle, attached\n * node positions/angles/sizes). Cache invalidates implicitly when the\n * version key changes — no explicit deletes needed; we just refetch.\n *\n * For the renderer this means: edges paint in O(samples) per frame\n * after the first miss; sampling cost is paid only when geometry truly\n * changes. Phase-1's incidentEdges map drives \"moving node → its edges\n * version changes\" propagation.\n */\nimport { isAttached } from '../types'\nimport type { Edge, EdgeId, Node, NodeId, Vec2, WorldRect } from '../types'\nimport { edgeAABBFromSamples } from './aabb'\nimport { autoRouteControls, rotateVecByAngle, sideNormalLocal, sideToward } from './auto-route'\nimport { projectEndToWorld } from './project'\nimport { samplesFor } from './samples'\nimport { sampleSelfLoop } from './self-loop'\n\nexport type EdgeGeometry = {\n /** Endpoint world positions (post-projection, pre-clip). */\n source: Vec2\n target: Vec2\n /** Polyline samples for paint / hit-test / clip. */\n samples: Vec2[]\n /** AABB enclosing samples (padded for arrowheads). */\n aabb: WorldRect\n /** Whether the edge is a self-loop (source.nodeId === target.nodeId). */\n isSelfLoop: boolean\n /** Source/target attached node IDs (or null). Used by paint to clip. */\n sourceNodeId: NodeId | null\n targetNodeId: NodeId | null\n}\n\n/**\n * Computes edge geometry from current node state. No caching — callers\n * memoize on a version key (see makeEdgeVersion).\n */\nexport const computeEdgeGeometry = (\n edge: Edge,\n getNode: (id: NodeId) => Node | undefined,\n): EdgeGeometry | null => {\n const sourceNode = isAttached(edge.source) ? (getNode(edge.source.nodeId) ?? null) : null\n const targetNode = isAttached(edge.target) ? (getNode(edge.target.nodeId) ?? null) : null\n const sourceNodeId = sourceNode ? sourceNode.id : null\n const targetNodeId = targetNode ? targetNode.id : null\n\n // Self-loop shortcut.\n if (sourceNodeId && sourceNodeId === targetNodeId && sourceNode) {\n const samples = sampleSelfLoop(sourceNode)\n return {\n source: samples[0]!,\n target: samples[samples.length - 1]!,\n samples,\n aabb: edgeAABBFromSamples(samples),\n isSelfLoop: true,\n sourceNodeId,\n targetNodeId,\n }\n }\n\n const sourceWorld = projectEndToWorld(edge.source, getNode)\n const targetWorld = projectEndToWorld(edge.target, getNode)\n if (!sourceWorld || !targetWorld) return null\n\n let samples: Vec2[]\n if (edge.pathStyle === 'bezier') {\n let c1: Vec2\n let c2: Vec2\n if (edge.control && edge.control.length >= 2) {\n // User-controlled bezier (midpoint drag, explicit control). The\n // endpoints stay at their projected positions; clipSamples trims\n // the in-node portions on the renderer side.\n c1 = edge.control[0]!\n c2 = edge.control[1]!\n } else {\n // Unified auto-route: each attached endpoint's control leaves\n // along the outward normal of the side the source→target line\n // exits through. Endpoints stay at the user-supplied localOffset\n // — clipSamples handles hiding any inside-rect portion.\n const sourceNormal = sourceNode\n ? rotateVecByAngle(sideNormalLocal(sideToward(sourceNode, targetWorld)), sourceNode.angle)\n : null\n const targetNormal = targetNode\n ? rotateVecByAngle(sideNormalLocal(sideToward(targetNode, sourceWorld)), targetNode.angle)\n : null\n ;({ c1, c2 } = autoRouteControls(sourceWorld, targetWorld, sourceNormal, targetNormal))\n }\n samples = samplesFor('bezier', sourceWorld, targetWorld, [c1, c2])\n } else {\n samples = samplesFor(edge.pathStyle, sourceWorld, targetWorld, edge.control)\n }\n\n return {\n source: sourceWorld,\n target: targetWorld,\n samples,\n aabb: edgeAABBFromSamples(samples),\n isSelfLoop: false,\n sourceNodeId,\n targetNodeId,\n }\n}\n\n/**\n * Cache wrapper: stores last-computed geometry per edge id, keyed by an\n * integer version supplied by the caller. The store maintains the version\n * counter and bumps it on geometry-affecting mutations (edge.update or\n * incident node moves), so this cache becomes a pure integer-compare.\n *\n * Earlier versions of this file used a `toFixed(2)`-built string version\n * to detect changes implicitly. That allocated ~14 strings per edge per\n * paint and cost ~5-8ms at 2k visible edges. Explicit integer versioning\n * eliminates that entirely.\n */\nexport class EdgeGeometryCache {\n private readonly entries = new Map<EdgeId, { version: number; geom: EdgeGeometry }>()\n\n /**\n * Returns the cached geometry if `version` matches the cache entry;\n * otherwise recomputes via `computeEdgeGeometry`, stores, and returns.\n * Caller is responsible for passing the current store-managed version.\n */\n get(edge: Edge, version: number, getNode: (id: NodeId) => Node | undefined): EdgeGeometry | null {\n const cached = this.entries.get(edge.id)\n if (cached && cached.version === version) return cached.geom\n const geom = computeEdgeGeometry(edge, getNode)\n if (geom) this.entries.set(edge.id, { version, geom })\n else this.entries.delete(edge.id)\n return geom\n }\n\n delete(id: EdgeId): void {\n this.entries.delete(id)\n }\n\n clear(): void {\n this.entries.clear()\n }\n}\n","import type { Vec2 } from '../types'\n\n/**\n * Returns `{ point, tangent }` at fractional arc-length `t ∈ [0..1]`\n * along a sample polyline.\n *\n * Walks the polyline summing segment lengths until the target is\n * reached; linearly interpolates inside the last segment. The tangent\n * is the unit direction of that segment.\n *\n * Used by edge-label placement (see ARCHITECTURE.md §6.11) — labels at\n * arc-length 0.5 sit at the geometric midpoint regardless of curve\n * shape, and the tangent lets a label rotate to follow the edge.\n *\n * @example\n * const { point, tangent } = getPointAndTangentAtArcLength(geom.samples, 0.5)\n * ctx.translate(point.x, point.y)\n */\nexport const getPointAndTangentAtArcLength = (\n samples: readonly Vec2[],\n t: number,\n): { point: Vec2; tangent: Vec2 } => {\n if (samples.length < 2) {\n const p = samples[0] ?? { x: 0, y: 0 }\n return { point: p, tangent: { x: 1, y: 0 } }\n }\n const clamped = Math.max(0, Math.min(1, t))\n\n // First pass: total length.\n let total = 0\n for (let i = 1; i < samples.length; i++) {\n const a = samples[i - 1]!\n const b = samples[i]!\n total += Math.hypot(b.x - a.x, b.y - a.y)\n }\n if (total === 0) {\n const p = samples[0]!\n return { point: p, tangent: { x: 1, y: 0 } }\n }\n const target = clamped * total\n\n // Second pass: walk until we hit the target.\n let traveled = 0\n for (let i = 1; i < samples.length; i++) {\n const a = samples[i - 1]!\n const b = samples[i]!\n const segLen = Math.hypot(b.x - a.x, b.y - a.y)\n if (segLen === 0) continue\n if (traveled + segLen >= target) {\n const local = (target - traveled) / segLen\n return {\n point: { x: a.x + (b.x - a.x) * local, y: a.y + (b.y - a.y) * local },\n tangent: { x: (b.x - a.x) / segLen, y: (b.y - a.y) / segLen },\n }\n }\n traveled += segLen\n }\n // Fell off the end (t === 1 case).\n const last = samples[samples.length - 1]!\n const prev = samples[samples.length - 2]!\n const segLen = Math.hypot(last.x - prev.x, last.y - prev.y) || 1\n return {\n point: last,\n tangent: { x: (last.x - prev.x) / segLen, y: (last.y - prev.y) / segLen },\n }\n}\n","import type { Vec2 } from '../types'\n\n/**\n * Converts a single midpoint `P` (the point the user dragged the\n * bezier midpoint handle to) into a pair of cubic control points\n * `(c1, c2)` such that the resulting cubic **passes through `P` at\n * t = 0.5**.\n *\n * Math: a cubic Bezier with endpoints S, T and controls c1, c2 has\n *\n * B(0.5) = (1/8) · S + (3/8) · c1 + (3/8) · c2 + (1/8) · T\n *\n * Solving for c1 + c2 when B(0.5) = P:\n *\n * c1 + c2 = (8P − S − T) / 3\n *\n * One equation, two unknowns. The convention here: split symmetrically\n * (c1 = c2). That keeps the curve smooth and predictable for the user.\n * A two-handle form (c1 / c2 draggable independently) is the v1.x\n * follow-up.\n */\nexport const midpointToCubicControls = (\n source: Vec2,\n midpoint: Vec2,\n target: Vec2,\n): { c1: Vec2; c2: Vec2 } => {\n const c = {\n x: (8 * midpoint.x - source.x - target.x) / 6,\n y: (8 * midpoint.y - source.y - target.y) / 6,\n }\n return { c1: c, c2: { ...c } }\n}\n","/**\n * Arrowheads — see ARCHITECTURE.md §6.5 + §3.4 (4 styles).\n *\n * The arrowhead sits at the clipped endpoint of the edge; its direction\n * comes from the curve's tangent at that arc-length position. We draw\n * in world coords so the strokeWidth follows the camera transform —\n * scale of strokeWidth/scale gives a constant-screen-px width.\n */\nimport type { Arrowhead, Vec2 } from '../types'\n\n/** Arrow length in world units at zoom 1; scales with strokeWidth. */\nconst ARROW_BASE_LENGTH = 12\nconst ARROW_BASE_WIDTH = 8\n\n/**\n * Draws an arrowhead at the given world tip, pointing toward `tipDir`\n * (the unit tangent direction at that point — pointing FROM the curve\n * INTO the tip).\n */\nexport const drawArrowhead = (\n ctx: CanvasRenderingContext2D,\n kind: Arrowhead,\n tip: Vec2,\n tipDir: Vec2,\n strokeColor: string,\n strokeWidth: number,\n): void => {\n if (kind === 'none') return\n\n // Scale arrowhead with stroke width so styling stays consistent.\n const scale = Math.max(1, strokeWidth / 2)\n const len = ARROW_BASE_LENGTH * scale\n const half = (ARROW_BASE_WIDTH / 2) * scale\n\n // Perpendicular to tipDir (rotate 90° ccw).\n const px = -tipDir.y\n const py = tipDir.x\n\n // Two base corners of the arrowhead triangle.\n const baseCenter: Vec2 = { x: tip.x - tipDir.x * len, y: tip.y - tipDir.y * len }\n const left: Vec2 = { x: baseCenter.x + px * half, y: baseCenter.y + py * half }\n const right: Vec2 = { x: baseCenter.x - px * half, y: baseCenter.y - py * half }\n\n ctx.save()\n if (kind === 'arrow') {\n // Two short strokes from the tip back along the curve direction.\n ctx.strokeStyle = strokeColor\n ctx.lineWidth = strokeWidth\n ctx.lineCap = 'round'\n ctx.lineJoin = 'round'\n ctx.beginPath()\n ctx.moveTo(left.x, left.y)\n ctx.lineTo(tip.x, tip.y)\n ctx.lineTo(right.x, right.y)\n ctx.stroke()\n } else if (kind === 'arrow-filled') {\n ctx.fillStyle = strokeColor\n ctx.beginPath()\n ctx.moveTo(tip.x, tip.y)\n ctx.lineTo(left.x, left.y)\n ctx.lineTo(right.x, right.y)\n ctx.closePath()\n ctx.fill()\n } else if (kind === 'barb') {\n // Open arrow with the base barbed inward (a notched chevron).\n const notch: Vec2 = {\n x: baseCenter.x + tipDir.x * len * 0.35,\n y: baseCenter.y + tipDir.y * len * 0.35,\n }\n ctx.strokeStyle = strokeColor\n ctx.lineWidth = strokeWidth\n ctx.lineCap = 'round'\n ctx.lineJoin = 'round'\n ctx.fillStyle = strokeColor\n ctx.beginPath()\n ctx.moveTo(tip.x, tip.y)\n ctx.lineTo(left.x, left.y)\n ctx.lineTo(notch.x, notch.y)\n ctx.lineTo(right.x, right.y)\n ctx.closePath()\n ctx.fill()\n }\n ctx.restore()\n}\n\n/**\n * World-space length added to the visible arrowhead at a given stroke\n * width. Used to know how much to shorten the curve's visible portion\n * so the line tail doesn't poke through the arrowhead tip.\n */\nexport const arrowheadLength = (kind: Arrowhead, strokeWidth: number): number => {\n if (kind === 'none') return 0\n const scale = Math.max(1, strokeWidth / 2)\n return ARROW_BASE_LENGTH * scale\n}\n","import type { RoughDrawableLike } from './loader'\n\n/**\n * Bounded LRU cache of rough.js drawables keyed by shape signature.\n *\n * Building a drawable (`rc.generator.path(...)`) walks the SVG path\n * and emits jittered sub-paths — that's the expensive bit. Once built,\n * `rc.draw(drawable)` just strokes the cached path; cheap.\n *\n * Cache key composes all inputs that affect the generated path:\n * - primitive (rect / ellipse / diamond / capsule / edge)\n * - size + corner radius\n * - stroke color / style / width\n * - roughness + seed (jitter inputs)\n * - LOD bucket (curveStepCount, maxRandomnessOffset)\n *\n * On miss we build + insert; on overflow we evict the oldest entry.\n */\n\nconst cache = new Map<string, RoughDrawableLike>()\nconst MAX_ENTRIES = 1000\n\n/** Read-or-build for a drawable. `build` runs only on miss. */\nexport const getOrBuildDrawable = (\n key: string,\n build: () => RoughDrawableLike,\n): RoughDrawableLike => {\n const hit = cache.get(key)\n if (hit !== undefined) {\n // Touch — move to end (LRU).\n cache.delete(key)\n cache.set(key, hit)\n return hit\n }\n const drawable = build()\n if (cache.size >= MAX_ENTRIES) {\n // Evict oldest.\n const first = cache.keys().next().value\n if (first !== undefined) cache.delete(first)\n }\n cache.set(key, drawable)\n return drawable\n}\n\n/** Test / debug aid. */\nexport const clearRoughCache = (): void => {\n cache.clear()\n}\n\n/** Test / debug aid. */\nexport const getRoughCacheSize = (): number => cache.size\n\n/**\n * FNV-1a hash of a string id → 32-bit unsigned int. Used to derive\n * a stable per-node jitter seed so the wobble doesn't dance between\n * frames or sessions.\n */\nexport const seedFromId = (id: string): number => {\n let hash = 2166136261\n for (let i = 0; i < id.length; i += 1) {\n hash ^= id.charCodeAt(i)\n hash = Math.imul(hash, 16777619)\n }\n return hash >>> 0\n}\n","/**\n * Built-in style defaults — see ARCHITECTURE.md §3.4.\n *\n * Each render call resolves style via:\n * 1. node.style[token] if set\n * 2. theme(token) if a theme resolver is provided\n * 3. the value here\n */\nimport type { Style } from '../../types'\n\nexport const DEFAULT_STYLE: Required<\n Pick<\n Style,\n 'strokeColor' | 'strokeWidth' | 'strokeStyle' | 'backgroundColor' | 'opacity' | 'roundness'\n >\n> = {\n strokeColor: '#1f2937',\n strokeWidth: 2,\n strokeStyle: 'solid',\n backgroundColor: '#dbeafe',\n opacity: 100,\n roundness: 2,\n}\n\n/**\n * Resolves a style field with the precedence above.\n * `theme` lookup is optional and returns `undefined` if no override.\n *\n * Stable token catalog (consumer maps these to its design system):\n * - `strokeColor` edge + shape stroke\n * - `strokeWidth` shape + edge stroke width\n * - `backgroundColor` shape fill\n * - `textColor` shape text color\n * - `opacity` shape opacity (0-100)\n * - `selection.outline` selection outline color (overlay)\n * - `handle.fill` resize/rotate handle fill\n * - `handle.stroke` resize/rotate handle stroke\n * - `text.highlight` markdown ==highlight== chip color\n * - `text.codeBackground` markdown `code` chip color\n *\n * Tokens not in this list are passed through unchanged; consumers can\n * extend with their own (e.g. `node.shadow.color`).\n */\nexport type ThemeResolver = (token: string) => string | number | undefined\n\nexport const resolveColor = (\n style: Style | undefined,\n key: 'strokeColor' | 'backgroundColor' | 'textColor',\n fallback: string,\n theme?: ThemeResolver,\n): string => {\n const fromStyle = style?.[key]\n if (typeof fromStyle === 'string') return fromStyle\n const fromTheme = theme?.(key)\n if (typeof fromTheme === 'string') return fromTheme\n return fallback\n}\n\nexport const resolveStrokeWidth = (style: Style | undefined, theme?: ThemeResolver): number => {\n if (typeof style?.strokeWidth === 'number') return style.strokeWidth\n const fromTheme = theme?.('strokeWidth')\n if (typeof fromTheme === 'number') return fromTheme\n return DEFAULT_STYLE.strokeWidth\n}\n\nexport const resolveOpacity = (style: Style | undefined, theme?: ThemeResolver): number => {\n if (typeof style?.opacity === 'number') return style.opacity / 100\n const fromTheme = theme?.('opacity')\n if (typeof fromTheme === 'number') return fromTheme / 100\n return DEFAULT_STYLE.opacity / 100\n}\n\n/**\n * Returns true if a color string represents a fully-transparent paint —\n * either the literal `'transparent'` keyword or a hex with alpha 00.\n * Used everywhere we early-out on invisible fills/strokes.\n */\nexport const isFullyTransparent = (color: string): boolean => {\n if (color === 'transparent') return true\n if (color.length === 9 && color.startsWith('#') && color.slice(7, 9).toLowerCase() === '00')\n return true\n if (color.length === 5 && color.startsWith('#') && color[4] === '0') return true\n return false\n}\n\n/**\n * Maps the `strokeStyle` token to a canvas `setLineDash` argument.\n * Width-aware so dashes look right at different stroke widths.\n */\nexport const dashPatternFor = (\n strokeStyle: Style['strokeStyle'] | undefined,\n width: number,\n): number[] => {\n switch (strokeStyle) {\n case 'dashed':\n // Gap longer than dash so the pattern still reads as dashed when\n // rough.js's wobble + bowing eat into the gap on curved edges.\n // Previous 5:4 ratio (dash > gap) looked nearly continuous in\n // rough mode because the wobble closed the gaps.\n return [width * 3, width * 5]\n case 'dotted':\n // Small visible dot + generous gap. Non-zero dash so the pattern\n // also renders under default `butt` linecap (node strokes don't\n // override lineCap; the edge path sets `round` already). Gap is\n // tuned for the same wobble-survives-curvature reason as dashed.\n return [width * 1.5, width * 4]\n default:\n return []\n }\n}\n","/**\n * Lite-markdown tokenizer — ported verbatim from\n * `dim0/webui/src/components/markdown/canvas-lite-markdown.tsx`.\n *\n * The vocabulary is deliberately small: bold, italic, underline, strike,\n * highlight, inline code, links, fenced code blocks, hr lines. No\n * nesting, no escapes — single-pass regex tokenization keeps layout\n * fast at scale. See ARCHITECTURE.md §8.\n */\nexport type InlineType =\n | 'text'\n | 'bold'\n | 'italic'\n | 'underline'\n | 'strike'\n | 'highlight'\n | 'code'\n | 'link'\n /**\n * LaTeX math expression, content is the source between `$$...$$` (no\n * line breaks). Rendered via MathJax SVG output and rasterized to an\n * inline bitmap at paint time. See `text/math/`. Double-dollar\n * delimiters avoid the false-positives of single `$` in prose that\n * mentions currency (e.g. `$5 to $10`).\n */\n | 'math'\n\nexport type Token =\n | { type: InlineType; content: string }\n | { type: 'code-block'; content: string }\n | { type: 'br' }\n | { type: 'hr' }\n | { type: 'hr-double' }\n\n// Math `$$...$$` is matched first so its delimiters can't be confused\n// with italics (`*...*` etc.). Single `$` is treated as literal text —\n// avoids false-positives in prose mentioning currency (`$5 to $10`).\n// Empty math (`$$$$`) is intentionally not matched; lazy `+?` requires\n// at least one interior char.\nconst INLINE_PATTERN =\n /(\\$\\$[^\\n]+?\\$\\$|\\*\\*[^*]+\\*\\*|==[^=\\s](?:[^=]*?[^=\\s])?==|`[^`]+`|\\*[^*]+\\*|__[^_]+__|~~[^~]+~~|_[^_]+_|\\[[^\\]]+\\]\\([^)]+\\))/g\nconst HR_LINE_PATTERN = /^[ \\t]*---[ \\t]*$/\nconst DOUBLE_HR_LINE_PATTERN = /^[ \\t]*===[ \\t]*$/\n\n/**\n * Normalizes quick symbol shorthand to unicode glyphs before tokenization.\n */\nconst transformSymbols = (value: string) =>\n value.replace(/<=>|<->|<-|->|\\[\\]|\\[[vx]\\]/gi, match => {\n const normalized = match.toLowerCase()\n if (normalized === '->') return '→'\n if (normalized === '<-') return '←'\n if (normalized === '<->') return '↔'\n if (normalized === '<=>') return '⇔'\n if (normalized === '[]') return '☐'\n if (normalized === '[v]') return '✅'\n if (normalized === '[x]') return '❎'\n return match\n })\n\n/**\n * Tokenizes one line's inline content.\n */\nconst tokenizeInline = (segment: string): Token[] => {\n if (!segment) return []\n const tokens: Token[] = []\n let lastIndex = 0\n\n segment.replace(INLINE_PATTERN, (match, _group, offset) => {\n const idx = offset as number\n if (idx > lastIndex) {\n tokens.push({ type: 'text', content: transformSymbols(segment.slice(lastIndex, idx)) })\n }\n\n if (\n (match.startsWith('**') && match.endsWith('**')) ||\n (match.startsWith('__') && match.endsWith('__'))\n ) {\n tokens.push({ type: 'bold', content: transformSymbols(match.slice(2, -2)) })\n } else if (match.startsWith('*') && match.endsWith('*')) {\n tokens.push({ type: 'italic', content: transformSymbols(match.slice(1, -1)) })\n } else if (match.startsWith('~~') && match.endsWith('~~')) {\n tokens.push({ type: 'strike', content: transformSymbols(match.slice(2, -2)) })\n } else if (match.startsWith('==') && match.endsWith('==')) {\n tokens.push({ type: 'highlight', content: transformSymbols(match.slice(2, -2)) })\n } else if (match.startsWith('_') && match.endsWith('_')) {\n tokens.push({ type: 'underline', content: transformSymbols(match.slice(1, -1)) })\n } else if (match.startsWith('[') && match.includes('](') && match.endsWith(')')) {\n const splitIndex = match.indexOf('](')\n tokens.push({ type: 'link', content: transformSymbols(match.slice(1, splitIndex)) })\n } else if (match.startsWith('`') && match.endsWith('`')) {\n tokens.push({ type: 'code', content: match.slice(1, -1) })\n } else if (match.startsWith('$$') && match.endsWith('$$')) {\n // Strip the `$$...$$` delimiters; preserve interior whitespace\n // since LaTeX is whitespace-aware.\n tokens.push({ type: 'math', content: match.slice(2, -2) })\n } else {\n tokens.push({ type: 'text', content: transformSymbols(match) })\n }\n\n lastIndex = idx + match.length\n return match\n })\n\n if (lastIndex < segment.length) {\n tokens.push({ type: 'text', content: transformSymbols(segment.slice(lastIndex)) })\n }\n\n return tokens\n}\n\n/**\n * Tokenizes one line including hr / hr-double sentinels.\n */\nconst tokenizeLine = (line: string): Token[] => {\n if (DOUBLE_HR_LINE_PATTERN.test(line)) return [{ type: 'hr-double' }]\n if (HR_LINE_PATTERN.test(line)) return [{ type: 'hr' }]\n return tokenizeInline(line)\n}\n\n/**\n * Tokenizes plain-text sections (outside fenced code blocks) line by line.\n */\nconst tokenizeTextBlock = (block: string): Token[] => {\n if (!block) return []\n const tokens: Token[] = []\n const lines = block.split('\\n')\n lines.forEach((line, index) => {\n const lineTokens = tokenizeLine(line)\n tokens.push(...lineTokens)\n const isRuleLine =\n lineTokens.length === 1 &&\n (lineTokens[0]?.type === 'hr' || lineTokens[0]?.type === 'hr-double')\n if (index < lines.length - 1 && !isRuleLine) tokens.push({ type: 'br' })\n })\n return tokens\n}\n\n/**\n * Full markdown tokenizer with fenced code-block support. Code blocks\n * are display-only (no language badge / syntax highlighting).\n */\nexport const tokenize = (input: string): Token[] => {\n if (!input) return []\n const tokens: Token[] = []\n let cursor = 0\n\n while (cursor < input.length) {\n const fenceStart = input.indexOf('```', cursor)\n if (fenceStart === -1) {\n tokens.push(...tokenizeTextBlock(input.slice(cursor)))\n break\n }\n\n if (fenceStart > cursor) {\n tokens.push(...tokenizeTextBlock(input.slice(cursor, fenceStart)))\n }\n\n const fenceEnd = input.indexOf('```', fenceStart + 3)\n if (fenceEnd === -1) {\n tokens.push(...tokenizeTextBlock(input.slice(fenceStart)))\n break\n }\n\n const fenceContent = input.slice(fenceStart + 3, fenceEnd)\n const delimiterIndex = fenceContent.search(/[\\r\\n]/)\n let codeContent = fenceContent\n if (delimiterIndex >= 0) {\n codeContent = fenceContent.slice(delimiterIndex).replace(/^\\r?\\n/, '')\n }\n\n tokens.push({ type: 'code-block', content: codeContent.replace(/\\r\\n/g, '\\n') })\n cursor = fenceEnd + 3\n }\n\n return tokens\n}\n","/**\n * Font + line-height defaults — matches `dim0/webui/.../canvas-lite-markdown.tsx`\n * and `dim0/backend/topix/datatypes/note/style.py`.\n *\n * The maps below are the canonical contract between consumer style tokens\n * and concrete typography. Custom fonts live in the consumer's @font-face;\n * the library only renames them.\n */\nimport type { FontFamily, FontSize } from '../types'\n\n/**\n * Mirrors the font stacks defined in dim0's index.css so canvas measurement\n * matches DOM text. Custom fonts must be loaded by the consumer (via\n * @font-face / Google Fonts); the font-epoch reactivity (see font-epoch.ts)\n * invalidates the bitmap cache when fonts finish loading.\n */\nexport const FONT_FAMILY_MAP: Record<FontFamily, string> = {\n handwriting: '\"Architects Daughter\", cursive',\n 'sans-serif':\n '\"Atkinson Hyperlegible Next\", system-ui, -apple-system, BlinkMacSystemFont, \"Segoe UI\", Roboto, \"Helvetica Neue\", Arial, \"Noto Sans\", ui-sans-serif, sans-serif, \"Apple Color Emoji\", \"Segoe UI Emoji\", \"Segoe UI Symbol\", \"Noto Color Emoji\"',\n serif: '\"Lora\", \"Source Serif 4\", ui-serif, Georgia, Cambria, \"Times New Roman\", Times, serif',\n monospace:\n '\"Inconsolata\", ui-monospace, SFMono-Regular, Menlo, Monaco, Consolas, \"Liberation Mono\", \"Courier New\", monospace',\n informal: '\"Shantell Sans\", ui-handwriting, cursive',\n}\n\nexport const FONT_SIZE_MAP: Record<FontSize, number> = {\n S: 14,\n M: 16,\n L: 24,\n XL: 36,\n}\n\nexport const LINE_HEIGHT_MAP: Record<FontSize, number> = {\n S: 20,\n M: 24,\n L: 32,\n XL: 40,\n}\n\n// Layout-time visual constants. Match dim0 canvas-lite-markdown.\nexport const CODE_BLOCK_PADDING_X = 6\nexport const CODE_BLOCK_MARGIN_Y = 4\nexport const CONTENT_HEIGHT_BUFFER = 4\nexport const CONTENT_PADDING = 6\n\nexport const DEFAULT_TEXT_COLOR = '#1f2937'\nexport const DEFAULT_HIGHLIGHT_COLOR = '#fde047'\nexport const DEFAULT_HIGHLIGHT_COLOR_DARK = '#6b5a23'\nexport const LINK_COLOR = '#2563eb'\nexport const CODE_BG_COLOR = 'rgba(148, 163, 184, 0.18)'\n","/**\n * Lazy loader for MathJax — same pattern as `render/rough/loader.ts`.\n *\n * MathJax is ~600KB and only useful for scenes with LaTeX math. We\n * defer loading until the first `$$...$$` token requests a compile,\n * then convert LaTeX → SVG strings off the main rAF path.\n *\n * Loaded from jsDelivr CDN rather than bundled because the v4\n * tex-svg.js bundle uses `importScripts('sre/speech-worker.js')` for\n * accessibility; the relative URL resolves wrong when served from a\n * dev bundler's node_modules. The CDN serves sibling files at\n * predictable paths so the bundle finds its workers. Self-host by\n * pointing `VENDOR_URL` at your own copy of the v4 component files.\n *\n * Notes:\n * - MathJax's `tex-svg.js` bundle attaches itself to `window.MathJax`\n * when loaded. This is the documented v4 browser API.\n * - If a consumer also uses MathJax, they should configure the\n * global *before* canvas-harness's first math node loads.\n */\n\ntype MathJaxLike = {\n tex2svgPromise(\n source: string,\n opts?: { display?: boolean; em?: number; ex?: number; containerWidth?: number },\n ): Promise<MathJaxSvgElement>\n startup: {\n /**\n * The \"lite adaptor\" used by the SVG output in browser context.\n * `serializeXML` returns standalone-valid SVG markup with\n * namespaces intact (which `outerHTML` does not always do).\n */\n adaptor: {\n serializeXML?(el: MathJaxSvgElement): string\n outerHTML(el: MathJaxSvgElement): string\n }\n }\n}\n\n/**\n * MathJax returns a \"lite element\" virtual-DOM node, not a real SVG\n * element. We only need to serialize it via the adaptor.\n */\nexport type MathJaxSvgElement = unknown\n\n// `window.MathJax` is partially populated by us pre-load (config),\n// then fully populated by the tex-svg bundle post-load. We type it\n// as `unknown` here and cast at the two access sites.\ndeclare global {\n var MathJax: unknown\n}\n\nlet cached: MathJaxLike | null = null\nlet loadPromise: Promise<MathJaxLike | null> | null = null\nlet loadFailed = false\nconst readyCallbacks = new Set<() => void>()\n\n/**\n * Returns the configured MathJax instance if loaded, else `null` and\n * triggers the lazy import on first call. Subscribers via `onMathJaxReady`\n * are notified when the import resolves.\n */\nexport const getMathJax = (): MathJaxLike | null => {\n if (cached) return cached\n if (loadFailed) return null\n if (!loadPromise) {\n loadPromise = loadMathJax()\n .then(instance => {\n if (instance) {\n cached = instance\n // Fire pending callbacks ONLY on real load success — firing\n // on null would re-trigger cache drains in a loop.\n for (const cb of readyCallbacks) cb()\n } else {\n // SSR / no window — mark terminal so future `onMathJaxReady`\n // calls bail instead of accumulating callbacks.\n loadFailed = true\n }\n readyCallbacks.clear()\n return cached\n })\n .catch(err => {\n console.warn('[math] failed to load MathJax:', err)\n loadFailed = true\n readyCallbacks.clear()\n return null\n })\n }\n return null\n}\n\n/**\n * Registers a callback that fires once when MathJax becomes available.\n * No-op if already loaded — caller should check `getMathJax() !== null`\n * first. Used to trigger a re-paint of math-bearing text nodes.\n */\nexport const onMathJaxReady = (cb: () => void): void => {\n if (cached) return\n if (loadFailed) return\n readyCallbacks.add(cb)\n}\n\ntype MathJaxConfig = {\n startup?: { typeset?: boolean; promise?: Promise<void> }\n options?: {\n enableMenu?: boolean\n enableEnrichment?: boolean\n enableSpeech?: boolean\n enableComplexity?: boolean\n sre?: { speech?: 'none' | 'shallow' | 'deep' }\n }\n svg?: {\n scale?: number\n fontCache?: 'local' | 'global' | 'none'\n /**\n * v4 introduces inline-math linebreaking that splits long\n * formulas across MULTIPLE <svg> blocks separated by <mjx-break>\n * markers. Great for HTML flow layout, fatal for our Blob URL\n * pipeline (multiple root elements aren't valid in one SVG doc).\n * Disabling it forces one <svg> per formula no matter how wide.\n */\n linebreaks?: { inline?: boolean; width?: string }\n }\n}\n\nconst loadMathJax = async (): Promise<MathJaxLike | null> => {\n if (typeof window === 'undefined') return null\n\n // Configure before importing so MathJax picks up the settings. The\n // tex-svg bundle reads `window.MathJax` at script-execution time.\n // `fontCache: 'local'` embeds glyph paths inline in each SVG (bigger\n // SVG, no <defs> dependency). Required for SVGs that get detached\n // from MathJax's host container, like ours.\n const winAny = window as typeof window & { MathJax?: MathJaxConfig }\n // Disable a11y / SRE features. MathJax v4's tex-svg bundle tries to\n // load a speech-rule-engine worker by default for screen reader\n // support — its bundled path resolves to `http://sre//...` which\n // 404s in browsers and clutters the console. We're rendering to\n // canvas, not DOM — no AT to serve anyway.\n winAny.MathJax = {\n ...(winAny.MathJax ?? {}),\n startup: { typeset: false },\n options: {\n enableMenu: false,\n enableEnrichment: false,\n enableSpeech: false,\n enableComplexity: false,\n sre: { speech: 'none' },\n },\n // `fontCache: 'none'` inlines every glyph as a raw <path>\n // (slightly bigger SVG, no <use> references). Required for SVGs\n // we extract to a Blob URL and rasterize via <img> — `<use>`\n // refs to <defs> elsewhere in the page wouldn't resolve.\n // `linebreaks: { inline: false }` keeps the whole formula in one\n // <svg> element (v4 defaults to true for long inline math).\n svg: {\n scale: 1,\n fontCache: 'none',\n linebreaks: { inline: false },\n },\n }\n\n // Load via <script> tag from CDN rather than `import('mathjax/tex-svg.js')`.\n // The bundle's `importScripts('sre/speech-worker.js')` for the\n // accessibility feature uses a relative URL that Vite (and most\n // bundlers) can't serve from node_modules. The CDN serves sibling\n // files at predictable paths so the bundle finds its workers.\n // Override `MATHJAX_VENDOR_URL` to self-host.\n const VENDOR_URL = 'https://cdn.jsdelivr.net/npm/mathjax@4/tex-svg.js'\n await new Promise<void>((resolve, reject) => {\n const existing = document.querySelector(\n `script[src=\"${VENDOR_URL}\"]`,\n ) as HTMLScriptElement | null\n if (existing) {\n // Already injected by a previous call — wait for it to finish.\n existing.addEventListener('load', () => resolve(), { once: true })\n existing.addEventListener('error', () => reject(new Error('MathJax CDN load failed')), {\n once: true,\n })\n return\n }\n const script = document.createElement('script')\n script.src = VENDOR_URL\n script.async = true\n script.onload = () => resolve()\n script.onerror = () => reject(new Error('MathJax CDN load failed'))\n document.head.appendChild(script)\n })\n\n // MathJax's startup is a Promise; wait for it before returning.\n const mj = winAny.MathJax as (MathJaxLike & { startup?: { promise?: Promise<void> } }) | undefined\n if (!mj) throw new Error('MathJax did not install on window after import')\n if (typeof mj.tex2svgPromise !== 'function') {\n throw new Error('MathJax loaded but tex2svgPromise is missing — wrong bundle?')\n }\n await mj.startup?.promise\n return mj as MathJaxLike\n}\n\n/** Reset state — tests only. */\nexport const __resetMathLoader = (): void => {\n cached = null\n loadPromise = null\n loadFailed = false\n readyCallbacks.clear()\n}\n","/**\n * Math compile + raster cache.\n *\n * Pipeline per formula:\n * 1. LaTeX source → MathJax SVG string (sync once MathJax loaded)\n * 2. Inject the requested text color via `currentColor` substitution\n * 3. Rasterize to ImageBitmap at the requested on-device pixel size\n * 4. Cache by (source, color, sizeBucket)\n *\n * Compile work is queued and drained over rAF frames so a paste of\n * 100 math-heavy paragraphs doesn't block the main thread. Each\n * resolve bumps the math-epoch; the text bitmap cache reads the\n * epoch and invalidates only its math-bearing entries.\n */\nimport { getMathJax, onMathJaxReady } from './loader'\n\n// Round to integer to bound cache entries — math is keyed by\n// (source, color, sizePx). Font sizes in the library are a small\n// fixed set (14, 16, 24, 36), so no power-of-two bucketing needed;\n// integer rounding handles minor floating-point variance.\nconst normalizeSize = (px: number): number => Math.max(8, Math.round(px))\n\n/** Result of a successful math compile + raster. */\nexport type MathBitmap = {\n bitmap: ImageBitmap\n /** Width in logical CSS pixels at the requested font size. */\n width: number\n /** Height in logical CSS pixels at the requested font size. */\n height: number\n /**\n * Baseline offset in CSS pixels (positive = bitmap top sits ABOVE\n * the text baseline; the bottom dips below by `height - baseline`).\n * Parsed from MathJax's `vertical-align: -Nex` style attribute.\n */\n baselineOffset: number\n}\n\ntype Entry =\n | { state: 'pending' }\n | { state: 'ready'; bitmap: MathBitmap }\n | { state: 'error'; err: unknown }\n\nconst cache = new Map<string, Entry>()\nconst compileQueue: Array<{ key: string; source: string; color: string; sizePx: number }> = []\nlet compileScheduled = false\n\n// ---- epoch ----------------------------------------------------------\n// Bumped once per drained compile batch (not per formula), to amortize\n// text bitmap invalidation. Subscribed by the text bitmap cache.\n\nlet mathEpoch = 0\nconst epochSubscribers = new Set<() => void>()\n\nexport const getMathEpoch = (): number => mathEpoch\n\nexport const subscribeMathEpoch = (cb: () => void): (() => void) => {\n epochSubscribers.add(cb)\n return () => {\n epochSubscribers.delete(cb)\n }\n}\n\nconst bumpMathEpoch = (): void => {\n mathEpoch += 1\n for (const cb of epochSubscribers) cb()\n}\n\n// ---- public API ----------------------------------------------------\n\n/**\n * Look up a math bitmap or kick off compilation. Returns the cached\n * bitmap if ready, `null` if still loading / queued (caller should\n * paint a placeholder this frame). Triggers a math-epoch bump when\n * the formula resolves.\n *\n * `sizePx` is the on-screen height in logical px (typically the line\n * height of the surrounding text × DPR).\n */\nexport const getMathBitmap = (source: string, color: string, sizePx: number): MathBitmap | null => {\n const size = normalizeSize(sizePx)\n const key = `${size}:${color}:${source}`\n const existing = cache.get(key)\n if (existing) {\n if (existing.state === 'ready') return existing.bitmap\n return null\n }\n // Miss — enqueue for compile. The compile path triggers the lazy\n // MathJax load on its own; if it's not ready, we re-queue from\n // onMathJaxReady.\n cache.set(key, { state: 'pending' })\n compileQueue.push({ key, source, color, sizePx: size })\n scheduleCompile()\n return null\n}\n\nconst scheduleCompile = (): void => {\n if (compileScheduled) return\n compileScheduled = true\n if (typeof window === 'undefined' || typeof requestAnimationFrame === 'undefined') {\n // SSR / Node — drain synchronously so tests still progress.\n void drainQueue()\n return\n }\n requestAnimationFrame(() => {\n void drainQueue()\n })\n}\n\n/**\n * Compile loop. Time-sliced: each rAF tick spends up to 4ms on\n * compiles, then yields. After the queue drains, bumps the math\n * epoch once so text bitmaps containing math can invalidate in a\n * single pass.\n */\nconst drainQueue = async (): Promise<void> => {\n compileScheduled = false\n if (compileQueue.length === 0) return\n\n const mj = getMathJax()\n if (!mj) {\n // Not loaded yet — wait for the import, then resume.\n onMathJaxReady(() => scheduleCompile())\n return\n }\n\n const FRAME_BUDGET_MS = 4\n const start = performance.now()\n let didResolve = false\n\n while (compileQueue.length > 0 && performance.now() - start < FRAME_BUDGET_MS) {\n const item = compileQueue.shift()!\n if (cache.get(item.key)?.state !== 'pending') continue\n try {\n const bitmap = await compileOne(mj, item.source, item.color, item.sizePx)\n cache.set(item.key, { state: 'ready', bitmap })\n didResolve = true\n } catch (err) {\n cache.set(item.key, { state: 'error', err })\n console.warn(`[math] failed to compile \"${item.source}\":`, err)\n }\n }\n\n if (didResolve) bumpMathEpoch()\n if (compileQueue.length > 0) scheduleCompile()\n}\n\nconst compileOne = async (\n mj: NonNullable<ReturnType<typeof getMathJax>>,\n source: string,\n color: string,\n sizePx: number,\n): Promise<MathBitmap> => {\n // Step 1: LaTeX → SVG via MathJax. `em` controls the typesetting\n // scale; we pass the requested px so the SVG comes out at the right\n // intrinsic size.\n const svgElement = await mj.tex2svgPromise(source, { display: false, em: sizePx, ex: sizePx / 2 })\n // Prefer `serializeXML` (v4 canonical) so namespaces survive; fall\n // back to `outerHTML` for v3 compatibility.\n let markup = mj.startup.adaptor.serializeXML\n ? mj.startup.adaptor.serializeXML(svgElement)\n : mj.startup.adaptor.outerHTML(svgElement)\n // MathJax wraps the actual <svg> in a <mjx-container> element with\n // a sibling <mjx-speech> block for accessibility. We need just the\n // outer <svg>...</svg> for the blob.\n //\n // With `linebreaks.inline: false` set in the loader config, MathJax\n // produces exactly ONE <svg> per formula and no <mjx-break> markers.\n // We still defensively pick the FIRST <svg>...</svg> here (non-greedy)\n // in case the config doesn't fully prevent breaks for pathological\n // inputs — losing trailing fragments is preferable to a parse error\n // that kills the whole formula.\n const svgMatch = /<svg[\\s\\S]*?<\\/svg>/.exec(markup)\n if (svgMatch) markup = svgMatch[0]\n // Strip accessibility / semantic attributes. MathJax v4 emits a\n // huge set of data-semantic-*, data-speech-*, aria-*, role, and\n // focusable attributes whose values contain XML-encoded HTML. When\n // the SVG is loaded via a Blob URL into `<img>`, the strict XML\n // parser chokes on some of these (specifically the speech / braille\n // ones for certain formulas). We're rendering to canvas — no AT\n // consumes these — so dropping them is safe and shrinks the blob\n // ~70%.\n markup = markup\n .replace(/\\sdata-semantic-[a-z0-9-]+=\"[^\"]*\"/g, '')\n .replace(/\\sdata-speech-[a-z0-9-]+=\"[^\"]*\"/g, '')\n .replace(/\\sdata-mml-node=\"[^\"]*\"/g, '')\n .replace(/\\sdata-latex=\"[^\"]*\"/g, '')\n .replace(/\\sdata-braille[a-z0-9-]*=\"[^\"]*\"/g, '')\n .replace(/\\saria-[a-z0-9-]+=\"[^\"]*\"/g, '')\n .replace(/\\srole=\"[^\"]*\"/g, '')\n .replace(/\\sfocusable=\"[^\"]*\"/g, '')\n .replace(/\\stabindex=\"[^\"]*\"/g, '')\n .replace(/\\shas-speech=\"[^\"]*\"/g, '')\n // Ensure the xmlns is present (the lite-adaptor sometimes omits it,\n // which makes the <img> blob fail with a generic onerror).\n if (!markup.includes('xmlns=\"http://www.w3.org/2000/svg\"')) {\n markup = markup.replace(/^<svg\\b/, '<svg xmlns=\"http://www.w3.org/2000/svg\"')\n }\n\n // Step 2: tint. MathJax SVG output uses `currentColor` for glyph\n // fills; substitute the requested color.\n markup = markup.replace(/currentColor/gi, color)\n\n // Step 3: parse intrinsic dims + baseline offset from the SVG markup\n // before rasterizing. The outer <svg> carries `width` / `height` in\n // ex units and a `style=\"vertical-align: -Nex\"` for baseline.\n const dims = parseSvgDims(markup, sizePx)\n\n // Step 4: rasterize via Blob URL → Image → createImageBitmap.\n const blob = new Blob([markup], { type: 'image/svg+xml' })\n const url = URL.createObjectURL(blob)\n try {\n let img: HTMLImageElement\n try {\n img = await loadImage(url)\n } catch (e) {\n // Log the full markup so we can see WHY the SVG failed to load.\n console.warn(`[math] SVG failed to load for \"${source}\":\\n${markup}`)\n throw e\n }\n // Rasterize at 2x for crisp small glyphs without committing to a\n // full DPR-aware bucket key — sizes are already bucketed.\n const rasterW = Math.max(1, Math.ceil(dims.width * 2))\n const rasterH = Math.max(1, Math.ceil(dims.height * 2))\n const bitmap = await createImageBitmap(img, {\n resizeWidth: rasterW,\n resizeHeight: rasterH,\n resizeQuality: 'high',\n })\n return {\n bitmap,\n width: dims.width,\n height: dims.height,\n baselineOffset: dims.baselineOffset,\n }\n } finally {\n URL.revokeObjectURL(url)\n }\n}\n\nconst loadImage = (src: string): Promise<HTMLImageElement> =>\n new Promise((resolve, reject) => {\n const img = new Image()\n img.onload = () => resolve(img)\n img.onerror = e => reject(e)\n img.src = src\n })\n\n/**\n * Parse `<svg width=\"Nex\" height=\"Nex\" style=\"vertical-align: -Nex\">`\n * from the markup. Approximate `1 ex ≈ sizePx / 2`.\n */\nconst parseSvgDims = (\n markup: string,\n sizePx: number,\n): { width: number; height: number; baselineOffset: number } => {\n const exToPx = sizePx / 2\n const widthMatch = /<svg[^>]*\\bwidth=\"([0-9.]+)ex\"/.exec(markup)\n const heightMatch = /<svg[^>]*\\bheight=\"([0-9.]+)ex\"/.exec(markup)\n const vAlignMatch = /vertical-align:\\s*(-?[0-9.]+)ex/.exec(markup)\n\n const widthEx = widthMatch ? Number.parseFloat(widthMatch[1]!) : 2\n const heightEx = heightMatch ? Number.parseFloat(heightMatch[1]!) : 2\n const vAlignEx = vAlignMatch ? Number.parseFloat(vAlignMatch[1]!) : 0\n\n const width = widthEx * exToPx\n const height = heightEx * exToPx\n // vertical-align is negative = descend below baseline.\n // baselineOffset is the px from the bitmap top down to the text\n // baseline. If the bitmap descends `d` below baseline, baseline is\n // at `height - d` from the top.\n const descent = Math.abs(vAlignEx) * exToPx\n const baselineOffset = height - descent\n\n return { width, height, baselineOffset }\n}\n\n/** Test / debug aid. */\nexport const clearMathCache = (): void => {\n cache.clear()\n compileQueue.length = 0\n compileScheduled = false\n}\n\n/** Test / debug aid. */\nexport const getMathCacheSize = (): number => cache.size\n","import type { FontFamily, FontSize, TextStyle } from '../types'\n/**\n * Text measurement cache — ported from `canvas-lite-markdown.tsx`.\n *\n * `ctx.measureText` is the single most expensive operation in canvas text.\n * We memoize widths by (font, text) — a 5k-entry LRU keeps the working\n * set hot during pan/zoom and re-layouts.\n *\n * Cache is module-level so multiple Canvas instances share it. Eviction is\n * FIFO via Map iteration order (Maps preserve insertion order in JS).\n */\nimport { DEFAULT_TEXT_COLOR, FONT_FAMILY_MAP, FONT_SIZE_MAP } from './defaults'\nimport { getMathBitmap } from './math'\nimport type { InlineType } from './tokens'\n\nconst MAX_WIDTH_CACHE_SIZE = 5000\n\n// Shared one-off canvas used purely for measurement.\nconst measureCanvas: HTMLCanvasElement | null =\n typeof document !== 'undefined' ? document.createElement('canvas') : null\nconst measureCtx: CanvasRenderingContext2D | null = measureCanvas?.getContext('2d') ?? null\n\nconst widthCache = new Map<string, number>()\n\n/**\n * Returns the canvas `font` string for a given run.\n */\nexport const getCanvasFont = (opts: {\n type: InlineType\n fontFamily: FontFamily\n fontSize: FontSize\n textStyle: TextStyle\n}): string => {\n const weight = opts.type === 'bold' || opts.textStyle === 'bold' ? '700' : '400'\n const italic = opts.type === 'italic' || opts.textStyle === 'italic' ? 'italic' : 'normal'\n const family = opts.type === 'code' ? FONT_FAMILY_MAP.monospace : FONT_FAMILY_MAP[opts.fontFamily]\n return `${italic} ${weight} ${FONT_SIZE_MAP[opts.fontSize]}px ${family}`\n}\n\n/**\n * Memoized width measurement. Cache key includes font (so different\n * fonts/sizes/styles get separate entries).\n *\n * Falls back to a heuristic when no canvas is available (SSR / Node tests).\n */\nexport const measureText = (opts: {\n text: string\n type: InlineType\n fontFamily: FontFamily\n fontSize: FontSize\n textStyle: TextStyle\n}): number => {\n if (!opts.text) return 0\n // Math width comes from the bitmap cache (keyed by source + color +\n // size). Use DEFAULT_TEXT_COLOR so the lookup hits the SAME cache\n // entry that paint will later look up (paint's fallback is also\n // DEFAULT_TEXT_COLOR). Mismatch here = paint never finds the\n // bitmap layout compiled.\n if (opts.type === 'math') {\n const fontSizePx = FONT_SIZE_MAP[opts.fontSize]\n const bitmap = getMathBitmap(opts.text, DEFAULT_TEXT_COLOR, fontSizePx)\n if (bitmap) return bitmap.width\n return Math.max(8, opts.text.length * fontSizePx * 0.55 + fontSizePx)\n }\n const font = getCanvasFont(opts)\n const key = `${font}|${opts.text}`\n const cached = widthCache.get(key)\n if (cached !== undefined) return cached\n\n if (!measureCtx) {\n return opts.text.length * FONT_SIZE_MAP[opts.fontSize] * 0.55\n }\n\n measureCtx.font = font\n const width = measureCtx.measureText(opts.text).width\n widthCache.set(key, width)\n if (widthCache.size > MAX_WIDTH_CACHE_SIZE) {\n const oldestKey = widthCache.keys().next().value\n if (oldestKey !== undefined) widthCache.delete(oldestKey)\n }\n return width\n}\n\n/**\n * Clears all cached measurements. Called by the font-epoch system on\n * font load — fallback metrics returned before fonts settle would be\n * wrong, so we re-measure everything once they're ready.\n */\nexport const clearMeasureCache = (): void => {\n widthCache.clear()\n}\n","import type { FontFamily, FontSize, TextStyle } from '../types'\n/**\n * Wrap engine — ported from canvas-lite-markdown.tsx.\n *\n * Takes a stream of tokens + the wrap width + font settings; produces\n * an array of LayoutLines (text lines, code-block lines, rule lines).\n * Each text line is a sequence of StyledRuns (text + inline type).\n *\n * Code blocks wrap by character width using monospace metrics so they\n * fit precisely. Text lines wrap by word, falling back to char-wrap\n * for words longer than `width`.\n */\nimport { CODE_BLOCK_PADDING_X, DEFAULT_TEXT_COLOR, FONT_SIZE_MAP } from './defaults'\nimport { getMathBitmap } from './math'\nimport { measureText } from './measure'\nimport type { InlineType, Token } from './tokens'\n\nexport type StyledRun = {\n text: string\n type: InlineType\n}\n\nexport type LayoutLine =\n | { kind: 'text'; runs: StyledRun[] }\n | { kind: 'code-block'; runs: StyledRun[]; isFirst: boolean; isLast: boolean }\n | { kind: 'rule'; double: boolean }\n\nexport type LayoutOptions = {\n width: number\n fontFamily: FontFamily\n fontSize: FontSize\n textStyle: TextStyle\n /**\n * Used to key the math bitmap cache. Both layout (for measured dims)\n * and paint (for the actual bitmap) need to query the same cache\n * entry. Defaults to `#000000` for estimate-only callers.\n */\n textColor?: string\n}\n\nconst splitChunks = (text: string): string[] => text.split(/(\\s+)/g).filter(Boolean)\n\n/**\n * Wraps one fenced-code line by character width using monospace metrics.\n * Preserves whitespace and guarantees fit within `maxWidth`.\n */\nconst wrapCodeLine = (line: string, opts: LayoutOptions, maxWidth: number): string[] => {\n const normalized = line.replace(/\\t/g, ' ')\n if (!normalized) return ['']\n\n const wrapped: string[] = []\n let part = ''\n\n for (const ch of normalized) {\n const next = part + ch\n const nextWidth = measureText({\n text: next,\n type: 'code',\n fontFamily: opts.fontFamily,\n fontSize: opts.fontSize,\n textStyle: 'normal',\n })\n\n if (part && nextWidth > maxWidth) {\n wrapped.push(part)\n part = ch\n } else {\n part = next\n }\n }\n\n if (part) wrapped.push(part)\n return wrapped\n}\n\n/**\n * Turns tokens into drawable lines. Output consumed by the canvas paint pass.\n */\nexport const layoutTokens = (tokens: Token[], opts: LayoutOptions): LayoutLine[] => {\n const maxWidth = Math.max(40, opts.width)\n\n const lines: LayoutLine[] = []\n let currentRuns: StyledRun[] = []\n let cursorX = 0\n\n const pushLine = (): void => {\n lines.push({ kind: 'text', runs: currentRuns })\n currentRuns = []\n cursorX = 0\n }\n\n const pushRule = (double: boolean): void => {\n if (currentRuns.length > 0) pushLine()\n lines.push({ kind: 'rule', double })\n }\n\n const pushCodeBlock = (content: string): void => {\n if (currentRuns.length > 0) pushLine()\n const rawLines = content.split('\\n')\n const visualRuns: StyledRun[][] = []\n const codeMaxWidth = Math.max(20, maxWidth - CODE_BLOCK_PADDING_X * 2)\n\n for (const raw of rawLines) {\n for (const part of wrapCodeLine(raw, opts, codeMaxWidth)) {\n visualRuns.push([{ text: part, type: 'code' }])\n }\n }\n\n if (visualRuns.length === 0) {\n lines.push({ kind: 'code-block', runs: [], isFirst: true, isLast: true })\n return\n }\n\n for (let index = 0; index < visualRuns.length; index++) {\n const runs = visualRuns[index]!\n lines.push({\n kind: 'code-block',\n runs,\n isFirst: index === 0,\n isLast: index === visualRuns.length - 1,\n })\n }\n }\n\n const pushChunk = (chunk: string, type: InlineType): void => {\n if (!chunk) return\n\n const chunkWidth = measureText({\n text: chunk,\n type,\n fontFamily: opts.fontFamily,\n fontSize: opts.fontSize,\n textStyle: opts.textStyle,\n })\n\n if (!chunk.trim()) {\n if (cursorX === 0) return\n currentRuns.push({ text: chunk, type })\n cursorX += chunkWidth\n return\n }\n\n if (cursorX > 0 && cursorX + chunkWidth > maxWidth) {\n pushLine()\n }\n\n if (chunkWidth > maxWidth && chunk.length > 1) {\n let part = ''\n for (const ch of chunk) {\n const next = part + ch\n const nextWidth = measureText({\n text: next,\n type,\n fontFamily: opts.fontFamily,\n fontSize: opts.fontSize,\n textStyle: opts.textStyle,\n })\n if (cursorX > 0 && nextWidth > maxWidth) {\n if (part) {\n currentRuns.push({ text: part, type })\n cursorX += measureText({\n text: part,\n type,\n fontFamily: opts.fontFamily,\n fontSize: opts.fontSize,\n textStyle: opts.textStyle,\n })\n }\n pushLine()\n part = ch\n } else {\n part = next\n }\n }\n\n if (part) {\n currentRuns.push({ text: part, type })\n cursorX += measureText({\n text: part,\n type,\n fontFamily: opts.fontFamily,\n fontSize: opts.fontSize,\n textStyle: opts.textStyle,\n })\n }\n return\n }\n\n currentRuns.push({ text: chunk, type })\n cursorX += chunkWidth\n }\n\n const fontSizePx = FONT_SIZE_MAP[opts.fontSize]\n // Must match paint-canvas's fallback so the math cache lookup keys\n // align between layout (measuring) and paint (drawing). The cache\n // is keyed by (source, color, size); a mismatch means paint never\n // hits the bitmap layout compiled, and the placeholder sticks.\n const mathColor = opts.textColor || DEFAULT_TEXT_COLOR\n\n for (const token of tokens) {\n if (token.type === 'code-block') {\n pushCodeBlock(token.content)\n continue\n }\n if (token.type === 'br') {\n pushLine()\n continue\n }\n if (token.type === 'hr') {\n pushRule(false)\n continue\n }\n if (token.type === 'hr-double') {\n pushRule(true)\n continue\n }\n if (token.type === 'math') {\n // Math is an inline atom — never whitespace-split. Width comes\n // from the cached bitmap (if compiled) or a length-based\n // placeholder. When the cache resolves later, the math-epoch\n // bump invalidates this layout's bitmap cache entry.\n const bitmap = getMathBitmap(token.content, mathColor, fontSizePx)\n const width = bitmap\n ? bitmap.width\n : // Placeholder: roughly proportional to source length so wrap\n // doesn't dramatically shift on resolve. Capped at maxWidth.\n Math.min(maxWidth, token.content.length * fontSizePx * 0.55 + fontSizePx)\n if (cursorX > 0 && cursorX + width > maxWidth) pushLine()\n currentRuns.push({ text: token.content, type: 'math' })\n cursorX += width\n continue\n }\n for (const chunk of splitChunks(token.content)) pushChunk(chunk, token.type)\n }\n\n if (currentRuns.length > 0 || lines.length === 0) {\n lines.push({ kind: 'text', runs: currentRuns })\n }\n\n return lines\n}\n","/**\n * Font-load reactivity — ported from `canvas-lite-markdown.tsx`.\n *\n * Custom fonts (Architects Daughter, Inconsolata, etc.) load asynchronously\n * — `ctx.measureText` returns fallback metrics until they settle, which\n * means initial layouts would be wrong if we trusted them. The font-epoch\n * mechanism:\n *\n * 1. On first subscribe, attach listeners to document.fonts.ready and\n * 'loadingdone'.\n * 2. When fonts settle, bump an integer epoch and notify subscribers.\n * 3. Subscribers (measureCache + bitmap cache) clear themselves on bump.\n * 4. The renderer re-paints (one frame of \"jump\" as fonts settle, then\n * stable forever).\n */\nimport { clearMeasureCache } from './measure'\n\nconst fontEpochListeners = new Set<(epoch: number) => void>()\nlet fontEpoch = 0\nlet fontTrackingInitialized = false\n\nconst emitFontEpoch = (): void => {\n for (const listener of fontEpochListeners) listener(fontEpoch)\n}\n\n/**\n * Bumps the epoch and tells everyone. Caches (measure, bitmap) clear\n * themselves so the next paint pulls fresh metrics.\n */\nconst bumpFontEpoch = (): void => {\n fontEpoch += 1\n clearMeasureCache()\n emitFontEpoch()\n}\n\nconst initFontTracking = (): void => {\n if (fontTrackingInitialized) return\n fontTrackingInitialized = true\n\n if (typeof document === 'undefined' || !('fonts' in document)) return\n const fontSet = document.fonts\n let didSettleInitialFonts = false\n\n fontSet.ready\n .then(() => {\n if (didSettleInitialFonts) return\n didSettleInitialFonts = true\n bumpFontEpoch()\n })\n .catch(() => {\n /* ignore */\n })\n\n fontSet.addEventListener?.('loadingdone', () => {\n if (!didSettleInitialFonts) didSettleInitialFonts = true\n bumpFontEpoch()\n })\n}\n\n/**\n * Subscribe to font-epoch bumps. Lazy-initializes the document.fonts\n * listeners on first call. Returns an unsubscribe.\n */\nexport const subscribeFontEpoch = (listener: (epoch: number) => void): (() => void) => {\n initFontTracking()\n fontEpochListeners.add(listener)\n return () => {\n fontEpochListeners.delete(listener)\n }\n}\n\n/**\n * Current epoch — included in bitmap-cache keys so they invalidate when\n * custom fonts settle.\n */\nexport const getFontEpoch = (): number => fontEpoch\n","/**\n * Zoom + DPR quantization and moving-vs-idle render scale — ported\n * verbatim from canvas-lite-markdown.tsx.\n *\n * Bitmap-cache keys include `zoomBucket` and `dprBucket` instead of raw\n * camera.z and devicePixelRatio. Without quantization, tiny floating-\n * point drift on each wheel event would explode the cache. With it, a\n * zoom from 1.00 → 1.04 hits the same bucket and reuses the same bitmap.\n *\n * `resolveRenderScale` is the LOD selector: lower-quality rasterization\n * during pan/zoom motion, full quality on idle. Saves up to 60% of the\n * sample bitmap pixels when nothing's changing for the user anyway.\n */\nconst MIN_RENDER_SCALE = 0.15\nconst MAX_RENDER_SCALE = 1.5\nconst MAX_RENDER_WIDTH = 2000\nconst MAX_RENDER_HEIGHT = 1200\n\n/**\n * Buckets zoom to avoid cache churn from sub-1%-zoom changes.\n */\nexport const quantizeZoom = (value: number): number => {\n if (!Number.isFinite(value)) return 1\n return Math.max(0.1, Math.round(value * 10) / 10)\n}\n\n/**\n * Buckets DPR to keep cache keys stable across tiny devicePixelRatio\n * variance (e.g. when a window crosses a mixed-DPR monitor boundary).\n */\nexport const quantizeDpr = (value: number): number => {\n if (!Number.isFinite(value)) return 1\n const clamped = Math.max(1, Math.min(3, value))\n return Math.round(clamped * 4) / 4\n}\n\n/**\n * Chooses a render scale from a base scale, the current zoom bucket,\n * and whether the camera (or shape) is in motion. While moving, drop\n * quality for throughput; on idle, snap back to full quality.\n */\nexport const resolveRenderScale = (baseScale: number, zoom: number, isMoving: boolean): number => {\n const clampedBase = Math.max(MIN_RENDER_SCALE, Math.min(MAX_RENDER_SCALE, baseScale))\n let idleScale = clampedBase\n if (zoom <= 0.4) {\n idleScale = 0.45\n } else if (zoom <= 0.7) {\n idleScale = 0.85\n } else if (zoom <= 1) {\n idleScale = 1.15\n } else if (zoom <= 1.8) {\n idleScale = 1.35\n } else {\n idleScale = 1 + (zoom - 1.8) * 0.2\n }\n\n idleScale = Math.max(MIN_RENDER_SCALE, Math.min(MAX_RENDER_SCALE, idleScale))\n\n if (isMoving) {\n let movingScale = idleScale * (zoom >= 0.4 ? 0.72 : 0.6)\n if (zoom < 0.4) {\n movingScale = Math.min(movingScale, 0.22)\n } else if (zoom <= 0.7) {\n movingScale = Math.min(movingScale, 0.4)\n }\n return Math.max(MIN_RENDER_SCALE, Math.min(0.65, movingScale))\n }\n\n return idleScale\n}\n\n/**\n * Applies the absolute backing-store size cap so very-wide / very-tall\n * shapes don't blow up memory at high zoom.\n */\nexport const clampEffectiveScale = (baseScale: number, width: number, height: number): number => {\n const limiter = Math.min(\n 1,\n MAX_RENDER_WIDTH / Math.max(1, width * baseScale),\n MAX_RENDER_HEIGHT / Math.max(1, height * baseScale),\n )\n return baseScale * limiter\n}\n","import type { FontFamily, FontSize, TextStyle } from '../types'\n/**\n * Height-only probe for autosizing text shapes — ported from\n * canvas-lite-markdown.tsx.\n *\n * Same tokenize + layout pipeline as the paint pass; just skips the\n * actual draw. Used by the edit-mode autosize and by any consumer that\n * needs to compute the height a piece of markdown will take at a given\n * width.\n */\nimport { CODE_BLOCK_MARGIN_Y, CONTENT_HEIGHT_BUFFER, LINE_HEIGHT_MAP } from './defaults'\nimport { type LayoutLine, layoutTokens } from './layout'\nimport { tokenize } from './tokens'\n\nexport type EstimateOptions = {\n text: string\n width: number\n fontFamily?: FontFamily\n fontSize?: FontSize\n textStyle?: TextStyle\n}\n\nconst getLineAdvance = (line: LayoutLine, lineHeight: number): number => {\n if (line.kind !== 'code-block') return lineHeight\n let advance = lineHeight\n if (line.isFirst) advance += CODE_BLOCK_MARGIN_Y\n if (line.isLast) advance += CODE_BLOCK_MARGIN_Y\n return advance\n}\n\nexport const getContentHeight = (lines: LayoutLine[], lineHeight: number): number =>\n Math.max(\n lineHeight,\n lines.reduce((sum, line) => sum + getLineAdvance(line, lineHeight), 0),\n )\n\nexport const estimateMarkdownContentHeight = ({\n text,\n width,\n fontFamily = 'handwriting',\n fontSize = 'M',\n textStyle = 'normal',\n}: EstimateOptions): number => {\n const normalizedText = text.trim()\n if (!normalizedText) return 0\n\n const resolvedWidth = Math.max(40, Math.ceil(width))\n const lines = layoutTokens(tokenize(text), {\n width: resolvedWidth,\n fontFamily,\n fontSize,\n textStyle,\n })\n const lineHeight = LINE_HEIGHT_MAP[fontSize]\n return getContentHeight(lines, lineHeight) + CONTENT_HEIGHT_BUFFER\n}\n\nexport const getMarkdownLineHeightPx = (fontSize: FontSize): number => LINE_HEIGHT_MAP[fontSize]\n","import type { FontFamily, FontSize, TextAlign, TextStyle } from '../types'\n/**\n * Paints fully-laid-out markdown into a canvas context — ported from\n * canvas-lite-markdown.tsx with the output-stage simplification noted in\n * ARCHITECTURE.md §8.\n *\n * Caller is responsible for sizing the canvas + applying its own\n * transform. This function just paints content at (0, 0) into a rect of\n * the given (width, height).\n */\nimport {\n CODE_BG_COLOR,\n CODE_BLOCK_MARGIN_Y,\n CODE_BLOCK_PADDING_X,\n DEFAULT_HIGHLIGHT_COLOR,\n DEFAULT_TEXT_COLOR,\n FONT_SIZE_MAP,\n LINE_HEIGHT_MAP,\n LINK_COLOR,\n} from './defaults'\nimport { getContentHeight } from './estimate-height'\nimport { type LayoutLine, layoutTokens } from './layout'\nimport { getMathBitmap } from './math'\nimport { getCanvasFont, measureText } from './measure'\nimport { tokenize } from './tokens'\nimport type { InlineType } from './tokens'\n\nexport type DrawTextOptions = {\n text: string\n width: number\n height: number\n align: TextAlign\n fontFamily: FontFamily\n fontSize: FontSize\n textStyle: TextStyle\n textColor: string\n highlightColor: string\n}\n\nconst getLineAdvance = (line: LayoutLine, lineHeight: number): number => {\n if (line.kind !== 'code-block') return lineHeight\n let advance = lineHeight\n if (line.isFirst) advance += CODE_BLOCK_MARGIN_Y\n if (line.isLast) advance += CODE_BLOCK_MARGIN_Y\n return advance\n}\n\nconst getTextX = (opts: DrawTextOptions, lineWidth: number): number => {\n if (opts.align === 'center') return Math.floor((opts.width - lineWidth) / 2)\n if (opts.align === 'right') return Math.max(0, opts.width - lineWidth)\n return 0\n}\n\nconst drawRunDecoration = (\n ctx: CanvasRenderingContext2D,\n x: number,\n y: number,\n width: number,\n type: InlineType,\n fontSize: number,\n): void => {\n if (type === 'underline' || type === 'link') {\n const lineY = y + 2\n ctx.beginPath()\n ctx.moveTo(x, lineY)\n ctx.lineTo(x + width, lineY)\n ctx.lineWidth = 1\n ctx.stroke()\n }\n\n if (type === 'strike') {\n const lineY = y - Math.floor(fontSize * 0.35)\n ctx.beginPath()\n ctx.moveTo(x, lineY)\n ctx.lineTo(x + width, lineY)\n ctx.lineWidth = 1\n ctx.stroke()\n }\n}\n\n/**\n * Paints `text` (markdown) into the canvas at (0..width, 0..height) using\n * the laid-out lines and styled runs. Background chips for inline code +\n * highlight, vertical centering when content shorter than height, dashed\n * decorations for underline/strike/link.\n */\nexport const drawTextToCanvas = (ctx: CanvasRenderingContext2D, opts: DrawTextOptions): void => {\n const normalizedText = opts.text.trim()\n if (!normalizedText) return\n\n const lines = layoutTokens(tokenize(opts.text), {\n width: opts.width,\n fontFamily: opts.fontFamily,\n fontSize: opts.fontSize,\n textStyle: opts.textStyle,\n textColor: opts.textColor,\n })\n\n ctx.textBaseline = 'alphabetic'\n ctx.fillStyle = opts.textColor || DEFAULT_TEXT_COLOR\n ctx.strokeStyle = opts.textColor || DEFAULT_TEXT_COLOR\n\n const fontSizePx = FONT_SIZE_MAP[opts.fontSize]\n const lineHeight = LINE_HEIGHT_MAP[opts.fontSize]\n const contentHeight = getContentHeight(lines, lineHeight)\n const availableHeight = Math.max(0, opts.height)\n const shouldCenterVertically = contentHeight <= availableHeight\n const centeredTop = Math.floor((opts.height - contentHeight) / 2)\n const topInset = Math.ceil(fontSizePx * 0.92)\n const startBaseline = shouldCenterVertically\n ? Math.max(topInset, centeredTop + topInset)\n : topInset\n let y = startBaseline\n\n for (const line of lines) {\n const lineTop = y - fontSizePx\n const lineBottom = lineTop + getLineAdvance(line, lineHeight)\n\n if (lineBottom <= 0) {\n y += getLineAdvance(line, lineHeight)\n continue\n }\n if (lineTop >= opts.height) break\n\n if (line.kind === 'code-block') {\n if (line.isFirst) y += CODE_BLOCK_MARGIN_Y\n\n let lineWidth = 0\n for (const run of line.runs) {\n lineWidth += measureText({\n text: run.text,\n type: run.type,\n fontFamily: opts.fontFamily,\n fontSize: opts.fontSize,\n textStyle: 'normal',\n })\n }\n\n const blockX = 0\n const blockY = y - fontSizePx + 2\n const blockWidth = Math.max(10, opts.width)\n const blockHeight = lineHeight\n\n ctx.save()\n ctx.fillStyle = CODE_BG_COLOR\n ctx.fillRect(blockX, blockY, blockWidth, blockHeight)\n ctx.restore()\n\n let x = blockX + CODE_BLOCK_PADDING_X\n if (opts.align === 'center') {\n x = blockX + Math.max(CODE_BLOCK_PADDING_X, Math.floor((blockWidth - lineWidth) / 2))\n } else if (opts.align === 'right') {\n x = blockX + Math.max(CODE_BLOCK_PADDING_X, blockWidth - CODE_BLOCK_PADDING_X - lineWidth)\n }\n\n for (const run of line.runs) {\n const runWidth = measureText({\n text: run.text,\n type: run.type,\n fontFamily: opts.fontFamily,\n fontSize: opts.fontSize,\n textStyle: 'normal',\n })\n ctx.font = getCanvasFont({\n type: run.type,\n fontFamily: opts.fontFamily,\n fontSize: opts.fontSize,\n textStyle: 'normal',\n })\n ctx.fillStyle = opts.textColor || DEFAULT_TEXT_COLOR\n ctx.fillText(run.text, x, y)\n x += runWidth\n }\n\n y += lineHeight\n if (line.isLast) y += CODE_BLOCK_MARGIN_Y\n continue\n }\n\n if (line.kind === 'rule') {\n ctx.save()\n ctx.globalAlpha = 0.55\n ctx.beginPath()\n ctx.moveTo(0, y)\n ctx.lineTo(opts.width, y)\n ctx.lineWidth = 1\n ctx.stroke()\n if (line.double) {\n ctx.beginPath()\n ctx.moveTo(0, y + 3)\n ctx.lineTo(opts.width, y + 3)\n ctx.lineWidth = 1\n ctx.stroke()\n }\n ctx.restore()\n y += lineHeight\n continue\n }\n\n let lineWidth = 0\n for (const run of line.runs) {\n lineWidth += measureText({\n text: run.text,\n type: run.type,\n fontFamily: opts.fontFamily,\n fontSize: opts.fontSize,\n textStyle: opts.textStyle,\n })\n }\n\n let x = getTextX(opts, lineWidth)\n\n for (const run of line.runs) {\n const runWidth = measureText({\n text: run.text,\n type: run.type,\n fontFamily: opts.fontFamily,\n fontSize: opts.fontSize,\n textStyle: opts.textStyle,\n })\n\n // Math runs: blit the cached bitmap if ready, else paint a\n // subdued placeholder (light gray rectangle with `…`). The\n // math-epoch invalidates this bitmap on resolve so the next\n // paint picks up the real glyphs.\n if (run.type === 'math') {\n const mathColor = opts.textColor || DEFAULT_TEXT_COLOR\n const bitmap = getMathBitmap(run.text, mathColor, fontSizePx)\n if (bitmap) {\n // Align the bitmap's baseline to the text baseline `y`.\n // baselineOffset is px from the bitmap top down to baseline.\n ctx.drawImage(bitmap.bitmap, x, y - bitmap.baselineOffset, runWidth, bitmap.height)\n } else {\n ctx.save()\n ctx.fillStyle = 'rgba(148, 163, 184, 0.18)'\n ctx.fillRect(x, y - fontSizePx + 2, runWidth, fontSizePx)\n ctx.fillStyle = '#94a3b8'\n ctx.font = `italic ${Math.max(8, fontSizePx * 0.75)}px system-ui, sans-serif`\n ctx.textBaseline = 'alphabetic'\n ctx.fillText('…', x + runWidth / 2 - 4, y - 2)\n ctx.restore()\n }\n x += runWidth\n continue\n }\n\n if (run.type === 'highlight') {\n ctx.save()\n ctx.fillStyle = opts.highlightColor || DEFAULT_HIGHLIGHT_COLOR\n ctx.fillRect(x - 1, y - fontSizePx + 2, runWidth + 2, fontSizePx + 2)\n ctx.restore()\n }\n\n if (run.type === 'code') {\n ctx.save()\n ctx.fillStyle = CODE_BG_COLOR\n ctx.fillRect(x - 2, y - fontSizePx + 2, runWidth + 4, fontSizePx + 3)\n ctx.restore()\n }\n\n ctx.font = getCanvasFont({\n type: run.type,\n fontFamily: opts.fontFamily,\n fontSize: opts.fontSize,\n textStyle: opts.textStyle,\n })\n const runColor = run.type === 'link' ? LINK_COLOR : opts.textColor || DEFAULT_TEXT_COLOR\n ctx.fillStyle = runColor\n ctx.strokeStyle = runColor\n ctx.fillText(run.text, x, y)\n drawRunDecoration(ctx, x, y, runWidth, run.type, fontSizePx)\n\n x += runWidth\n }\n\n y += lineHeight\n }\n}\n","import type { FontFamily, FontSize, TextAlign, TextStyle } from '../types'\nimport { getFontEpoch, subscribeFontEpoch } from './font-epoch'\nimport { getMathEpoch, subscribeMathEpoch } from './math'\n/**\n * Bitmap cache for rendered markdown content — the architectural rewrite\n * called out in ARCHITECTURE.md §8.\n *\n * dim0's `canvas-lite-markdown.tsx` rendered into a private canvas, called\n * `canvas.toBlob('image/png')`, then wrapped the resulting Blob URL in an\n * `<img>` element. That made sense in a DOM-board context: each note was\n * already a React subtree, and swapping its text for one `<img>` cut DOM\n * paint cost. The async stage there required a queue + listener\n * coalescing + URL.revokeObjectURL lifecycle management — about 150 LOC.\n *\n * In the canvas-harness scene we render into a `<canvas>` already, so the\n * roundtrip to PNG and back is pure waste. This module caches to an\n * `OffscreenCanvas` (or detached `HTMLCanvasElement` fallback) keyed on\n * everything that affects pixel output. On a cache miss we draw\n * synchronously into the cached canvas; on hit we just blit via\n * `ctx.drawImage(cached, x, y, w, h)`.\n *\n * Cache scope is module-global; all `<Canvas>` instances share the same\n * LRU. ~1000-entry cap (configurable on init).\n */\nimport { drawTextToCanvas } from './paint-canvas'\nimport { clampEffectiveScale, quantizeDpr, quantizeZoom, resolveRenderScale } from './render-scale'\n\nconst MAX_CACHE_SIZE = 1000\n\nexport type BitmapCacheRequest = {\n /** Stable id for the source — typically the node id. */\n id: string\n text: string\n /** Logical CSS pixels of the destination rect. */\n width: number\n height: number\n zoom: number\n dpr: number\n isMoving: boolean\n align: TextAlign\n fontFamily: FontFamily\n fontSize: FontSize\n textStyle: TextStyle\n textColor: string\n highlightColor: string\n}\n\nexport type BitmapCacheEntry = {\n /** Backing-store canvas — pass to ctx.drawImage. */\n canvas: HTMLCanvasElement\n /** Logical (CSS) target width — what the caller should draw at. */\n width: number\n /** Logical (CSS) target height. */\n height: number\n}\n\ntype StoredEntry = {\n canvas: HTMLCanvasElement\n width: number\n height: number\n lastUsed: number\n}\n\nconst renderCache = new Map<string, StoredEntry>()\n\n/**\n * Memoize FNV-1a text hashes so the per-frame cache-key build doesn't\n * re-walk the content string for every visible node. Bounded; cleared on\n * font-epoch bump alongside the bitmap cache.\n */\nconst HASH_CACHE_MAX = 2000\nconst textHashCache = new Map<string, string>()\n\n/** Listen for font load → invalidate. */\nsubscribeFontEpoch(() => {\n renderCache.clear()\n textHashCache.clear()\n})\n\n/**\n * Listen for math compile resolves → cause math-bearing bitmaps to\n * miss the cache. We don't actively evict; the new key encodes the\n * bumped epoch so stale entries simply don't match. They LRU out.\n */\nsubscribeMathEpoch(() => {\n // No-op body — the epoch bump alone is enough since `makeKey` reads\n // `getMathEpoch()` for any text containing `$`. We still subscribe\n // to keep the hook active so consumer-side listeners (e.g. the\n // renderer triggering a repaint) can opt in via the same channel.\n})\n\n/**\n * Lookup-or-build. Always returns a non-null entry as long as `text` is\n * non-empty — on miss it draws synchronously and stores. Same call site\n * for hit and miss.\n *\n * Returns null only when the input is empty/whitespace.\n */\nexport const getOrRenderTextBitmap = (req: BitmapCacheRequest): BitmapCacheEntry | null => {\n const text = req.text\n if (!text || !text.trim()) return null\n\n const quantZoom = quantizeZoom(req.zoom)\n const quantDpr = quantizeDpr(req.dpr)\n const renderScale = resolveRenderScale(1, quantZoom, req.isMoving)\n const epoch = getFontEpoch()\n\n const key = makeKey(req, quantZoom, quantDpr, renderScale, epoch)\n\n const cached = renderCache.get(key)\n if (cached) {\n cached.lastUsed = Date.now()\n return { canvas: cached.canvas, width: cached.width, height: cached.height }\n }\n\n const entry = drawIntoNewCanvas(req, quantDpr, renderScale)\n if (!entry) return null\n\n renderCache.set(key, { ...entry, lastUsed: Date.now() })\n evictIfNeeded()\n return { canvas: entry.canvas, width: entry.width, height: entry.height }\n}\n\nconst makeKey = (\n req: BitmapCacheRequest,\n zoom: number,\n dpr: number,\n scale: number,\n epoch: number,\n): string => {\n // Cheap deterministic key — small string concat, no number formatting.\n // cachedTextHash memoizes the FNV-1a walk so a node's content is hashed\n // once across frames, not on every cache lookup.\n //\n // Math-epoch is folded in ONLY when the text contains `$` (cheap\n // includes check). Bitmaps without math never invalidate when math\n // compiles resolve; bitmaps with math get a new key on each epoch\n // bump and stale entries LRU out naturally.\n const mathSuffix = req.text.includes('$') ? `:m${getMathEpoch()}` : ''\n return `${epoch}:${cachedTextHash(req.text)}:${req.width}:${req.height}:${zoom}:${dpr}:${scale}:${req.align}:${req.fontFamily}:${req.fontSize}:${req.textStyle}:${req.textColor}:${req.highlightColor}${mathSuffix}`\n}\n\nconst cachedTextHash = (value: string): string => {\n const hit = textHashCache.get(value)\n if (hit !== undefined) return hit\n const hash = textHash(value)\n // Cap is a simple bound; on overflow clear the whole table rather than\n // pay LRU bookkeeping. The bitmap cache below it remains authoritative.\n if (textHashCache.size >= HASH_CACHE_MAX) textHashCache.clear()\n textHashCache.set(value, hash)\n return hash\n}\n\n/**\n * Fast non-cryptographic hash used to avoid putting full text in the key.\n */\nconst textHash = (value: string): string => {\n let hash = 2166136261\n for (let index = 0; index < value.length; index += 1) {\n hash ^= value.charCodeAt(index)\n hash = Math.imul(hash, 16777619)\n }\n return (hash >>> 0).toString(36)\n}\n\n/**\n * Draws the request into a fresh detached canvas at the resolved scale.\n * Synchronous; returns null if document is unavailable (SSR / Node).\n */\nconst drawIntoNewCanvas = (\n req: BitmapCacheRequest,\n dpr: number,\n baseScale: number,\n): BitmapCacheEntry | null => {\n if (typeof document === 'undefined') return null\n\n const effectiveScale = clampEffectiveScale(baseScale * dpr, req.width, req.height)\n const canvas = document.createElement('canvas')\n canvas.width = Math.max(1, Math.ceil(req.width * effectiveScale))\n canvas.height = Math.max(1, Math.ceil(req.height * effectiveScale))\n\n const ctx = canvas.getContext('2d')\n if (!ctx) return null\n\n // Draw in logical pixels (matches the request width/height) so\n // measureText / layout don't care about the backing-store scale.\n ctx.scale(effectiveScale, effectiveScale)\n\n drawTextToCanvas(ctx, {\n text: req.text,\n width: req.width,\n height: req.height,\n align: req.align,\n fontFamily: req.fontFamily,\n fontSize: req.fontSize,\n textStyle: req.textStyle,\n textColor: req.textColor,\n highlightColor: req.highlightColor,\n })\n\n return { canvas, width: req.width, height: req.height }\n}\n\n/**\n * LRU eviction. Sorts by lastUsed and trims to cap.\n */\nconst evictIfNeeded = (): void => {\n if (renderCache.size <= MAX_CACHE_SIZE) return\n const entries = [...renderCache.entries()].sort((a, b) => a[1].lastUsed - b[1].lastUsed)\n const toRemove = renderCache.size - MAX_CACHE_SIZE\n for (let i = 0; i < toRemove; i++) {\n const victim = entries[i]\n if (!victim) break\n renderCache.delete(victim[0])\n }\n}\n\n/** Test / debug aid. */\nexport const clearTextBitmapCache = (): void => {\n renderCache.clear()\n textHashCache.clear()\n}\n\n/** Test / debug aid. */\nexport const getTextBitmapCacheSize = (): number => renderCache.size\n","/**\n * Brushy edge bodies via perfect-freehand. Used for `solid` rough edges\n * — the dim0 \"Spider-Verse\" look: tapered ends, variable thickness,\n * filled polygon rather than a stroked line.\n *\n * Pipeline:\n * sample polyline → pressure-bell profile → getStroke() → Path2D\n *\n * Caching: the resulting Path2D is keyed on a coarse signature of the\n * sample points + strokeWidth + seed. Subsequent paints (stable scenes)\n * hit the cache and pay only one `ctx.fill()`.\n *\n * `dashed` / `dotted` strokes don't route here — they fall back to\n * `drawRoughEdge` (rough.js linearPath) since a filled polygon can't\n * dash naturally.\n */\nimport { getStroke } from 'perfect-freehand'\nimport type { Vec2 } from '../types'\n\n/**\n * LRU-ish cap on cached Path2Ds. Bigger payload per entry than rough\n * drawables (polygon vertices), so set lower than ROUGH_PATH_CACHE_MAX.\n */\nconst FREEHAND_CACHE_MAX = 500\nconst cache = new Map<string, Path2D>()\n\nconst remember = (key: string, path: Path2D): void => {\n cache.set(key, path)\n if (cache.size > FREEHAND_CACHE_MAX) {\n // Map iteration order is insertion order; evict oldest.\n const oldest = cache.keys().next().value\n if (oldest !== undefined) cache.delete(oldest)\n }\n}\n\n/**\n * Coarse signature: stride-sampled endpoints + length. Quantized to 1px\n * so sub-pixel jitter from camera math doesn't bust the cache every\n * frame. Length is the hash anchor.\n */\nconst signaturePoints = (samples: Vec2[]): string => {\n if (samples.length === 0) return 'e'\n const n = samples.length\n const step = Math.max(1, Math.floor(n / 6))\n const parts: string[] = [String(n)]\n for (let i = 0; i < n; i += step) {\n const p = samples[i]!\n parts.push(`${Math.round(p.x)},${Math.round(p.y)}`)\n }\n const last = samples[n - 1]!\n parts.push(`${Math.round(last.x)},${Math.round(last.y)}`)\n return parts.join('|')\n}\n\ntype StrokeOpts = {\n size: number\n thinning: number\n smoothing: number\n streamline: number\n simulatePressure: false\n last: true\n start: { taper: number; cap: true }\n end: { taper: number; cap: true }\n}\n\n/**\n * perfect-freehand expects `[x, y, pressure]`. Bell profile produces a\n * brush stroke that's thin at both ends and fatter in the middle —\n * matches dim0's signature look.\n */\nconst buildPressurePoints = (samples: Vec2[]): [number, number, number][] => {\n const n = samples.length\n if (n === 0) return []\n const out: [number, number, number][] = new Array(n)\n for (let i = 0; i < n; i++) {\n const t = n === 1 ? 0.5 : i / (n - 1)\n const bell = Math.sin(Math.PI * t)\n const pressure = 0.35 + 0.55 * bell\n const p = samples[i]!\n out[i] = [p.x, p.y, pressure]\n }\n return out\n}\n\n/**\n * Builds the outline polygon and emits a closed Path2D. Quadratic\n * midpoint smoothing on the polygon edges (the tldraw trick) gives\n * soft corners instead of faceted ones.\n */\nconst outlineToPath2D = (ring: number[][]): Path2D => {\n const path = new Path2D()\n const n = ring.length\n if (n === 0) return path\n if (n < 3) {\n path.moveTo(ring[0]![0]!, ring[0]![1]!)\n path.closePath()\n return path\n }\n path.moveTo(ring[0]![0]!, ring[0]![1]!)\n for (let i = 0; i < n; i++) {\n const a = ring[i]!\n const b = ring[(i + 1) % n]!\n const mx = (a[0]! + b[0]!) / 2\n const my = (a[1]! + b[1]!) / 2\n path.quadraticCurveTo(a[0]!, a[1]!, mx, my)\n }\n path.closePath()\n return path\n}\n\n/**\n * Returns a Path2D representing the brushy outline of `samples`. Cached\n * by sample-signature + strokeWidth + seed. Caller fills it with\n * `ctx.fillStyle = stroke; ctx.fill(path)`.\n *\n * `seed` exists to keep the cache key stable per-edge across frames\n * even though perfect-freehand itself is deterministic — different\n * edges produce different polygons because their inputs differ, not\n * because of any random source.\n */\nexport const getOrBuildFreehandPath = (\n samples: Vec2[],\n strokeWidth: number,\n seed: number,\n): Path2D | null => {\n if (samples.length < 2) return null\n const cacheKey = `${seed}|${strokeWidth.toFixed(2)}|${signaturePoints(samples)}`\n const hit = cache.get(cacheKey)\n if (hit) {\n // LRU touch: re-insert at tail.\n cache.delete(cacheKey)\n cache.set(cacheKey, hit)\n return hit\n }\n\n const pts = buildPressurePoints(samples)\n if (pts.length < 2) return null\n\n const size = Math.max(1.2, strokeWidth) * 1.3\n const taper = Math.min(24, size * 3)\n const strokeOpts: StrokeOpts = {\n size,\n thinning: 0.55,\n smoothing: 0.6,\n streamline: 0.55,\n simulatePressure: false,\n last: true,\n start: { taper, cap: true },\n end: { taper, cap: true },\n }\n const ring = getStroke(pts, strokeOpts)\n if (!ring || ring.length === 0) return null\n\n const path = outlineToPath2D(ring)\n remember(cacheKey, path)\n return path\n}\n\n/** Reset state — tests only. */\nexport const __resetFreehandCache = (): void => {\n cache.clear()\n}\n\n/** Diagnostic only. */\nexport const getFreehandCacheSize = (): number => cache.size\n","import { seedFromId } from '../render/rough/cache'\nimport { type ThemeResolver, dashPatternFor } from '../render/shapes/defaults'\nimport {\n DEFAULT_TEXT_COLOR,\n FONT_SIZE_MAP,\n LINE_HEIGHT_MAP,\n getOrRenderTextBitmap,\n measureText,\n subscribeFontEpoch,\n} from '../text'\nimport type { Edge, EdgeStyle, Node, Vec2 } from '../types'\n/**\n * Edge paint pipeline — see ARCHITECTURE.md §6.5–§6.7.\n *\n * Takes a precomputed EdgeGeometry (samples + AABB) and the attached\n * nodes, runs auto-clip, paints the visible polyline, draws arrowheads\n * at the clipped endpoints. World coords; caller already applied the\n * camera transform.\n */\nimport { getPointAndTangentAtArcLength } from './arc-length'\nimport { arrowheadLength, drawArrowhead } from './arrowhead'\nimport type { EdgeGeometry } from './cache'\nimport { clipSamples, fullVisibleClipResult } from './clip'\nimport { getOrBuildFreehandPath } from './freehand'\n\n/** Defaults for edge style — see ARCHITECTURE.md §3.4. */\nconst DEFAULT_EDGE_STYLE: Required<\n Pick<\n EdgeStyle,\n 'strokeColor' | 'strokeWidth' | 'strokeStyle' | 'sourceArrowhead' | 'targetArrowhead'\n >\n> = {\n strokeColor: '#475569',\n strokeWidth: 2,\n strokeStyle: 'solid',\n sourceArrowhead: 'none',\n targetArrowhead: 'arrow-filled',\n}\n\nconst STROKE_VISIBILITY_THRESHOLD_PX = 0.5\n\n/** Below this on-screen length, an arrowhead is invisible noise; skip it. */\nconst ARROWHEAD_VISIBILITY_THRESHOLD_PX = 2\n\n/**\n * How many polyline samples to skip per drawn segment when painting the\n * body. The cached sample array is 32 segments for visual smoothness at\n * full zoom, but at low zoom adjacent samples are within a fraction of a\n * pixel — drawing every-Nth is indistinguishable but cuts work N-fold.\n *\n * Hit-test, auto-clip, and arrowhead-tangent still walk the full sample\n * array — only the per-frame path build skips. So no correctness impact.\n */\nconst samplePaintStride = (scale: number): number => {\n if (scale < 0.15) return 8\n if (scale < 0.3) return 4\n if (scale < 0.7) return 2\n return 1\n}\n\n/**\n * Edge paint entry. `scale` is the world → device factor (camera.z ×\n * dpr) — kept for back-compat with PNG export and tests. `opts.zoom`,\n * `opts.dpr`, `opts.isMoving` control the label bitmap-cache LOD; if\n * omitted, derived from `scale` (zoom = scale, dpr = 1, idle).\n */\nexport const drawEdge = (\n ctx: CanvasRenderingContext2D,\n edge: Edge,\n geom: EdgeGeometry,\n sourceNode: Node | null,\n targetNode: Node | null,\n scale: number,\n theme?: ThemeResolver,\n opts?: { roughEnabled?: boolean; zoom?: number; dpr?: number; isMoving?: boolean },\n): void => {\n if (edge.hidden) return\n const samples = geom.samples\n if (samples.length < 2) return\n\n const style = edge.style\n const strokeWidth =\n typeof style?.strokeWidth === 'number'\n ? style.strokeWidth\n : ((theme?.('strokeWidth') as number | undefined) ?? DEFAULT_EDGE_STYLE.strokeWidth)\n if (strokeWidth * scale < STROKE_VISIBILITY_THRESHOLD_PX) return\n\n const strokeColor =\n typeof style?.strokeColor === 'string'\n ? style.strokeColor\n : ((theme?.('edge.strokeColor') as string | undefined) ?? DEFAULT_EDGE_STYLE.strokeColor)\n const sourceArrowhead = style?.sourceArrowhead ?? DEFAULT_EDGE_STYLE.sourceArrowhead\n const targetArrowhead = style?.targetArrowhead ?? DEFAULT_EDGE_STYLE.targetArrowhead\n\n // Self-loop doesn't get clipped (both endpoints are on the same node).\n const clip = geom.isSelfLoop\n ? fullVisibleClipResult(samples)\n : clipSamples(samples, sourceNode, targetNode)\n if (!clip.visible) return\n\n // Arrowheads vanish at sub-perceivable on-screen size; the line still\n // shows, just without the cap.\n const headStartWorld = arrowheadLength(sourceArrowhead, strokeWidth)\n const headEndWorld = arrowheadLength(targetArrowhead, strokeWidth)\n const drawSourceArrow =\n sourceArrowhead !== 'none' && headStartWorld * scale >= ARROWHEAD_VISIBILITY_THRESHOLD_PX\n const drawTargetArrow =\n targetArrowhead !== 'none' && headEndWorld * scale >= ARROWHEAD_VISIBILITY_THRESHOLD_PX\n\n // Pull the rendered polyline endpoints back by the arrowhead length so\n // the line tail doesn't poke through the arrow tip — only when actually\n // drawing the arrow.\n const lineStart = drawSourceArrow\n ? retreatFromPoint(samples, clip.startIndex, clip.startPoint, headStartWorld, +1)\n : clip.startPoint\n const lineEnd = drawTargetArrow\n ? retreatFromPoint(samples, clip.endIndex, clip.endPoint, headEndWorld, -1)\n : clip.endPoint\n\n // ---- body ----\n // Rough body when (a) gate from caller is on, (b) style.roughness > 0.\n // Two technique dispatch:\n // solid stroke → perfect-freehand brushy polygon (filled, tapered).\n // dashed/dotted → plain ctx.stroke below (rough.js's per-segment\n // wobble + bowing distorts each dash differently,\n // leaving the line fuzzy rather than reading as a\n // regular pattern). Drops the wobble for dashed\n // edges but the pattern stays cleanly visible.\n const isSolidStroke = (style?.strokeStyle ?? 'solid') === 'solid'\n const useRough = isSolidStroke && (opts?.roughEnabled ?? false) && (style?.roughness ?? 0) > 0\n if (useRough) {\n // Build a clipped sub-sample sequence so the rough body doesn't\n // extend past the visible portion (otherwise the wobble/brush pokes\n // into the node bodies). Re-uses the existing clip indices.\n const clipped: Vec2[] = [lineStart]\n for (let i = clip.startIndex + 1; i < clip.endIndex; i++) clipped.push(samples[i]!)\n clipped.push(lineEnd)\n\n const seed = edge.id ? (seedFromId(edge.id) % 2147483646) + 1 : 1337\n const path = getOrBuildFreehandPath(clipped, strokeWidth, seed)\n if (path) {\n ctx.save()\n ctx.fillStyle = strokeColor\n ctx.fill(path)\n ctx.restore()\n if (drawSourceArrow) {\n const tipDir = directionTowardTip(samples, clip.startIndex, clip.startPoint, +1)\n drawArrowhead(\n ctx,\n sourceArrowhead,\n clip.startPoint,\n negateVec(tipDir),\n strokeColor,\n strokeWidth,\n )\n }\n if (drawTargetArrow) {\n const tipDir = directionTowardTip(samples, clip.endIndex, clip.endPoint, -1)\n drawArrowhead(ctx, targetArrowhead, clip.endPoint, tipDir, strokeColor, strokeWidth)\n }\n if (edge.content?.trim()) drawEdgeLabel(ctx, edge, geom, scale, theme, opts)\n return\n }\n // freehand returned null (degenerate samples) — fall through to plain.\n }\n\n ctx.save()\n ctx.strokeStyle = strokeColor\n ctx.lineWidth = strokeWidth\n ctx.lineCap = 'round'\n ctx.lineJoin = 'round'\n ctx.setLineDash(dashPatternFor(style?.strokeStyle, strokeWidth))\n ctx.beginPath()\n ctx.moveTo(lineStart.x, lineStart.y)\n // Adaptive sampling: stride through the cached polyline at low zoom.\n // Hit-test / clip still use the full samples; only paint skips.\n const stride = samplePaintStride(scale)\n const limit = clip.endIndex - 1\n for (let i = clip.startIndex + stride; i <= limit; i += stride) {\n const p = samples[i]!\n ctx.lineTo(p.x, p.y)\n }\n ctx.lineTo(lineEnd.x, lineEnd.y)\n ctx.stroke()\n ctx.restore()\n\n // ---- arrowheads ----\n if (drawSourceArrow) {\n const tipDir = directionTowardTip(samples, clip.startIndex, clip.startPoint, +1)\n drawArrowhead(\n ctx,\n sourceArrowhead,\n clip.startPoint,\n negateVec(tipDir),\n strokeColor,\n strokeWidth,\n )\n }\n if (drawTargetArrow) {\n const tipDir = directionTowardTip(samples, clip.endIndex, clip.endPoint, -1)\n drawArrowhead(ctx, targetArrowhead, clip.endPoint, tipDir, strokeColor, strokeWidth)\n }\n\n // ---- label (§6.11) ----\n // Painted last so it sits on top of the body + arrowheads.\n if (edge.content?.trim()) {\n drawEdgeLabel(ctx, edge, geom, scale, theme, opts)\n }\n}\n\n/** Minimum on-screen font size — text smaller than this is unreadable\n * noise, skip the chip + blit. Same threshold the node-content paint uses. */\nconst LABEL_MIN_READABLE_FONT_PX = 3\nconst LABEL_MAX_WIDTH_PX = 240\nconst LABEL_PADDING_X = 6\nconst LABEL_PADDING_Y = 2\nconst LABEL_BORDER_RADIUS = 3\n\nconst DEFAULT_LABEL_BACKGROUND = '#ffffff'\n\ntype LabelDims = { width: number; height: number; fontPx: number }\n\n/**\n * Memoizes `computeLabelDims` per (content, font-family, font-size,\n * font-style) tuple. Many edges share labels in real graphs (\"yes\" /\n * \"no\" / \"depends on\"), so the hit rate is high. Cleared on font-epoch\n * bump because `measureText` depends on font load state.\n */\nconst labelDimsCache = new Map<string, LabelDims>()\nconst LABEL_DIMS_CACHE_MAX = 512\n\nsubscribeFontEpoch(() => {\n labelDimsCache.clear()\n})\n\n/**\n * Computes the label dimensions for an edge in world units. Heuristic:\n * - width: single-line measurement of the raw content, clamped to\n * [20, LABEL_MAX_WIDTH_PX]. Beyond the cap, the markdown layout\n * wraps to multiple lines.\n * - height: one line-height per wrap line, plus vertical padding.\n *\n * Returns null if dimensions are zero (empty content).\n */\nconst computeLabelDims = (edge: Edge): LabelDims | null => {\n const content = edge.content\n if (!content) return null\n const style = edge.style\n const fontFamily = style?.fontFamily ?? 'handwriting'\n const fontSize = style?.fontSize ?? 'M'\n const textStyle = style?.textStyle ?? 'normal'\n const cacheKey = `${content}|${fontFamily}|${fontSize}|${textStyle}`\n const hit = labelDimsCache.get(cacheKey)\n if (hit) return hit\n\n const fontPx = FONT_SIZE_MAP[fontSize]\n const naturalWidth = measureText({\n text: content,\n type: 'text',\n fontFamily,\n fontSize,\n textStyle,\n })\n const width = Math.min(LABEL_MAX_WIDTH_PX, Math.max(20, naturalWidth + LABEL_PADDING_X * 2))\n const lines = Math.max(1, Math.ceil(naturalWidth / Math.max(1, width - LABEL_PADDING_X * 2)))\n const height = lines * LINE_HEIGHT_MAP[fontSize] + LABEL_PADDING_Y * 2\n const dims: LabelDims = { width, height, fontPx }\n if (labelDimsCache.size >= LABEL_DIMS_CACHE_MAX) labelDimsCache.clear()\n labelDimsCache.set(cacheKey, dims)\n return dims\n}\n\n/**\n * Memoizes `getPointAndTangentAtArcLength` per (geometry, arcLength).\n * The geometry-cache returns the same object reference until any input\n * changes, so a WeakMap keyed on geometry auto-invalidates for free.\n *\n * Hot path: ~5-8µs / labeled edge saved per frame (the two-pass walk\n * over 32 samples per edge becomes a Map lookup).\n */\nconst anchorCache = new WeakMap<EdgeGeometry, Map<number, { point: Vec2; tangent: Vec2 }>>()\n\nconst getCachedLabelAnchor = (\n geom: EdgeGeometry,\n arcLength: number,\n): { point: Vec2; tangent: Vec2 } => {\n let bucket = anchorCache.get(geom)\n if (!bucket) {\n bucket = new Map()\n anchorCache.set(geom, bucket)\n }\n const hit = bucket.get(arcLength)\n if (hit) return hit\n const fresh = getPointAndTangentAtArcLength(geom.samples, arcLength)\n bucket.set(arcLength, fresh)\n return fresh\n}\n\nconst drawEdgeLabel = (\n ctx: CanvasRenderingContext2D,\n edge: Edge,\n geom: EdgeGeometry,\n scale: number,\n theme?: ThemeResolver,\n opts?: { zoom?: number; dpr?: number; isMoving?: boolean },\n): void => {\n const style = edge.style\n const fontSize = style?.fontSize ?? 'M'\n if (FONT_SIZE_MAP[fontSize] * scale < LABEL_MIN_READABLE_FONT_PX) return\n\n const dims = computeLabelDims(edge)\n if (!dims) return\n\n const t = clamp01(style?.labelArcLength ?? 0.5)\n const { point, tangent } = getCachedLabelAnchor(geom, t)\n const followTangent = style?.labelFollowsTangent === true\n\n // Per-edge override wins; falls through to theme, then to the\n // built-in white default.\n const bg =\n style?.labelBackground ??\n (theme?.('edge.label.background') as string | undefined) ??\n DEFAULT_LABEL_BACKGROUND\n\n ctx.save()\n ctx.translate(point.x, point.y)\n if (followTangent) {\n let angle = Math.atan2(tangent.y, tangent.x)\n // Keep text readable: flip upside-down labels so they read L→R.\n if (angle > Math.PI / 2) angle -= Math.PI\n if (angle < -Math.PI / 2) angle += Math.PI\n ctx.rotate(angle)\n }\n\n // Center the label rect on the anchor.\n const w = dims.width\n const h = dims.height\n const x = -w / 2\n const y = -h / 2\n\n // Chip background (rounded rect). Skipped when transparent so the\n // text renders directly over the edge line.\n if (bg !== 'none' && bg !== 'transparent') {\n ctx.fillStyle = bg\n drawRoundRect(ctx, x, y, w, h, LABEL_BORDER_RADIUS)\n ctx.fill()\n }\n\n // Text bitmap (reuses the Phase-6 cache). Matches the LOD args used\n // by node content paint — zoom = camera.z (not camera.z × dpr); dpr\n // = staticSurface.dpr (sharp on retina); isMoving threads through\n // from the renderer for the motion-LOD drop.\n const bitmap = getOrRenderTextBitmap({\n id: edge.id,\n text: edge.content ?? '',\n width: w,\n height: h,\n zoom: opts?.zoom ?? scale,\n dpr: opts?.dpr ?? 1,\n isMoving: opts?.isMoving ?? false,\n align: 'center',\n fontFamily: style?.fontFamily ?? 'handwriting',\n fontSize,\n textStyle: style?.textStyle ?? 'normal',\n textColor: style?.textColor ?? DEFAULT_TEXT_COLOR,\n highlightColor: '#fde047',\n })\n if (bitmap) ctx.drawImage(bitmap.canvas, x, y, w, h)\n ctx.restore()\n}\n\nconst clamp01 = (v: number): number => Math.max(0, Math.min(1, v))\n\nconst drawRoundRect = (\n ctx: CanvasRenderingContext2D,\n x: number,\n y: number,\n w: number,\n h: number,\n r: number,\n): void => {\n const radius = Math.min(r, w / 2, h / 2)\n ctx.beginPath()\n ctx.moveTo(x + radius, y)\n ctx.lineTo(x + w - radius, y)\n ctx.arcTo(x + w, y, x + w, y + radius, radius)\n ctx.lineTo(x + w, y + h - radius)\n ctx.arcTo(x + w, y + h, x + w - radius, y + h, radius)\n ctx.lineTo(x + radius, y + h)\n ctx.arcTo(x, y + h, x, y + h - radius, radius)\n ctx.lineTo(x, y + radius)\n ctx.arcTo(x, y, x + radius, y, radius)\n ctx.closePath()\n}\n\n/**\n * World-space label bounding box. Used by the hit-test (see\n * `hitTestEdge`). Returns `null` when the edge has no content.\n */\nexport const edgeLabelBoundsWorld = (\n edge: Edge,\n geom: EdgeGeometry,\n): { x: number; y: number; w: number; h: number } | null => {\n if (!edge.content || !edge.content.trim()) return null\n const dims = computeLabelDims(edge)\n if (!dims) return null\n const t = clamp01(edge.style?.labelArcLength ?? 0.5)\n const { point } = getCachedLabelAnchor(geom, t)\n return {\n x: point.x - dims.width / 2,\n y: point.y - dims.height / 2,\n w: dims.width,\n h: dims.height,\n }\n}\n\n/**\n * Returns a unit vector pointing along the curve toward the clipped tip.\n * `direction` = +1 walks samples forward (for source end), -1 backward.\n */\nconst directionTowardTip = (\n samples: Vec2[],\n clippedIndex: number,\n clipPoint: Vec2,\n direction: 1 | -1,\n): Vec2 => {\n const neighbor =\n direction === 1\n ? samples[Math.min(clippedIndex + 1, samples.length - 1)]!\n : samples[Math.max(clippedIndex - 1, 0)]!\n // tip direction = unit vector FROM neighbor TO tip\n const dx = clipPoint.x - neighbor.x\n const dy = clipPoint.y - neighbor.y\n const len = Math.hypot(dx, dy)\n if (len < 1e-6) return { x: direction, y: 0 }\n return { x: dx / len, y: dy / len }\n}\n\n/**\n * Returns the point `dist` along the curve back from `clipPoint`, toward\n * the curve interior. Used to retreat the line so the body doesn't poke\n * through the arrowhead tip.\n */\nconst retreatFromPoint = (\n samples: Vec2[],\n clippedIndex: number,\n clipPoint: Vec2,\n dist: number,\n direction: 1 | -1,\n): Vec2 => {\n if (dist <= 0) return clipPoint\n const neighbor =\n direction === 1\n ? samples[Math.min(clippedIndex + 1, samples.length - 1)]!\n : samples[Math.max(clippedIndex - 1, 0)]!\n const dx = clipPoint.x - neighbor.x\n const dy = clipPoint.y - neighbor.y\n const len = Math.hypot(dx, dy)\n if (len < 1e-6) return clipPoint\n const t = Math.min(1, dist / len)\n return {\n x: clipPoint.x - (dx / len) * dist * Math.min(1, t),\n y: clipPoint.y - (dy / len) * dist * Math.min(1, t),\n }\n}\n\nconst negateVec = (v: Vec2): Vec2 => ({ x: -v.x, y: -v.y })\n","/**\n * Custom node type definitions — see ARCHITECTURE.md §5.\n *\n * `defineNode` creates a registerable NodeTypeDef. The core doesn't know\n * about React; the `view` field is typed as `unknown` so the React layer\n * (or the playground for phase 5) can stash a component reference there\n * without coupling the core package to React.\n *\n * The library reads:\n * - kind: 'canvas' | 'react' — which render path applies\n * - renderCanvas / drawPlaceholder — canvas paint functions\n * - getSnapshot — optional bitmap fallback for LOD / motion\n * - hitTest / getOutline — interaction hooks\n * - lod — zoom thresholds\n * - lifecycle hooks\n *\n * Consumers register types via `createCanvasStore({ nodeTypes: [...] })`.\n */\nimport type { Node, Vec2 } from '../types'\n\nexport type RenderEnv = {\n zoom: number\n isMoving: boolean\n isSelected: boolean\n isHovered: boolean\n isEditing: boolean\n theme(token: string): string | number | undefined\n}\n\nexport type SnapshotEnv = {\n width: number\n height: number\n dpr: number\n}\n\nexport type NodeTypeDefOptions = {\n /** Unique type id, e.g. 'chart-card'. */\n type: string\n\n // ----- canvas paint paths (one of renderCanvas or react view required) -----\n /**\n * Canvas paint for the node body. Caller has already applied the\n * camera + node transform, so paint at `(0, 0, node.w, node.h)`.\n *\n * Context state contract:\n * - The renderer wraps this call in `ctx.save()` / `ctx.restore()`\n * so any state you change (fillStyle, strokeStyle, lineWidth,\n * setLineDash, globalAlpha, font, …) is automatically rolled\n * back before the next node draws — set whatever you need\n * without worrying about cleanup.\n * - Conversely, **do NOT assume default state on entry.** Always\n * set the styles you depend on; the previous node's values\n * may still be in effect.\n * - The transform is NOT save/restore-protected at this level\n * (it's managed one frame up by the renderer). Don't leave\n * `translate` / `rotate` / `scale` calls un-paired.\n */\n renderCanvas?: (ctx: CanvasRenderingContext2D, node: Node, env: RenderEnv) => void\n /**\n * Low-zoom / motion fallback paint — see ARCHITECTURE.md §5.3 LOD.\n * Same context-state contract as `renderCanvas`.\n */\n drawPlaceholder?: (ctx: CanvasRenderingContext2D, node: Node, env: RenderEnv) => void\n\n // ----- React view (opaque to core; the React layer / playground knows what to do) -----\n /**\n * The React view component reference. Stored as `unknown` here because the\n * core package is framework-agnostic. The React layer reads this field\n * when it needs to mount a custom node in the DOM overlay.\n */\n view?: unknown\n\n // ----- LOD config (defaults applied in normalizeNodeTypeDef) -----\n lod?: {\n /** Below this zoom, prefer drawPlaceholder over the React view. Default 0.7. */\n minZoomForReact?: number\n /** Below this zoom, skip the node entirely. Default 0.3. */\n minZoomForPlaceholder?: number\n /** ms; default Infinity. After this age, the snapshot is regenerated. */\n snapshotMaxAge?: number\n }\n\n /**\n * Author-provided rasterized fallback. Library calls this when it needs a\n * fast paint (motion, low zoom) and uses `drawImage` to blit. Returns null\n * to fall back to `drawPlaceholder`.\n */\n getSnapshot?: (\n node: Node,\n env: SnapshotEnv,\n ) => CanvasImageSource | null | Promise<CanvasImageSource | null>\n\n // ----- behavior -----\n /**\n * Custom hit-test. Receives the world point pre-transformed into the node's\n * pre-rotation local frame, origin top-left. Default: AABB.\n */\n hitTest?: (node: Node, localPoint: Vec2) => boolean\n /**\n * Custom outline polygon (in node-local coords). Default: rect AABB.\n * Used by the edge auto-clip system when an edge attaches to this node.\n */\n getOutline?: (node: Node) => Vec2[] | null\n\n // ----- lifecycle -----\n /** Called when the node enters the viewport / mounts a live React view. */\n onEnter?: (node: Node) => void\n /** Called when the node exits the viewport / unmounts. */\n onExit?: (node: Node) => void\n /**\n * If true, the React view stays mounted (hidden via visibility:hidden) when\n * off-screen instead of unmounting. Use sparingly — defeats viewport culling.\n * Default false.\n */\n keepMounted?: boolean\n\n /** Validation / migration on scene load. */\n parse?: (raw: unknown) => Node['data']\n migrate?: (data: unknown, fromVersion: number) => Node['data']\n}\n\n/**\n * Normalized form of a node type definition. The `kind` field is derived\n * from which render paths are provided so the renderer dispatch is one\n * `switch` away.\n */\nexport type NodeTypeDef = NodeTypeDefOptions & {\n kind: 'canvas-only' | 'react-only' | 'mixed' | 'invalid'\n lod: {\n minZoomForReact: number\n minZoomForPlaceholder: number\n snapshotMaxAge: number\n }\n}\n\nconst DEFAULT_LOD = {\n minZoomForReact: 0.7,\n minZoomForPlaceholder: 0.3,\n snapshotMaxAge: Number.POSITIVE_INFINITY,\n} as const\n\n/**\n * Defines a custom node type. Register the returned def via\n * `createCanvasStore({ nodeTypes: [myDef, ...] })`; then any `Node`\n * with `type === opts.type` will be dispatched to your renderers + hit\n * test + lifecycle hooks.\n *\n * A type must supply at least one render path: `renderCanvas` (paints\n * via the 2D context), `view` (React component reference — used by\n * `<Canvas renderCustomNodeView>`), or both (`mixed` — canvas at low\n * zoom, React at high zoom).\n *\n * @example\n * // Canvas-only — fastest path, paints with the 2D context.\n * export const sparklineDef = defineNode({\n * type: 'sparkline',\n * renderCanvas(ctx, node, env) {\n * ctx.strokeStyle = env.theme('node.stroke') as string ?? '#000'\n * // ...draw a sparkline...\n * },\n * hitTest: (node, p) => p.x >= 0 && p.x <= node.w && p.y >= 0 && p.y <= node.h,\n * })\n *\n * @example\n * // React view — full UI; library mounts it in the DOM overlay above\n * // the canvas at high zoom, falls back to drawPlaceholder below.\n * export const chartCardDef = defineNode({\n * type: 'chart-card',\n * view: ChartCardComponent,\n * drawPlaceholder(ctx, node) {\n * ctx.fillStyle = '#e0e7ff'\n * ctx.fillRect(0, 0, node.w, node.h)\n * },\n * lod: { minZoomForReact: 0.7, minZoomForPlaceholder: 0.3 },\n * })\n */\nexport const defineNode = (opts: NodeTypeDefOptions): NodeTypeDef => {\n const hasCanvas = !!opts.renderCanvas\n const hasView = !!opts.view\n let kind: NodeTypeDef['kind']\n if (hasCanvas && hasView) kind = 'mixed'\n else if (hasCanvas) kind = 'canvas-only'\n else if (hasView) kind = 'react-only'\n else kind = 'invalid'\n\n return {\n ...opts,\n kind,\n lod: {\n minZoomForReact: opts.lod?.minZoomForReact ?? DEFAULT_LOD.minZoomForReact,\n minZoomForPlaceholder: opts.lod?.minZoomForPlaceholder ?? DEFAULT_LOD.minZoomForPlaceholder,\n snapshotMaxAge: opts.lod?.snapshotMaxAge ?? DEFAULT_LOD.snapshotMaxAge,\n },\n }\n}\n","import { LINE_HEIGHT_MAP, estimateMarkdownContentHeight } from '../text'\nimport type { Node } from '../types'\n\n/**\n * Auto-fit policy — see ARCHITECTURE.md §8 and IMPLEMENTATION.md Phase 7.\n *\n * Height of a content-bearing node is recomputed on **commit boundaries**:\n * - `store.addNode` (when creating a node with content)\n * - `store.commitEdit` (when the user finishes editing)\n * - resize-commit (when a width-resize ends; new wrap → new height)\n *\n * NEVER per-keystroke. The textarea-editor grows its own DOM textarea\n * during typing; the canvas catches up once on commit.\n */\n\n/**\n * Should this node auto-fit its height to its content?\n *\n * Default: true for all node types — matches tldraw/excalidraw behavior\n * where a sticky / shape grows to fit whatever you type. Set\n * `style.autoFit: false` to opt out.\n */\nexport const shouldAutoFit = (node: Node): boolean => {\n return node.style?.autoFit !== false\n}\n\n/**\n * Returns the height this node *would* have if its content laid out at its\n * current width and style. For empty content, returns one line-height so a\n * shape with the empty-content placeholder isn't zero-sized.\n */\nexport const computeAutoFitHeight = (node: Node): number => {\n const fontSize = node.style?.fontSize ?? 'M'\n const oneLine = LINE_HEIGHT_MAP[fontSize]\n const content = node.content ?? ''\n if (!content.trim()) return oneLine\n return Math.max(\n oneLine,\n estimateMarkdownContentHeight({\n text: content,\n width: node.w,\n fontFamily: node.style?.fontFamily,\n fontSize,\n textStyle: node.style?.textStyle,\n }),\n )\n}\n\n/**\n * Pure: returns a copy of `node` with `h` adjusted to fit `content`, if\n * the node opts into autofit. Otherwise returns the input unchanged.\n *\n * Pure-by-design so it can run inside `addNode` before the op is enqueued\n * (avoids a double op: add + update-height).\n */\nexport const withAutoFitHeight = (node: Node): Node => {\n if (!shouldAutoFit(node)) return node\n // Empty content → no autofit; preserve the user's explicit h. Otherwise\n // we'd shrink every freshly-created shape to a single line.\n if (!node.content || !node.content.trim()) return node\n const fitted = computeAutoFitHeight(node)\n // Grow-only: never collapse a deliberately-tall node down to its\n // content height. tldraw / excalidraw behave the same way.\n if (fitted <= node.h) return node\n return { ...node, h: fitted }\n}\n","/**\n * Editor markdown shortcuts — see IMPLEMENTATION.md Phase 7.\n *\n * Pure string-transform helpers, framework-agnostic. The default DOM\n * textarea editor wires these to keyboard events; consumers using a\n * custom adapter (Lexical / ProseMirror) can ignore this module.\n *\n * Each transform takes `(value, selStart, selEnd)` and returns the new\n * value + new selection so the editor can update its DOM textarea in\n * one pass.\n */\n\nexport type Transform = {\n value: string\n selStart: number\n selEnd: number\n}\n\nconst wrapSelection = (\n value: string,\n selStart: number,\n selEnd: number,\n wrapper: string,\n): Transform => {\n const wrapLen = wrapper.length\n // Case 1: selection is immediately surrounded by the wrapper (selection\n // is the inner text). Strip the surrounding markers.\n if (\n selStart >= wrapLen &&\n value.slice(selStart - wrapLen, selStart) === wrapper &&\n value.slice(selEnd, selEnd + wrapLen) === wrapper\n ) {\n const next =\n value.slice(0, selStart - wrapLen) +\n value.slice(selStart, selEnd) +\n value.slice(selEnd + wrapLen)\n return {\n value: next,\n selStart: selStart - wrapLen,\n selEnd: selEnd - wrapLen,\n }\n }\n const middle = value.slice(selStart, selEnd)\n const before = value.slice(0, selStart)\n const after = value.slice(selEnd)\n // Case 2: selection itself starts and ends with the wrapper (user\n // selected the markers along with the content).\n if (middle.startsWith(wrapper) && middle.endsWith(wrapper) && middle.length >= wrapLen * 2) {\n const inner = middle.slice(wrapLen, middle.length - wrapLen)\n const next = before + inner + after\n return { value: next, selStart, selEnd: selStart + inner.length }\n }\n // Case 3: wrap the selection.\n const next = before + wrapper + middle + wrapper + after\n return {\n value: next,\n selStart: selStart + wrapLen,\n selEnd: selEnd + wrapLen,\n }\n}\n\nexport const toggleBold = (v: string, s: number, e: number): Transform =>\n wrapSelection(v, s, e, '**')\n\nexport const toggleItalic = (v: string, s: number, e: number): Transform =>\n wrapSelection(v, s, e, '*')\n\nexport const toggleUnderline = (v: string, s: number, e: number): Transform =>\n wrapSelection(v, s, e, '__')\n\nexport const toggleStrike = (v: string, s: number, e: number): Transform =>\n wrapSelection(v, s, e, '~~')\n\nexport const toggleCode = (v: string, s: number, e: number): Transform =>\n wrapSelection(v, s, e, '`')\n\n/**\n * Inserts `[selection](url)`. If `url` is empty the cursor lands inside\n * the parens so the user can type the URL.\n */\nexport const insertLink = (\n value: string,\n selStart: number,\n selEnd: number,\n url: string,\n): Transform => {\n const before = value.slice(0, selStart)\n const middle = value.slice(selStart, selEnd) || 'link'\n const after = value.slice(selEnd)\n const inserted = `[${middle}](${url})`\n const next = before + inserted + after\n // Place cursor inside the url parens if url is empty, else at end.\n if (url) {\n const newSel = selStart + inserted.length\n return { value: next, selStart: newSel, selEnd: newSel }\n }\n const newSel = before.length + middle.length + 3 // after \"](\"\n return { value: next, selStart: newSel, selEnd: newSel }\n}\n\n/**\n * Auto-list — when the user presses Enter inside a `- ` (or `* `, or\n * `1. ` etc.) line, the next line gets the same prefix prepended.\n * Two consecutive Enters on an empty list line exit the list.\n *\n * Returns a transform when an auto-list rule fires, else null. The\n * editor should fall back to the textarea's default Enter behavior in\n * the null case.\n */\nexport const handleEnter = (value: string, selStart: number, selEnd: number): Transform | null => {\n if (selStart !== selEnd) return null\n const lineStart = value.lastIndexOf('\\n', selStart - 1) + 1\n const lineText = value.slice(lineStart, selStart)\n const match = lineText.match(/^(\\s*)([-*]|\\d+\\.) (.*)$/)\n if (!match) return null\n const indent = match[1] ?? ''\n const bullet = match[2] ?? ''\n const rest = match[3] ?? ''\n // Empty list line + Enter → exit list (remove the bullet from current\n // line; produce a plain newline).\n if (rest.trim() === '') {\n const next = value.slice(0, lineStart) + value.slice(selStart)\n return { value: next, selStart: lineStart, selEnd: lineStart }\n }\n const nextBullet = /^\\d+\\.$/.test(bullet) ? `${Number.parseInt(bullet, 10) + 1}.` : bullet\n const insertion = `\\n${indent}${nextBullet} `\n const next = value.slice(0, selStart) + insertion + value.slice(selStart)\n const newSel = selStart + insertion.length\n return { value: next, selStart: newSel, selEnd: newSel }\n}\n","import { FONT_FAMILY_MAP, FONT_SIZE_MAP, LINE_HEIGHT_MAP } from '../text'\nimport type { EditorAdapter, EditorAdapterFactory } from './adapter'\nimport {\n handleEnter,\n insertLink,\n toggleBold,\n toggleCode,\n toggleItalic,\n toggleStrike,\n toggleUnderline,\n} from './markdown-shortcuts'\n\n/**\n * Default in-place editor — a plain `<textarea>` positioned over the\n * editing node. See Phase 7 plan.\n *\n * - Auto-sizes its height to its scrollHeight (DOM-native).\n * - Font matches the node's style so what you type roughly matches what\n * you'll see on commit.\n * - Cmd+B/I/U/Shift+X/E/K: bold/italic/underline/strike/code/link.\n * - Enter inside a `- ` line continues the bullet; double-Enter exits.\n * - Esc / Cmd+Enter / blur: commit. (cancel is wired by the renderer.)\n */\nexport const createDefaultTextareaEditor: EditorAdapterFactory = ({\n node,\n container,\n camera,\n onCommit,\n onCancel,\n}): EditorAdapter => {\n void onCancel\n const style = node.style ?? {}\n const fontSize = style.fontSize ?? 'M'\n const fontFamily = style.fontFamily ?? 'handwriting'\n const align = style.textAlign ?? 'center'\n const color = style.textColor ?? '#1f2937'\n\n const fontPx = FONT_SIZE_MAP[fontSize]\n const lineHeightPx = LINE_HEIGHT_MAP[fontSize]\n\n // Screen-space placement: node world-(x,y) → screen via camera.\n const screenX = (node.x - camera.x) * camera.z\n const screenY = (node.y - camera.y) * camera.z\n const screenW = node.w * camera.z\n const screenH = node.h * camera.z\n\n const alignToFlex: Record<string, string> = {\n left: 'flex-start',\n center: 'center',\n right: 'flex-end',\n }\n\n // Wrapper handles vertical centering so the textarea visually matches\n // the canvas paint (which centers when content fits within node.h).\n // When content grows past min-height, the wrapper grows with it.\n const wrap = document.createElement('div')\n wrap.style.position = 'absolute'\n wrap.style.left = `${screenX}px`\n wrap.style.top = `${screenY}px`\n wrap.style.width = `${screenW}px`\n wrap.style.minHeight = `${screenH}px`\n wrap.style.display = 'flex'\n wrap.style.flexDirection = 'column'\n wrap.style.justifyContent = 'center'\n wrap.style.alignItems = alignToFlex[align] ?? 'center'\n wrap.style.boxSizing = 'border-box'\n wrap.style.border = '1px solid #3b82f6'\n wrap.style.borderRadius = '4px'\n wrap.style.background = style.backgroundColor ?? '#ffffff'\n wrap.style.zIndex = '20'\n // EditorMount's host div is pointerEvents:'none' so clicks on the\n // canvas behind still pan/select. The editor itself MUST opt back in,\n // otherwise mouse clicks pass through and you can't position the\n // caret by clicking — only arrow keys move it.\n wrap.style.pointerEvents = 'auto'\n\n const ta = document.createElement('textarea')\n ta.value = node.content ?? ''\n ta.spellcheck = false\n ta.style.width = '100%'\n ta.style.padding = '6px'\n ta.style.margin = '0'\n ta.style.boxSizing = 'border-box'\n ta.style.border = 'none'\n ta.style.outline = 'none'\n ta.style.resize = 'none'\n ta.style.overflow = 'hidden'\n ta.style.background = 'transparent'\n ta.style.color = color\n ta.style.fontFamily = FONT_FAMILY_MAP[fontFamily]\n ta.style.fontSize = `${fontPx * camera.z}px`\n ta.style.lineHeight = `${lineHeightPx * camera.z}px`\n ta.style.textAlign = align\n ta.style.whiteSpace = 'pre-wrap'\n ta.style.wordBreak = 'break-word'\n\n const autosize = (): void => {\n ta.style.height = 'auto'\n ta.style.height = `${ta.scrollHeight}px`\n }\n\n const commitNow = (): void => {\n onCommit(ta.value)\n }\n\n const applyTransform = (t: { value: string; selStart: number; selEnd: number }): void => {\n ta.value = t.value\n ta.setSelectionRange(t.selStart, t.selEnd)\n autosize()\n }\n\n const onInput = (): void => {\n autosize()\n }\n const onBlur = (): void => {\n commitNow()\n }\n const onKeyDown = (e: KeyboardEvent): void => {\n if (e.key === 'Escape') {\n e.preventDefault()\n commitNow()\n return\n }\n const meta = e.metaKey || e.ctrlKey\n if (meta && e.key === 'Enter') {\n e.preventDefault()\n commitNow()\n return\n }\n if (meta && !e.shiftKey && (e.key === 'b' || e.key === 'B')) {\n e.preventDefault()\n applyTransform(toggleBold(ta.value, ta.selectionStart, ta.selectionEnd))\n return\n }\n if (meta && !e.shiftKey && (e.key === 'i' || e.key === 'I')) {\n e.preventDefault()\n applyTransform(toggleItalic(ta.value, ta.selectionStart, ta.selectionEnd))\n return\n }\n if (meta && !e.shiftKey && (e.key === 'u' || e.key === 'U')) {\n e.preventDefault()\n applyTransform(toggleUnderline(ta.value, ta.selectionStart, ta.selectionEnd))\n return\n }\n if (meta && e.shiftKey && (e.key === 'x' || e.key === 'X')) {\n e.preventDefault()\n applyTransform(toggleStrike(ta.value, ta.selectionStart, ta.selectionEnd))\n return\n }\n if (meta && !e.shiftKey && (e.key === 'e' || e.key === 'E')) {\n e.preventDefault()\n applyTransform(toggleCode(ta.value, ta.selectionStart, ta.selectionEnd))\n return\n }\n if (meta && !e.shiftKey && (e.key === 'k' || e.key === 'K')) {\n e.preventDefault()\n const url = window.prompt('URL') ?? ''\n applyTransform(insertLink(ta.value, ta.selectionStart, ta.selectionEnd, url))\n return\n }\n if (e.key === 'Enter' && !e.shiftKey && !meta) {\n const t = handleEnter(ta.value, ta.selectionStart, ta.selectionEnd)\n if (t) {\n e.preventDefault()\n applyTransform(t)\n }\n }\n }\n\n ta.addEventListener('input', onInput)\n ta.addEventListener('blur', onBlur)\n ta.addEventListener('keydown', onKeyDown)\n wrap.appendChild(ta)\n container.appendChild(wrap)\n // Defer focus until after mount to ensure layout settled.\n requestAnimationFrame(() => {\n ta.focus()\n ta.setSelectionRange(ta.value.length, ta.value.length)\n autosize()\n })\n\n return {\n focus: () => ta.focus(),\n getValue: () => ta.value,\n setValue: (text: string) => {\n ta.value = text\n autosize()\n },\n destroy: () => {\n ta.removeEventListener('input', onInput)\n ta.removeEventListener('blur', onBlur)\n ta.removeEventListener('keydown', onKeyDown)\n wrap.remove()\n },\n }\n}\n","/**\n * Raster image utilities used by `store.addImage` and the renderer's\n * asset cache.\n *\n * Inputs accepted: `File`, `Blob`, or a `data:image/(png|jpeg)` URI.\n * External URLs are rejected — scenes must be self-contained (no\n * out-of-document references, no CORS surprises).\n *\n * Anything larger than `MAX_IMAGE_BYTES` or not PNG/JPEG is rejected\n * up front with a clear error so consumers can show a useful message.\n */\n\nexport const MAX_IMAGE_BYTES = 2 * 1024 * 1024\nconst ACCEPTED_MIME = new Set<string>(['image/png', 'image/jpeg'])\n\n/**\n * Validates that the input is a PNG/JPEG within the size cap. Throws\n * on rejection — meant for the synchronous prologue of an async\n * `addImage` call so consumers see the failure immediately, not after\n * an in-flight load.\n */\nexport const validateImageInput = (input: File | Blob | string): void => {\n if (typeof input === 'string') {\n if (!input.startsWith('data:')) {\n throw new Error(\n 'addImage: external URL strings are not supported. Pass a File, Blob, or `data:image/(png|jpeg)` URI.',\n )\n }\n const mimeMatch = /^data:([^;,]+)/.exec(input)\n const mime = mimeMatch?.[1] ?? ''\n if (!ACCEPTED_MIME.has(mime)) {\n throw new Error(\n `addImage: unsupported MIME \"${mime || '(unknown)'}\". Only image/png and image/jpeg are supported.`,\n )\n }\n // base64-encoded payload ≈ 4/3 of decoded byte count\n const comma = input.indexOf(',')\n if (comma < 0) throw new Error('addImage: malformed data URI (missing payload separator)')\n const decodedBytes = Math.floor(((input.length - comma - 1) * 3) / 4)\n if (decodedBytes > MAX_IMAGE_BYTES) {\n throw new Error(\n `addImage: image exceeds the 2 MB limit (${Math.round(decodedBytes / 1024)} KB).`,\n )\n }\n return\n }\n if (!ACCEPTED_MIME.has(input.type)) {\n throw new Error(\n `addImage: unsupported file type \"${input.type || '(unknown)'}\". Only image/png and image/jpeg are supported.`,\n )\n }\n if (input.size > MAX_IMAGE_BYTES) {\n throw new Error(`addImage: file exceeds the 2 MB limit (${Math.round(input.size / 1024)} KB).`)\n }\n}\n\n/** Normalize any accepted `addImage` input to a `Blob`. */\nexport const toImageBlob = async (input: File | Blob | string): Promise<Blob> => {\n if (typeof input === 'string') {\n // data URIs round-trip through fetch reliably across browsers.\n const res = await fetch(input)\n return res.blob()\n }\n return input\n}\n\n/**\n * Downscales a blob's image if its longer side exceeds `maxDim`. Returns\n * the original blob unchanged when no downscale is needed. The output\n * MIME mirrors the input (PNG stays PNG to preserve alpha; JPEG stays\n * JPEG with q=0.9).\n *\n * `maxDim <= 0` disables downscaling entirely — useful when the caller\n * wants the original bytes (e.g. they're going to do their own\n * processing or they need full fidelity).\n */\nexport const downscaleImageBlob = async (\n blob: Blob,\n maxDim: number,\n): Promise<{ blob: Blob; naturalW: number; naturalH: number }> => {\n const bitmap = await createImageBitmap(blob)\n const naturalW = bitmap.width\n const naturalH = bitmap.height\n const maxSide = Math.max(naturalW, naturalH)\n if (maxDim <= 0 || maxSide <= maxDim) {\n bitmap.close?.()\n return { blob, naturalW, naturalH }\n }\n const scale = maxDim / maxSide\n const w = Math.max(1, Math.round(naturalW * scale))\n const h = Math.max(1, Math.round(naturalH * scale))\n const canvas = new OffscreenCanvas(w, h)\n const ctx = canvas.getContext('2d')\n if (!ctx) throw new Error('addImage: failed to acquire OffscreenCanvas 2d context')\n ctx.drawImage(bitmap, 0, 0, w, h)\n bitmap.close?.()\n const outType = blob.type === 'image/png' ? 'image/png' : 'image/jpeg'\n const outBlob = await canvas.convertToBlob({ type: outType, quality: 0.9 })\n return { blob: outBlob, naturalW: w, naturalH: h }\n}\n\n/**\n * Encodes a blob as a `data:` URI. The store persists this string on\n * `node.data.src` so the node round-trips through serialize/restore\n * without needing an external asset store.\n */\nexport const blobToDataUri = (blob: Blob): Promise<string> => {\n return new Promise((resolve, reject) => {\n const reader = new FileReader()\n reader.onload = () => {\n if (typeof reader.result === 'string') resolve(reader.result)\n else reject(new Error('FileReader returned non-string result'))\n }\n reader.onerror = () => reject(reader.error ?? new Error('FileReader failed'))\n reader.readAsDataURL(blob)\n })\n}\n","/**\n * SVG utilities used by `store.addSvg` and the renderer's asset cache.\n *\n * SVG is XML — it can carry `<script>` tags, `on*` event handlers, and\n * `javascript:` hrefs that execute when the markup is inlined into the\n * DOM. We rasterize SVGs (so the DOM is never asked to live-render\n * them as elements), but a defense-in-depth sanitize still runs since\n * the rasterization itself goes through `<img src=blob:>` and a stray\n * embedded `<foreignObject>` could host arbitrary HTML.\n */\n\nexport const MAX_SVG_BYTES = 2 * 1024 * 1024\nconst DEFAULT_SVG_SIZE = 24\n\n/**\n * Cheap \"is this plausibly SVG markup?\" check + size cap. Throws on\n * rejection so consumers see the error immediately.\n */\nexport const validateSvgMarkup = (markup: string): void => {\n if (typeof markup !== 'string') {\n throw new Error('addSvg: src must be a string of SVG markup')\n }\n // UTF-8 byte length, not character count.\n const byteLen = new Blob([markup]).size\n if (byteLen > MAX_SVG_BYTES) {\n throw new Error(`addSvg: SVG markup exceeds the 2 MB limit (${Math.round(byteLen / 1024)} KB).`)\n }\n if (!/<svg[\\s>]/i.test(markup)) {\n throw new Error('addSvg: src does not look like SVG markup (no <svg> tag found)')\n }\n}\n\n/**\n * Removes attack surfaces from SVG markup:\n * - `<script>` and `<foreignObject>` elements entirely\n * - `on*` event-handler attributes\n * - `href` / `xlink:href` / `src` attributes whose value starts with\n * `javascript:` (case-insensitive)\n * - External entity references (`<!DOCTYPE` / `<!ENTITY`) by parsing\n * in SVG mode (DOMParser ignores DTDs in SVG context)\n *\n * Returns the cleaned markup. Throws if the parser can't make sense\n * of the input.\n */\nexport const sanitizeSvg = (markup: string): string => {\n const parser = new DOMParser()\n const doc = parser.parseFromString(markup, 'image/svg+xml')\n const root = doc.documentElement\n if (root.nodeName === 'parsererror' || root.querySelector('parsererror')) {\n throw new Error('addSvg: malformed SVG (parser error)')\n }\n\n const removable: Element[] = []\n const walker = doc.createTreeWalker(doc, NodeFilter.SHOW_ELEMENT)\n let n: Node | null = walker.nextNode()\n while (n) {\n const el = n as Element\n const tag = el.tagName.toLowerCase()\n if (tag === 'script' || tag === 'foreignobject') {\n removable.push(el)\n } else {\n for (const attr of [...el.attributes]) {\n const name = attr.name.toLowerCase()\n const value = attr.value.trim().toLowerCase()\n if (name.startsWith('on')) {\n el.removeAttribute(attr.name)\n } else if (\n (name === 'href' || name === 'xlink:href' || name === 'src') &&\n value.startsWith('javascript:')\n ) {\n el.removeAttribute(attr.name)\n }\n }\n }\n n = walker.nextNode()\n }\n for (const el of removable) el.remove()\n return new XMLSerializer().serializeToString(doc)\n}\n\n/**\n * Resolves intended display dimensions for an SVG. Order of preference:\n * 1. explicit `width` + `height` attributes (numeric, units stripped)\n * 2. `viewBox` width/height\n * 3. fallback 24×24\n *\n * The result is the SVG's \"natural size\" — what `addSvg` uses as the\n * default node dimensions when caller omits `w`/`h`.\n */\nexport const extractSvgDimensions = (markup: string): { w: number; h: number } => {\n const parser = new DOMParser()\n const doc = parser.parseFromString(markup, 'image/svg+xml')\n const svg = doc.documentElement\n if (svg.nodeName.toLowerCase() !== 'svg') {\n return { w: DEFAULT_SVG_SIZE, h: DEFAULT_SVG_SIZE }\n }\n const widthAttr = svg.getAttribute('width')\n const heightAttr = svg.getAttribute('height')\n if (widthAttr && heightAttr) {\n const w = Number.parseFloat(widthAttr)\n const h = Number.parseFloat(heightAttr)\n if (Number.isFinite(w) && Number.isFinite(h) && w > 0 && h > 0) return { w, h }\n }\n const viewBox = svg.getAttribute('viewBox')\n if (viewBox) {\n const parts = viewBox.split(/[\\s,]+/).map(Number.parseFloat)\n if (parts.length === 4 && parts.every(Number.isFinite) && parts[2]! > 0 && parts[3]! > 0) {\n return { w: parts[2]!, h: parts[3]! }\n }\n }\n return { w: DEFAULT_SVG_SIZE, h: DEFAULT_SVG_SIZE }\n}\n\n/**\n * Substitutes every `currentColor` occurrence in the markup with the\n * given color literal. Case-insensitive. Used by the rasterizer cache\n * to bake the icon's tint into the rendered bitmap.\n *\n * Single-color recoloring covers ~95% of real icon libraries (Lucide,\n * Heroicons, Phosphor, Tabler, etc.) which are designed monochromatic.\n * Two-tone icons can pre-color their markup and skip this step.\n */\nexport const applySvgColor = (markup: string, color: string): string => {\n return markup.replace(/currentColor/gi, color)\n}\n","import type { Edge, Node, Op, OpBatch } from '../types'\n\n/**\n * LWW conflict detection — see ARCHITECTURE.md §10.6.\n *\n * For remote `node.update` / `edge.update` ops, the `prev` slice\n * captures what the *remote* client thought the value was before its\n * change. If our local current value differs, two clients touched the\n * same field concurrently: LWW says higher `batch.ts` wins (we still\n * apply the remote op), but we surface a 'conflict' event for\n * telemetry / consumer UX (e.g. \"your background color was just\n * overwritten by Alice\").\n */\nexport type ConflictRecord = { op: Op; field: string }\n\nexport type GetCurrentNode = (id: Node['id']) => Node | undefined\nexport type GetCurrentEdge = (id: Edge['id']) => Edge | undefined\n\n/**\n * Walks a remote OpBatch and returns the set of `(op, field)` pairs\n * where the local current value disagrees with the op's `prev` slice.\n * No state is mutated.\n */\nexport const detectConflicts = (\n batch: OpBatch,\n getNode: GetCurrentNode,\n getEdge: GetCurrentEdge,\n): ConflictRecord[] => {\n const out: ConflictRecord[] = []\n for (const op of batch.ops) {\n if (op.type === 'node.update') {\n const current = getNode(op.id)\n if (!current) continue\n for (const key of Object.keys(op.prev) as (keyof Node)[]) {\n if (!sameValue(current[key], op.prev[key])) {\n out.push({ op, field: String(key) })\n }\n }\n continue\n }\n if (op.type === 'edge.update') {\n const current = getEdge(op.id)\n if (!current) continue\n for (const key of Object.keys(op.prev) as (keyof Edge)[]) {\n if (!sameValue(current[key], op.prev[key])) {\n out.push({ op, field: String(key) })\n }\n }\n }\n }\n return out\n}\n\n/**\n * Field-equality used by the conflict check. Numbers / strings /\n * booleans by value; objects by JSON.stringify (small / bounded data).\n */\nconst sameValue = (a: unknown, b: unknown): boolean => {\n if (a === b) return true\n // null and undefined are equivalent for our wire/diff purposes —\n // they both mean \"field unset\" to the render and hit-test code.\n // Without this clause, JSON round-trips that turn undefined into\n // null (see normalizeUndefinedToNull in store.ts) would flag every\n // forward edit of a previously-unset field as a conflict.\n if (a == null && b == null) return true\n if (a == null || b == null) return false\n if (typeof a !== typeof b) return false\n if (typeof a === 'object') return JSON.stringify(a) === JSON.stringify(b)\n return false\n}\n","import type { ResizeHandle } from '../hit-test/handle'\n/**\n * InteractionState — see ARCHITECTURE.md §10.11.\n *\n * Per-client ephemeral state: what's the user doing right now. Drives the\n * interactive canvas paint, status bars, AI-mode gating, custom-node\n * `env.isMoving`. NOT in the op log; not synced; not in undo stack.\n *\n * Phase 3 ships dragging / resizing / marqueeing modes. Pan/zoom/edit\n * arrive later but the type covers them now to avoid breaking changes.\n */\nimport type { EdgeEnd, EdgeId, NodeId, Vec2, WorldRect } from '../types'\n\nexport type InteractionMode =\n | 'idle'\n | 'panning'\n | 'zooming'\n | 'dragging'\n | 'resizing'\n | 'rotating'\n | 'marqueeing'\n | 'creating-shape'\n | 'creating-edge'\n | 'reconnecting-edge'\n | 'editing'\n\nexport type PointerInfo = {\n worldX: number\n worldY: number\n screenX: number\n screenY: number\n pointerType: 'mouse' | 'touch' | 'pen'\n pressure?: number\n}\n\n/**\n * The frozen geometry of a node at drag-start, used to compute the\n * uncommitted display position during drag (= original + delta).\n */\nexport type DragOriginal = {\n id: NodeId\n x: number\n y: number\n w: number\n h: number\n angle: number\n}\n\nexport type InteractionState = {\n mode: InteractionMode\n pointer: PointerInfo | null\n\n // Drag state — populated when mode is 'dragging' or 'resizing'.\n draggedIds: NodeId[]\n dragOriginals: DragOriginal[]\n /** World-space delta from drag start; renderer applies this to draw the dragged set. */\n dragDelta: Vec2\n\n // Resize state — populated when mode is 'resizing'.\n resizeHandle: ResizeHandle | null\n /** Whether the user is holding Shift during a resize (aspect-lock). */\n resizeLockAspect: boolean\n /** Whether the user is holding Alt during a resize (resize from center). */\n resizeFromCenter: boolean\n /**\n * Live in-progress geometry of the resized node — written every\n * pointermove, committed to the store once on pointer-up. While\n * present, `store.getNode(id)` still returns the original geometry;\n * the renderer overlays this draft via `mapDragPositions` for the\n * interactive layer paint. Mirrors how `dragDelta` works for drag.\n */\n resizeDraft: { x: number; y: number; w: number; h: number; angle: number } | null\n\n // Marquee state — populated when mode is 'marqueeing'.\n marqueeRect: WorldRect | null\n /** Whether the marquee should add to (true, shift held) or replace selection. */\n marqueeAdditive: boolean\n\n /**\n * Live in-progress cubic controls of an edge being mid-point-dragged.\n * Written every pointermove, committed to the store once on\n * pointer-up. Same draft+commit model as `resizeDraft` and\n * `dragDelta` — keeps mid-gesture mutations off the 'change' bus.\n */\n midpointDraft: { edgeId: EdgeId; control: [Vec2, Vec2] } | null\n\n // Edge-creation state — populated when mode is 'creating-edge' or\n // 'reconnecting-edge'. `draftEdge` is the source/target the renderer\n // should paint as a preview.\n draftEdge: {\n source: EdgeEnd\n target: EdgeEnd\n /** When reconnecting an existing edge, the id; null for new edges. */\n reconnectingId: import('../types').EdgeId | null\n /** Snap candidate (a node id the target endpoint is hovering over). */\n snapTargetNodeId: NodeId | null\n } | null\n\n // Edit state — populated when mode is 'editing' (phase 7 + 12.5).\n // Phase 7 only edited node content; phase 12.5 generalizes to edge\n // labels too, so the field is `editingTarget: { kind, id } | null`.\n editingTarget: EditTarget | null\n\n // Drag-create state — populated while mode is 'creating-shape'.\n // The renderer paints `createDraftRect` as a preview on the\n // interactive canvas; `<Canvas onCreateDrag>` consumes the rect on\n // commit.\n createDraftRect: WorldRect | null\n createTool: string | null\n}\n\n/** Identifies what's currently being edited — a node (text content) or\n * an edge (label content). See `store.beginEdit`. */\nexport type EditTarget = { kind: 'node'; id: NodeId } | { kind: 'edge'; id: EdgeId }\n\nexport const idleInteractionState = (): InteractionState => ({\n mode: 'idle',\n pointer: null,\n draggedIds: [],\n dragOriginals: [],\n dragDelta: { x: 0, y: 0 },\n resizeHandle: null,\n resizeLockAspect: false,\n resizeFromCenter: false,\n resizeDraft: null,\n midpointDraft: null,\n marqueeRect: null,\n marqueeAdditive: false,\n draftEdge: null,\n editingTarget: null,\n createDraftRect: null,\n createTool: null,\n})\n\n/**\n * Convenience: any pointer-driven, per-frame-invalidating gesture is\n * \"moving\". Drives LOD swaps in the renderer (custom-node React→canvas\n * fallback, text bitmap downscale, edge-label bitmap downscale).\n *\n * `marqueeing` belongs here even though the scene doesn't translate:\n * the marquee rect updates every pointermove → static cache invalidates\n * → full repaint per frame. Without the swap, dense scenes paint\n * full-LOD React overlays + full-res text bitmaps under the moving\n * rect and the gesture janks.\n */\nexport const isMoving = (state: InteractionState): boolean => {\n const m = state.mode\n return (\n m === 'panning' ||\n m === 'zooming' ||\n m === 'dragging' ||\n m === 'resizing' ||\n m === 'rotating' ||\n m === 'marqueeing'\n )\n}\n","/**\n * Op inversion — see ARCHITECTURE.md §10.2.\n *\n * Every committed `Op` carries enough state (full snapshot for add/remove,\n * `prev` slice for updates) to derive its inverse with no diffing. Undo\n * applies `inverseBatch(batch)` with `origin: 'history'`; redo re-applies\n * the original batch.\n *\n * Inverse rules:\n * - add ↔ remove (full snapshot retained)\n * - update.patch ↔ update.prev\n * - group.upsert with `prev` ↔ group.upsert with prev fields swapped; if\n * `prev` is absent, the upsert was a fresh insert → invert to remove.\n */\nimport type { Op, OpBatch } from '../types'\n\nexport const inverseOp = (op: Op): Op => {\n switch (op.type) {\n case 'node.add':\n return { type: 'node.remove', node: op.node }\n case 'node.remove':\n return { type: 'node.add', node: op.node }\n case 'node.update':\n return { type: 'node.update', id: op.id, patch: op.prev, prev: op.patch }\n case 'edge.add':\n return { type: 'edge.remove', edge: op.edge }\n case 'edge.remove':\n return { type: 'edge.add', edge: op.edge }\n case 'edge.update':\n return { type: 'edge.update', id: op.id, patch: op.prev, prev: op.patch }\n case 'group.upsert':\n if (op.prev) return { type: 'group.upsert', group: op.prev, prev: op.group }\n return { type: 'group.remove', group: op.group }\n case 'group.remove':\n return { type: 'group.upsert', group: op.group }\n case 'frame.reorder':\n return { type: 'frame.reorder', ids: op.prev, prev: op.ids }\n }\n}\n\n/**\n * Inverse batch: reverse op order, invert each op. Reversing preserves\n * \"later ops depended on earlier ones\" semantics — e.g. a batch that\n * (1) adds a node and (2) updates it must undo (2) first, then (1).\n */\nexport const inverseBatch = (batch: OpBatch): Op[] => {\n const inv: Op[] = []\n for (let i = batch.ops.length - 1; i >= 0; i--) {\n inv.push(inverseOp(batch.ops[i]!))\n }\n return inv\n}\n","import type { ClientId, EdgeId, NodeId, Vec2 } from '../types'\n\n/**\n * Per-client awareness state that other clients see in real time.\n * Synced over the {@link SyncAdapter}; never in the op log; never\n * persisted by `toJSON`.\n *\n * Set the local copy via `store.presence.setLocal({...})`. Read the\n * remote copy via `usePresence()` / `usePresence(clientId)` (React) or\n * `store.presence.get(...)` / `store.presence.getAll()`.\n */\nexport type PresenceState = {\n /** Stable id of the owning client. */\n clientId: ClientId\n /** Cursor world position; null when the cursor has left the surface. */\n cursor: Vec2 | null\n /** Ids the remote client has selected — for shared-awareness highlights. */\n selection: (NodeId | EdgeId)[]\n /** Node id the remote client is currently editing (or null). */\n editing: NodeId | null\n /** Display color (hex). Used for remote cursors + selection outlines. */\n color: string\n /** Display name. */\n name: string\n}\n\nexport const emptyPresenceState = (clientId: ClientId): PresenceState => ({\n clientId,\n cursor: null,\n selection: [],\n editing: null,\n color: '#3b82f6',\n name: '',\n})\n\nexport type PresencePatch = Partial<Omit<PresenceState, 'clientId'>>\n\n/**\n * Returns true if any remote presence has this node currently open in\n * edit mode. Used to enforce the exclusive edit-lock when a SyncAdapter\n * is attached (see ARCHITECTURE.md §9 collab edit semantics).\n */\nexport const isNodeRemoteEditing = (\n remote: ReadonlyMap<ClientId, PresenceState>,\n nodeId: NodeId,\n): boolean => {\n for (const p of remote.values()) {\n if (p.editing === nodeId) return true\n }\n return false\n}\n","/**\n * CanvasStore implementation — see ARCHITECTURE.md §10.\n *\n * Phase 1: typed-Op-driven mutations, signia atoms for fine-grained reactivity,\n * spatial index kept in sync, framework-agnostic.\n *\n * NOT in phase 1 (added later):\n * - undo/redo (phase 8): the op log is built; the inverse machinery is not\n * - presence (phase 8)\n * - sync adapter (phase 8)\n * - signia-based React hooks (phase 9)\n */\nimport { type Atom, atom, transact } from 'signia'\n\nimport {\n blobToDataUri,\n downscaleImageBlob,\n extractSvgDimensions,\n sanitizeSvg,\n toImageBlob,\n validateImageInput,\n validateSvgMarkup,\n} from '../assets'\nimport { DEFAULT_CAMERA } from '../camera'\nimport { type EdgeGeometry, EdgeGeometryCache } from '../edges/cache'\nimport { shouldAutoFit, withAutoFitHeight } from '../edit/auto-fit'\nimport { type IdGenerator, makeIdGenerator, randomClientId } from '../ids'\nimport { UniformGrid, nodeAABB } from '../spatial'\nimport { SCHEMA_VERSION, asBatchId, asNodeId, isAttached } from '../types'\nimport type {\n CameraState,\n ClientId,\n Edge,\n EdgeId,\n Group,\n GroupId,\n IconNodeData,\n ImageNodeData,\n Node,\n NodeId,\n Op,\n OpBatch,\n Scene,\n Style,\n} from '../types'\nimport { detectConflicts } from './conflict'\nimport { type InteractionState, idleInteractionState } from './interaction'\nimport { inverseBatch } from './inverse-op'\nimport { type PresencePatch, type PresenceState, emptyPresenceState } from './presence'\nimport type {\n CanvasStore,\n OpOrigin,\n SpatialQuery,\n SpatialResult,\n StoreEventHandler,\n StoreEventName,\n StoreEvents,\n StoreOptions,\n Unsubscribe,\n} from './types'\n\nconst EMPTY_SCENE = (): Scene => ({\n schemaVersion: SCHEMA_VERSION,\n nodes: {},\n edges: {},\n groups: {},\n camera: DEFAULT_CAMERA,\n selection: [],\n})\n\n/**\n * Creates a new canvas store. One per scene / document. Pass into\n * `<CanvasProvider>` (React) or use the imperative API directly.\n *\n * @example\n * // Minimal\n * const store = createCanvasStore()\n *\n * @example\n * // With custom node types + a hydrated scene from JSON\n * const store = createCanvasStore({\n * nodeTypes: [chartCardDef, todoCardDef],\n * initial: fromSerialized(savedScene),\n * })\n */\n/**\n * Index of the first entry strictly greater than `target`, or -1 if\n * none. Assumes `arr` is sorted ascending. Used by bringForward to\n * find the immediate-above neighbour's z.\n */\nconst binaryFirstGreater = (arr: number[], target: number): number => {\n let lo = 0\n let hi = arr.length\n while (lo < hi) {\n const mid = (lo + hi) >>> 1\n if (arr[mid]! <= target) lo = mid + 1\n else hi = mid\n }\n return lo < arr.length ? lo : -1\n}\n\n/**\n * Index of the last entry strictly less than `target`, or -1 if none.\n * Used by sendBackward.\n */\nconst binaryLastLess = (arr: number[], target: number): number => {\n let lo = 0\n let hi = arr.length\n while (lo < hi) {\n const mid = (lo + hi) >>> 1\n if (arr[mid]! < target) lo = mid + 1\n else hi = mid\n }\n return lo > 0 ? lo - 1 : -1\n}\n\nexport const createCanvasStore = (opts: StoreOptions = {}): CanvasStore => {\n const clientId: ClientId = opts.clientId ?? randomClientId()\n const idGenerator: IdGenerator = opts.idGenerator ?? makeIdGenerator(clientId)\n const initial = opts.initial ?? EMPTY_SCENE()\n\n // ---- reactive state ----------------------------------------------------\n // One atom per entity gives us fine-grained subscriptions. The id-list\n // atoms drive iteration; the spatial index drives viewport queries.\n\n const nodeAtoms = new Map<NodeId, Atom<Node>>()\n const edgeAtoms = new Map<EdgeId, Atom<Edge>>()\n const groupAtoms = new Map<GroupId, Atom<Group>>()\n\n const nodeIdsAtom = atom<NodeId[]>('nodeIds', [])\n const edgeIdsAtom = atom<EdgeId[]>('edgeIds', [])\n const groupIdsAtom = atom<GroupId[]>('groupIds', [])\n\n const cameraAtom = atom<CameraState>('camera', initial.camera)\n const selectionAtom = atom<(NodeId | EdgeId)[]>('selection', initial.selection)\n // Presentation order for frame-typed nodes. Auto-maintained on\n // node.add (push) / node.remove (filter); explicitly mutated via the\n // `frame.reorder` op. See types/scene.ts.\n const frameOrderAtom = atom<NodeId[]>('frameOrder', initial.frameOrder ?? [])\n const interactionAtom = atom<InteractionState>('interaction', idleInteractionState())\n const localPresenceAtom = atom<PresenceState>('presence', emptyPresenceState(clientId))\n const remotePresence = new Map<ClientId, PresenceState>()\n\n const nodeIndex = new UniformGrid()\n const edgeIndex = new UniformGrid()\n const edgeGeoCache = new EdgeGeometryCache()\n\n // Custom node type registry — keyed by NodeTypeDef.type.\n const nodeTypeRegistry = new Map<string, import('../node-types').NodeTypeDef>()\n for (const def of opts.nodeTypes ?? []) {\n nodeTypeRegistry.set(def.type, def)\n }\n\n // Per-edge integer version. Bumped on edge.add/update and on node.update\n // for incident edges. Drives the EdgeGeometryCache invalidation without\n // having to compare full-state strings. See ARCHITECTURE.md §6.12.\n const edgeVersions = new Map<EdgeId, number>()\n const bumpEdgeVersion = (id: EdgeId): void => {\n edgeVersions.set(id, (edgeVersions.get(id) ?? 0) + 1)\n }\n\n // incidentEdges: nodeId -> set of edgeIds. Used by reindexEdge when a\n // node moves (to refresh all its edges' AABBs in the spatial index) and\n // by removeNode to cascade-delete attached edges.\n const incidentEdges = new Map<NodeId, Set<EdgeId>>()\n\n // Running extremes of node + edge z values. `topZ` only goes up\n // (++ on auto-create + bringToFront); `bottomZ` only goes down\n // (-- on sendToBack). New entities created without an explicit z\n // get `++topZ` (Figma / Excalidraw default — new on top); sendToBack\n // uses `--bottomZ`. Negative z is a first-class value: anything\n // sendToBack'd sits at z=-1, -2, … and z=0 is a neutral middle\n // position between front and back stacks.\n //\n // Both counters are tracked from every z-mutation centrally in\n // `applyOpInternal` so updateNode({ z: ... }) calls and remote ops\n // keep them in sync. Initialized from `initial` so hydration from\n // a saved scene preserves the high/low watermarks.\n let topZ = 0\n let bottomZ = 0\n for (const n of Object.values(initial.nodes) as Node[]) {\n if (n.z > topZ) topZ = n.z\n if (n.z < bottomZ) bottomZ = n.z\n }\n for (const e of Object.values(initial.edges) as Edge[]) {\n if (e.z > topZ) topZ = e.z\n if (e.z < bottomZ) bottomZ = e.z\n }\n\n const getNodeForGeo = (id: NodeId): Node | undefined => nodeAtoms.get(id)?.value\n\n // ---- batching ----------------------------------------------------------\n let currentBatchOps: Op[] | null = null\n let batchDepth = 0\n\n const startBatch = (): void => {\n if (batchDepth === 0) currentBatchOps = []\n batchDepth++\n }\n\n const endBatch = (): OpBatch | null => {\n batchDepth--\n if (batchDepth > 0) return null\n const ops = currentBatchOps ?? []\n currentBatchOps = null\n if (ops.length === 0) return null\n return {\n id: asBatchId(idGenerator()),\n clientId,\n ts: Date.now(),\n origin: 'local',\n ops,\n }\n }\n\n // ---- undo / redo stacks ------------------------------------------------\n // Local committed batches push onto undoStack; redoStack is cleared on\n // any fresh local op (the standard \"branching\" rule). Remote and history\n // batches do not push to undoStack — see emitChange below. Cap at 50.\n const UNDO_STACK_CAP = 50\n const undoStack: OpBatch[] = []\n const redoStack: OpBatch[] = []\n\n // ---- event bus ---------------------------------------------------------\n type Subscribers = { [E in StoreEventName]: Set<StoreEventHandler<E>> }\n const subscribers: Subscribers = {\n change: new Set(),\n camera: new Set(),\n selection: new Set(),\n interaction: new Set(),\n presence: new Set(),\n conflict: new Set(),\n }\n const emit = <E extends StoreEventName>(event: E, payload: StoreEvents[E]): void => {\n for (const cb of subscribers[event]) cb(payload)\n }\n\n /**\n * Single entry point for 'change' emission. Centralizes the undo-stack\n * bookkeeping so every call site (enqueueOp, removeNode cascade,\n * applyOp, applyBatch) gets it for free. Only `origin: 'local'`\n * batches enter the undo stack; remote and history batches don't.\n */\n const emitChange = (batch: OpBatch): void => {\n if (batch.origin === 'local') {\n undoStack.push(batch)\n if (undoStack.length > UNDO_STACK_CAP) undoStack.shift()\n // A fresh local op invalidates any redo branch.\n redoStack.length = 0\n }\n emit('change', batch)\n }\n\n // ---- spatial-index helpers --------------------------------------------\n const reindexNode = (node: Node): void => {\n nodeIndex.insert(node.id, nodeAABB(node))\n }\n const reindexEdge = (edge: Edge): void => {\n const version = edgeVersions.get(edge.id) ?? 0\n const geom = edgeGeoCache.get(edge, version, getNodeForGeo)\n if (geom) {\n edgeIndex.insert(edge.id, geom.aabb)\n } else {\n // Edge references a missing node; remove from index until things settle.\n edgeIndex.remove(edge.id)\n }\n }\n const unindexNode = (id: NodeId): void => {\n nodeIndex.remove(id)\n }\n const unindexEdge = (id: EdgeId): void => {\n edgeIndex.remove(id)\n edgeGeoCache.delete(id)\n }\n\n const trackIncidence = (edge: Edge): void => {\n for (const end of [edge.source, edge.target]) {\n if (isAttached(end)) {\n let s = incidentEdges.get(end.nodeId)\n if (!s) {\n s = new Set()\n incidentEdges.set(end.nodeId, s)\n }\n s.add(edge.id)\n }\n }\n }\n const untrackIncidence = (edge: Edge): void => {\n for (const end of [edge.source, edge.target]) {\n if (isAttached(end)) {\n incidentEdges.get(end.nodeId)?.delete(edge.id)\n }\n }\n }\n\n // ---- op application (internal, no event emission per-op) ---------------\n const applyOpInternal = (op: Op): void => {\n switch (op.type) {\n case 'node.add': {\n const a = atom<Node>(`node:${op.node.id}`, op.node)\n nodeAtoms.set(op.node.id, a)\n nodeIdsAtom.update(ids => [...ids, op.node.id])\n reindexNode(op.node)\n if (op.node.z > topZ) topZ = op.node.z\n if (op.node.z < bottomZ) bottomZ = op.node.z\n if (op.node.type === 'frame') {\n frameOrderAtom.update(ids => (ids.includes(op.node.id) ? ids : [...ids, op.node.id]))\n }\n break\n }\n case 'node.update': {\n const a = nodeAtoms.get(op.id)\n if (!a) return\n const next = { ...a.value, ...op.patch }\n a.set(next)\n reindexNode(next)\n if (op.patch.z !== undefined) {\n if (op.patch.z > topZ) topZ = op.patch.z\n if (op.patch.z < bottomZ) bottomZ = op.patch.z\n }\n // Edges whose endpoint is on this node now have stale geometry.\n // Bump each incident edge's version so the cache invalidates.\n const incident = incidentEdges.get(op.id)\n if (incident) {\n for (const eid of incident) {\n bumpEdgeVersion(eid)\n const e = edgeAtoms.get(eid)\n if (e) reindexEdge(e.value)\n }\n }\n break\n }\n case 'node.remove': {\n const id = op.node.id\n nodeAtoms.delete(id)\n nodeIdsAtom.update(ids => ids.filter(x => x !== id))\n unindexNode(id)\n incidentEdges.delete(id)\n if (op.node.type === 'frame') {\n frameOrderAtom.update(ids => ids.filter(x => x !== id))\n }\n break\n }\n case 'edge.add': {\n const a = atom<Edge>(`edge:${op.edge.id}`, op.edge)\n edgeAtoms.set(op.edge.id, a)\n edgeIdsAtom.update(ids => [...ids, op.edge.id])\n trackIncidence(op.edge)\n bumpEdgeVersion(op.edge.id)\n reindexEdge(op.edge)\n if (op.edge.z > topZ) topZ = op.edge.z\n if (op.edge.z < bottomZ) bottomZ = op.edge.z\n break\n }\n case 'edge.update': {\n const a = edgeAtoms.get(op.id)\n if (!a) return\n const prev = a.value\n const next = { ...prev, ...op.patch }\n untrackIncidence(prev)\n trackIncidence(next)\n a.set(next)\n bumpEdgeVersion(op.id)\n reindexEdge(next)\n if (op.patch.z !== undefined) {\n if (op.patch.z > topZ) topZ = op.patch.z\n if (op.patch.z < bottomZ) bottomZ = op.patch.z\n }\n break\n }\n case 'edge.remove': {\n const id = op.edge.id\n const a = edgeAtoms.get(id)\n if (a) untrackIncidence(a.value)\n edgeAtoms.delete(id)\n edgeIdsAtom.update(ids => ids.filter(x => x !== id))\n edgeVersions.delete(id)\n unindexEdge(id)\n break\n }\n case 'group.upsert': {\n const existing = groupAtoms.get(op.group.id)\n if (existing) {\n existing.set(op.group)\n } else {\n groupAtoms.set(op.group.id, atom(`group:${op.group.id}`, op.group))\n groupIdsAtom.update(ids => [...ids, op.group.id])\n }\n break\n }\n case 'group.remove': {\n const id = op.group.id\n groupAtoms.delete(id)\n groupIdsAtom.update(ids => ids.filter(x => x !== id))\n break\n }\n case 'frame.reorder': {\n frameOrderAtom.set([...op.ids])\n break\n }\n }\n }\n\n // ---- public surface ----------------------------------------------------\n const enqueueOp = (op: Op): void => {\n if (currentBatchOps === null) {\n // single-op outside batch — wrap in implicit batch for consistency\n startBatch()\n currentBatchOps!.push(op)\n applyOpInternal(op)\n const batch = endBatch()\n if (batch) emitChange(batch)\n } else {\n currentBatchOps.push(op)\n applyOpInternal(op)\n }\n }\n\n /**\n * Replaces `undefined` values with `null` in-place on the copied\n * object. `null` survives `JSON.stringify` (`undefined` keys get\n * dropped, breaking JSON-serialized sync adapters), and is\n * indistinguishable from `undefined` to the render / hit-test / text\n * code that reads node and edge fields. The TS cast is pragmatic —\n * field types rarely include `null`, but the value never escapes the\n * op/wire layer; downstream spreads it back into the record where\n * \"falsy\" is the only thing that matters.\n */\n const normalizeUndefinedToNull = <T extends object>(obj: T): T => {\n const out: Record<string, unknown> = {}\n for (const key of Object.keys(obj)) {\n const v = (obj as Record<string, unknown>)[key]\n out[key] = v === undefined ? null : v\n }\n return out as T\n }\n\n /**\n * Records the prev slice for an update op. Values that were\n * previously `undefined` are stored as `null` so the resulting\n * inverse op (which becomes the wire payload during undo) survives\n * a JSON round-trip — otherwise peers silently no-op on clears of\n * previously-unset fields.\n */\n const slicePrev = <T>(current: T, patch: Partial<T>): Partial<T> => {\n const prev: Partial<T> = {}\n for (const key of Object.keys(patch) as (keyof T)[]) {\n prev[key] = current[key]\n }\n return normalizeUndefinedToNull(prev)\n }\n\n // hoisted because applyOp/applyBatch and the public methods both need them\n const populateInitial = (scene: Scene): void => {\n // If the scene didn't carry an explicit frameOrder (older saves),\n // derive it from iteration order over frame-typed nodes so the\n // store has a usable order from the first frame the consumer asks\n // for. The explicit `scene.frameOrder` (when present) wins.\n const seededFrameOrder: NodeId[] = []\n for (const id of Object.keys(scene.nodes)) {\n const node = scene.nodes[id as NodeId]\n if (!node) continue\n const a = atom<Node>(`node:${node.id}`, node)\n nodeAtoms.set(node.id, a)\n nodeIdsAtom.update(ids => [...ids, node.id])\n reindexNode(node)\n if (node.type === 'frame') seededFrameOrder.push(node.id)\n }\n if (!scene.frameOrder) frameOrderAtom.set(seededFrameOrder)\n for (const id of Object.keys(scene.edges)) {\n const edge = scene.edges[id as EdgeId]\n if (!edge) continue\n const a = atom<Edge>(`edge:${edge.id}`, edge)\n edgeAtoms.set(edge.id, a)\n edgeIdsAtom.update(ids => [...ids, edge.id])\n trackIncidence(edge)\n bumpEdgeVersion(edge.id)\n reindexEdge(edge)\n }\n for (const id of Object.keys(scene.groups)) {\n const group = scene.groups[id as GroupId]\n if (!group) continue\n groupAtoms.set(group.id, atom(`group:${group.id}`, group))\n groupIdsAtom.update(ids => [...ids, group.id])\n }\n }\n\n populateInitial(initial)\n\n const store: CanvasStore = {\n clientId,\n generateId: () => idGenerator(),\n\n addNode(node) {\n // Auto-top z when the caller omits the field — newly created\n // nodes sit above everything else (Figma / Excalidraw default).\n // An explicit value (incl. 0 or negative) is honored as-is.\n // `topZ` is then tracked centrally in applyOpInternal.\n const z = node.z ?? ++topZ\n const fitted = withAutoFitHeight({ ...node, z })\n enqueueOp({ type: 'node.add', node: fitted })\n return fitted.id\n },\n updateNode(id, patch) {\n const current = nodeAtoms.get(id)?.value\n if (!current) return\n let resolvedPatch = patch\n // Auto-fit on commit-boundary fields: content (commitEdit) or font\n // style (StylePanel applies). Width changes from a resize stream\n // deliberately do NOT trigger autofit — that would override the\n // user's drag mid-stream. Resize-commit refits explicitly.\n const next = { ...current, ...patch }\n const styleChanged =\n patch.style &&\n (patch.style.fontFamily !== undefined ||\n patch.style.fontSize !== undefined ||\n patch.style.textStyle !== undefined)\n if (shouldAutoFit(next) && (patch.content !== undefined || styleChanged)) {\n const fitted = withAutoFitHeight(next)\n if (fitted.h !== next.h) {\n resolvedPatch = { ...patch, h: fitted.h }\n }\n }\n enqueueOp({\n type: 'node.update',\n id,\n // Normalize both halves so explicit-clear patches (e.g.\n // `updateNode(id, { content: undefined })`) and first-time-set\n // prev slices both survive a JSON-serialized sync transport.\n patch: normalizeUndefinedToNull(resolvedPatch),\n prev: slicePrev(current, resolvedPatch),\n })\n },\n removeNode(id) {\n const node = nodeAtoms.get(id)?.value\n if (!node) return\n transact(() => {\n startBatch()\n // cascade-remove incident edges first; phase 8 will surface a config knob\n const incident = incidentEdges.get(id)\n if (incident) {\n for (const eid of [...incident]) {\n const edge = edgeAtoms.get(eid)?.value\n if (edge) {\n currentBatchOps!.push({ type: 'edge.remove', edge })\n applyOpInternal({ type: 'edge.remove', edge })\n }\n }\n }\n currentBatchOps!.push({ type: 'node.remove', node })\n applyOpInternal({ type: 'node.remove', node })\n const batch = endBatch()\n if (batch) emitChange(batch)\n })\n },\n\n async addImage(opts) {\n validateImageInput(opts.src)\n const rawBlob = await toImageBlob(opts.src)\n const maxDim = opts.maxDimension ?? 2048\n const { blob, naturalW, naturalH } = await downscaleImageBlob(rawBlob, maxDim)\n const src = await blobToDataUri(blob)\n // Default sizing: natural dimensions clamped to 400 px on the\n // longer side so a screen-filling node isn't created from a big\n // image. Aspect ratio is preserved.\n const DEFAULT_MAX_NODE_SIDE = 400\n const aspectScale = Math.min(1, DEFAULT_MAX_NODE_SIDE / Math.max(naturalW, naturalH))\n const w = opts.w ?? Math.max(1, Math.round(naturalW * aspectScale))\n const h = opts.h ?? Math.max(1, Math.round(naturalH * aspectScale))\n const id = asNodeId(idGenerator())\n this.addNode({\n id,\n type: 'image',\n x: opts.x,\n y: opts.y,\n w,\n h,\n angle: 0,\n groups: [],\n style: opts.style,\n data: { src, naturalW, naturalH, alt: opts.alt } satisfies ImageNodeData,\n })\n return id\n },\n async addSvg(opts) {\n validateSvgMarkup(opts.src)\n const sanitized = sanitizeSvg(opts.src)\n const intrinsic = extractSvgDimensions(sanitized)\n const w = opts.w ?? intrinsic.w\n const h = opts.h ?? intrinsic.h\n const mergedStyle: Style | undefined =\n opts.color || opts.style\n ? { ...(opts.color ? { iconColor: opts.color } : {}), ...opts.style }\n : undefined\n const id = asNodeId(idGenerator())\n this.addNode({\n id,\n type: 'icon',\n x: opts.x,\n y: opts.y,\n w,\n h,\n angle: 0,\n groups: [],\n ...(mergedStyle ? { style: mergedStyle } : {}),\n data: { src: sanitized, alt: opts.alt } satisfies IconNodeData,\n })\n return id\n },\n\n addEdge(edge) {\n // Same auto-top behavior as addNode — omit z for \"on top\",\n // pass an explicit value (incl. 0 / negative) to override.\n const z = edge.z ?? ++topZ\n const withZ = { ...edge, z }\n enqueueOp({ type: 'edge.add', edge: withZ })\n return withZ.id\n },\n updateEdge(id, patch) {\n const current = edgeAtoms.get(id)?.value\n if (!current) return\n // Normalize both halves so an explicit-undefined clear and a\n // first-time-set prev both survive JSON-serialized transports.\n enqueueOp({\n type: 'edge.update',\n id,\n patch: normalizeUndefinedToNull(patch),\n prev: slicePrev(current, patch),\n })\n },\n removeEdge(id) {\n const edge = edgeAtoms.get(id)?.value\n if (!edge) return\n enqueueOp({ type: 'edge.remove', edge })\n },\n\n bringToFront(ids) {\n this.batch(() => {\n for (const id of ids) {\n if (nodeAtoms.has(id as NodeId)) this.updateNode(id as NodeId, { z: ++topZ })\n else if (edgeAtoms.has(id as EdgeId)) this.updateEdge(id as EdgeId, { z: ++topZ })\n }\n })\n },\n sendToBack(ids) {\n // O(1) per target via the monotonic `--bottomZ` counter. Multi-\n // select preserves relative order because each step decrements\n // (first selected lands one above the next).\n this.batch(() => {\n for (const id of ids) {\n if (nodeAtoms.has(id as NodeId)) this.updateNode(id as NodeId, { z: --bottomZ })\n else if (edgeAtoms.has(id as EdgeId)) this.updateEdge(id as EdgeId, { z: --bottomZ })\n }\n })\n },\n bringForward(ids) {\n // For each target, find the next-higher z among non-targets and\n // step the target above it. Self-stable: targets keep their\n // relative order if they're all moved past the same neighbour.\n const targets = new Set<string>(ids as string[])\n const allZ: number[] = []\n for (const a of nodeAtoms.values()) if (!targets.has(a.value.id)) allZ.push(a.value.z)\n for (const a of edgeAtoms.values()) if (!targets.has(a.value.id)) allZ.push(a.value.z)\n allZ.sort((a, b) => a - b)\n this.batch(() => {\n for (const id of ids) {\n const node = nodeAtoms.get(id as NodeId)?.value\n const edge = node ? null : edgeAtoms.get(id as EdgeId)?.value\n const currentZ = node?.z ?? edge?.z\n if (currentZ === undefined) continue\n // Smallest non-target z strictly greater than currentZ.\n // `applyOpInternal` keeps topZ in sync with the new value.\n const idx = binaryFirstGreater(allZ, currentZ)\n const nextZ = idx >= 0 ? allZ[idx]! + 1 : currentZ + 1\n if (node) this.updateNode(id as NodeId, { z: nextZ })\n else this.updateEdge(id as EdgeId, { z: nextZ })\n }\n })\n },\n sendBackward(ids) {\n const targets = new Set<string>(ids as string[])\n const allZ: number[] = []\n for (const a of nodeAtoms.values()) if (!targets.has(a.value.id)) allZ.push(a.value.z)\n for (const a of edgeAtoms.values()) if (!targets.has(a.value.id)) allZ.push(a.value.z)\n allZ.sort((a, b) => a - b)\n this.batch(() => {\n for (const id of ids) {\n const node = nodeAtoms.get(id as NodeId)?.value\n const edge = node ? null : edgeAtoms.get(id as EdgeId)?.value\n const currentZ = node?.z ?? edge?.z\n if (currentZ === undefined) continue\n // Largest non-target z strictly less than currentZ.\n const idx = binaryLastLess(allZ, currentZ)\n const nextZ = idx >= 0 ? allZ[idx]! - 1 : currentZ - 1\n if (node) this.updateNode(id as NodeId, { z: nextZ })\n else this.updateEdge(id as EdgeId, { z: nextZ })\n }\n })\n },\n\n upsertGroup(group) {\n const prev = groupAtoms.get(group.id)?.value\n enqueueOp({ type: 'group.upsert', group, prev })\n },\n removeGroup(id) {\n const group = groupAtoms.get(id)?.value\n if (!group) return\n enqueueOp({ type: 'group.remove', group })\n },\n\n batch(fn) {\n transact(() => {\n startBatch()\n try {\n fn()\n } finally {\n const batch = endBatch()\n if (batch) emitChange(batch)\n }\n })\n },\n\n applyOp(op, applyOpts) {\n const origin: OpOrigin = applyOpts?.origin ?? 'local'\n if (origin !== 'local') {\n // remote / history ops bypass the local batch buffer; emit their own\n applyOpInternal(op)\n emitChange({\n id: asBatchId(idGenerator()),\n clientId,\n ts: Date.now(),\n origin,\n ops: [op],\n })\n return\n }\n enqueueOp(op)\n },\n\n applyBatch(b) {\n transact(() => {\n // Conflict detection runs BEFORE apply — the remote op's `prev`\n // slice describes what the remote client expected; once we apply\n // we lose the chance to compare. LWW still wins (we apply\n // regardless), but consumers get a 'conflict' event for UX.\n if (b.origin === 'remote') {\n const conflicts = detectConflicts(\n b,\n id => nodeAtoms.get(id)?.value,\n id => edgeAtoms.get(id)?.value,\n )\n if (conflicts.length > 0) emit('conflict', { batch: b, conflicts })\n }\n for (const op of b.ops) applyOpInternal(op)\n emitChange(b)\n })\n },\n\n canUndo: () => undoStack.length > 0,\n canRedo: () => redoStack.length > 0,\n undo() {\n const batch = undoStack.pop()\n if (!batch) return false\n const ops = inverseBatch(batch)\n const inverseB: OpBatch = {\n id: asBatchId(idGenerator()),\n clientId,\n ts: Date.now(),\n origin: 'history',\n ops,\n }\n transact(() => {\n for (const op of ops) applyOpInternal(op)\n emit('change', inverseB) // bypass emitChange — history doesn't push\n })\n redoStack.push(batch)\n return true\n },\n redo() {\n const batch = redoStack.pop()\n if (!batch) return false\n // Replay with history origin so the inverse machinery stays clean,\n // and the redo batch goes back onto the undo stack so the user can\n // undo it again.\n const redoB: OpBatch = { ...batch, origin: 'history' }\n transact(() => {\n for (const op of redoB.ops) applyOpInternal(op)\n emit('change', redoB)\n })\n undoStack.push(batch)\n return true\n },\n clearHistory() {\n undoStack.length = 0\n redoStack.length = 0\n },\n\n // reads\n getNode: id => nodeAtoms.get(id)?.value,\n getEdge: id => edgeAtoms.get(id)?.value,\n getGroup: id => groupAtoms.get(id)?.value,\n getAllNodes: () => nodeIdsAtom.value.map(id => nodeAtoms.get(id)!.value),\n getAllEdges: () => edgeIdsAtom.value.map(id => edgeAtoms.get(id)!.value),\n getAllGroups: () => groupIdsAtom.value.map(id => groupAtoms.get(id)!.value),\n getNodeCount: () => nodeIdsAtom.value.length,\n getEdgeCount: () => edgeIdsAtom.value.length,\n getGroupCount: () => groupIdsAtom.value.length,\n\n getFrames: () => {\n const out: Node[] = []\n for (const id of frameOrderAtom.value) {\n const n = nodeAtoms.get(id)?.value\n if (n && n.type === 'frame') out.push(n)\n }\n return out\n },\n setFrameOrder(ids: NodeId[]) {\n const valid = new Set<NodeId>()\n for (const a of nodeAtoms.values()) {\n if (a.value.type === 'frame') valid.add(a.value.id)\n }\n // Drop ids that aren't (or no longer are) frames; append any\n // frames the caller forgot so the order remains a permutation\n // of the actual frame set.\n const filtered: NodeId[] = []\n const seen = new Set<NodeId>()\n for (const id of ids) {\n if (valid.has(id) && !seen.has(id)) {\n filtered.push(id)\n seen.add(id)\n }\n }\n for (const id of valid) {\n if (!seen.has(id)) filtered.push(id)\n }\n const prev = [...frameOrderAtom.value]\n // No-op short-circuit.\n if (filtered.length === prev.length && filtered.every((id, i) => id === prev[i])) {\n return\n }\n enqueueOp({ type: 'frame.reorder', ids: filtered, prev })\n },\n getNodesInFrame(id: NodeId) {\n const frame = nodeAtoms.get(id)?.value\n if (!frame || frame.type !== 'frame') return []\n const frameAabb = nodeAABB(frame)\n // Spatial broad-phase: any node intersecting the frame's AABB\n // is a candidate. Then filter to \"fully inside\" — node's AABB\n // entirely contained by the frame's AABB.\n const candidates = nodeIndex.queryRect(frameAabb) as NodeId[]\n const out: Node[] = []\n for (const cid of candidates) {\n if (cid === id) continue\n const node = nodeAtoms.get(cid)?.value\n if (!node || node.type === 'frame') continue\n const a = nodeAABB(node)\n if (\n a.x >= frameAabb.x &&\n a.y >= frameAabb.y &&\n a.x + a.w <= frameAabb.x + frameAabb.w &&\n a.y + a.h <= frameAabb.y + frameAabb.h\n ) {\n out.push(node)\n }\n }\n return out\n },\n\n getEdgeGeometry(id: EdgeId): EdgeGeometry | undefined {\n const edge = edgeAtoms.get(id)?.value\n if (!edge) return undefined\n const version = edgeVersions.get(id) ?? 0\n return edgeGeoCache.get(edge, version, getNodeForGeo) ?? undefined\n },\n getIncidentEdges(id: NodeId): EdgeId[] {\n const set = incidentEdges.get(id)\n return set ? [...set] : []\n },\n getNodeTypeDef(type: string) {\n return nodeTypeRegistry.get(type)\n },\n\n querySpatial(q: SpatialQuery): SpatialResult {\n const rect = q.rect ?? (q.point ? { x: q.point.x, y: q.point.y, w: 0, h: 0 } : null)\n if (!rect) return { nodes: [], edges: [] }\n return {\n nodes: nodeIndex.queryRect(rect) as NodeId[],\n edges: edgeIndex.queryRect(rect) as EdgeId[],\n }\n },\n\n getCamera: () => cameraAtom.value,\n setCamera(patch) {\n const next: CameraState = { ...cameraAtom.value, ...patch }\n cameraAtom.set(next)\n emit('camera', next)\n },\n\n getSelection: () => selectionAtom.value,\n setSelection(ids) {\n selectionAtom.set(ids)\n emit('selection', ids)\n },\n\n getInteractionState: () => interactionAtom.value,\n setInteractionState(patch) {\n const next: InteractionState = { ...interactionAtom.value, ...patch }\n interactionAtom.set(next)\n emit('interaction', next)\n },\n resetInteractionState() {\n const next = idleInteractionState()\n interactionAtom.set(next)\n emit('interaction', next)\n },\n\n beginEdit(id) {\n // Polymorphic: id may belong to a node or an edge. Resolve which.\n let target: import('./interaction').EditTarget | null = null\n if (nodeAtoms.has(id as NodeId)) target = { kind: 'node', id: id as NodeId }\n else if (edgeAtoms.has(id as EdgeId)) target = { kind: 'edge', id: id as EdgeId }\n if (!target) return\n const next: InteractionState = {\n ...interactionAtom.value,\n mode: 'editing',\n editingTarget: target,\n }\n interactionAtom.set(next)\n emit('interaction', next)\n },\n commitEdit(content) {\n const state = interactionAtom.value\n if (state.mode !== 'editing' || !state.editingTarget) return\n const target = state.editingTarget\n // Write content + autofit-derived height in one update so the\n // bitmap cache sees the final geometry on the next paint, not an\n // intermediate one.\n if (target.kind === 'node') this.updateNode(target.id, { content })\n else this.updateEdge(target.id, { content })\n const idleState = { ...interactionAtom.value, mode: 'idle' as const, editingTarget: null }\n interactionAtom.set(idleState)\n emit('interaction', idleState)\n },\n cancelEdit() {\n const state = interactionAtom.value\n if (state.mode !== 'editing') return\n const idleState = { ...state, mode: 'idle' as const, editingTarget: null }\n interactionAtom.set(idleState)\n emit('interaction', idleState)\n },\n\n presence: {\n setLocal(patch: PresencePatch) {\n const next: PresenceState = { ...localPresenceAtom.value, ...patch }\n localPresenceAtom.set(next)\n emit('presence', { state: next })\n },\n getLocal: () => localPresenceAtom.value,\n get: (id: ClientId) => remotePresence.get(id),\n getAll: () => remotePresence,\n applyRemote(id: ClientId, state: PresenceState | null) {\n if (state === null) {\n if (remotePresence.delete(id)) emit('presence', { clientId: id, removed: true })\n return\n }\n remotePresence.set(id, state)\n emit('presence', { state })\n },\n },\n\n subscribe<E extends StoreEventName>(event: E, cb: StoreEventHandler<E>): Unsubscribe {\n subscribers[event].add(cb)\n return () => {\n subscribers[event].delete(cb)\n }\n },\n }\n\n return store\n}\n","import type { ClientId, OpBatch } from '../types'\nimport type { PresencePatch, PresenceState } from './presence'\nimport type { CanvasStore, Unsubscribe } from './types'\n\n/**\n * SyncAdapter — see ARCHITECTURE.md §10.6.\n *\n * Pluggable transport contract for collab. The library never ships a\n * concrete adapter (transport is consumer territory: WebSocket, Yjs,\n * Automerge, BroadcastChannel, …). v1 ships:\n *\n * - This interface\n * - `attachSync(store, adapter)` — wires local commits → adapter and\n * remote batches → store with `origin: 'remote'`\n * - A separate package `@canvas-harness/sync-broadcast` providing a\n * BroadcastChannel-backed adapter for single-machine demos\n *\n * **v1 sync is experimental.** Conflict semantics assume causally-ordered\n * op delivery from the adapter. Adapters without causal ordering must\n * advertise `capabilities.crdt: true` and own merge themselves.\n */\nexport type SyncAdapterCapabilities = {\n /**\n * Adapter guarantees ops arrive in the same causal order all clients\n * see. Required for the default LWW path.\n */\n causalOrdering?: boolean\n /**\n * Adapter merges via CRDT (Yjs / Automerge / ...). Skips library-side\n * LWW because the adapter has already resolved conflicts.\n */\n crdt?: boolean\n}\n\n/**\n * Pluggable collab transport. Implementations forward op batches +\n * presence patches between peers. The library is transport-agnostic;\n * see `@canvas-harness/sync-broadcast` for a reference adapter using\n * `BroadcastChannel`.\n *\n * Authors typically wrap a WebSocket / Yjs / Automerge instance.\n *\n * @example\n * const myAdapter: SyncAdapter = {\n * capabilities: { causalOrdering: true },\n * sendBatch: b => ws.send(JSON.stringify({ kind: 'op', batch: b })),\n * sendPresence: p => ws.send(JSON.stringify({ kind: 'presence', patch: p })),\n * onBatch(cb) {\n * const h = (e: MessageEvent) => { const m = JSON.parse(e.data); if (m.kind === 'op') cb(m.batch) }\n * ws.addEventListener('message', h)\n * return () => ws.removeEventListener('message', h)\n * },\n * onPresence(cb) { … },\n * destroy() { ws.close() },\n * }\n * const detach = attachSync(store, myAdapter)\n */\nexport type SyncAdapter = {\n capabilities: SyncAdapterCapabilities\n\n /** Send a locally-committed (or history) batch to peers. */\n sendBatch(batch: OpBatch): void\n /** Send a local presence patch to peers. */\n sendPresence(patch: PresencePatch): void\n\n /** Receive remote batches. Subscription persists until `destroy()`. */\n onBatch(cb: (batch: OpBatch) => void): Unsubscribe\n /**\n * Receive remote presence patches. `state === null` means the remote\n * client has left and should be removed from the presence map.\n */\n onPresence(cb: (clientId: ClientId, state: PresenceState | null) => void): Unsubscribe\n\n /** Optional teardown — closes sockets, clears buffers, etc. */\n destroy?(): void\n}\n\n/**\n * Wires a {@link SyncAdapter} to a {@link CanvasStore}. Returns a\n * `detach()` function that disconnects everything (including the\n * adapter's own `destroy()`).\n *\n * Throws if the adapter advertises neither `causalOrdering` nor\n * `crdt` — the default LWW path requires causal order.\n *\n * After attach:\n * - Local + history batches forward to peers via `adapter.sendBatch`.\n * - Local presence updates forward via `adapter.sendPresence`.\n * - Remote batches apply to the store with `origin: 'remote'`\n * (don't enter undo stack; conflict event fires on `prev` mismatch).\n * - Remote presence updates merge into `store.presence`.\n *\n * @example\n * import { createBroadcastSyncAdapter } from '@canvas-harness/sync-broadcast'\n * const adapter = createBroadcastSyncAdapter({\n * channelName: 'my-board',\n * clientId: store.clientId,\n * })\n * const detach = attachSync(store, adapter)\n * // ...later, on unmount:\n * detach()\n */\nexport const attachSync = (store: CanvasStore, adapter: SyncAdapter): Unsubscribe => {\n if (!adapter.capabilities.causalOrdering && !adapter.capabilities.crdt) {\n throw new Error(\n 'SyncAdapter must advertise capabilities.causalOrdering or capabilities.crdt. ' +\n 'See ARCHITECTURE.md §10.6.',\n )\n }\n\n const unsubChange = store.subscribe('change', batch => {\n // Forward local mutations AND history batches (undo/redo). Remote\n // batches are echoes from peers and must not be re-broadcast.\n if (batch.origin !== 'remote') adapter.sendBatch(batch)\n })\n\n const unsubPresence = store.subscribe('presence', e => {\n if ('removed' in e && e.removed) return\n if (e.state.clientId !== store.clientId) return\n // Strip clientId from the patch — peers know who it's from from the channel.\n const { clientId: _id, ...patch } = e.state\n adapter.sendPresence(patch)\n })\n\n const unsubRemoteBatch = adapter.onBatch(batch => {\n // Bypass undo stack; apply with origin: 'remote' (origin is in the\n // batch itself for applyBatch). Conflict detection lives in\n // applyRemoteBatch (see conflict.ts).\n store.applyBatch({ ...batch, origin: 'remote' })\n })\n\n const unsubRemotePresence = adapter.onPresence((clientId, state) => {\n store.presence.applyRemote(clientId, state)\n })\n\n return () => {\n unsubChange()\n unsubPresence()\n unsubRemoteBatch()\n unsubRemotePresence()\n adapter.destroy?.()\n }\n}\n","/**\n * Palm-rejection helper — see IMPLEMENTATION.md Phase 11.\n *\n * When a stylus is actively touching the surface, mobile/tablet OSes\n * sometimes mis-route palm contacts as `pointerType: 'touch'`. The\n * heuristic: when a pen pointer is down (or has just lifted), drop all\n * incoming `touch` pointers for a short grace period.\n *\n * Pure state holder + helpers. The `<Canvas>` gesture hooks call\n * `notePenActive` / `notePenInactive` on pen pointer events, and\n * `shouldRejectTouch` before processing a touch event.\n */\n\nexport type PalmRejectionState = {\n /** True while at least one pen pointer is currently down. */\n penActive: boolean\n /** Timestamp (ms since epoch) at which the most recent pen pointer lifted. */\n lastPenUpAt: number\n}\n\nexport const PALM_REJECTION_GRACE_MS = 300\n\nexport const createPalmRejectionState = (): PalmRejectionState => ({\n penActive: false,\n lastPenUpAt: 0,\n})\n\nexport const notePenActive = (state: PalmRejectionState): void => {\n state.penActive = true\n}\n\nexport const notePenInactive = (state: PalmRejectionState, now: number): void => {\n state.penActive = false\n state.lastPenUpAt = now\n}\n\n/**\n * Returns true if this touch event should be ignored because a pen is\n * active (or just lifted within the grace window).\n */\nexport const shouldRejectTouch = (state: PalmRejectionState, now: number): boolean => {\n if (state.penActive) return true\n return now - state.lastPenUpAt < PALM_REJECTION_GRACE_MS\n}\n","import type { CanvasStore } from '../store'\n/**\n * Scene serialization codec — see ARCHITECTURE.md §3.8.\n *\n * In-memory uses Record<Id, T> for O(1) lookup; the wire format uses\n * arrays (smaller JSON, gzips better, deterministic iteration order).\n * Cost is one O(n) pass at the codec boundary, paid only on load/save.\n *\n * Schema migration: registered migrators run on `fromJSON` when the\n * incoming `schemaVersion` is lower than the current one.\n */\nimport { SCHEMA_VERSION, asEdgeId, asGroupId, asNodeId } from '../types'\nimport type { Scene, SerializedScene } from '../types'\n\nexport type Migrator = (raw: unknown) => unknown\n\nconst migrators = new Map<number, Migrator>()\n\n/**\n * Register a migrator that runs when loading data at version `fromVersion`.\n * The migrator should return data shaped for `fromVersion + 1`.\n */\nexport const registerMigrator = (fromVersion: number, fn: Migrator): void => {\n migrators.set(fromVersion, fn)\n}\n\n/**\n * Serializes a scene to its wire form.\n */\nexport const toSerialized = (scene: Scene): SerializedScene => ({\n schemaVersion: scene.schemaVersion,\n nodes: Object.values(scene.nodes),\n edges: Object.values(scene.edges),\n groups: Object.values(scene.groups),\n camera: scene.camera,\n selection: scene.selection,\n ...(scene.frameOrder && scene.frameOrder.length > 0 ? { frameOrder: scene.frameOrder } : {}),\n})\n\n/**\n * Deserializes from wire form into the in-memory Scene shape.\n * Runs migrators if the version is older than current.\n */\nexport const fromSerialized = (raw: SerializedScene | unknown): Scene => {\n let working: unknown = raw\n let version = (working as { schemaVersion?: number }).schemaVersion ?? 0\n\n while (version < SCHEMA_VERSION) {\n const fn = migrators.get(version)\n if (!fn) {\n throw new Error(\n `Cannot migrate scene from schemaVersion ${version} to ${SCHEMA_VERSION}; no migrator registered`,\n )\n }\n working = fn(working)\n version++\n }\n\n const ser = working as SerializedScene\n\n return {\n schemaVersion: SCHEMA_VERSION,\n nodes: Object.fromEntries(ser.nodes.map(n => [asNodeId(n.id), n])) as Scene['nodes'],\n edges: Object.fromEntries(ser.edges.map(e => [asEdgeId(e.id), e])) as Scene['edges'],\n groups: Object.fromEntries(ser.groups.map(g => [asGroupId(g.id), g])) as Scene['groups'],\n camera: ser.camera,\n selection: ser.selection,\n ...(ser.frameOrder ? { frameOrder: ser.frameOrder } : {}),\n }\n}\n\n/**\n * Convenience: dump a store's current state to wire form.\n */\nexport const storeToJSON = (store: CanvasStore): SerializedScene => ({\n schemaVersion: SCHEMA_VERSION,\n nodes: store.getAllNodes(),\n edges: store.getAllEdges(),\n groups: store.getAllGroups(),\n camera: store.getCamera(),\n selection: store.getSelection(),\n})\n","/**\n * DPR + size management for canvas elements.\n *\n * The backing-store size is `cssSize × dpr`, where `dpr` is clamped by\n * `maxDpr`. At native device-pixel-ratio on hi-DPI displays (Mac Retina\n * ≈ 2, Windows 4K @ 175% ≈ 1.75), the backing buffer can hit 8-25 MP —\n * every paint pays a proportional GPU-upload cost that often dominates\n * the frame budget.\n *\n * Default behavior when `maxDpr` is omitted: pick a cap from the\n * canvas's CSS-pixel area so the backing buffer stays in a healthy\n * 3-8 MP zone regardless of monitor / OS scaling. Tiered:\n *\n * - CSS canvas ≥ 2.5 MP (4K-ish, e.g. 4K Mac native, 4K Win @ 175%)\n * → cap at 1 (crispness sacrificed for perf, high-density makes\n * the softness less visible anyway)\n * - CSS canvas ≥ 1.5 MP (1440p / 2K-ish)\n * → cap at 1.5\n * - CSS canvas < 1.5 MP (1080p Retina laptops, embedded canvases)\n * → cap at 2 (DPR=2 is free at this size — keep crispness)\n *\n * Explicit `maxDpr={n}` always overrides the tier default. Text\n * remains crisp regardless of canvas DPR — the text bitmap cache\n * rasterizes glyphs at its own DPR-aware scale and blits.\n */\nconst HARD_MAX_DPR = 3 // anything above this just burns memory\n\n/**\n * Picks a sensible default `maxDpr` for the given CSS-pixel canvas\n * size. Targets ~3-8 MP backing buffer across the realistic hardware\n * spectrum. See module-level doc for the tier breakpoints.\n */\nexport const defaultMaxDprForSize = (cssW: number, cssH: number): number => {\n const cssPx = cssW * cssH\n if (cssPx >= 2_500_000) return 1\n if (cssPx >= 1_500_000) return 1.5\n return 2\n}\n\nexport type CanvasSurface = {\n canvas: HTMLCanvasElement\n ctx: CanvasRenderingContext2D\n /** Logical CSS pixels (the size you set in JS / read with getBoundingClientRect). */\n cssWidth: number\n cssHeight: number\n /** Device pixels — backing-store size. */\n dpr: number\n}\n\n/**\n * Resolved DPR for the canvas backing store. Clamped by `maxDpr`\n * (consumer-supplied) and the absolute `HARD_MAX_DPR` ceiling. When\n * `maxDpr` is omitted, the tier-based default (see\n * `defaultMaxDprForSize`) is used — pass `cssW`/`cssH` to enable it.\n */\nexport const getDpr = (maxDpr?: number, cssW = 0, cssH = 0): number => {\n if (typeof window === 'undefined') return 1\n const raw = window.devicePixelRatio || 1\n const resolvedMax =\n maxDpr === undefined && cssW > 0 && cssH > 0 ? defaultMaxDprForSize(cssW, cssH) : (maxDpr ?? 1)\n const cap = Math.max(1, Math.min(HARD_MAX_DPR, resolvedMax))\n return Math.max(1, Math.min(cap, raw))\n}\n\n/**\n * Builds a managed canvas surface. Caller pins the canvas element; we size\n * it and reset the 2d context's transform to logical-pixel space.\n *\n * Subsequent calls to `setSize` re-allocate the backing store if the new\n * `cssW × cssH × DPR` differs from the current.\n */\n// `maxDpr` is accepted but not yet used here — the actual DPR is\n// resolved in `sizeSurface` once we have the canvas dimensions for\n// the tier-default lookup. Kept on the signature for API symmetry.\nexport const setupSurface = (canvas: HTMLCanvasElement, _maxDpr?: number): CanvasSurface => {\n const ctx = canvas.getContext('2d')\n if (!ctx) throw new Error('Canvas 2d context unavailable')\n return {\n canvas,\n ctx,\n cssWidth: 0,\n cssHeight: 0,\n dpr: 1, // placeholder; `sizeSurface` writes the real value\n }\n}\n\n/**\n * Resizes the surface to a new CSS-pixel size, picking up the current DPR.\n * Returns true if anything changed (caller should redraw).\n */\nexport const sizeSurface = (\n surface: CanvasSurface,\n cssW: number,\n cssH: number,\n maxDpr?: number,\n): boolean => {\n const dpr = getDpr(maxDpr, cssW, cssH)\n if (surface.cssWidth === cssW && surface.cssHeight === cssH && surface.dpr === dpr) {\n return false\n }\n surface.cssWidth = cssW\n surface.cssHeight = cssH\n surface.dpr = dpr\n surface.canvas.width = Math.max(1, Math.round(cssW * dpr))\n surface.canvas.height = Math.max(1, Math.round(cssH * dpr))\n surface.canvas.style.width = `${cssW}px`\n surface.canvas.style.height = `${cssH}px`\n return true\n}\n\n/**\n * Clears the entire backing store. Call before setting the camera transform.\n */\nexport const clearSurface = (surface: CanvasSurface): void => {\n surface.ctx.setTransform(1, 0, 0, 1, 0, 0)\n surface.ctx.clearRect(0, 0, surface.canvas.width, surface.canvas.height)\n}\n","/**\n * rAF-driven frame loop — see ARCHITECTURE.md §4.3.\n *\n * The renderer marks layers dirty via `requestFrame()`; the loop coalesces\n * multiple requests into one paint per rAF tick. Idle frames cost nothing\n * because we only schedule when something is dirty.\n *\n * Per-frame timing is captured so consumers can drive perf overlays.\n */\nexport type FrameStats = {\n /** Most recent frame duration in ms (drawFn + overhead). */\n lastMs: number\n /** Running average over the last `historySize` frames. */\n avgMs: number\n /** Number of frames painted since start. */\n frames: number\n /** Frames drawn in the last 1000ms (FPS measurement). */\n fps: number\n}\n\nexport type FrameLoop = {\n start(): void\n stop(): void\n requestFrame(): void\n stats(): FrameStats\n}\n\ntype Opts = {\n draw: () => void\n historySize?: number\n}\n\nexport const createFrameLoop = ({ draw, historySize = 60 }: Opts): FrameLoop => {\n let running = false\n let scheduled = false\n let frameId = 0\n const history: number[] = []\n let frames = 0\n let lastMs = 0\n let avgMs = 0\n // rolling window of frame timestamps for FPS in the last second\n const fpsWindow: number[] = []\n let fps = 0\n\n const tick = (): void => {\n frameId = 0\n scheduled = false\n if (!running) return\n\n const t0 = performance.now()\n draw()\n const dur = performance.now() - t0\n\n history.push(dur)\n if (history.length > historySize) history.shift()\n let sum = 0\n for (const v of history) sum += v\n avgMs = sum / history.length\n lastMs = dur\n frames++\n\n fpsWindow.push(t0)\n const cutoff = t0 - 1000\n while (fpsWindow.length > 0 && fpsWindow[0]! < cutoff) fpsWindow.shift()\n fps = fpsWindow.length\n }\n\n const schedule = (): void => {\n if (scheduled || !running) return\n scheduled = true\n frameId = requestAnimationFrame(tick)\n }\n\n return {\n start() {\n if (running) return\n running = true\n schedule()\n },\n stop() {\n running = false\n if (frameId !== 0) {\n cancelAnimationFrame(frameId)\n frameId = 0\n }\n scheduled = false\n },\n requestFrame() {\n schedule()\n },\n stats: () => ({ lastMs, avgMs, frames, fps }),\n }\n}\n","/**\n * Renderer-side asset cache for `image` and `icon` node types.\n *\n * Why a cache: paint hot-path is sync; image / SVG decoding is async.\n * Each node carries its source on `node.data.src`; on first paint we\n * trigger an async decode and return a placeholder. When the decode\n * lands the cache fires `onReady`, which the renderer wires to a\n * static repaint so the next frame blits the real bitmap.\n *\n * Eviction: LRU bounded by `MAX_ENTRIES`. Entries hold either an\n * `HTMLImageElement` (raster) or an `ImageBitmap` (rasterized SVG).\n * Decoded images are GC-friendly — once the cache evicts the wrapper,\n * the browser frees the underlying pixel buffer.\n *\n * SVG raster cache keys by (markup, color, sizeBucket) so resizing an\n * icon node only rasterizes at the new size, leaving the previous\n * resolution available for siblings still at that size.\n */\nimport { applySvgColor } from '../../assets'\n\nconst MAX_ENTRIES = 256\n\ntype ImageEntry = {\n kind: 'image'\n state: 'pending' | 'ready' | 'error'\n bitmap: HTMLImageElement | null\n err?: unknown\n}\n\ntype IconEntry = {\n kind: 'icon'\n state: 'pending' | 'ready' | 'error'\n bitmap: ImageBitmap | null\n err?: unknown\n}\n\ntype Entry = ImageEntry | IconEntry\n\n/**\n * Bucket the requested icon raster size to a power-of-two step so\n * minor zoom changes don't churn the rasterizer. 32, 64, 128, 256,\n * 512. Above 512 the cache disables bucketing (one entry per exact\n * size) since fewer nodes hit those sizes.\n */\nconst bucketSize = (px: number): number => {\n if (px <= 32) return 32\n if (px <= 64) return 64\n if (px <= 128) return 128\n if (px <= 256) return 256\n if (px <= 512) return 512\n return Math.ceil(px / 256) * 256\n}\n\nexport type AssetCacheOptions = {\n /** Called when a pending entry transitions to ready or error. */\n onReady?: () => void\n}\n\nexport type AssetCache = {\n /** Returns a loaded HTMLImageElement or null if still loading. */\n getImage(src: string): HTMLImageElement | null\n /**\n * Returns a rasterized ImageBitmap for the given SVG markup at the\n * given on-device pixel size + tint color, or null if pending.\n */\n getIcon(markup: string, color: string | undefined, devicePixelSize: number): ImageBitmap | null\n /** Frees decoded bitmaps. Call from renderer.dispose(). */\n dispose(): void\n}\n\nexport const createAssetCache = (opts: AssetCacheOptions = {}): AssetCache => {\n const entries = new Map<string, Entry>()\n let disposed = false\n\n const notify = (): void => {\n if (disposed) return\n opts.onReady?.()\n }\n\n const touch = (key: string, entry: Entry): void => {\n entries.delete(key)\n entries.set(key, entry)\n if (entries.size > MAX_ENTRIES) {\n // Evict the oldest entry (insertion-order iteration on Map).\n const oldestKey = entries.keys().next().value\n if (oldestKey !== undefined) {\n const evicted = entries.get(oldestKey)\n if (evicted?.kind === 'icon' && evicted.bitmap) evicted.bitmap.close?.()\n entries.delete(oldestKey)\n }\n }\n }\n\n const startImageDecode = (key: string, src: string): void => {\n const entry: ImageEntry = { kind: 'image', state: 'pending', bitmap: null }\n touch(key, entry)\n const img = new Image()\n // Data URIs are same-origin; no crossorigin attribute needed.\n img.onload = () => {\n if (disposed) return\n entry.state = 'ready'\n entry.bitmap = img\n notify()\n }\n img.onerror = e => {\n if (disposed) return\n entry.state = 'error'\n entry.err = e\n notify()\n }\n img.src = src\n }\n\n const startIconRaster = (\n key: string,\n markup: string,\n color: string | undefined,\n sizePx: number,\n ): void => {\n const entry: IconEntry = { kind: 'icon', state: 'pending', bitmap: null }\n touch(key, entry)\n const colored = color ? applySvgColor(markup, color) : markup\n const blob = new Blob([colored], { type: 'image/svg+xml' })\n const url = URL.createObjectURL(blob)\n const img = new Image()\n img.onload = async () => {\n URL.revokeObjectURL(url)\n if (disposed) return\n try {\n // Use the intrinsic image dimensions but cap to the requested\n // bucket size; createImageBitmap with options gives a crisp\n // result at the target pixel grid without an OffscreenCanvas\n // dance in the simple cases.\n const bitmap = await createImageBitmap(img, {\n resizeWidth: sizePx,\n resizeHeight: sizePx,\n resizeQuality: 'high',\n })\n if (disposed) {\n bitmap.close?.()\n return\n }\n entry.state = 'ready'\n entry.bitmap = bitmap\n notify()\n } catch (e) {\n entry.state = 'error'\n entry.err = e\n notify()\n }\n }\n img.onerror = e => {\n URL.revokeObjectURL(url)\n if (disposed) return\n entry.state = 'error'\n entry.err = e\n notify()\n }\n img.src = url\n }\n\n return {\n getImage(src) {\n const key = `img:${src}`\n const existing = entries.get(key)\n if (existing && existing.kind === 'image') {\n if (existing.state === 'ready') {\n // Promote on access so LRU works.\n touch(key, existing)\n return existing.bitmap\n }\n return null\n }\n startImageDecode(key, src)\n return null\n },\n getIcon(markup, color, devicePixelSize) {\n const size = bucketSize(Math.max(1, Math.ceil(devicePixelSize)))\n const key = `icon:${size}:${color ?? ''}:${markup}`\n const existing = entries.get(key)\n if (existing && existing.kind === 'icon') {\n if (existing.state === 'ready') {\n touch(key, existing)\n return existing.bitmap\n }\n return null\n }\n startIconRaster(key, markup, color, size)\n return null\n },\n dispose() {\n disposed = true\n for (const entry of entries.values()) {\n if (entry.kind === 'icon' && entry.bitmap) entry.bitmap.close?.()\n }\n entries.clear()\n },\n }\n}\n","/**\n * Paint helpers for `image` and `icon` node types. Caller is already\n * inside `drawWithNodeTransform` (origin at the node's top-left,\n * rotation applied), so we paint into local space `(0, 0, w, h)`.\n *\n * Both helpers return true when a bitmap was blitted, false when the\n * bitmap is still loading (caller may paint a placeholder).\n */\nimport type { IconNodeData, ImageNodeData, Node } from '../../types'\nimport { resolveOpacity } from '../shapes/defaults'\nimport type { ThemeResolver } from '../shapes/defaults'\nimport type { AssetCache } from './cache'\n\n/** Cheap loading placeholder — light fill so the user sees a tile while we decode. */\nconst PLACEHOLDER_FILL = '#e5e7eb'\nconst PLACEHOLDER_TEXT_FILL = '#94a3b8'\n\nconst paintPlaceholder = (ctx: CanvasRenderingContext2D, w: number, h: number, label: string) => {\n ctx.fillStyle = PLACEHOLDER_FILL\n ctx.fillRect(0, 0, w, h)\n if (w >= 32 && h >= 16) {\n ctx.fillStyle = PLACEHOLDER_TEXT_FILL\n ctx.font = '11px system-ui, sans-serif'\n ctx.textAlign = 'center'\n ctx.textBaseline = 'middle'\n ctx.fillText(label, w / 2, h / 2)\n }\n}\n\nexport const paintImageNode = (\n ctx: CanvasRenderingContext2D,\n node: Node,\n cache: AssetCache,\n theme?: ThemeResolver,\n): void => {\n if (node.w <= 0 || node.h <= 0) return\n const data = node.data as ImageNodeData | undefined\n if (!data?.src) return\n const bitmap = cache.getImage(data.src)\n const opacity = resolveOpacity(node.style, theme)\n const needsScope = opacity !== 1\n if (needsScope) {\n ctx.save()\n ctx.globalAlpha = opacity\n }\n if (bitmap?.complete) {\n ctx.drawImage(bitmap, 0, 0, node.w, node.h)\n } else {\n paintPlaceholder(ctx, node.w, node.h, 'loading…')\n }\n if (needsScope) ctx.restore()\n}\n\nexport const paintIconNode = (\n ctx: CanvasRenderingContext2D,\n node: Node,\n cache: AssetCache,\n scale: number,\n theme?: ThemeResolver,\n): void => {\n if (node.w <= 0 || node.h <= 0) return\n const data = node.data as IconNodeData | undefined\n if (!data?.src) return\n // Bucket raster size by on-device pixels. We pass the longer side\n // so non-square nodes still render at their native quality on the\n // larger axis.\n const sizePx = Math.max(node.w, node.h) * scale\n const color = node.style?.iconColor\n const bitmap = cache.getIcon(data.src, color, sizePx)\n const opacity = resolveOpacity(node.style, theme)\n const needsScope = opacity !== 1\n if (needsScope) {\n ctx.save()\n ctx.globalAlpha = opacity\n }\n if (bitmap) {\n ctx.drawImage(bitmap, 0, 0, node.w, node.h)\n } else {\n paintPlaceholder(ctx, node.w, node.h, 'svg…')\n }\n if (needsScope) ctx.restore()\n}\n","import { type CanvasBackground, DEFAULT_BACKGROUND, type WorldRect } from '../types'\n\n/**\n * Page background + optional infinite dot / grid pattern.\n *\n * Called inside `paintStatic` after the camera transform is applied,\n * before nodes. Dots / grid lines are drawn in world coordinates so\n * they anchor to the world origin — panning moves the user *through*\n * the pattern, zooming changes visual density.\n *\n * LOD: when `gap × zoom` drops below `MIN_PATTERN_SCREEN_PX`, the\n * effective gap doubles in octaves so the pattern stays roughly the\n * same on-screen density. Below `MIN_VISIBLE_PATTERN_PX` the pattern\n * is omitted entirely (sub-pixel would be unreadable mush + waste).\n */\nexport type PaintBackgroundOptions = {\n /** Visible world rect (after viewport-overscan). */\n viewport: WorldRect\n /** camera.z — used for LOD octave selection + screen-px conversion. */\n zoom: number\n background?: CanvasBackground\n}\n\nconst MIN_PATTERN_SCREEN_PX = 8\nconst MIN_VISIBLE_PATTERN_PX = 2\n\nexport const paintBackground = (\n ctx: CanvasRenderingContext2D,\n opts: PaintBackgroundOptions,\n): void => {\n const bg = { ...DEFAULT_BACKGROUND, ...opts.background }\n\n // 1. Solid page color. Fill the visible world rect; the caller has\n // already applied the camera transform so we paint in world coords.\n ctx.save()\n ctx.fillStyle = bg.color\n ctx.fillRect(opts.viewport.x, opts.viewport.y, opts.viewport.w, opts.viewport.h)\n ctx.restore()\n\n if (bg.pattern === 'none') return\n\n // 2a. User-configured zoom cliffs — hide pattern outside [minZoom, maxZoom].\n if (opts.zoom < bg.minZoom) return\n if (opts.zoom > bg.maxZoom) return\n\n // 2b. LOD — densify the gap in octaves until each cell is at least\n // MIN_PATTERN_SCREEN_PX on-screen. Skip entirely when pattern\n // would be sub-visible.\n let effectiveGap = bg.gap\n while (effectiveGap * opts.zoom < MIN_PATTERN_SCREEN_PX) {\n effectiveGap *= 2\n if (effectiveGap > 1e6) return // runaway guard\n }\n if (effectiveGap * opts.zoom < MIN_VISIBLE_PATTERN_PX) return\n\n // 3. First grid line / dot inside the viewport — snap to the gap.\n const minX = Math.floor(opts.viewport.x / effectiveGap) * effectiveGap\n const minY = Math.floor(opts.viewport.y / effectiveGap) * effectiveGap\n const maxX = opts.viewport.x + opts.viewport.w\n const maxY = opts.viewport.y + opts.viewport.h\n\n if (bg.pattern === 'dots') {\n paintDots(ctx, minX, minY, maxX, maxY, effectiveGap, bg.patternColor, opts.zoom)\n } else if (bg.pattern === 'grid') {\n paintGrid(ctx, minX, minY, maxX, maxY, effectiveGap, bg.patternColor, opts.zoom)\n }\n}\n\nconst paintDots = (\n ctx: CanvasRenderingContext2D,\n minX: number,\n minY: number,\n maxX: number,\n maxY: number,\n gap: number,\n color: string,\n zoom: number,\n): void => {\n // Use a tiny `fillRect` per dot rather than `arc + fill`. At 1-2px\n // on-screen the corners aren't perceivable (antialiasing softens\n // them into something visually indistinguishable from a small\n // round dot), and one canvas2d call replaces three (beginPath /\n // arc / fill) plus the implicit curve approximation. ~3-5x faster\n // across thousands of dots/frame.\n const sizeWorld = Math.max(1, 1.6 / zoom)\n const half = sizeWorld / 2\n ctx.save()\n ctx.fillStyle = color\n for (let y = minY; y <= maxY; y += gap) {\n for (let x = minX; x <= maxX; x += gap) {\n ctx.fillRect(x - half, y - half, sizeWorld, sizeWorld)\n }\n }\n ctx.restore()\n}\n\nconst paintGrid = (\n ctx: CanvasRenderingContext2D,\n minX: number,\n minY: number,\n maxX: number,\n maxY: number,\n gap: number,\n color: string,\n zoom: number,\n): void => {\n const lineWidth = 1 / zoom // constant 1px on screen\n ctx.save()\n ctx.strokeStyle = color\n ctx.lineWidth = lineWidth\n ctx.beginPath()\n for (let x = minX; x <= maxX; x += gap) {\n ctx.moveTo(x, minY)\n ctx.lineTo(x, maxY)\n }\n for (let y = minY; y <= maxY; y += gap) {\n ctx.moveTo(minX, y)\n ctx.lineTo(maxX, y)\n }\n ctx.stroke()\n ctx.restore()\n}\n","/**\n * Resize-handle hit testing — see ARCHITECTURE.md §11.6.\n *\n * Handles are drawn at constant screen size (e.g. 8px), so their world-space\n * bounds change with camera zoom. They sit at the 8 cardinal points of the\n * node's bounding rect; for rotated nodes the handle positions rotate with\n * the node so a \"north-east\" handle is actually at the rotated NE corner.\n */\nimport type { Node, Vec2 } from '../types'\n\nexport type ResizeHandle = 'nw' | 'n' | 'ne' | 'e' | 'se' | 's' | 'sw' | 'w'\n\nexport const RESIZE_HANDLES: ResizeHandle[] = ['nw', 'n', 'ne', 'e', 'se', 's', 'sw', 'w']\n\n/**\n * Screen-pixel size of a resize-handle hit target. Visual size matches.\n * Sized for touch reach (~14px) without being intrusive on desktop;\n * tldraw uses a similar value.\n */\nexport const RESIZE_HANDLE_SIZE_PX = 14\n\n/**\n * Screen-pixel distance from the top edge of the node to the rotation\n * handle center. Visual + hit-target match.\n */\nexport const ROTATE_HANDLE_OFFSET_PX = 24\n\n/** Screen-pixel radius of the rotation-handle hit target. */\nexport const ROTATE_HANDLE_RADIUS_PX = 9\n\n/**\n * World-space centers of all 8 resize handles for the given node.\n * Rotation-aware: handles rotate with the node so they sit on the corners\n * and edge midpoints of the rotated rect (not the rotated AABB).\n */\nexport const handleWorldPositions = (node: Node): Record<ResizeHandle, Vec2> => {\n const localCenters: Record<ResizeHandle, Vec2> = {\n nw: { x: 0, y: 0 },\n n: { x: node.w / 2, y: 0 },\n ne: { x: node.w, y: 0 },\n e: { x: node.w, y: node.h / 2 },\n se: { x: node.w, y: node.h },\n s: { x: node.w / 2, y: node.h },\n sw: { x: 0, y: node.h },\n w: { x: 0, y: node.h / 2 },\n }\n if (node.angle === 0) {\n const offsetX = node.x\n const offsetY = node.y\n return {\n nw: { x: offsetX + localCenters.nw.x, y: offsetY + localCenters.nw.y },\n n: { x: offsetX + localCenters.n.x, y: offsetY + localCenters.n.y },\n ne: { x: offsetX + localCenters.ne.x, y: offsetY + localCenters.ne.y },\n e: { x: offsetX + localCenters.e.x, y: offsetY + localCenters.e.y },\n se: { x: offsetX + localCenters.se.x, y: offsetY + localCenters.se.y },\n s: { x: offsetX + localCenters.s.x, y: offsetY + localCenters.s.y },\n sw: { x: offsetX + localCenters.sw.x, y: offsetY + localCenters.sw.y },\n w: { x: offsetX + localCenters.w.x, y: offsetY + localCenters.w.y },\n }\n }\n\n const cx = node.x + node.w / 2\n const cy = node.y + node.h / 2\n const cos = Math.cos(node.angle)\n const sin = Math.sin(node.angle)\n const rotate = (p: Vec2): Vec2 => {\n // local coords (top-left origin) → center-origin → rotate → world\n const dx = p.x - node.w / 2\n const dy = p.y - node.h / 2\n return { x: cx + dx * cos - dy * sin, y: cy + dx * sin + dy * cos }\n }\n return {\n nw: rotate(localCenters.nw),\n n: rotate(localCenters.n),\n ne: rotate(localCenters.ne),\n e: rotate(localCenters.e),\n se: rotate(localCenters.se),\n s: rotate(localCenters.s),\n sw: rotate(localCenters.sw),\n w: rotate(localCenters.w),\n }\n}\n\n/**\n * Returns the handle hit by a world point, or null. `cameraZ` lets us map\n * the constant screen-size handle box to its current world-space footprint.\n */\nexport const hitTestHandles = (\n node: Node,\n worldPoint: Vec2,\n cameraZ: number,\n): ResizeHandle | null => {\n const halfWorld = RESIZE_HANDLE_SIZE_PX / 2 / cameraZ\n const positions = handleWorldPositions(node)\n for (const h of RESIZE_HANDLES) {\n const center = positions[h]\n if (\n Math.abs(worldPoint.x - center.x) <= halfWorld &&\n Math.abs(worldPoint.y - center.y) <= halfWorld\n ) {\n return h\n }\n }\n return null\n}\n\n/**\n * World-space position of the rotation handle — sits a constant 22px\n * (screen) above the node's top edge midpoint, perpendicular to the\n * rotated top edge.\n */\nexport const rotateHandleWorldPosition = (node: Node, cameraZ: number): Vec2 => {\n const offsetWorld = ROTATE_HANDLE_OFFSET_PX / cameraZ\n const cx = node.x + node.w / 2\n const cy = node.y + node.h / 2\n // Local coords (relative to node center, y-up): midpoint of top edge is\n // (0, -h/2 - offsetWorld). Apply rotation; node.angle is clockwise on\n // a y-down canvas.\n const localX = 0\n const localY = -node.h / 2 - offsetWorld\n const cos = Math.cos(node.angle)\n const sin = Math.sin(node.angle)\n return {\n x: cx + localX * cos - localY * sin,\n y: cy + localX * sin + localY * cos,\n }\n}\n\n/**\n * Returns true if `worldPoint` is over the rotation handle for the node.\n */\nexport const hitTestRotateHandle = (node: Node, worldPoint: Vec2, cameraZ: number): boolean => {\n const center = rotateHandleWorldPosition(node, cameraZ)\n const rWorld = ROTATE_HANDLE_RADIUS_PX / cameraZ\n const dx = worldPoint.x - center.x\n const dy = worldPoint.y - center.y\n return dx * dx + dy * dy <= rWorld * rWorld\n}\n","/**\n * Selection-overlay drawing — runs on the interactive canvas.\n *\n * Renders:\n * - selection outlines around selected node bounds\n * - 8 resize handles for a single-node or multi-select selection\n * - the marquee rect during marquee selection\n * - dragged nodes at their uncommitted (delta-offset) positions\n *\n * Visual sizes are constant in screen pixels — `scale` (camera.z × DPR)\n * is used to convert px → world for outline strokes and handle sizes.\n *\n * Color: every draw takes `color` so the renderer can thread its\n * `selectionColor` option through to all chrome. Marquee fill tints\n * via `globalAlpha = MARQUEE_FILL_ALPHA` so any color format works\n * (hex, rgb(), named) without parsing.\n */\nimport {\n RESIZE_HANDLE_SIZE_PX,\n ROTATE_HANDLE_RADIUS_PX,\n handleWorldPositions,\n rotateHandleWorldPosition,\n} from '../hit-test/handle'\nimport type { Node, Vec2, WorldRect } from '../types'\n\n/** Default selection chrome color when no override is provided. */\nexport const DEFAULT_SELECTION_COLOR = '#3b82f6'\nexport const SELECTION_OUTLINE_PX = 1.5\n/** Marquee fill = selection color at this alpha, applied via globalAlpha. */\nconst MARQUEE_FILL_ALPHA = 0.08\nconst MARQUEE_STROKE_PX = 1\n\n/**\n * Draws a 1.5px-on-screen outline around the node's (rotated) bounds.\n */\nexport const drawSelectionOutline = (\n ctx: CanvasRenderingContext2D,\n node: Node,\n scale: number,\n color: string,\n): void => {\n if (node.angle === 0) {\n ctx.save()\n ctx.strokeStyle = color\n ctx.lineWidth = SELECTION_OUTLINE_PX / scale\n ctx.beginPath()\n ctx.rect(node.x, node.y, node.w, node.h)\n ctx.stroke()\n ctx.restore()\n return\n }\n // Rotated: build the 4-corner path manually\n const cx = node.x + node.w / 2\n const cy = node.y + node.h / 2\n const cos = Math.cos(node.angle)\n const sin = Math.sin(node.angle)\n const corners: Vec2[] = [\n { x: -node.w / 2, y: -node.h / 2 },\n { x: node.w / 2, y: -node.h / 2 },\n { x: node.w / 2, y: node.h / 2 },\n { x: -node.w / 2, y: node.h / 2 },\n ].map(p => ({ x: cx + p.x * cos - p.y * sin, y: cy + p.x * sin + p.y * cos }))\n\n ctx.save()\n ctx.strokeStyle = color\n ctx.lineWidth = SELECTION_OUTLINE_PX / scale\n ctx.beginPath()\n const first = corners[0]!\n ctx.moveTo(first.x, first.y)\n for (let i = 1; i < corners.length; i++) {\n const c = corners[i]!\n ctx.lineTo(c.x, c.y)\n }\n ctx.closePath()\n ctx.stroke()\n ctx.restore()\n}\n\n/**\n * Draws the 8 resize handles for a node at constant screen size.\n */\nexport const drawResizeHandles = (\n ctx: CanvasRenderingContext2D,\n node: Node,\n scale: number,\n color: string,\n): void => {\n const halfPx = RESIZE_HANDLE_SIZE_PX / 2\n const halfWorld = halfPx / scale\n const positions = handleWorldPositions(node)\n\n ctx.save()\n ctx.fillStyle = '#fff'\n ctx.strokeStyle = color\n ctx.lineWidth = SELECTION_OUTLINE_PX / scale\n for (const key of Object.keys(positions) as (keyof typeof positions)[]) {\n const p = positions[key]\n ctx.beginPath()\n ctx.rect(p.x - halfWorld, p.y - halfWorld, halfWorld * 2, halfWorld * 2)\n ctx.fill()\n ctx.stroke()\n }\n ctx.restore()\n}\n\n/**\n * Draws the rotation handle — circle above the top edge midpoint,\n * connected by a tether line. Constant screen size; rotation-aware so\n * the handle stays \"above\" the rotated top edge.\n *\n * cameraZ is passed separately from `scale` because the handle's\n * world-space offset depends on plain zoom (not DPR-multiplied scale).\n */\nexport const drawRotateHandle = (\n ctx: CanvasRenderingContext2D,\n node: Node,\n scale: number,\n cameraZ: number,\n color: string,\n): void => {\n const center = rotateHandleWorldPosition(node, cameraZ)\n const radiusWorld = ROTATE_HANDLE_RADIUS_PX / scale\n\n // Tether: top edge midpoint → handle center, in the node's local frame.\n const cx = node.x + node.w / 2\n const cy = node.y + node.h / 2\n const cos = Math.cos(node.angle)\n const sin = Math.sin(node.angle)\n const topMidLocalY = -node.h / 2\n const topMidWorld = {\n x: cx + 0 * cos - topMidLocalY * sin,\n y: cy + 0 * sin + topMidLocalY * cos,\n }\n\n ctx.save()\n ctx.strokeStyle = color\n ctx.lineWidth = SELECTION_OUTLINE_PX / scale\n ctx.beginPath()\n ctx.moveTo(topMidWorld.x, topMidWorld.y)\n ctx.lineTo(center.x, center.y)\n ctx.stroke()\n\n ctx.fillStyle = '#fff'\n ctx.beginPath()\n ctx.arc(center.x, center.y, radiusWorld, 0, Math.PI * 2)\n ctx.fill()\n ctx.stroke()\n ctx.restore()\n}\n\n/**\n * Draws a single midpoint handle at the visual midpoint of a selected\n * bezier/polyline edge. Drag it to reshape the curve (the gesture in\n * `useInteractionGesture` converts the drag point into cubic controls\n * via `midpointToCubicControls`).\n */\nexport const drawEdgeMidpointHandle = (\n ctx: CanvasRenderingContext2D,\n midpoint: { x: number; y: number },\n scale: number,\n color: string,\n): void => {\n const radiusPx = 5\n const radiusWorld = radiusPx / scale\n ctx.save()\n ctx.fillStyle = '#fff'\n ctx.strokeStyle = color\n ctx.lineWidth = SELECTION_OUTLINE_PX / scale\n ctx.beginPath()\n ctx.arc(midpoint.x, midpoint.y, radiusWorld, 0, Math.PI * 2)\n ctx.fill()\n ctx.stroke()\n ctx.restore()\n}\n\n/**\n * Draws the endpoint handles for a selected edge at the source/target\n * world points. Used during edit/reconnection.\n */\nexport const drawEdgeEndpointHandles = (\n ctx: CanvasRenderingContext2D,\n source: { x: number; y: number },\n target: { x: number; y: number },\n scale: number,\n color: string,\n): void => {\n const radiusPx = 5\n const radiusWorld = radiusPx / scale\n ctx.save()\n ctx.fillStyle = '#fff'\n ctx.strokeStyle = color\n ctx.lineWidth = SELECTION_OUTLINE_PX / scale\n for (const p of [source, target]) {\n ctx.beginPath()\n ctx.arc(p.x, p.y, radiusWorld, 0, Math.PI * 2)\n ctx.fill()\n ctx.stroke()\n }\n ctx.restore()\n}\n\n/**\n * Draws the marquee selection rectangle.\n */\nexport const drawMarquee = (\n ctx: CanvasRenderingContext2D,\n rect: WorldRect,\n scale: number,\n color: string,\n): void => {\n ctx.save()\n // Fill via globalAlpha so any color literal (hex, rgb(), named) tints\n // correctly — no parsing needed.\n ctx.globalAlpha = MARQUEE_FILL_ALPHA\n ctx.fillStyle = color\n ctx.fillRect(rect.x, rect.y, rect.w, rect.h)\n ctx.globalAlpha = 1\n ctx.strokeStyle = color\n ctx.lineWidth = MARQUEE_STROKE_PX / scale\n ctx.setLineDash([4 / scale, 3 / scale])\n ctx.strokeRect(rect.x, rect.y, rect.w, rect.h)\n ctx.restore()\n}\n","/**\n * Paint for `type: 'frame'` nodes. Frames are slide regions that sit\n * visually behind content — see ARCHITECTURE.md §3.7 frames.\n *\n * Visual:\n * - Thin 1.5px-on-screen border in a subdued color\n * - Faint fill so the boundary reads even on textured backgrounds\n * - Name label above the top edge (`node.content`, fallback \"Frame\")\n *\n * Caller is already inside `drawWithNodeTransform` (origin at frame's\n * top-left, rotation applied). No rough.js — frames are organizational\n * chrome, not hand-drawn content.\n */\nimport type { Node } from '../types'\nimport { resolveColor, resolveOpacity } from './shapes/defaults'\nimport type { ThemeResolver } from './shapes/defaults'\n\nconst FRAME_BORDER_PX = 1.5\nconst FRAME_BORDER_COLOR_DEFAULT = '#94a3b8'\nconst FRAME_FILL_DEFAULT = 'rgba(148, 163, 184, 0.06)'\nconst FRAME_LABEL_FONT_PX = 12\nconst FRAME_LABEL_GAP_PX = 6\nconst FRAME_LABEL_COLOR = '#64748b'\n\nexport const paintFrameNode = (\n ctx: CanvasRenderingContext2D,\n node: Node,\n scale: number,\n theme?: ThemeResolver,\n): void => {\n if (node.w <= 0 || node.h <= 0) return\n const opacity = resolveOpacity(node.style, theme)\n const needsScope = opacity !== 1\n if (needsScope) {\n ctx.save()\n ctx.globalAlpha = opacity\n }\n\n // Fill\n const fill =\n node.style?.backgroundColor ??\n (theme ? (theme('frame.background') as string | undefined) : undefined) ??\n FRAME_FILL_DEFAULT\n ctx.fillStyle = fill\n ctx.fillRect(0, 0, node.w, node.h)\n\n // Border\n const stroke = resolveColor(node.style, 'strokeColor', FRAME_BORDER_COLOR_DEFAULT, theme)\n ctx.strokeStyle = stroke\n ctx.lineWidth = FRAME_BORDER_PX / scale\n ctx.setLineDash([])\n ctx.strokeRect(0, 0, node.w, node.h)\n\n // Label above the top edge. Drawn in screen-pixel sizes via\n // 1/scale so it stays constant across zoom levels.\n const labelPx = FRAME_LABEL_FONT_PX / scale\n const gapPx = FRAME_LABEL_GAP_PX / scale\n const label = node.content?.trim() || 'Frame'\n ctx.fillStyle = FRAME_LABEL_COLOR\n ctx.textBaseline = 'bottom'\n ctx.textAlign = 'left'\n ctx.font = `500 ${labelPx}px system-ui, -apple-system, sans-serif`\n ctx.fillText(label, 0, -gapPx)\n\n if (needsScope) ctx.restore()\n}\n","/**\n * Rough-rendering thresholds — see IMPROVEMENTS.md and dim0/rough.\n *\n * Below `ROUGH_MIN_ZOOM` or above `ROUGH_MAX_NODES` we fall back to\n * plain strokes; the wobble is invisible at low zoom and the per-shape\n * cost stacks up past the cap. These are the two cheap gates that\n * protect the frame budget without the consumer having to think about\n * it.\n */\nexport const ROUGH_MIN_ZOOM = 0.4\nexport const ROUGH_MAX_NODES = 800\n\n/**\n * Above this many simultaneously-dragged/resized/rotated nodes, we drop\n * rough rendering for the frame. Dragging a single node (or a small\n * group) keeps the hand-drawn look stable — only large marquee moves\n * fall back to plain. Pan/zoom always disables rough regardless.\n */\nexport const ROUGH_MAX_MOVING_NODES = 5\n\n/**\n * Path-cache hard cap. Keyed entries: per-shape `(type, w, h, stroke,\n * style, roughness, seed)` tuples. LRU eviction.\n */\nexport const ROUGH_PATH_CACHE_MAX = 1000\n\n/**\n * rough.js generator defaults. The combination of `disableMultiStroke`\n * + `preserveVertices` + `bowing: 2` is the one that yields the\n * excalidraw-feeling stroke without the 3-5× cost of multi-stroke.\n */\nexport const ROUGH_DEFAULTS = {\n bowing: 2,\n disableMultiStroke: true,\n preserveVertices: true,\n} as const\n\n/**\n * Print-misregistration offset — the fill is translated by this delta\n * before paint, while the rough stroke stays at the wrapper origin.\n * The resulting gap mimics an old CMYK plate that didn't quite line up.\n * Only applied when a shape opts into rough (`style.roughness > 0`).\n * Matches dim0's `--shape-misregister-x/y` (-3, -2) defaults.\n */\nexport const ROUGH_FILL_MISREGISTER_X = -3\nexport const ROUGH_FILL_MISREGISTER_Y = -2\n","/**\n * Small color utilities shared by the rendering pipeline. Pure\n * functions on hex strings — no canvas or DOM dependencies.\n */\n\nconst TONE_BLEND = 0.2\n\nconst parseHex = (hex: string): [number, number, number] | null => {\n if (!hex.startsWith('#')) return null\n const h = hex.slice(1)\n if (h.length === 3) {\n return [\n Number.parseInt(h[0]! + h[0]!, 16),\n Number.parseInt(h[1]! + h[1]!, 16),\n Number.parseInt(h[2]! + h[2]!, 16),\n ]\n }\n if (h.length === 6 || h.length === 8) {\n return [\n Number.parseInt(h.slice(0, 2), 16),\n Number.parseInt(h.slice(2, 4), 16),\n Number.parseInt(h.slice(4, 6), 16),\n ]\n }\n return null\n}\n\nconst toHexPair = (n: number): string =>\n Math.max(0, Math.min(255, Math.round(n)))\n .toString(16)\n .padStart(2, '0')\n\n/** Linear mix between two hex colors. `t = 0` returns `a`, `t = 1` returns `b`. */\nexport const mixHex = (a: string, b: string, t: number): string => {\n const A = parseHex(a)\n const B = parseHex(b)\n if (!A || !B) return a\n const p = Math.max(0, Math.min(1, t))\n return `#${toHexPair(A[0] * (1 - p) + B[0] * p)}${toHexPair(A[1] * (1 - p) + B[1] * p)}${toHexPair(A[2] * (1 - p) + B[2] * p)}`\n}\n\nconst darkenCache = new Map<string, string>()\n\n/**\n * Returns `hex` shifted 20% toward black. Memoized — colors used by\n * many layered nodes share a cache entry. Returns the input unchanged\n * if it isn't a parseable hex.\n */\nexport const darkenHex = (hex: string): string => {\n const cached = darkenCache.get(hex)\n if (cached !== undefined) return cached\n const result = mixHex(hex, '#000000', TONE_BLEND)\n darkenCache.set(hex, result)\n return result\n}\n","/**\n * Path-building helpers shared by shape draw functions.\n *\n * Each builds a path on the context using the node's local rect (0..w, 0..h);\n * the renderer has already applied translate(node.x, node.y) + rotation,\n * so shapes can think in pure local coordinates.\n */\nexport const buildRectPath = (\n ctx: CanvasRenderingContext2D,\n w: number,\n h: number,\n radius: number,\n): void => {\n ctx.beginPath()\n if (radius <= 0) {\n ctx.rect(0, 0, w, h)\n return\n }\n // Native roundRect — one C++ call per rect. The manual 4×\n // quadraticCurveTo + 4× lineTo build was 28k JS→native crossings\n // per frame at 7k visible rects and dominated paint on lower-end\n // GPUs (Windows 4K + integrated graphics). roundRect clamps the\n // radius to min(w/2, h/2) internally, matching the previous behavior.\n ctx.roundRect(0, 0, w, h, radius)\n}\n\nexport const buildEllipsePath = (ctx: CanvasRenderingContext2D, w: number, h: number): void => {\n const rx = w / 2\n const ry = h / 2\n ctx.beginPath()\n ctx.ellipse(rx, ry, rx, ry, 0, 0, Math.PI * 2)\n}\n\n/**\n * Diamond inscribed in `(0, 0, w, h)`. When `radius` > 0, each 45° edge is\n * trimmed by `radius * √2` and the corner vertex is replaced with a\n * quadratic curve — produces the \"soft diamond\" excalidraw look. At\n * radius 0 the corners are sharp.\n */\nexport const buildDiamondPath = (\n ctx: CanvasRenderingContext2D,\n w: number,\n h: number,\n radius = 0,\n): void => {\n ctx.beginPath()\n if (radius <= 0) {\n ctx.moveTo(w / 2, 0)\n ctx.lineTo(w, h / 2)\n ctx.lineTo(w / 2, h)\n ctx.lineTo(0, h / 2)\n ctx.closePath()\n return\n }\n const cx = w / 2\n const cy = h / 2\n const T = { x: cx, y: 0 }\n const R = { x: w, y: cy }\n const B = { x: cx, y: h }\n const L = { x: 0, y: cy }\n const edgeLen = Math.hypot(R.x - T.x, R.y - T.y)\n const sMax = Math.max(0, edgeLen / 2 - 0.01)\n const s = Math.min(radius * Math.SQRT2, sMax)\n if (s <= 0.0001) {\n ctx.moveTo(T.x, T.y)\n ctx.lineTo(R.x, R.y)\n ctx.lineTo(B.x, B.y)\n ctx.lineTo(L.x, L.y)\n ctx.closePath()\n return\n }\n const along = (a: { x: number; y: number }, b: { x: number; y: number }, d: number) => {\n const dx = b.x - a.x\n const dy = b.y - a.y\n const len = Math.hypot(dx, dy) || 1\n const t = d / len\n return { x: a.x + dx * t, y: a.y + dy * t }\n }\n const TR = along(T, R, s)\n const RT = along(R, T, s)\n const RB = along(R, B, s)\n const BR = along(B, R, s)\n const BL = along(B, L, s)\n const LB = along(L, B, s)\n const LT = along(L, T, s)\n const TL = along(T, L, s)\n ctx.moveTo(TR.x, TR.y)\n ctx.lineTo(RT.x, RT.y)\n ctx.quadraticCurveTo(R.x, R.y, RB.x, RB.y)\n ctx.lineTo(BR.x, BR.y)\n ctx.quadraticCurveTo(B.x, B.y, BL.x, BL.y)\n ctx.lineTo(LB.x, LB.y)\n ctx.quadraticCurveTo(L.x, L.y, LT.x, LT.y)\n ctx.lineTo(TL.x, TL.y)\n ctx.quadraticCurveTo(T.x, T.y, TR.x, TR.y)\n ctx.closePath()\n}\n\n/**\n * Compute thought-cloud geometry — used by both the canvas builder and\n * the SVG-path builder so the visible silhouette stays identical\n * between plain and rough rendering.\n */\nexport const thoughtCloudGeometry = (w: number, h: number) => {\n const domeW = Math.min(w * 0.4, h * 1.2)\n const domeH = Math.min(h * 0.45, domeW)\n const domeAnchorX = w * 0.3\n const domeX = Math.max(0, Math.min(w - domeW, domeAnchorX - domeW / 2))\n return {\n domeX,\n domeW,\n domeH,\n cx: domeX + domeW / 2,\n cy: domeH / 2,\n rx: domeW / 2,\n ry: domeH / 2,\n bodyY: domeH * 0.55,\n }\n}\n\n/**\n * Thought-cloud as a single union path — rect body with a dome that\n * merges seamlessly into the top edge. No internal border between\n * dome and rect; the silhouette reads as one continuous outline.\n */\nexport const buildThoughtCloudPath = (\n ctx: CanvasRenderingContext2D,\n w: number,\n h: number,\n radius: number,\n): void => {\n const g = thoughtCloudGeometry(w, h)\n const bodyH = h - g.bodyY\n const r = Math.max(0, Math.min(radius, bodyH / 2, w / 2))\n\n // Find where the dome's lower arc crosses the rect's top edge.\n const t = g.ry > 0 ? (g.bodyY - g.cy) / g.ry : 0\n const inRange = Math.abs(t) < 1\n let xL = g.domeX\n let xR = g.domeX + g.domeW\n if (inRange) {\n const xOffset = g.rx * Math.sqrt(1 - t * t)\n xL = g.cx - xOffset\n xR = g.cx + xOffset\n }\n // Clamp so the dome ends don't cross the rect's rounded corners.\n xL = Math.max(r, xL)\n xR = Math.min(w - r, xR)\n\n ctx.beginPath()\n ctx.moveTo(r, g.bodyY)\n ctx.lineTo(xL, g.bodyY)\n\n // Arc OVER the dome. Use ellipse parameter (not raw angle-from-center)\n // so non-circular domes start/end exactly on the rect top edge.\n const startAngle = Math.atan2((g.bodyY - g.cy) / g.ry, (xL - g.cx) / g.rx)\n let endAngle = Math.atan2((g.bodyY - g.cy) / g.ry, (xR - g.cx) / g.rx)\n // Canvas `anticlockwise=false` traces in the direction of increasing\n // angle (visually clockwise through the top of the dome). Wrap so the\n // arc takes the upper route, not the bottom.\n if (endAngle <= startAngle) endAngle += 2 * Math.PI\n ctx.ellipse(g.cx, g.cy, g.rx, g.ry, 0, startAngle, endAngle, false)\n\n ctx.lineTo(w - r, g.bodyY)\n ctx.quadraticCurveTo(w, g.bodyY, w, g.bodyY + r)\n ctx.lineTo(w, h - r)\n ctx.quadraticCurveTo(w, h, w - r, h)\n ctx.lineTo(r, h)\n ctx.quadraticCurveTo(0, h, 0, h - r)\n ctx.lineTo(0, g.bodyY + r)\n ctx.quadraticCurveTo(0, g.bodyY, r, g.bodyY)\n ctx.closePath()\n}\n\n/**\n * Tag shape — pointed notch on the left flowing into a rounded body.\n * `notch` is the horizontal distance from the tip to the body edge.\n * Ported from dim0/components/rough/paths.ts.\n */\nexport const buildTagPath = (\n ctx: CanvasRenderingContext2D,\n w: number,\n h: number,\n radius = 8,\n): void => {\n const notch = Math.min(h * 0.5, w * 0.3)\n const tipRadius = 6\n const tipX = 0\n const tipY = h / 2\n\n const bodyLeft = Math.max(0, Math.min(notch, w))\n const right = w\n const bottom = h\n const rBody = Math.min(radius, h / 2, (right - bodyLeft) / 2)\n const rJoin = Math.min(radius, h * 0.45, bodyLeft * 0.8)\n\n ctx.beginPath()\n if (bodyLeft <= 0.001) {\n const r = Math.min(radius, h / 2, w / 2)\n ctx.moveTo(r, 0)\n ctx.lineTo(w - r, 0)\n ctx.quadraticCurveTo(w, 0, w, r)\n ctx.lineTo(w, h - r)\n ctx.quadraticCurveTo(w, h, w - r, h)\n ctx.lineTo(r, h)\n ctx.quadraticCurveTo(0, h, 0, h - r)\n ctx.lineTo(0, r)\n ctx.quadraticCurveTo(0, 0, r, 0)\n ctx.closePath()\n return\n }\n\n const pTop = { x: bodyLeft, y: rJoin }\n const pBot = { x: bodyLeft, y: bottom - rJoin }\n const dirX = tipX - bodyLeft\n const dirYTop = tipY - rJoin\n const dirYBot = tipY - (bottom - rJoin)\n const lenTop = Math.hypot(dirX, dirYTop) || 1\n const lenBot = Math.hypot(dirX, dirYBot) || 1\n const maxTipRound = Math.min(lenTop, lenBot) * 0.49\n const t = Math.max(0, Math.min(tipRadius, maxTipRound))\n const tipEnter = { x: tipX - (dirX / lenBot) * t, y: tipY - (dirYBot / lenBot) * t }\n const tipExit = { x: tipX - (dirX / lenTop) * t, y: tipY - (dirYTop / lenTop) * t }\n const k = rJoin * 0.65\n const topStart = { x: bodyLeft + rBody, y: 0 }\n const botEnd = { x: bodyLeft + rBody, y: bottom }\n\n ctx.moveTo(topStart.x, topStart.y)\n ctx.lineTo(right - rBody, 0)\n ctx.quadraticCurveTo(right, 0, right, rBody)\n ctx.lineTo(right, bottom - rBody)\n ctx.quadraticCurveTo(right, bottom, right - rBody, bottom)\n ctx.lineTo(botEnd.x, botEnd.y)\n ctx.bezierCurveTo(\n botEnd.x - k,\n bottom,\n pBot.x - (dirX / lenBot) * k,\n pBot.y - (dirYBot / lenBot) * k,\n pBot.x,\n pBot.y,\n )\n ctx.lineTo(t > 0 ? tipEnter.x : tipX, t > 0 ? tipEnter.y : tipY)\n if (t > 0) ctx.quadraticCurveTo(tipX, tipY, tipExit.x, tipExit.y)\n ctx.lineTo(pTop.x, pTop.y)\n ctx.bezierCurveTo(\n pTop.x - (dirX / lenTop) * k,\n pTop.y - (dirYTop / lenTop) * k,\n topStart.x - k,\n 0,\n topStart.x,\n 0,\n )\n ctx.closePath()\n}\n","/**\n * Generic primitive paint pass.\n *\n * The renderer applies camera + node transforms (translate to node center,\n * rotate, translate back to top-left) before calling this. The drawer\n * just builds a local-space path and fills/strokes it with resolved style.\n *\n * `scale` is the current camera × DPR factor (world-units → device-pixels).\n * Callers compute it once per frame and pass it in so each drawShape call\n * doesn't allocate a DOMMatrix via ctx.getTransform().\n */\nimport type { Node, Style } from '../../types'\nimport { darkenHex } from '../color'\nimport {\n DEFAULT_STYLE,\n type ThemeResolver,\n dashPatternFor,\n isFullyTransparent,\n resolveColor,\n resolveOpacity,\n resolveStrokeWidth,\n} from './defaults'\nimport {\n buildDiamondPath,\n buildEllipsePath,\n buildRectPath,\n buildTagPath,\n buildThoughtCloudPath,\n} from './path-helpers'\n\n/**\n * Atomic single-path primitives. Composites paint multiple of these.\n * Thought-cloud is atomic — its union geometry is one continuous path\n * so the rough wobble unifies the silhouette.\n */\nexport type AtomicPrimitive = 'rect' | 'ellipse' | 'diamond' | 'tag' | 'thought-cloud'\n\n/**\n * Composite primitives built from multiple atomic sub-shapes. Capsule\n * is intentionally composite — the visible seam between the accent\n * circle and the rect body reads as two stacked hand-drawn shapes\n * (medicine-pill aesthetic), which we want to keep.\n */\ntype CompositePrimitive =\n | 'capsule'\n | 'layered-rect'\n | 'layered-ellipse'\n | 'layered-diamond'\n | 'soft-diamond'\n\nexport type PrimitiveType = AtomicPrimitive | CompositePrimitive\n\nconst ATOMIC: ReadonlySet<string> = new Set(['rect', 'ellipse', 'diamond', 'tag', 'thought-cloud'])\nconst COMPOSITE: ReadonlySet<string> = new Set([\n 'capsule',\n 'layered-rect',\n 'layered-ellipse',\n 'layered-diamond',\n 'soft-diamond',\n])\n\n/** Whether `type` is a composite primitive (paints multiple atomic sub-shapes). */\nexport const isCompositePrimitive = (type: string): boolean => COMPOSITE.has(type)\n\n/** Returns true if `node.type` is one of the built-ins drawShape can render. */\nexport const isDrawablePrimitive = (type: string): type is PrimitiveType =>\n ATOMIC.has(type) || COMPOSITE.has(type)\n\n/**\n * Below this threshold the rounded-rect path is visually indistinguishable\n * from a plain rect — at sub-pixel corner radius the difference disappears.\n */\nconst PLAIN_RECT_CORNER_THRESHOLD_PX = 1.5\n\n/** Offset for layered composites — back layer shifted down-right by this amount. */\nconst LAYERED_OFFSET = 12\n\nexport const drawShape = (\n ctx: CanvasRenderingContext2D,\n node: Node,\n scale: number,\n theme?: ThemeResolver,\n opts?: { skipStroke?: boolean },\n): void => {\n if (!isDrawablePrimitive(node.type)) return\n if (node.hidden) return\n if (node.w <= 0 || node.h <= 0) return\n\n if (COMPOSITE.has(node.type)) {\n drawComposite(ctx, node, scale, theme, opts)\n return\n }\n drawAtomic(ctx, node.type as AtomicPrimitive, node.w, node.h, node.style, scale, theme, opts)\n}\n\n/**\n * Paints a single atomic primitive at (0, 0, w, h) using the provided\n * `style`. Composites call this for each sub-shape with a translated ctx.\n */\nexport const drawAtomic = (\n ctx: CanvasRenderingContext2D,\n type: AtomicPrimitive,\n w: number,\n h: number,\n style: Style | undefined,\n scale: number,\n theme: ThemeResolver | undefined,\n opts?: { skipStroke?: boolean },\n): void => {\n if (w <= 0 || h <= 0) return\n const strokeWidth = resolveStrokeWidth(style, theme)\n const opacity = resolveOpacity(style, theme)\n const fill = resolveColor(style, 'backgroundColor', DEFAULT_STYLE.backgroundColor, theme)\n const stroke = resolveColor(style, 'strokeColor', DEFAULT_STYLE.strokeColor, theme)\n const fillVisible = !isFullyTransparent(fill)\n const strokeVisible = strokeWidth > 0 && !isFullyTransparent(stroke)\n if (!fillVisible && !strokeVisible) return\n\n const cornerRadius = (style?.roundness ?? DEFAULT_STYLE.roundness) * 4\n\n switch (type) {\n case 'rect': {\n if (cornerRadius * scale < PLAIN_RECT_CORNER_THRESHOLD_PX) {\n ctx.beginPath()\n ctx.rect(0, 0, w, h)\n } else {\n buildRectPath(ctx, w, h, cornerRadius)\n }\n break\n }\n case 'ellipse':\n buildEllipsePath(ctx, w, h)\n break\n case 'diamond':\n buildDiamondPath(ctx, w, h, cornerRadius)\n break\n case 'tag':\n buildTagPath(ctx, w, h, cornerRadius)\n break\n case 'thought-cloud':\n buildThoughtCloudPath(ctx, w, h, cornerRadius)\n break\n }\n\n const needsScope = opacity !== 1\n if (needsScope) {\n ctx.save()\n ctx.globalAlpha = opacity\n }\n if (fillVisible) {\n ctx.fillStyle = fill\n ctx.fill()\n }\n if (strokeVisible && !opts?.skipStroke) {\n ctx.strokeStyle = stroke\n // Clamp lineWidth so the on-screen stroke is at least 1 device\n // pixel. At low zoom this keeps the shape silhouette visible\n // (the alternative — skipping the stroke — made big nodes look\n // like featureless colored blobs at fit-all). The scene cache\n // makes this affordable: pan reuses the rendered border, only\n // zoom/edit pays the per-frame cost.\n ctx.lineWidth = Math.max(strokeWidth, 1 / scale)\n // Dash pattern stays keyed to the natural strokeWidth — at low\n // zoom sub-pixel dashes collapse visually into a near-solid line,\n // matching what the user would perceive anyway.\n const dash = dashPatternFor(style?.strokeStyle, strokeWidth)\n ctx.setLineDash(dash)\n ctx.stroke()\n // Reset to solid so subsequent strokers that don't manage their\n // own dash (overlay drawers — selection box, resize/rotate\n // handles, edge endpoint/midpoint handles) don't inherit this\n // node's dash via ctx state. needsScope only fires when opacity\n // !== 1, so we can't rely on the save/restore below.\n if (dash.length > 0) ctx.setLineDash([])\n }\n if (needsScope) ctx.restore()\n}\n\n/**\n * Layout each composite type as a list of `{ x, y, w, h, atomic }` sub-shapes\n * in the node's local frame. Paint order is back-to-front.\n *\n * For `layered-*`, the back layer's style is darkened to set it apart from\n * the front; the front uses the node's resolved style as-is.\n */\nconst drawComposite = (\n ctx: CanvasRenderingContext2D,\n node: Node,\n scale: number,\n theme: ThemeResolver | undefined,\n opts?: { skipStroke?: boolean },\n): void => {\n const subs = compositeLayout(node)\n for (const s of subs) {\n ctx.save()\n ctx.translate(s.x, s.y)\n drawAtomic(ctx, s.atomic, s.w, s.h, s.style ?? node.style, scale, theme, opts)\n ctx.restore()\n }\n}\n\ntype SubShape = {\n atomic: AtomicPrimitive\n x: number\n y: number\n w: number\n h: number\n style?: Style\n}\n\n/** Builds the back-to-front sub-shape list for a composite node. Exported for rough. */\nexport const compositeLayout = (node: Node): SubShape[] => {\n const { w, h } = node\n switch (node.type) {\n case 'capsule': {\n // Medicine-pill: small accent circle on the left + rect body.\n // Kept composite (vs. a single union path) so the visible seam\n // between circle and rect reads as two stacked hand-drawn shapes.\n const circ = Math.min(h * 0.55, w * 0.28, 56)\n const overlap = circ * 0.15\n const rectX = circ - overlap\n const rectW = Math.max(0, w - rectX)\n const circY = (h - circ) / 2\n return [\n { atomic: 'ellipse', x: 0, y: circY, w: circ, h: circ },\n { atomic: 'rect', x: rectX, y: 0, w: rectW, h },\n ]\n }\n case 'layered-rect':\n case 'layered-ellipse':\n case 'layered-diamond': {\n const atomic: AtomicPrimitive =\n node.type === 'layered-rect'\n ? 'rect'\n : node.type === 'layered-ellipse'\n ? 'ellipse'\n : 'diamond'\n // Match dim0: front fills the bbox exactly, back is a same-sized\n // copy translated past the bbox by `LAYERED_OFFSET`. The back\n // reads as a \"shadow\" peeking out bottom-right rather than as\n // a distinct second shape. Clamped on small nodes so the offset\n // stays visually proportional.\n const off = Math.min(LAYERED_OFFSET, w * 0.15, h * 0.15)\n const back: SubShape = {\n atomic,\n x: off,\n y: off,\n w,\n h,\n style: darkenedStyle(node.style),\n }\n const front: SubShape = { atomic, x: 0, y: 0, w, h }\n return [back, front]\n }\n case 'soft-diamond': {\n // Concentric scale-layered diamond — matches dim0's SoftDiamond.\n // Back is 108% of the bbox centered (slight overshoot reads as a\n // tinted outer outline); front is 96% centered (slight inset).\n // No offset like `layered-diamond` — both centered on the same\n // point. Reads as a soft-outlined / double-stroked diamond.\n const backScale = 1.08\n const frontScale = 0.96\n const bw = w * backScale\n const bh = h * backScale\n const fw = w * frontScale\n const fh = h * frontScale\n const back: SubShape = {\n atomic: 'diamond',\n x: (w - bw) / 2,\n y: (h - bh) / 2,\n w: bw,\n h: bh,\n style: darkenedStyle(node.style),\n }\n const front: SubShape = {\n atomic: 'diamond',\n x: (w - fw) / 2,\n y: (h - fh) / 2,\n w: fw,\n h: fh,\n }\n return [back, front]\n }\n }\n return []\n}\n\n/**\n * Returns a clone of `style` with both fill and stroke shifted 20%\n * toward black — the \"back layer\" tone used by layered composites.\n *\n * Memoized via WeakMap on the parent style reference. The store\n * replaces (not mutates) `node.style` on updates, so refs are stable\n * across paints for nodes whose style hasn't changed — meaning a 1k\n * layered scene that's idle hits the cache 100% of the time instead\n * of allocating a fresh Style object per node per frame.\n */\nconst DARKENED_NO_STYLE: Style = {}\nconst darkenedStyleCache = new WeakMap<Style, Style>()\nconst darkenedStyle = (style: Style | undefined): Style => {\n if (!style) return DARKENED_NO_STYLE\n const hit = darkenedStyleCache.get(style)\n if (hit) return hit\n const fill = style.backgroundColor\n const stroke = style.strokeColor\n const next: Style = {\n ...style,\n ...(fill ? { backgroundColor: darkenHex(fill) } : {}),\n ...(stroke ? { strokeColor: darkenHex(stroke) } : {}),\n }\n darkenedStyleCache.set(style, next)\n return next\n}\n","/**\n * Lazy-loader for `roughjs` — avoids inlining its ~30KB gzip into core\n * for users who never set `roughness > 0`.\n *\n * First caller triggers `import('roughjs/bin/canvas')`. Until the\n * promise resolves, `getRoughCanvas` returns `null` and the renderer\n * falls back to plain strokes. Once loaded, subsequent calls return\n * the cached factory synchronously.\n */\ntype RoughCanvasCtor = new (canvas: HTMLCanvasElement) => RoughCanvasLike\n\nexport type RoughCanvasLike = {\n generator: {\n path(d: string, options?: object): RoughDrawableLike\n linearPath(points: [number, number][], options?: object): RoughDrawableLike\n ellipse(x: number, y: number, w: number, h: number, options?: object): RoughDrawableLike\n }\n draw(drawable: RoughDrawableLike): void\n}\n\nexport type RoughDrawableLike = unknown\n\nlet cachedCtor: RoughCanvasCtor | null = null\nlet loadPromise: Promise<RoughCanvasCtor | null> | null = null\nconst readyCallbacks = new Set<() => void>()\n\n/**\n * Returns the `RoughCanvas` constructor if ready. Triggers the lazy\n * import on first call. Returns `null` until the module resolves;\n * callers should fall back to plain stroke that frame and call\n * `onRoughReady(cb)` to repaint when rough.js becomes available.\n */\nexport const getRoughCanvasCtor = (): RoughCanvasCtor | null => {\n if (cachedCtor) return cachedCtor\n if (!loadPromise) {\n loadPromise = import('roughjs/bin/canvas')\n .then(mod => {\n cachedCtor = mod.RoughCanvas as unknown as RoughCanvasCtor\n for (const cb of readyCallbacks) cb()\n readyCallbacks.clear()\n return cachedCtor\n })\n .catch(err => {\n console.warn('[rough] failed to load roughjs:', err)\n return null\n })\n }\n return null\n}\n\n/**\n * Registers a callback that fires once when rough.js becomes\n * available. No-op when rough is already loaded — caller should check\n * `getRoughCanvasCtor() !== null` first. Used by the renderer to\n * trigger a repaint after the first opt-in to `roughness > 0`.\n */\nexport const onRoughReady = (cb: () => void): void => {\n if (cachedCtor) return\n readyCallbacks.add(cb)\n}\n\n/** Reset state — tests only. */\nexport const __resetRoughLoader = (): void => {\n cachedCtor = null\n loadPromise = null\n readyCallbacks.clear()\n}\n","/**\n * SVG-path builders for our shape primitives. Designed to feed\n * `rough.generator.path(d, ...)`.\n *\n * Rounded rect / diamond follow the excalidraw style — quadratic\n * curves at the corners that, combined with rough.js jitter, look\n * organically imperfect.\n */\n\nexport const rectPath = (x: number, y: number, w: number, h: number): string => {\n return `M${x} ${y} L${x + w} ${y} L${x + w} ${y + h} L${x} ${y + h} Z`\n}\n\n/**\n * Excalidraw-style rounded rect — corners use quadratic curves rather\n * than perfect arcs. Slight asymmetry under rough.js jitter looks\n * hand-drawn instead of CAD-clean.\n */\nexport const excalidrawRoundedRectPath = (\n x: number,\n y: number,\n w: number,\n h: number,\n radius: number,\n): string => {\n const r = Math.max(0, Math.min(radius, w / 2, h / 2))\n if (r === 0) return rectPath(x, y, w, h)\n const x2 = x + w\n const y2 = y + h\n return [\n `M${x + r} ${y}`,\n `L${x2 - r} ${y}`,\n `Q${x2} ${y}, ${x2} ${y + r}`,\n `L${x2} ${y2 - r}`,\n `Q${x2} ${y2}, ${x2 - r} ${y2}`,\n `L${x + r} ${y2}`,\n `Q${x} ${y2}, ${x} ${y2 - r}`,\n `L${x} ${y + r}`,\n `Q${x} ${y}, ${x + r} ${y}`,\n 'Z',\n ].join(' ')\n}\n\n/**\n * Diamond inscribed in `(x, y, w, h)`. At `radius = 0` the corners are\n * sharp; positive radius produces the soft-diamond excalidraw look —\n * each edge trimmed by r·√2, corners replaced with quadratic curves.\n */\nexport const diamondPath = (x: number, y: number, w: number, h: number, radius = 0): string => {\n const cx = x + w / 2\n const cy = y + h / 2\n if (radius <= 0) {\n return `M${cx} ${y} L${x + w} ${cy} L${cx} ${y + h} L${x} ${cy} Z`\n }\n const T = { x: cx, y }\n const R = { x: x + w, y: cy }\n const B = { x: cx, y: y + h }\n const L = { x, y: cy }\n const edgeLen = Math.hypot(R.x - T.x, R.y - T.y)\n const sMax = Math.max(0, edgeLen / 2 - 0.01)\n const s = Math.min(radius * Math.SQRT2, sMax)\n if (s <= 0.0001) {\n return `M${T.x} ${T.y} L${R.x} ${R.y} L${B.x} ${B.y} L${L.x} ${L.y} Z`\n }\n const along = (a: { x: number; y: number }, b: { x: number; y: number }, d: number) => {\n const dx = b.x - a.x\n const dy = b.y - a.y\n const len = Math.hypot(dx, dy) || 1\n const t = d / len\n return { x: a.x + dx * t, y: a.y + dy * t }\n }\n const TR = along(T, R, s)\n const RT = along(R, T, s)\n const RB = along(R, B, s)\n const BR = along(B, R, s)\n const BL = along(B, L, s)\n const LB = along(L, B, s)\n const LT = along(L, T, s)\n const TL = along(T, L, s)\n return [\n `M${TR.x} ${TR.y}`,\n `L${RT.x} ${RT.y}`,\n `Q${R.x} ${R.y}, ${RB.x} ${RB.y}`,\n `L${BR.x} ${BR.y}`,\n `Q${B.x} ${B.y}, ${BL.x} ${BL.y}`,\n `L${LB.x} ${LB.y}`,\n `Q${L.x} ${L.y}, ${LT.x} ${LT.y}`,\n `L${TL.x} ${TL.y}`,\n `Q${T.x} ${T.y}, ${TR.x} ${TR.y}`,\n 'Z',\n ].join(' ')\n}\n\n/**\n * Ellipse as an SVG path. rough.js has its own `ellipse` primitive\n * but using a single path keeps the rough cache key compact.\n */\nexport const ellipsePath = (x: number, y: number, w: number, h: number): string => {\n const cx = x + w / 2\n const rx = w / 2\n const ry = h / 2\n return [\n `M${cx} ${y}`,\n `A${rx} ${ry} 0 1 0 ${cx} ${y + h}`,\n `A${rx} ${ry} 0 1 0 ${cx} ${y}`,\n 'Z',\n ].join(' ')\n}\n\n/**\n * Thought-cloud — rect body with a dome that merges seamlessly into\n * the top edge. Single continuous outline, no internal seam between\n * dome and rect.\n */\nexport const thoughtCloudPath = (\n x: number,\n y: number,\n w: number,\n h: number,\n radius: number,\n): string => {\n const domeW = Math.min(w * 0.4, h * 1.2)\n const domeH = Math.min(h * 0.45, domeW)\n const domeAnchorX = w * 0.3\n const domeX = Math.max(0, Math.min(w - domeW, domeAnchorX - domeW / 2))\n const cx = x + domeX + domeW / 2\n const cy = y + domeH / 2\n const rx = domeW / 2\n const ry = domeH / 2\n const bodyY = y + domeH * 0.55\n const bodyH = y + h - bodyY\n const r = Math.max(0, Math.min(radius, bodyH / 2, w / 2))\n\n const t = ry > 0 ? (bodyY - cy) / ry : 0\n let xL = x + domeX\n let xR = x + domeX + domeW\n if (Math.abs(t) < 1) {\n const xOffset = rx * Math.sqrt(1 - t * t)\n xL = cx - xOffset\n xR = cx + xOffset\n }\n xL = Math.max(x + r, xL)\n xR = Math.min(x + w - r, xR)\n\n // Large-arc=1 (longer arc, through top), sweep=1 (clockwise / positive\n // angle direction in SVG, i.e. up over the dome).\n return [\n `M${x + r} ${bodyY}`,\n `L${xL} ${bodyY}`,\n `A${rx} ${ry} 0 1 1 ${xR} ${bodyY}`,\n `L${x + w - r} ${bodyY}`,\n `Q${x + w} ${bodyY}, ${x + w} ${bodyY + r}`,\n `L${x + w} ${y + h - r}`,\n `Q${x + w} ${y + h}, ${x + w - r} ${y + h}`,\n `L${x + r} ${y + h}`,\n `Q${x} ${y + h}, ${x} ${y + h - r}`,\n `L${x} ${bodyY + r}`,\n `Q${x} ${bodyY}, ${x + r} ${bodyY}`,\n 'Z',\n ].join(' ')\n}\n\n/**\n * Tag — pointed notch on the left flowing into a rounded body.\n * Ported from dim0. `radius` controls both the body corner radius and\n * the join smoothness.\n */\nexport const tagPath = (x: number, y: number, w: number, h: number, radius = 8): string => {\n const notch = Math.min(h * 0.5, w * 0.3)\n const tipRadius = 6\n const tipX = x\n const tipY = y + h / 2\n const bodyLeft = x + Math.max(0, Math.min(notch, w))\n const right = x + w\n const bottom = y + h\n const rBody = Math.min(radius, h / 2, (right - bodyLeft) / 2)\n const rJoin = Math.min(radius, h * 0.45, (bodyLeft - x) * 0.8)\n\n if (bodyLeft - x <= 0.001) {\n return excalidrawRoundedRectPath(x, y, w, h, Math.min(radius, h / 2, w / 2))\n }\n\n const pTop = { x: bodyLeft, y: y + rJoin }\n const pBot = { x: bodyLeft, y: bottom - rJoin }\n const dirX = tipX - bodyLeft\n const dirYTop = tipY - pTop.y\n const dirYBot = tipY - pBot.y\n const lenTop = Math.hypot(dirX, dirYTop) || 1\n const lenBot = Math.hypot(dirX, dirYBot) || 1\n const maxTipRound = Math.min(lenTop, lenBot) * 0.49\n const t = Math.max(0, Math.min(tipRadius, maxTipRound))\n const tipEnter = { x: tipX - (dirX / lenBot) * t, y: tipY - (dirYBot / lenBot) * t }\n const tipExit = { x: tipX - (dirX / lenTop) * t, y: tipY - (dirYTop / lenTop) * t }\n const k = rJoin * 0.65\n const topStart = { x: bodyLeft + rBody, y }\n const botEnd = { x: bodyLeft + rBody, y: bottom }\n\n const parts: string[] = [\n `M${topStart.x} ${topStart.y}`,\n `L${right - rBody} ${y}`,\n `Q${right} ${y}, ${right} ${y + rBody}`,\n `L${right} ${bottom - rBody}`,\n `Q${right} ${bottom}, ${right - rBody} ${bottom}`,\n `L${botEnd.x} ${botEnd.y}`,\n `C${botEnd.x - k} ${bottom}, ${pBot.x - (dirX / lenBot) * k} ${pBot.y - (dirYBot / lenBot) * k}, ${pBot.x} ${pBot.y}`,\n `L${t > 0 ? tipEnter.x : tipX} ${t > 0 ? tipEnter.y : tipY}`,\n ]\n if (t > 0) parts.push(`Q${tipX} ${tipY}, ${tipExit.x} ${tipExit.y}`)\n parts.push(\n `L${pTop.x} ${pTop.y}`,\n `C${pTop.x - (dirX / lenTop) * k} ${pTop.y - (dirYTop / lenTop) * k}, ${topStart.x - k} ${y}, ${topStart.x} ${topStart.y}`,\n 'Z',\n )\n return parts.join(' ')\n}\n","/**\n * Derive a visible border color for rough shapes whose `strokeColor` is\n * transparent — without this, the rough.js pass paints nothing and the\n * misregistration effect (offset fill vs. stroke) has nothing to show.\n *\n * Mirrors dim0's `resolveEdgeRender` + tonal-shift mix:\n * light mode: `mixHex(fill, '#fff', 0.2)` → lighter than fill\n * dark mode: `mixHex(fill, '#000', 0.2)` → darker than fill\n *\n * Result is memoized per `(fill, isDark)` pair so the rough drawable\n * cache key stays stable across renders.\n */\nimport { mixHex } from '../color'\nimport { isFullyTransparent } from '../shapes/defaults'\n\nconst TONE_BLEND = 0.2\nconst cache = new Map<string, string>()\n\n/**\n * If `stroke` is transparent and `fill` is a visible color, returns a\n * tonally-shifted variant of `fill` suitable for drawing a soft border.\n * Otherwise returns `stroke` unchanged. Memoized.\n */\nexport const deriveRoughStrokeColor = (stroke: string, fill: string, isDark: boolean): string => {\n if (!isFullyTransparent(stroke)) return stroke\n if (isFullyTransparent(fill)) return stroke\n const key = `${fill}|${isDark ? 'd' : 'l'}`\n const hit = cache.get(key)\n if (hit) return hit\n const next = mixHex(fill, isDark ? '#000000' : '#ffffff', TONE_BLEND)\n cache.set(key, next)\n return next\n}\n\n/** Reset state — tests only. */\nexport const __resetToneDownCache = (): void => {\n cache.clear()\n}\n","/**\n * Per-shape rough stroke pass.\n *\n * Caller (renderer) decides whether to call this (via the gate). Fill\n * has already been painted by the regular `drawShape` pipeline — we\n * paint only the wobbly outline on top.\n *\n * Returns false when the rough.js module hasn't loaded yet; caller\n * should fall back to plain stroke.\n *\n * For composite nodes (capsule, thought-cloud, layered-*), the rough\n * pass walks `compositeLayout` and paints each sub-shape's outline as\n * its own rough drawable. Each sub-shape gets its own cache entry so\n * scrubbing one node attribute only invalidates the affected subset.\n */\nimport type { Edge, Node, Style, Vec2 } from '../../types'\nimport {\n DEFAULT_STYLE,\n type ThemeResolver,\n dashPatternFor,\n isFullyTransparent,\n resolveColor,\n resolveStrokeWidth,\n} from '../shapes/defaults'\nimport { compositeLayout, drawAtomic } from '../shapes/draw-shape'\nimport { getOrBuildDrawable, seedFromId } from './cache'\nimport { ROUGH_DEFAULTS, ROUGH_FILL_MISREGISTER_X, ROUGH_FILL_MISREGISTER_Y } from './constants'\nimport { type RoughCanvasLike, getRoughCanvasCtor } from './loader'\nimport {\n diamondPath,\n ellipsePath,\n excalidrawRoundedRectPath,\n rectPath,\n tagPath,\n thoughtCloudPath,\n} from './paths'\nimport { deriveRoughStrokeColor } from './tone-down'\n\ntype AtomicRoughPrimitive = 'rect' | 'ellipse' | 'diamond' | 'tag' | 'thought-cloud'\n\nconst apparentDetail = (\n maxSide: number,\n zoom: number,\n): { curveStepCount: number; maxRandomnessOffset: number } => {\n const apparent = maxSide * Math.min(1, zoom)\n if (apparent >= 800) return { curveStepCount: 3, maxRandomnessOffset: 0.9 }\n if (apparent >= 400) return { curveStepCount: 4, maxRandomnessOffset: 1.1 }\n return { curveStepCount: 5, maxRandomnessOffset: 1.3 }\n}\n\n/**\n * Paints the rough stroke for an ATOMIC primitive at the node's local\n * origin. Caller (renderer) decides whether to call this. Returns\n * false if rough.js isn't loaded yet. Composites use\n * `drawCompositeRough` instead — they need interleaved fill+stroke\n * painting per sub-shape, not the two-pass model used for atomics.\n */\nexport const drawRoughShape = (\n ctx: CanvasRenderingContext2D,\n node: Node,\n scale: number,\n theme?: ThemeResolver,\n): boolean => {\n const Ctor = getRoughCanvasCtor()\n if (!Ctor) return false\n const rc = ensureRoughCanvas(ctx, Ctor)\n if (!rc) return false\n\n const seed = node.id ? (seedFromId(node.id) % 2147483646) + 1 : 1337\n paintAtomicRough(\n rc,\n ctx,\n node.type as AtomicRoughPrimitive,\n node.w,\n node.h,\n node.style,\n scale,\n theme,\n seed,\n )\n return true\n}\n\n/**\n * Composite-aware rough paint. Walks the composite layout and for\n * each sub-shape paints fill (misregistered) + rough stroke before\n * moving to the next sub. This interleaving is critical: if all fills\n * paint first and all strokes after, the back layer's stroke ends up\n * sitting on top of the front layer's fill in the overlap region.\n *\n * Returns false if rough.js isn't loaded yet (caller should fall back\n * to the plain `drawShape` path).\n */\nexport const drawCompositeRough = (\n ctx: CanvasRenderingContext2D,\n node: Node,\n scale: number,\n theme?: ThemeResolver,\n): boolean => {\n const Ctor = getRoughCanvasCtor()\n if (!Ctor) return false\n const rc = ensureRoughCanvas(ctx, Ctor)\n if (!rc) return false\n\n const subs = compositeLayout(node)\n const baseSeed = node.id ? (seedFromId(node.id) % 2147483646) + 1 : 1337\n for (let i = 0; i < subs.length; i++) {\n const s = subs[i]!\n const subStyle = s.style ?? node.style\n ctx.save()\n ctx.translate(s.x, s.y)\n // Misregister this sub's fill — same printing-press offset effect\n // as atomic shapes, applied per sub so the back's fill and stroke\n // misalign just like the front's do.\n ctx.translate(ROUGH_FILL_MISREGISTER_X, ROUGH_FILL_MISREGISTER_Y)\n drawAtomic(ctx, s.atomic, s.w, s.h, subStyle, scale, theme, { skipStroke: true })\n ctx.translate(-ROUGH_FILL_MISREGISTER_X, -ROUGH_FILL_MISREGISTER_Y)\n // Rough stroke for this sub. Painted before the next sub's fill so\n // the front layer's fill correctly covers the back's stroke in\n // the overlap region.\n paintAtomicRough(\n rc,\n ctx,\n s.atomic as AtomicRoughPrimitive,\n s.w,\n s.h,\n subStyle,\n scale,\n theme,\n ((baseSeed + i * 7919) % 2147483646) + 1,\n )\n ctx.restore()\n }\n return true\n}\n\n/** Paints a single atomic primitive at (0, 0, w, h) using the given style. */\nconst paintAtomicRough = (\n rc: RoughCanvasLike,\n ctx: CanvasRenderingContext2D,\n type: AtomicRoughPrimitive,\n w: number,\n h: number,\n style: Style | undefined,\n scale: number,\n theme: ThemeResolver | undefined,\n seed: number,\n): void => {\n if (w <= 0 || h <= 0) return\n const rawStroke = resolveColor(style, 'strokeColor', '#1f2937', theme)\n const isDark = theme?.('mode') === 'dark'\n const fill = resolveColor(style, 'backgroundColor', DEFAULT_STYLE.backgroundColor, theme)\n const strokeColor = deriveRoughStrokeColor(rawStroke, fill, isDark)\n const rawStrokeWidth = resolveStrokeWidth(style, theme)\n if (rawStrokeWidth <= 0) return\n\n const roughness = style?.roughness ?? 0\n if (roughness <= 0) return\n\n // When the user picked \"no border\" (transparent stroke), rough still\n // paints a soft fill-derived outline for the misregistration effect\n // — but the user's strokeStyle (dashed/dotted) and strokeWidth were\n // *border* choices they didn't make, so don't apply them to the soft\n // outline. Force the system baseline so every no-border node renders\n // a uniform subtle outline regardless of the panel's current values.\n // Nodes with a real strokeColor keep the user's chosen style + width.\n const isNoBorderIntent = isFullyTransparent(rawStroke)\n const effectiveStrokeStyle = isNoBorderIntent ? 'solid' : (style?.strokeStyle ?? 'solid')\n const strokeWidth = isNoBorderIntent ? DEFAULT_STYLE.strokeWidth : rawStrokeWidth\n\n const cornerRadius = (style?.roundness ?? DEFAULT_STYLE.roundness) * 4\n const radius = Math.max(0, Math.min(cornerRadius, w / 2, h / 2))\n const dash = dashPatternFor(effectiveStrokeStyle, strokeWidth)\n const detail = apparentDetail(Math.max(w, h), scale)\n\n const cacheKey = [\n type,\n w.toFixed(1),\n h.toFixed(1),\n radius.toFixed(1),\n strokeColor,\n strokeWidth.toFixed(2),\n effectiveStrokeStyle,\n roughness.toFixed(2),\n seed,\n detail.curveStepCount,\n detail.maxRandomnessOffset.toFixed(2),\n ].join('|')\n\n const drawable = getOrBuildDrawable(cacheKey, () => {\n const pathData = buildPath(type, 0, 0, w, h, radius)\n return rc.generator.path(pathData, {\n ...ROUGH_DEFAULTS,\n stroke: strokeColor,\n strokeWidth,\n roughness,\n seed,\n // Always pass an explicit array (empty = solid) so rough.js calls\n // ctx.setLineDash() to a known state. Passing `undefined` makes\n // rough skip that call, and the canvas inherits whatever the\n // previous draw left behind — a transparent-stroke node's\n // fill-derived outline would pick up the dash from an earlier\n // dashed node in the same paint pass.\n strokeLineDash: dash,\n curveStepCount: detail.curveStepCount,\n maxRandomnessOffset: detail.maxRandomnessOffset,\n })\n })\n\n ctx.save()\n ctx.lineJoin = 'round'\n rc.draw(drawable)\n ctx.restore()\n}\n\n/**\n * Paints a rough stroke for an edge body. `samples` is the cached\n * polyline. We use rough's `linearPath` because it preserves the\n * shape exactly (excalidraw connectors). Arrowheads + clip stay plain\n * — wobble on arrowheads doesn't add visual value.\n */\nexport const drawRoughEdge = (\n ctx: CanvasRenderingContext2D,\n edge: Edge,\n samples: Vec2[],\n scale: number,\n theme?: ThemeResolver,\n): boolean => {\n const Ctor = getRoughCanvasCtor()\n if (!Ctor) return false\n if (samples.length < 2) return true\n\n const style = edge.style\n const strokeColor = resolveColor(style, 'strokeColor', '#475569', theme)\n const strokeWidth = resolveStrokeWidth(style, theme)\n if (strokeWidth <= 0) return true\n\n const roughness = style?.roughness ?? 0\n if (roughness <= 0) return true\n\n const seed = edge.id ? (seedFromId(edge.id) % 2147483646) + 1 : 1337\n const dash = dashPatternFor(style?.strokeStyle, strokeWidth)\n let minX = samples[0]!.x\n let maxX = samples[0]!.x\n let minY = samples[0]!.y\n let maxY = samples[0]!.y\n for (const p of samples) {\n if (p.x < minX) minX = p.x\n if (p.x > maxX) maxX = p.x\n if (p.y < minY) minY = p.y\n if (p.y > maxY) maxY = p.y\n }\n const detail = apparentDetail(Math.max(maxX - minX, maxY - minY), scale)\n\n const cacheKey = [\n 'edge',\n edge.id,\n samples.length,\n Math.round(minX),\n Math.round(minY),\n Math.round(maxX),\n Math.round(maxY),\n strokeColor,\n strokeWidth.toFixed(2),\n style?.strokeStyle ?? 'solid',\n roughness.toFixed(2),\n seed,\n detail.curveStepCount,\n detail.maxRandomnessOffset.toFixed(2),\n ].join('|')\n\n const rc = ensureRoughCanvas(ctx, Ctor)\n if (!rc) return false\n\n const drawable = getOrBuildDrawable(cacheKey, () => {\n const points: [number, number][] = samples.map(s => [s.x, s.y])\n return rc.generator.linearPath(points, {\n ...ROUGH_DEFAULTS,\n stroke: strokeColor,\n strokeWidth,\n roughness,\n seed,\n // See paintAtomicRough — pass an explicit array (empty = solid)\n // so rough resets the canvas dash; `undefined` lets stale state\n // from a previous draw leak through.\n strokeLineDash: dash,\n curveStepCount: detail.curveStepCount,\n maxRandomnessOffset: detail.maxRandomnessOffset,\n })\n })\n\n ctx.save()\n ctx.lineJoin = 'round'\n rc.draw(drawable)\n ctx.restore()\n return true\n}\n\n/**\n * Reuses one `RoughCanvas` per CanvasRenderingContext2D — building it\n * is cheap (~5µs) but per-frame stacks up. Stored on the context as\n * a hidden property.\n */\nconst ROUGH_CANVAS_KEY = '__roughCanvas'\nconst ensureRoughCanvas = (\n ctx: CanvasRenderingContext2D,\n Ctor: NonNullable<ReturnType<typeof getRoughCanvasCtor>>,\n): RoughCanvasLike | null => {\n const ctxWithCache = ctx as CanvasRenderingContext2D & {\n [ROUGH_CANVAS_KEY]?: RoughCanvasLike\n }\n if (ctxWithCache[ROUGH_CANVAS_KEY]) return ctxWithCache[ROUGH_CANVAS_KEY]\n const rc = new Ctor(ctx.canvas) as RoughCanvasLike\n ctxWithCache[ROUGH_CANVAS_KEY] = rc\n return rc\n}\n\nconst buildPath = (\n type: AtomicRoughPrimitive,\n x: number,\n y: number,\n w: number,\n h: number,\n radius: number,\n): string => {\n switch (type) {\n case 'rect':\n return radius > 0 ? excalidrawRoundedRectPath(x, y, w, h, radius) : rectPath(x, y, w, h)\n case 'ellipse':\n return ellipsePath(x, y, w, h)\n case 'diamond':\n return diamondPath(x, y, w, h, radius)\n case 'tag':\n return tagPath(x, y, w, h, radius)\n case 'thought-cloud':\n return thoughtCloudPath(x, y, w, h, radius)\n }\n}\n","/**\n * Per-shape content bounds — the rect within a node where text content\n * is laid out and painted. Defaults to the full node bbox; shapes with\n * non-rectangular interiors override so text doesn't bleed into the\n * non-content areas (capsule's accent circle, diamond's narrow tips,\n * thought-cloud's dome, tag's notch, etc.).\n *\n * Returned in node-local coords. Renderer's `paintNodeContent` already\n * applies the node transform before drawing — bounds are relative to\n * (0, 0) inside the node.\n */\nimport type { Node } from '../../types'\n\nexport type ContentBounds = { x: number; y: number; w: number; h: number }\n\nconst SQRT2_INV = 1 / Math.SQRT2\n\nexport const contentBounds = (node: Node): ContentBounds => {\n const { w, h } = node\n switch (node.type) {\n case 'capsule': {\n // Skip the accent circle — text fills the rect body to its right.\n // Must mirror compositeLayout's capsule geometry.\n const circ = Math.min(h * 0.55, w * 0.28, 56)\n const overlap = circ * 0.15\n const rectX = circ - overlap\n return { x: rectX, y: 0, w: Math.max(0, w - rectX), h }\n }\n case 'diamond':\n case 'layered-diamond':\n case 'soft-diamond': {\n // Inscribed rectangle of a square rotated 45° = bbox × (1/√2).\n // For `soft-diamond` the inner (front) diamond is 96% of bbox so\n // its inscribed rect is slightly tighter, but the bbox-relative\n // formula reads well enough without a separate case.\n const cw = w * SQRT2_INV\n const ch = h * SQRT2_INV\n return { x: (w - cw) / 2, y: (h - ch) / 2, w: cw, h: ch }\n }\n case 'ellipse':\n case 'layered-ellipse': {\n // True ellipse-inscribed rect is bbox × (1/√2). Using 0.7 gives a\n // tiny safety margin so text doesn't kiss the curve at the edges.\n const f = 0.7\n const cw = w * f\n const ch = h * f\n return { x: (w - cw) / 2, y: (h - ch) / 2, w: cw, h: ch }\n }\n case 'thought-cloud': {\n // Rect body only — skip the dome area at the top. Must mirror\n // the geometry in `path-helpers.ts thoughtCloudGeometry`.\n const domeW = Math.min(w * 0.4, h * 1.2)\n const domeH = Math.min(h * 0.45, domeW)\n const bodyY = domeH * 0.55\n return { x: 0, y: bodyY, w, h: Math.max(0, h - bodyY) }\n }\n case 'tag': {\n // Skip the left notch — text fills the body to the right.\n const notch = Math.min(h * 0.5, w * 0.3)\n return { x: notch, y: 0, w: Math.max(0, w - notch), h }\n }\n default:\n return { x: 0, y: 0, w, h }\n }\n}\n","/**\n * Camera transform application + viewport math.\n *\n * The trick: instead of transforming each shape's coordinates by hand,\n * we set the canvas matrix once per frame and draw every shape in world\n * coordinates. The DPR factor is folded into the matrix so logical-pixel\n * stroke widths come out crisp.\n */\nimport { viewportWorldRect } from '../camera'\nimport type { CameraState, Node, WorldRect } from '../types'\nimport type { CanvasSurface } from './canvas-setup'\n\n/**\n * Sets the 2d transform so subsequent draw calls take world coords.\n *\n * screen.x = (world.x - camera.x) * camera.z * dpr\n * screen.y = (world.y - camera.y) * camera.z * dpr\n */\nexport const applyCameraTransform = (surface: CanvasSurface, camera: CameraState): void => {\n const sx = camera.z * surface.dpr\n const sy = camera.z * surface.dpr\n const tx = -camera.x * sx\n const ty = -camera.y * sy\n surface.ctx.setTransform(sx, 0, 0, sy, tx, ty)\n}\n\n/**\n * The world rect currently visible inside the surface.\n */\nexport const worldViewport = (surface: CanvasSurface, camera: CameraState): WorldRect =>\n viewportWorldRect(camera, surface.cssWidth, surface.cssHeight)\n\n/**\n * Wraps a draw callback in the local-frame transform for one node:\n * translates to the node's center, rotates by node.angle, then translates\n * back to the node's top-left so the drawer can build paths in (0..w, 0..h).\n *\n * Fast path: when `node.angle === 0` (the common case) we skip the\n * canvas2d save/restore pair entirely and manually un-translate after\n * the callback. `save()`/`restore()` allocate + swap a full graphics\n * state record; at 10k+ nodes/frame that's ~1ms of the paint budget.\n * The callback is responsible for not leaking transform state — all\n * built-in drawers (drawShape, drawCompositeRough, paintFrameNode,\n * paintImageNode, paintIconNode) honor this contract by either\n * leaving the transform untouched or restoring their own inner pushes.\n */\nexport const drawWithNodeTransform = (\n ctx: CanvasRenderingContext2D,\n node: Node,\n fn: () => void,\n): void => {\n if (node.angle === 0) {\n ctx.translate(node.x, node.y)\n fn()\n ctx.translate(-node.x, -node.y)\n return\n }\n // Rotated path keeps the save/restore — un-doing translate + rotate\n // + translate manually is error-prone and rotated nodes are rare.\n ctx.save()\n const cx = node.x + node.w / 2\n const cy = node.y + node.h / 2\n ctx.translate(cx, cy)\n ctx.rotate(node.angle)\n ctx.translate(-node.w / 2, -node.h / 2)\n fn()\n ctx.restore()\n}\n","import { computeEdgeGeometry, drawEdge } from '../edges'\n/**\n * Renderer — see ARCHITECTURE.md §4.\n *\n * Owns two canvases (static + interactive) and one DOM overlay div; reads\n * from a CanvasStore; redraws in response to store changes, camera changes,\n * interaction-state changes, and viewport resizes.\n *\n * static — every committed primitive at its committed position. Redraws\n * only when committed scene state, camera, or selection changes.\n * interactive — selection outlines, resize handles, marquee rect, and any\n * shape currently being dragged at its uncommitted position.\n * Redrawn every rAF tick while interaction.mode !== 'idle'.\n */\nimport { getPointAndTangentAtArcLength } from '../edges/arc-length'\nimport type { NodeTypeDef, RenderEnv } from '../node-types'\nimport { inflateRect, nodeAABB } from '../spatial'\nimport { type CanvasStore, type InteractionState, isMoving as isMovingState } from '../store'\nimport {\n DEFAULT_HIGHLIGHT_COLOR,\n DEFAULT_TEXT_COLOR,\n FONT_SIZE_MAP,\n getOrRenderTextBitmap,\n subscribeFontEpoch,\n subscribeMathEpoch,\n} from '../text'\nimport type { CameraState, CanvasBackground, Edge, EdgeId, Node, NodeId, WorldRect } from '../types'\nimport { type AssetCache, createAssetCache, paintIconNode, paintImageNode } from './assets'\nimport { paintBackground } from './background'\nimport { type CanvasSurface, clearSurface, setupSurface, sizeSurface } from './canvas-setup'\nimport { type FrameLoop, type FrameStats, createFrameLoop } from './frame-loop'\nimport {\n DEFAULT_SELECTION_COLOR,\n drawEdgeEndpointHandles,\n drawEdgeMidpointHandle,\n drawMarquee,\n drawResizeHandles,\n drawRotateHandle,\n drawSelectionOutline,\n} from './overlay'\nimport { paintFrameNode } from './paint-frame'\nimport { ROUGH_MAX_NODES, ROUGH_MIN_ZOOM, drawCompositeRough, drawRoughShape } from './rough'\nimport {\n ROUGH_FILL_MISREGISTER_X,\n ROUGH_FILL_MISREGISTER_Y,\n ROUGH_MAX_MOVING_NODES,\n} from './rough/constants'\nimport { getRoughCanvasCtor, onRoughReady } from './rough/loader'\nimport {\n type ThemeResolver,\n contentBounds,\n drawShape,\n isCompositePrimitive,\n isDrawablePrimitive,\n} from './shapes'\nimport { applyCameraTransform, drawWithNodeTransform, worldViewport } from './transform'\n\n/**\n * The static scene is rendered into an offscreen cache sized to the\n * viewport plus this margin (CSS px) on every side. The on-screen\n * canvas is presented from that cache: a sub-margin pan blits, a pan\n * past the margin shifts + repaints only the exposed strip, and only a\n * content/zoom change re-renders the whole scene. The margin is the\n * pan distance reused before a strip extend is needed. See\n * ARCHITECTURE.md §4.4.\n */\nconst SCENE_CACHE_MARGIN_PX = 256\n\n/**\n * Minimum on-screen size (in logical CSS pixels) for a shape to be worth drawing.\n * Below this both dimensions, the shape can't be perceived anyway; skipping it\n * saves the entire path build + fill/stroke for that node.\n */\nconst MIN_ON_SCREEN_SIZE_PX = 1.5\n\n/**\n * Minimum on-screen font size (in logical CSS pixels) for text to be worth\n * rasterizing. Below ~3px nothing is readable; skipping the bitmap lookup +\n * blit saves several μs/node and matters at extreme zoom-out with thousands\n * of content-bearing nodes visible.\n */\nconst MIN_READABLE_FONT_PX = 3\n\nexport type RendererOptions = {\n store: CanvasStore\n staticCanvas: HTMLCanvasElement\n interactiveCanvas: HTMLCanvasElement\n theme?: ThemeResolver\n /** Initial CSS-pixel size. Use `setSize()` to update on resize. */\n width: number\n height: number\n /**\n * Optional page background + dot/grid pattern. Local-only (not in\n * the synced scene). Update at runtime via `Renderer.setBackground`.\n */\n background?: CanvasBackground\n /**\n * Color for all selection chrome: selection outlines, resize +\n * rotate handles, edge endpoint + midpoint handles, marquee rect,\n * and the drag-create preview. Defaults to `#3b82f6` (the standard\n * canvas-app blue). Update at runtime via `Renderer.setSelectionColor`.\n *\n * Accepts any CSS color literal (hex, rgb(), named). The marquee\n * fill tints via globalAlpha — no parsing needed.\n */\n selectionColor?: string\n /**\n * Cap on the canvas backing-store DPR (device-pixel ratio). At\n * native DPR on hi-DPI displays, the backing buffer can hit\n * 20-30 megapixels per frame; the GPU-upload step alone dominates\n * the frame budget. Defaults to `1` for consistent perf across\n * hardware. Bump to `2` (or `window.devicePixelRatio`) for\n * pixel-crisp rendering at the cost of FPS on hi-DPI displays.\n *\n * Text is unaffected — the text bitmap cache renders glyphs at\n * its own DPR-aware scale.\n */\n maxDpr?: number\n /**\n * Fires when the set of custom nodes that should be rendered in the DOM\n * overlay changes. Consumers use this to mount/unmount React subtrees\n * (or whatever framework). See ARCHITECTURE.md §5.2 lifecycle.\n *\n * The callback receives the FULL current set, not a delta — consumers\n * compute the mount/unmount diff themselves.\n */\n onOverlayChange?: (mountedIds: NodeId[]) => void\n}\n\nexport type Renderer = {\n /** Begin the rAF loop. Idempotent. */\n start(): void\n /** Stop the rAF loop. Idempotent. */\n stop(): void\n /** Force a static repaint on the next rAF tick. */\n invalidate(): void\n /** Resize both canvases to a new CSS-pixel viewport. */\n setSize(cssW: number, cssH: number): void\n /** Update the page background / pattern. Triggers a static repaint. */\n setBackground(bg: CanvasBackground | undefined): void\n /** Update the selection chrome color. Triggers an interactive repaint. */\n setSelectionColor(color: string): void\n /**\n * Toggle frame-node paint. Use during a presentation flow to drop\n * the slide border + label so only the frame contents are visible.\n * Triggers a static repaint.\n */\n setHideFrames(hidden: boolean): void\n /** Per-frame timing (FPS, lastMs, avgMs, frames). */\n stats(): FrameStats\n /** Number of items the most recent paint actually drew. */\n lastDrawCount(): number\n /** Current overlay-mounted custom-node ids. */\n getOverlaySet(): NodeId[]\n /**\n * Renderer-owned asset cache (decoded image bitmaps + rasterized\n * SVG icons). Pass to {@link exportSelection} / {@link exportViewport}\n * so PNG export paints image + icon nodes from the same bitmaps the\n * live canvas uses.\n */\n getAssetCache(): AssetCache\n /** Detach event listeners. The store is left untouched. */\n dispose(): void\n}\n\nexport const createRenderer = (opts: RendererOptions): Renderer => {\n const { store, theme, onOverlayChange } = opts\n const maxDpr = opts.maxDpr\n const staticSurface = setupSurface(opts.staticCanvas, maxDpr)\n const interactiveSurface = setupSurface(opts.interactiveCanvas, maxDpr)\n let background: CanvasBackground | undefined = opts.background\n let selectionColor: string = opts.selectionColor ?? DEFAULT_SELECTION_COLOR\n let hideFrames = false\n sizeSurface(staticSurface, opts.width, opts.height, maxDpr)\n sizeSurface(interactiveSurface, opts.width, opts.height, maxDpr)\n\n let staticDirty = true\n let interactiveDirty = false\n /** Custom nodes whose React view is currently mounted in the overlay. */\n let overlaySet: ReadonlySet<NodeId> = new Set()\n let lastDrawn = 0\n\n // Offscreen scene cache (viewport + margin). Rendered by\n // `renderFullCache`, blitted to the on-screen static surface by\n // `presentStatic`. `cacheCam*` records the camera the cache is valid\n // for — used by the present blit to compute the source offset (and,\n // from Phase 2 on, to decide whether a re-render is needed at all).\n let cacheSurface: CanvasSurface | null = null\n let cacheCamX = 0\n let cacheCamY = 0\n let cacheCamZ = 1\n // True when the cache's *content* is stale (a scene/zoom/size change,\n // anything but a pure pan). Pan leaves it false so `paintStatic` can\n // present by blitting alone. `renderFullCache` clears it.\n let cacheStale = true\n\n /**\n * Lazily allocates / resizes the offscreen cache to `viewport + 2·margin`\n * at the static surface's DPR. The DPR is copied from `staticSurface`\n * (not recomputed from the cache's larger size) so the cache↔screen blit\n * stays a 1:1 device-pixel copy.\n */\n const ensureCacheSurface = (): CanvasSurface => {\n const dpr = staticSurface.dpr\n const cssW = staticSurface.cssWidth + 2 * SCENE_CACHE_MARGIN_PX\n const cssH = staticSurface.cssHeight + 2 * SCENE_CACHE_MARGIN_PX\n if (!cacheSurface) {\n const canvas = document.createElement('canvas')\n const ctx = canvas.getContext('2d')\n if (!ctx) throw new Error('Canvas 2d context unavailable')\n cacheSurface = { canvas, ctx, cssWidth: 0, cssHeight: 0, dpr: 1 }\n }\n if (\n cacheSurface.cssWidth !== cssW ||\n cacheSurface.cssHeight !== cssH ||\n cacheSurface.dpr !== dpr\n ) {\n cacheSurface.cssWidth = cssW\n cacheSurface.cssHeight = cssH\n cacheSurface.dpr = dpr\n cacheSurface.canvas.width = Math.max(1, Math.round(cssW * dpr))\n cacheSurface.canvas.height = Math.max(1, Math.round(cssH * dpr))\n }\n return cacheSurface\n }\n\n // Sorted-by-(z, id) caches of ALL scene nodes / edges. Rebuilt\n // lazily on first access and invalidated on every `'change'` op.\n // Lets `visibleNodes` / `visibleEdges` skip per-frame Array.sort —\n // during pan, the scene doesn't mutate so these stay valid for the\n // whole gesture. At 10k nodes this saves ~1ms / frame.\n let sortedNodeIdsCache: NodeId[] | null = null\n let sortedEdgeIdsCache: EdgeId[] | null = null\n const invalidateSortedCaches = (): void => {\n sortedNodeIdsCache = null\n sortedEdgeIdsCache = null\n }\n\n // Asset cache for image + icon node types. The `onReady` hook fires\n // when a pending decode lands so the next frame blits the bitmap.\n // `loop` is created later in this scope, so we wrap the request in a\n // closure that resolves it at call time.\n const requestRepaint = (): void => {\n staticDirty = true\n cacheStale = true\n loop.requestFrame()\n }\n const assetCache = createAssetCache({ onReady: requestRepaint })\n\n const isInteractive = (state: InteractionState): boolean =>\n state.mode !== 'idle' || store.getSelection().length > 0\n\n const drawFrame = (): void => {\n if (staticDirty) {\n paintStatic()\n staticDirty = false\n }\n if (interactiveDirty) {\n paintInteractive()\n interactiveDirty = false\n }\n }\n\n /**\n * Paints the full static scene (background + frames + nodes + edges)\n * into `surface` in world coordinates. The caller is responsible for\n * having cleared the surface and applied the world→device transform;\n * `viewport` is the world rect to cull against (it may extend beyond\n * the on-screen viewport when painting into the oversized cache).\n */\n const paintSceneBody = (\n surface: CanvasSurface,\n camera: CameraState,\n viewport: WorldRect,\n // Strip renders (Phase 3 cache extension) paint only a sliver of\n // the scene, so they must NOT publish the draw count or the\n // React-overlay mount set — those describe the whole viewport and\n // are owned by full renders. Same contract as the blit-only path,\n // which doesn't run this body at all.\n fullRender = true,\n ): void => {\n const scale = camera.z * surface.dpr\n const interaction = store.getInteractionState()\n // Per ARCHITECTURE.md §4.2: nodes currently being dragged or resized,\n // AND edges incident to them, are excluded from static and drawn on\n // the interactive canvas at their uncommitted positions instead.\n const excludedNodes =\n interaction.mode === 'dragging' || interaction.mode === 'resizing'\n ? new Set(interaction.draggedIds)\n : null\n // An edge being mid-point-dragged is excluded too — the interactive\n // layer paints it with the in-progress control from `midpointDraft`.\n const baseExcludedEdges = excludedNodes ? incidentEdgeIds(excludedNodes) : null\n const midpointEdgeId = interaction.midpointDraft?.edgeId ?? null\n const excludedEdges: ReadonlySet<EdgeId> | null =\n midpointEdgeId !== null\n ? new Set<EdgeId>([...(baseExcludedEdges ?? []), midpointEdgeId])\n : baseExcludedEdges\n\n // ---- background (page color + dot/grid pattern) ----\n paintBackground(surface.ctx, { viewport, zoom: camera.z, background })\n\n // ---- nodes ----\n const visible = visibleNodes(camera, viewport)\n const isMoving = isMovingState(interaction)\n const minOnScreen = MIN_ON_SCREEN_SIZE_PX\n const nextOverlaySet = new Set<NodeId>()\n let drawn = 0\n\n // Render env shared by built-in content rendering + custom-node dispatch.\n const renderEnv: RenderEnv = {\n zoom: camera.z,\n isMoving,\n isSelected: false,\n isHovered: false,\n isEditing: false,\n theme: token => (theme ? theme(token) : undefined),\n }\n const editingNodeId =\n interaction.editingTarget?.kind === 'node' ? interaction.editingTarget.id : null\n\n // Rough-stroke gate — paint the wobbly outline only when ALL hold:\n // - pan/zoom is NOT in progress (whole viewport in motion would\n // blow the frame budget),\n // - any drag/resize/rotate affects <= ROUGH_MAX_MOVING_NODES (so a\n // single-node drag keeps the rough look on its neighbours; a\n // big marquee move falls back to plain),\n // - zoom is high enough that the wobble is perceptible,\n // - visible node count is below the cap.\n // Per-node `style.roughness > 0` is the final per-shape gate inside\n // `drawRoughShape`. When the gate is false, plain strokes only.\n const cameraIsMoving = interaction.mode === 'panning' || interaction.mode === 'zooming'\n const movingNodeCount = excludedNodes?.size ?? 0\n const roughEnabled =\n !cameraIsMoving &&\n movingNodeCount <= ROUGH_MAX_MOVING_NODES &&\n camera.z >= ROUGH_MIN_ZOOM &&\n visible.length <= ROUGH_MAX_NODES\n\n // First pass: frames. They render behind everything else so the\n // slide chrome reads as a background region. The main loop below\n // skips `type === 'frame'`. `hideFrames` (set by a present-mode\n // flow) skips painting them entirely.\n if (!hideFrames) {\n for (const node of visible) {\n if (node.type !== 'frame') continue\n if (excludedNodes?.has(node.id)) continue\n drawWithNodeTransform(surface.ctx, node, () => {\n paintFrameNode(surface.ctx, node, scale, theme)\n })\n drawn++\n }\n }\n\n for (const node of visible) {\n if (node.type === 'frame') continue\n if (excludedNodes?.has(node.id)) continue\n\n // The editing node's content is occluded by the textarea overlay —\n // skip its bitmap paint so the canvas underneath doesn't show stale\n // pixels through the textarea's translucent edges.\n const isEditingThis = editingNodeId === node.id\n\n // Built-in primitive path: shape paint + optional content paint.\n if (isDrawablePrimitive(node.type)) {\n const useRough = roughEnabled && (node.style?.roughness ?? 0) > 0\n // Peek (and trigger lazy import) — null means rough.js hasn't\n // resolved yet this session.\n const roughReady = useRough ? getRoughCanvasCtor() !== null : false\n const composite = isCompositePrimitive(node.type)\n drawWithNodeTransform(surface.ctx, node, () => {\n if (useRough && roughReady) {\n if (composite) {\n // Composites paint each sub fully (misregistered fill +\n // rough stroke) before moving to the next sub. Crucial\n // so the back layer's stroke is covered by the front\n // layer's fill in the overlap region.\n drawCompositeRough(surface.ctx, node, camera.z, theme)\n } else {\n // Atomic: misregistered fill in one pass, rough stroke\n // in a second pass. Print-misregistration shifts fill\n // up-and-left a few pixels from the rough stroke. See\n // ROUGH_FILL_MISREGISTER_X/Y in rough/constants.\n surface.ctx.translate(ROUGH_FILL_MISREGISTER_X, ROUGH_FILL_MISREGISTER_Y)\n drawShape(surface.ctx, node, scale, theme, { skipStroke: true })\n surface.ctx.translate(-ROUGH_FILL_MISREGISTER_X, -ROUGH_FILL_MISREGISTER_Y)\n drawRoughShape(surface.ctx, node, camera.z, theme)\n }\n } else {\n // Plain fill + stroke at native origin — also the fallback\n // for the one frame before rough.js finishes loading.\n // Rough auto-disable during pan/zoom (via the interaction\n // mode propagation set up in `use-pan-zoom`) is what keeps\n // layered shapes smooth here; no special LOD fast-path\n // needed for composites at the count cap.\n drawShape(surface.ctx, node, scale, theme)\n if (useRough && !roughReady) {\n onRoughReady(() => {\n staticDirty = true\n cacheStale = true\n loop.requestFrame()\n })\n }\n }\n if (!isEditingThis) paintNodeContent(surface.ctx, node, renderEnv)\n })\n drawn++\n continue\n }\n // Image node: blit cached bitmap (or placeholder if still loading).\n if (node.type === 'image') {\n drawWithNodeTransform(surface.ctx, node, () => {\n paintImageNode(surface.ctx, node, assetCache, theme)\n })\n drawn++\n continue\n }\n // Icon node: rasterized SVG with optional `style.iconColor` tint.\n if (node.type === 'icon') {\n drawWithNodeTransform(surface.ctx, node, () => {\n paintIconNode(surface.ctx, node, assetCache, scale, theme)\n })\n drawn++\n continue\n }\n // Text-only shape: no fill/stroke, just content (or placeholder).\n if (node.type === 'text') {\n drawWithNodeTransform(surface.ctx, node, () => {\n if (isEditingThis) return\n const hasContent = node.content && node.content.trim().length > 0\n if (hasContent) {\n paintNodeContent(surface.ctx, node, renderEnv)\n } else {\n paintEmptyTextPlaceholder(surface.ctx, node, camera.z)\n }\n })\n drawn++\n continue\n }\n\n // Custom-node dispatch (§5.3 LOD ladder).\n const def = store.getNodeTypeDef(node.type)\n if (!def) continue\n // Sub-pixel skip — same threshold as built-ins.\n if (node.w * camera.z < minOnScreen && node.h * camera.z < minOnScreen) continue\n if (camera.z < def.lod.minZoomForPlaceholder) continue\n\n // Below the React threshold OR currently moving: prefer cheap canvas\n // paths. Order: getSnapshot → drawPlaceholder → renderCanvas → skip.\n const preferCanvas = camera.z < def.lod.minZoomForReact || isMoving\n if (preferCanvas) {\n if (paintCustomCanvasFallback(surface.ctx, node, def, scale, renderEnv)) {\n drawn++\n }\n continue\n }\n\n // Full quality: prefer React overlay; else renderCanvas; else skip.\n if (def.view) {\n nextOverlaySet.add(node.id)\n continue\n }\n if (def.renderCanvas) {\n // Custom-node drawers get a save/restore scope: built-in\n // drawers honor the \"set every state you depend on\" contract\n // (see drawWithNodeTransform), but consumer code can't be\n // assumed to. Cost is one extra save/restore per visible\n // custom node — negligible since custom nodes are rare.\n drawWithNodeTransform(surface.ctx, node, () => {\n surface.ctx.save()\n def.renderCanvas!(surface.ctx, node, renderEnv)\n surface.ctx.restore()\n })\n drawn++\n }\n }\n\n // ---- edges ----\n const visEdges = visibleEdges(viewport)\n // Edges share the same gate as nodes — extra cap protects against\n // mass-labeled scenes where edge counts dominate the budget.\n const edgeRoughEnabled =\n !cameraIsMoving &&\n movingNodeCount <= ROUGH_MAX_MOVING_NODES &&\n camera.z >= ROUGH_MIN_ZOOM &&\n visEdges.length <= ROUGH_MAX_NODES\n for (const edge of visEdges) {\n if (excludedEdges?.has(edge.id)) continue\n paintOneEdge(surface.ctx, edge, scale, edgeRoughEnabled, camera.z, isMoving)\n drawn++\n }\n if (!fullRender) return\n lastDrawn = drawn\n\n // Emit overlay event if the React-mount set changed.\n if (!setsEqual(nextOverlaySet, overlaySet)) {\n overlaySet = nextOverlaySet\n onOverlayChange?.([...overlaySet])\n }\n }\n\n /**\n * Renders the whole scene into the offscreen cache at `camera`, with a\n * margin offset so the cache covers the viewport inflated by\n * SCENE_CACHE_MARGIN_PX on every side. Records `cacheCam*` so a\n * subsequent `presentStatic` knows where the viewport sits inside it.\n */\n /**\n * Sets the cache's world→device transform centered on (`centerX`,\n * `centerY`) at zoom `z`, shifted by the margin so the world point at\n * screen (-margin, -margin) maps to cache device (0, 0).\n */\n const applyCacheTransform = (\n cache: CanvasSurface,\n centerX: number,\n centerY: number,\n z: number,\n ): void => {\n const s = z * cache.dpr\n const m = SCENE_CACHE_MARGIN_PX * cache.dpr\n cache.ctx.setTransform(s, 0, 0, s, -centerX * s + m, -centerY * s + m)\n }\n\n const renderFullCache = (camera: CameraState): void => {\n const cache = ensureCacheSurface()\n clearSurface(cache)\n applyCacheTransform(cache, camera.x, camera.y, camera.z)\n const marginWorld = SCENE_CACHE_MARGIN_PX / camera.z\n const viewport = inflateRect(worldViewport(staticSurface, camera), marginWorld)\n paintSceneBody(cache, camera, viewport)\n cacheCamX = camera.x\n cacheCamY = camera.y\n cacheCamZ = camera.z\n cacheStale = false\n }\n\n /**\n * True when a pan past the margin still overlaps the cache enough to\n * be worth extending (vs a full re-render). False on big jumps\n * (minimap click, programmatic teleport) where nothing can be reused.\n */\n const canExtend = (camera: CameraState): boolean => {\n if (!cacheSurface) return false\n const s = camera.z * staticSurface.dpr\n const dx = Math.abs((cacheCamX - camera.x) * s)\n const dy = Math.abs((cacheCamY - camera.y) * s)\n return dx < cacheSurface.canvas.width && dy < cacheSurface.canvas.height\n }\n\n /**\n * Repaints one device-space strip of the cache: clip + clear it, then\n * render the scene clipped to that strip under the cache transform\n * centered on (`centerX`, `centerY`).\n */\n const renderCacheStrip = (\n cache: CanvasSurface,\n centerX: number,\n centerY: number,\n z: number,\n px: number,\n py: number,\n pw: number,\n ph: number,\n ): void => {\n const ctx = cache.ctx\n const s = z * cache.dpr\n const m = SCENE_CACHE_MARGIN_PX * cache.dpr\n ctx.save()\n // Clip + clear in device space; the clip persists across setTransform.\n ctx.setTransform(1, 0, 0, 1, 0, 0)\n ctx.beginPath()\n ctx.rect(px, py, pw, ph)\n ctx.clip()\n ctx.clearRect(px, py, pw, ph)\n applyCacheTransform(cache, centerX, centerY, z)\n // device → world for the strip rect (inverse of the cache transform).\n const viewport: WorldRect = {\n x: (px - m) / s + centerX,\n y: (py - m) / s + centerY,\n w: pw / s,\n h: ph / s,\n }\n paintSceneBody(cache, { x: centerX, y: centerY, z }, viewport, false)\n ctx.restore()\n }\n\n /**\n * Reuses the cache across a pan that left the margin: shifts the\n * existing pixels to recenter on `camera` (integer device-px copy, so\n * no resample / no accumulating blur), then repaints only the\n * L-shaped strip the shift exposed. Pre: cache valid, same zoom,\n * `canExtend(camera)` true.\n */\n const extendCache = (camera: CameraState): void => {\n const cache = ensureCacheSurface()\n const s = camera.z * cache.dpr\n const cacheW = cache.canvas.width\n const cacheH = cache.canvas.height\n // Integer device-px shift that recenters old content on `camera`,\n // and the exact world center that integer shift implies (keeps the\n // transform consistent with the rounded copy).\n const dx = Math.round((cacheCamX - camera.x) * s)\n const dy = Math.round((cacheCamY - camera.y) * s)\n const newCamX = cacheCamX - dx / s\n const newCamY = cacheCamY - dy / s\n\n // 1. Shift existing pixels. Self-copy is spec-safe (source snapshot).\n cache.ctx.setTransform(1, 0, 0, 1, 0, 0)\n cache.ctx.drawImage(cache.canvas, 0, 0, cacheW, cacheH, dx, dy, cacheW, cacheH)\n cacheCamX = newCamX\n cacheCamY = newCamY\n cacheCamZ = camera.z\n\n // 2. Repaint the vacated L-shape as two disjoint rects. Horizontal\n // strip spans full height; vertical strip takes the remaining\n // width so the corner is painted exactly once.\n const hw = Math.abs(dx)\n const vh = Math.abs(dy)\n const hx = dx > 0 ? 0 : cacheW - hw\n const vy = dy > 0 ? 0 : cacheH - vh\n const vx = dx > 0 ? hw : 0\n const vw = cacheW - hw\n if (hw > 0) renderCacheStrip(cache, newCamX, newCamY, camera.z, hx, 0, hw, cacheH)\n if (vh > 0 && vw > 0) renderCacheStrip(cache, newCamX, newCamY, camera.z, vx, vy, vw, vh)\n }\n\n /**\n * The viewport's top-left offset inside the cache, in cache device\n * pixels, given the pan since `cacheCam*`. Rounded so the present blit\n * and the fits-in-cache test agree on the same integer rect.\n */\n const cacheSourceOffset = (camera: CameraState): { x: number; y: number } => {\n const dpr = staticSurface.dpr\n return {\n x: Math.round(((camera.x - cacheCamX) * cacheCamZ + SCENE_CACHE_MARGIN_PX) * dpr),\n y: Math.round(((camera.y - cacheCamY) * cacheCamZ + SCENE_CACHE_MARGIN_PX) * dpr),\n }\n }\n\n /**\n * True when the current viewport lies entirely within the cached\n * region — i.e. the pan since the last full render stayed inside the\n * margin, so we can present by blitting alone.\n */\n const viewportFitsInCache = (camera: CameraState): boolean => {\n if (!cacheSurface) return false\n const { x, y } = cacheSourceOffset(camera)\n return (\n x >= 0 &&\n y >= 0 &&\n x + staticSurface.canvas.width <= cacheSurface.canvas.width &&\n y + staticSurface.canvas.height <= cacheSurface.canvas.height\n )\n }\n\n /**\n * Blits the viewport-sized sub-rect of the cache onto the on-screen\n * static surface. The source offset is the viewport's position inside\n * the cache, derived from the pan since `cacheCam*`.\n */\n const presentStatic = (camera: CameraState): void => {\n const cache = ensureCacheSurface()\n const w = staticSurface.canvas.width\n const h = staticSurface.canvas.height\n const { x: srcX, y: srcY } = cacheSourceOffset(camera)\n staticSurface.ctx.setTransform(1, 0, 0, 1, 0, 0)\n staticSurface.ctx.clearRect(0, 0, w, h)\n staticSurface.ctx.drawImage(cache.canvas, srcX, srcY, w, h, 0, 0, w, h)\n }\n\n /**\n * Static-layer paint entry point. Three tiers, cheapest first:\n * 1. cache valid + viewport inside the margin → blit only (Phase 2)\n * 2. cache valid + panned past the margin but still overlapping →\n * shift + repaint the exposed strip, then blit (Phase 3)\n * 3. otherwise (stale content, zoom, big jump) → full re-render\n */\n const paintStatic = (): void => {\n const camera = store.getCamera()\n if (!cacheStale && camera.z === cacheCamZ) {\n if (viewportFitsInCache(camera)) {\n presentStatic(camera)\n return\n }\n if (canExtend(camera)) {\n extendCache(camera)\n presentStatic(camera)\n return\n }\n }\n renderFullCache(camera)\n presentStatic(camera)\n }\n\n /**\n * Tries the cheap canvas paths in order; returns true if anything was\n * painted. Order: getSnapshot → drawPlaceholder → renderCanvas.\n * Async snapshot returns are treated as \"no snapshot ready\"; consumer's\n * own caching is responsible for the eventual blit.\n */\n const paintCustomCanvasFallback = (\n ctx: CanvasRenderingContext2D,\n node: Node,\n def: NodeTypeDef,\n drawScale: number,\n env: RenderEnv,\n ): boolean => {\n void drawScale\n if (def.getSnapshot) {\n const snap = def.getSnapshot(node, {\n width: node.w,\n height: node.h,\n dpr: staticSurface.dpr,\n })\n // Phase 5 ships sync-only snapshot handling; promise-returning\n // authors get a no-op until v2 adds the cache layer.\n if (snap && !(snap instanceof Promise)) {\n drawWithNodeTransform(ctx, node, () => {\n ctx.drawImage(snap as CanvasImageSource, 0, 0, node.w, node.h)\n })\n return true\n }\n }\n if (def.drawPlaceholder) {\n // Consumer-supplied drawer — wrap in save/restore so any state\n // it leaves behind doesn't bleed into the next node.\n drawWithNodeTransform(ctx, node, () => {\n ctx.save()\n def.drawPlaceholder!(ctx, node, env)\n ctx.restore()\n })\n return true\n }\n if (def.renderCanvas) {\n drawWithNodeTransform(ctx, node, () => {\n ctx.save()\n def.renderCanvas!(ctx, node, env)\n ctx.restore()\n })\n return true\n }\n return false\n }\n\n /**\n * Paints node.content (lite markdown) via the bitmap cache. Caller is\n * already inside drawWithNodeTransform (origin at node's top-left,\n * rotation applied). No-op when content is empty.\n */\n const paintNodeContent = (ctx: CanvasRenderingContext2D, node: Node, env: RenderEnv): void => {\n const content = node.content\n if (!content || !content.trim()) return\n const style = node.style\n const fontSize = style?.fontSize ?? 'M'\n // Readability skip — text below ~3px on-screen is unreadable noise.\n // Bypasses cache lookup (FNV walk + concat) and the drawImage blit.\n if (FONT_SIZE_MAP[fontSize] * env.zoom < MIN_READABLE_FONT_PX) return\n // Layout the text within the shape's visible interior (capsule's\n // rect body excluding the accent circle, diamond's inscribed rect,\n // ellipse's inscribed rect, thought-cloud's body below the dome,\n // tag's body past the notch). Rect/text fall through to full bbox.\n const bounds = contentBounds(node)\n if (bounds.w <= 0 || bounds.h <= 0) return\n const bitmap = getOrRenderTextBitmap({\n id: node.id,\n text: content,\n width: bounds.w,\n height: bounds.h,\n zoom: env.zoom,\n dpr: staticSurface.dpr,\n isMoving: env.isMoving,\n align: style?.textAlign ?? 'center',\n fontFamily: style?.fontFamily ?? 'handwriting',\n fontSize,\n textStyle: style?.textStyle ?? 'normal',\n textColor: style?.textColor ?? DEFAULT_TEXT_COLOR,\n highlightColor: DEFAULT_HIGHLIGHT_COLOR,\n })\n if (!bitmap) return\n ctx.drawImage(bitmap.canvas, bounds.x, bounds.y, bounds.w, bounds.h)\n }\n\n /**\n * Paints \"Type to edit…\" centered in a text-typed node that has no\n * content. Hidden during edit (the textarea covers the rect).\n */\n const paintEmptyTextPlaceholder = (\n ctx: CanvasRenderingContext2D,\n node: Node,\n zoom: number,\n ): void => {\n const fontSize = node.style?.fontSize ?? 'M'\n const fontPx = FONT_SIZE_MAP[fontSize]\n if (fontPx * zoom < MIN_READABLE_FONT_PX) return\n ctx.save()\n ctx.fillStyle = '#94a3b8'\n ctx.textBaseline = 'middle'\n ctx.textAlign = 'center'\n ctx.font = `italic ${fontPx}px ${node.style?.fontFamily ?? 'sans-serif'}`\n ctx.fillText('Type to edit…', node.w / 2, node.h / 2)\n ctx.restore()\n }\n\n const setsEqual = (a: ReadonlySet<NodeId>, b: ReadonlySet<NodeId>): boolean => {\n if (a.size !== b.size) return false\n for (const v of a) if (!b.has(v)) return false\n return true\n }\n\n /**\n * Union of edge ids incident to any of the given node ids. Used by the\n * \"exclude from static during drag\" rule (§4.2). O(node count) via the\n * store's internal incidentEdges map.\n */\n const incidentEdgeIds = (nodeIds: ReadonlySet<NodeId>): ReadonlySet<EdgeId> => {\n const result = new Set<EdgeId>()\n for (const nid of nodeIds) {\n for (const eid of store.getIncidentEdges(nid)) result.add(eid)\n }\n return result\n }\n\n /**\n * Helper: paint a single edge using its cached geometry from the store.\n * `roughEnabled` mirrors the same gate used for nodes — caller threads it in.\n */\n const paintOneEdge = (\n ctx: CanvasRenderingContext2D,\n edge: Edge,\n scale: number,\n roughEnabled: boolean,\n zoom: number,\n isMoving: boolean,\n ): void => {\n const geom = store.getEdgeGeometry(edge.id)\n if (!geom) return\n const sourceNode = geom.sourceNodeId ? (store.getNode(geom.sourceNodeId) ?? null) : null\n const targetNode = geom.targetNodeId ? (store.getNode(geom.targetNodeId) ?? null) : null\n drawEdge(ctx, edge, geom, sourceNode, targetNode, scale, theme, {\n roughEnabled,\n zoom,\n dpr: staticSurface.dpr,\n isMoving,\n })\n }\n\n const getSortedEdgeIds = (): EdgeId[] => {\n if (sortedEdgeIdsCache) return sortedEdgeIdsCache\n const all = store.getAllEdges()\n sortedEdgeIdsCache = all\n .slice()\n .sort((a, b) => a.z - b.z || (a.id < b.id ? -1 : 1))\n .map(e => e.id)\n return sortedEdgeIdsCache\n }\n\n const visibleEdges = (viewport: WorldRect): Edge[] => {\n const ids = store.querySpatial({ rect: viewport }).edges as EdgeId[]\n if (ids.length === 0) return []\n const visibleSet = new Set<EdgeId>(ids)\n const sorted = getSortedEdgeIds()\n const result: Edge[] = []\n for (const id of sorted) {\n if (!visibleSet.has(id)) continue\n const e = store.getEdge(id)\n if (e) result.push(e)\n }\n return result\n }\n\n const paintInteractive = (): void => {\n const camera = store.getCamera()\n clearSurface(interactiveSurface)\n applyCameraTransform(interactiveSurface, camera)\n const scale = camera.z * interactiveSurface.dpr\n const interaction = store.getInteractionState()\n const ctx = interactiveSurface.ctx\n\n // 1. Dragged / resizing nodes at their uncommitted positions.\n if (interaction.mode === 'dragging' || interaction.mode === 'resizing') {\n const inDragMap = mapDragPositions(interaction)\n const dragEnv: RenderEnv = {\n zoom: camera.z,\n isMoving: true,\n isSelected: true,\n isHovered: false,\n isEditing: false,\n theme: token => (theme ? theme(token) : undefined),\n }\n // Mirror the static-surface rough gate so the dragged node keeps\n // its hand-drawn look on small drags. Pan/zoom can't be active in\n // this branch (we're inside dragging/resizing), so the only knobs\n // are the moving-count cap and the zoom floor.\n const dragRoughEnabled =\n inDragMap.size <= ROUGH_MAX_MOVING_NODES && camera.z >= ROUGH_MIN_ZOOM\n for (const node of inDragMap.values()) {\n if (\n !isDrawablePrimitive(node.type) &&\n node.type !== 'text' &&\n node.type !== 'image' &&\n node.type !== 'icon' &&\n node.type !== 'frame'\n )\n continue\n drawWithNodeTransform(ctx, node, () => {\n if (node.type === 'frame') {\n paintFrameNode(ctx, node, scale, theme)\n return\n }\n if (node.type === 'image') {\n paintImageNode(ctx, node, assetCache, theme)\n return\n }\n if (node.type === 'icon') {\n paintIconNode(ctx, node, assetCache, scale, theme)\n return\n }\n if (isDrawablePrimitive(node.type)) {\n const useRough = dragRoughEnabled && (node.style?.roughness ?? 0) > 0\n const roughReady = useRough ? getRoughCanvasCtor() !== null : false\n if (useRough && roughReady) {\n if (isCompositePrimitive(node.type)) {\n drawCompositeRough(ctx, node, camera.z, theme)\n } else {\n ctx.translate(ROUGH_FILL_MISREGISTER_X, ROUGH_FILL_MISREGISTER_Y)\n drawShape(ctx, node, scale, theme, { skipStroke: true })\n ctx.translate(-ROUGH_FILL_MISREGISTER_X, -ROUGH_FILL_MISREGISTER_Y)\n drawRoughShape(ctx, node, camera.z, theme)\n }\n } else {\n drawShape(ctx, node, scale, theme)\n }\n }\n paintNodeContent(ctx, node, dragEnv)\n })\n }\n\n // Edges incident to a dragged node redraw with the offset applied.\n // We wrap getNode so endpoint projection sees the dragged position.\n const wrapGetNode = (id: NodeId): Node | undefined => inDragMap.get(id) ?? store.getNode(id)\n const drawnEdgeIds = new Set<EdgeId>()\n for (const nodeId of inDragMap.keys()) {\n for (const eid of store.getIncidentEdges(nodeId)) {\n if (drawnEdgeIds.has(eid)) continue\n drawnEdgeIds.add(eid)\n const edge = store.getEdge(eid)\n if (!edge) continue\n // Compute geometry directly — bypass the cache so we get the\n // uncommitted positions. Cheap; samples-per-frame is bounded\n // by drag size, not scene size.\n const geom = computeEdgeGeometry(edge, wrapGetNode)\n if (!geom) continue\n const sourceNode = geom.sourceNodeId ? (wrapGetNode(geom.sourceNodeId) ?? null) : null\n const targetNode = geom.targetNodeId ? (wrapGetNode(geom.targetNodeId) ?? null) : null\n drawEdge(ctx, edge, geom, sourceNode, targetNode, scale, theme, {\n zoom: camera.z,\n dpr: interactiveSurface.dpr,\n isMoving: true,\n })\n }\n }\n }\n\n // 1b. Edge being mid-point-dragged. Excluded from the static layer\n // via excludedEdges; painted here with the draft cubic controls.\n // Bypasses the edge-geometry cache (keyed on edge.version, which\n // doesn't bump during the gesture).\n if (interaction.midpointDraft) {\n const { edgeId, control } = interaction.midpointDraft\n const edge = store.getEdge(edgeId)\n if (edge) {\n const draftEdge: Edge = { ...edge, control }\n const geom = computeEdgeGeometry(draftEdge, id => store.getNode(id))\n if (geom) {\n const sourceNode = geom.sourceNodeId ? (store.getNode(geom.sourceNodeId) ?? null) : null\n const targetNode = geom.targetNodeId ? (store.getNode(geom.targetNodeId) ?? null) : null\n drawEdge(ctx, draftEdge, geom, sourceNode, targetNode, scale, theme, {\n zoom: camera.z,\n dpr: interactiveSurface.dpr,\n isMoving: true,\n })\n }\n }\n }\n\n // 2. Selection outlines + handles for selected nodes (uses current /\n // in-progress geometry).\n const selection = store.getSelection()\n const selectedNodeIds: NodeId[] = []\n const selectedEdgeIds: EdgeId[] = []\n for (const id of selection) {\n if (store.getNode(id as NodeId)) selectedNodeIds.push(id as NodeId)\n else if (store.getEdge(id as EdgeId)) selectedEdgeIds.push(id as EdgeId)\n }\n if (selectedNodeIds.length > 0) {\n const inDragMap = mapDragPositions(interaction)\n for (const id of selectedNodeIds) {\n const node = inDragMap.get(id) ?? store.getNode(id)\n if (!node) continue\n drawSelectionOutline(ctx, node, scale, selectionColor)\n }\n // Resize + rotate handles only for non-dragging selection. (During\n // a drag, the handles would jitter with the dragged geometry —\n // Excalidraw hides them mid-drag for the same reason.)\n if (interaction.mode !== 'dragging' && selectedNodeIds.length === 1) {\n const node = inDragMap.get(selectedNodeIds[0]!) ?? store.getNode(selectedNodeIds[0]!)\n if (node) {\n drawResizeHandles(ctx, node, scale, selectionColor)\n drawRotateHandle(ctx, node, scale, camera.z, selectionColor)\n }\n }\n }\n // Edge endpoint handles on selected edges.\n for (const id of selectedEdgeIds) {\n const geom = store.getEdgeGeometry(id)\n if (geom) {\n drawEdgeEndpointHandles(ctx, geom.source, geom.target, scale, selectionColor)\n // Midpoint handle — drag to reshape (Phase 12.6). Only on\n // bezier; polyline / straight don't have a meaningful curve to\n // sculpt with one drag point.\n const edge = store.getEdge(id)\n if (edge && edge.pathStyle === 'bezier') {\n const mid = getPointAndTangentAtArcLength(geom.samples, 0.5).point\n drawEdgeMidpointHandle(ctx, mid, scale, selectionColor)\n }\n }\n }\n\n // 3. Marquee rect.\n if (interaction.mode === 'marqueeing' && interaction.marqueeRect) {\n drawMarquee(ctx, interaction.marqueeRect, scale, selectionColor)\n }\n\n // 3.5 Drag-create preview — dashed outline matching the active\n // shape tool's intended footprint.\n if (interaction.mode === 'creating-shape' && interaction.createDraftRect) {\n drawMarquee(ctx, interaction.createDraftRect, scale, selectionColor)\n }\n\n // 4. Draft edge during creation / reconnection.\n if (\n (interaction.mode === 'creating-edge' || interaction.mode === 'reconnecting-edge') &&\n interaction.draftEdge\n ) {\n const draft: Edge = {\n id: 'draft' as EdgeId,\n source: interaction.draftEdge.source,\n target: interaction.draftEdge.target,\n pathStyle: 'bezier',\n z: 0,\n groups: [],\n style: { strokeColor: selectionColor },\n }\n const geom = computeEdgeGeometry(draft, id => store.getNode(id))\n if (geom) {\n const sNode = geom.sourceNodeId ? (store.getNode(geom.sourceNodeId) ?? null) : null\n const tNode = geom.targetNodeId ? (store.getNode(geom.targetNodeId) ?? null) : null\n drawEdge(ctx, draft, geom, sNode, tNode, scale, theme, {\n zoom: camera.z,\n dpr: interactiveSurface.dpr,\n isMoving: true,\n })\n }\n }\n }\n\n const mapDragPositions = (interaction: InteractionState): Map<NodeId, Node> => {\n const m = new Map<NodeId, Node>()\n if (interaction.mode !== 'dragging' && interaction.mode !== 'resizing') return m\n for (const orig of interaction.dragOriginals) {\n const live = store.getNode(orig.id)\n if (!live) continue\n if (interaction.mode === 'dragging') {\n m.set(orig.id, {\n ...live,\n x: orig.x + interaction.dragDelta.x,\n y: orig.y + interaction.dragDelta.y,\n })\n } else {\n // Resize: the store still holds the original geometry until\n // pointer-up. Overlay the in-progress geometry from resizeDraft\n // so the interactive layer (and incident-edge re-routing\n // through this same map) paints the live shape.\n const d = interaction.resizeDraft\n if (d) {\n m.set(orig.id, { ...live, x: d.x, y: d.y, w: d.w, h: d.h, angle: d.angle })\n } else {\n m.set(orig.id, live)\n }\n }\n }\n return m\n }\n\n const getSortedNodeIds = (): NodeId[] => {\n if (sortedNodeIdsCache) return sortedNodeIdsCache\n const all = store.getAllNodes()\n sortedNodeIdsCache = all\n .slice()\n .sort((a, b) => a.z - b.z || (a.id < b.id ? -1 : 1))\n .map(n => n.id)\n return sortedNodeIdsCache\n }\n\n const visibleNodes = (camera: CameraState, viewport: WorldRect): Node[] => {\n const ids = store.querySpatial({ rect: viewport }).nodes as NodeId[]\n if (ids.length === 0) return []\n // Build a Set of broad-phase-visible ids (the spatial query is\n // bucket-based, so this is a superset of the true visible set).\n const visibleSet = new Set<NodeId>(ids)\n // Walk the cached sorted list in order and emit those in the\n // visible set after the exact-AABB intersection check. No\n // per-frame Array.sort.\n const sorted = getSortedNodeIds()\n const result: Node[] = []\n const minWorldSize = MIN_ON_SCREEN_SIZE_PX / camera.z\n for (const id of sorted) {\n if (!visibleSet.has(id)) continue\n const n = store.getNode(id)\n if (!n) continue\n if (n.w < minWorldSize && n.h < minWorldSize) continue\n if (intersectsViewport(n, viewport)) result.push(n)\n }\n return result\n }\n\n const loop: FrameLoop = createFrameLoop({ draw: drawFrame })\n\n const onStoreChange = (): void => {\n // Any commit may have added / removed / re-z-ordered an entity,\n // so the sorted caches must rebuild on next paint. Camera /\n // selection / interaction events do NOT invalidate (z-order is\n // independent of viewport + selection state).\n invalidateSortedCaches()\n staticDirty = true\n cacheStale = true\n interactiveDirty = true\n loop.requestFrame()\n }\n // Camera is the one static-dirtying event that does NOT stale the\n // cache content: a pure pan reuses the cache (blit-only), and a zoom\n // is caught by the `z !== cacheCamZ` check in `paintStatic`.\n const onCameraChange = (): void => {\n staticDirty = true\n interactiveDirty = true\n loop.requestFrame()\n }\n const onSelectionChange = (): void => {\n interactiveDirty = true\n loop.requestFrame()\n }\n const onInteractionChange = (state: InteractionState): void => {\n interactiveDirty = true\n // Mode transitions that affect what the static surface paints:\n // - dragging/resizing toggle the excluded set\n // - rotating/panning/zooming flip motion-LOD on for layered\n // - idle restores full-quality after any of the above\n // Any of these need a static repaint at the transition boundary\n // so the LOD changes (motion fast-path, rough auto-disable, text\n // bitmap downscale) take effect on the very next frame.\n if (\n state.mode === 'dragging' ||\n state.mode === 'resizing' ||\n state.mode === 'rotating' ||\n state.mode === 'panning' ||\n state.mode === 'zooming' ||\n state.mode === 'idle'\n ) {\n staticDirty = true\n // A mode transition changes the excluded set and/or motion-LOD,\n // so the cache content must be rebuilt. This also guarantees the\n // first frame of a pan does a full render — which is what swaps\n // custom-node React overlays to their canvas fallback.\n cacheStale = true\n }\n loop.requestFrame()\n }\n\n const unsubChange = store.subscribe('change', onStoreChange)\n const unsubCamera = store.subscribe('camera', onCameraChange)\n const unsubSelection = store.subscribe('selection', onSelectionChange)\n const unsubInteraction = store.subscribe('interaction', onInteractionChange)\n // Custom-font load → bitmap cache clears itself; we just need a repaint.\n const unsubFontEpoch = subscribeFontEpoch(() => {\n staticDirty = true\n cacheStale = true\n loop.requestFrame()\n })\n // Math formula compile → math-bearing bitmaps get a new cache key\n // via the math-epoch; repaint to pick up the real glyphs.\n const unsubMathEpoch = subscribeMathEpoch(() => {\n staticDirty = true\n cacheStale = true\n loop.requestFrame()\n })\n\n return {\n start() {\n loop.start()\n staticDirty = true\n cacheStale = true\n interactiveDirty = isInteractive(store.getInteractionState())\n loop.requestFrame()\n },\n stop() {\n loop.stop()\n },\n invalidate() {\n staticDirty = true\n cacheStale = true\n interactiveDirty = true\n loop.requestFrame()\n },\n setSize(cssW, cssH) {\n const a = sizeSurface(staticSurface, cssW, cssH, maxDpr)\n const b = sizeSurface(interactiveSurface, cssW, cssH, maxDpr)\n if (a || b) {\n staticDirty = true\n cacheStale = true\n interactiveDirty = true\n loop.requestFrame()\n }\n },\n setBackground(bg) {\n background = bg\n staticDirty = true\n cacheStale = true\n loop.requestFrame()\n },\n setSelectionColor(color) {\n selectionColor = color\n // Selection chrome lives on the interactive surface; static doesn't\n // need to repaint. The draft-edge stroke is also interactive-only.\n interactiveDirty = true\n loop.requestFrame()\n },\n setHideFrames(hidden) {\n hideFrames = hidden\n staticDirty = true\n cacheStale = true\n loop.requestFrame()\n },\n stats: () => loop.stats(),\n lastDrawCount: () => lastDrawn,\n getOverlaySet: () => [...overlaySet],\n getAssetCache: () => assetCache,\n dispose() {\n loop.stop()\n unsubChange()\n unsubCamera()\n unsubSelection()\n unsubInteraction()\n unsubFontEpoch()\n unsubMathEpoch()\n assetCache.dispose()\n if (cacheSurface) {\n // Drop the backing store so the GPU buffer is freed promptly.\n cacheSurface.canvas.width = 0\n cacheSurface.canvas.height = 0\n cacheSurface = null\n }\n },\n }\n}\n\n/**\n * Narrow-phase check: does the (rotation-aware) node AABB intersect the viewport?\n */\nconst intersectsViewport = (\n node: Node,\n viewport: { x: number; y: number; w: number; h: number },\n) => {\n const a = nodeAABB(node)\n return (\n a.x < viewport.x + viewport.w &&\n a.x + a.w > viewport.x &&\n a.y < viewport.y + viewport.h &&\n a.y + a.h > viewport.y\n )\n}\n","import { nodeAABB } from '../spatial'\nimport type { CanvasStore } from '../store'\nimport type { CameraState, WorldRect } from '../types'\n\n/**\n * Minimap rendering — see IMPROVEMENTS.md (UX) and the React layer's\n * `<Minimap />` component.\n *\n * Splits into two paths consumers can compose independently:\n *\n * - `renderMinimapContent(ctx, store, ...)` — paints every node as a\n * plain `fillRect` at its scaled AABB. Edge bodies are skipped\n * (not useful at this scale and would multiply cost). Run on\n * committed scene change ONLY; cache the result as an\n * OffscreenCanvas/HTMLCanvasElement and blit.\n *\n * - `drawMinimapViewport(ctx, camera, sceneBounds, mapSize)` — paints\n * a tiny rectangle showing the visible viewport. Cheap; run on\n * every camera change.\n *\n * Cost model:\n * - content render: O(N) — only fires on committed mutations.\n * - viewport overlay: O(1) per frame.\n *\n * Hard cap (`maxNodes`) — above which the content render skips\n * entirely and the consumer is expected to show a \"minimap disabled\"\n * placeholder. Default 5000.\n */\n\nexport const DEFAULT_MINIMAP_MAX_NODES = 5000\n\nexport type MinimapContentOptions = {\n /** Hard upper bound on node count; above this, content is skipped. */\n maxNodes?: number\n /** Override fill color for nodes (used when node has no style.backgroundColor). */\n defaultNodeColor?: string\n /** Background color drawn first inside the minimap rect. */\n backgroundColor?: string\n}\n\n/**\n * Returns the world-space bounding rect that encloses every visible\n * node, or `null` if the scene is empty. Used to scale the minimap so\n * the entire scene fits inside it.\n */\nexport const sceneBounds = (store: CanvasStore): WorldRect | null => {\n const nodes = store.getAllNodes()\n if (nodes.length === 0) return null\n let minX = Number.POSITIVE_INFINITY\n let minY = Number.POSITIVE_INFINITY\n let maxX = Number.NEGATIVE_INFINITY\n let maxY = Number.NEGATIVE_INFINITY\n for (const n of nodes) {\n if (n.hidden) continue\n // Frames are excluded from minimap content paint; exclude them\n // from the bounds calculation too, otherwise an off-canvas frame\n // would scale the minimap to mostly-empty space.\n if (n.type === 'frame') continue\n const r = nodeAABB(n)\n if (r.x < minX) minX = r.x\n if (r.y < minY) minY = r.y\n if (r.x + r.w > maxX) maxX = r.x + r.w\n if (r.y + r.h > maxY) maxY = r.y + r.h\n }\n if (!Number.isFinite(minX)) return null\n return { x: minX, y: minY, w: maxX - minX, h: maxY - minY }\n}\n\n/**\n * Paints the scene's nodes into the minimap canvas's logical pixel\n * space. Caller has already cleared the target. Returns true on\n * success, false when skipped (empty scene or over the node cap).\n */\nexport const renderMinimapContent = (\n ctx: CanvasRenderingContext2D,\n store: CanvasStore,\n mapWidth: number,\n mapHeight: number,\n opts: MinimapContentOptions = {},\n): boolean => {\n const cap = opts.maxNodes ?? DEFAULT_MINIMAP_MAX_NODES\n const count = store.getNodeCount()\n if (count === 0 || count > cap) return false\n\n const bounds = sceneBounds(store)\n if (!bounds || bounds.w === 0 || bounds.h === 0) return false\n\n // Pad the bounds so shapes near the edges aren't clipped.\n const pad = Math.max(bounds.w, bounds.h) * 0.05\n const bx = bounds.x - pad\n const by = bounds.y - pad\n const bw = bounds.w + pad * 2\n const bh = bounds.h + pad * 2\n const scale = Math.min(mapWidth / bw, mapHeight / bh)\n // Center the scaled content in the map rect.\n const offX = (mapWidth - bw * scale) / 2\n const offY = (mapHeight - bh * scale) / 2\n\n if (opts.backgroundColor) {\n ctx.fillStyle = opts.backgroundColor\n ctx.fillRect(0, 0, mapWidth, mapHeight)\n }\n\n const defaultColor = opts.defaultNodeColor ?? '#94a3b8'\n for (const node of store.getAllNodes()) {\n if (node.hidden) continue\n // Frames are slide chrome, not content — skip them so the minimap\n // shows content density rather than slide boundaries.\n if (node.type === 'frame') continue\n const r = nodeAABB(node)\n const x = offX + (r.x - bx) * scale\n const y = offY + (r.y - by) * scale\n const w = Math.max(1, r.w * scale)\n const h = Math.max(1, r.h * scale)\n ctx.fillStyle = node.style?.backgroundColor ?? defaultColor\n ctx.fillRect(x, y, w, h)\n }\n return true\n}\n\n/**\n * Paints the camera viewport rectangle on top of the cached minimap\n * content. Cheap; consumers call this on every camera tick.\n *\n * `sceneRect` should be the same bounds used by `renderMinimapContent`\n * for the current cache. `viewportWorld` is the visible world rect\n * (caller derives from camera + screen size).\n */\nexport const drawMinimapViewport = (\n ctx: CanvasRenderingContext2D,\n viewportWorld: WorldRect,\n sceneRect: WorldRect,\n mapWidth: number,\n mapHeight: number,\n color = '#3b82f6',\n): void => {\n // Same scaling math as renderMinimapContent — keeps the viewport\n // overlay perfectly registered with the cached content.\n const pad = Math.max(sceneRect.w, sceneRect.h) * 0.05\n const bx = sceneRect.x - pad\n const by = sceneRect.y - pad\n const bw = sceneRect.w + pad * 2\n const bh = sceneRect.h + pad * 2\n const scale = Math.min(mapWidth / bw, mapHeight / bh)\n const offX = (mapWidth - bw * scale) / 2\n const offY = (mapHeight - bh * scale) / 2\n\n const x = offX + (viewportWorld.x - bx) * scale\n const y = offY + (viewportWorld.y - by) * scale\n const w = viewportWorld.w * scale\n const h = viewportWorld.h * scale\n\n ctx.save()\n ctx.strokeStyle = color\n ctx.lineWidth = 1.5\n ctx.strokeRect(x, y, w, h)\n ctx.restore()\n}\n\n/**\n * Inverse mapping for click-to-pan: a screen point inside the minimap\n * rect → the world point it corresponds to. Returns null when the\n * scene is empty (no bounds to scale against).\n */\nexport const minimapScreenToWorld = (\n store: CanvasStore,\n screenX: number,\n screenY: number,\n mapWidth: number,\n mapHeight: number,\n): { x: number; y: number } | null => {\n const bounds = sceneBounds(store)\n if (!bounds || bounds.w === 0 || bounds.h === 0) return null\n const pad = Math.max(bounds.w, bounds.h) * 0.05\n const bx = bounds.x - pad\n const by = bounds.y - pad\n const bw = bounds.w + pad * 2\n const bh = bounds.h + pad * 2\n const scale = Math.min(mapWidth / bw, mapHeight / bh)\n const offX = (mapWidth - bw * scale) / 2\n const offY = (mapHeight - bh * scale) / 2\n return {\n x: (screenX - offX) / scale + bx,\n y: (screenY - offY) / scale + by,\n }\n}\n\n/**\n * World-space viewport rect from the camera + a screen size. Pass to\n * `drawMinimapViewport`. Caller's responsibility to supply the\n * canvas/CSS pixel dimensions.\n */\nexport const worldViewportFromCamera = (\n camera: CameraState,\n screenW: number,\n screenH: number,\n): WorldRect => ({\n x: camera.x,\n y: camera.y,\n w: screenW / camera.z,\n h: screenH / camera.z,\n})\n","/**\n * Node hit testing — see ARCHITECTURE.md §6.9 (parallels edge hit testing\n * structure for phase 4).\n *\n * For axis-aligned nodes: a fast AABB check.\n * For rotated nodes: transform the world point into node-local pre-rotation\n * coords (collapsing the rotation problem to AABB).\n */\nimport type { Node, Vec2, WorldRect } from '../types'\n\n/**\n * Returns true if the world-space point is inside the (possibly rotated) node.\n */\nexport const pointInNode = (point: Vec2, node: Node): boolean => {\n if (node.hidden) return false\n if (node.w <= 0 || node.h <= 0) return false\n\n if (node.angle === 0) {\n return (\n point.x >= node.x &&\n point.x <= node.x + node.w &&\n point.y >= node.y &&\n point.y <= node.y + node.h\n )\n }\n\n const cx = node.x + node.w / 2\n const cy = node.y + node.h / 2\n const cos = Math.cos(-node.angle)\n const sin = Math.sin(-node.angle)\n const dx = point.x - cx\n const dy = point.y - cy\n // localCoord = rotate(point - center, -angle) + (w/2, h/2)\n const localX = dx * cos - dy * sin + node.w / 2\n const localY = dx * sin + dy * cos + node.h / 2\n return localX >= 0 && localX <= node.w && localY >= 0 && localY <= node.h\n}\n\n/**\n * Returns true if the node's rotated rect intersects the given AABB.\n * For axis-aligned nodes this collapses to two AABB ranges; for rotated\n * nodes we test all 4 corners + 4 axis projections (SAT).\n */\nexport const nodeIntersectsRect = (node: Node, rect: WorldRect): boolean => {\n if (node.hidden) return false\n if (node.w <= 0 || node.h <= 0) return false\n\n if (node.angle === 0) {\n return (\n node.x < rect.x + rect.w &&\n node.x + node.w > rect.x &&\n node.y < rect.y + rect.h &&\n node.y + node.h > rect.y\n )\n }\n\n // SAT against the rotated rect — cheap enough that this is fine for marquee.\n const cx = node.x + node.w / 2\n const cy = node.y + node.h / 2\n const cos = Math.cos(node.angle)\n const sin = Math.sin(node.angle)\n const localCorners: Vec2[] = [\n { x: -node.w / 2, y: -node.h / 2 },\n { x: node.w / 2, y: -node.h / 2 },\n { x: node.w / 2, y: node.h / 2 },\n { x: -node.w / 2, y: node.h / 2 },\n ]\n const worldCorners: Vec2[] = localCorners.map(p => ({\n x: cx + p.x * cos - p.y * sin,\n y: cy + p.x * sin + p.y * cos,\n }))\n const rectCorners: Vec2[] = [\n { x: rect.x, y: rect.y },\n { x: rect.x + rect.w, y: rect.y },\n { x: rect.x + rect.w, y: rect.y + rect.h },\n { x: rect.x, y: rect.y + rect.h },\n ]\n const axes: Vec2[] = [\n { x: 1, y: 0 },\n { x: 0, y: 1 },\n { x: cos, y: sin },\n { x: -sin, y: cos },\n ]\n for (const a of axes) {\n let minA = Number.POSITIVE_INFINITY\n let maxA = Number.NEGATIVE_INFINITY\n for (const p of worldCorners) {\n const v = p.x * a.x + p.y * a.y\n if (v < minA) minA = v\n if (v > maxA) maxA = v\n }\n let minB = Number.POSITIVE_INFINITY\n let maxB = Number.NEGATIVE_INFINITY\n for (const p of rectCorners) {\n const v = p.x * a.x + p.y * a.y\n if (v < minB) minB = v\n if (v > maxB) maxB = v\n }\n if (maxA < minB || maxB < minA) return false\n }\n return true\n}\n","/**\n * Edge hit testing — see ARCHITECTURE.md §6.9.\n *\n * Broad-phase via the spatial index; narrow-phase via point-to-polyline\n * distance over the cached samples. Sub-region detection: arrowhead tips\n * and (when selected) endpoint handles are tested before the body.\n */\nimport { getPointAndTangentAtArcLength } from '../edges/arc-length'\nimport { edgeLabelBoundsWorld } from '../edges/draw'\nimport type { CanvasStore, EdgeGeometry } from '../store'\nimport type { Edge, EdgeId, Vec2 } from '../types'\n\n/** Hit-slop in screen pixels for the edge body. */\nexport const EDGE_HIT_SLOP_PX = 8\n/** Hit-slop in screen pixels for endpoint / arrowhead handles. */\nexport const EDGE_HANDLE_SLOP_PX = 12\n/** Hit-slop in screen pixels for the midpoint handle (Phase 12.6). */\nexport const EDGE_MIDPOINT_SLOP_PX = 10\n\nexport type EdgeHit =\n | { kind: 'body'; edgeId: EdgeId; distance: number; arcLength: number }\n | { kind: 'source-handle'; edgeId: EdgeId; distance: number }\n | { kind: 'target-handle'; edgeId: EdgeId; distance: number }\n | { kind: 'midpoint-handle'; edgeId: EdgeId }\n | { kind: 'label'; edgeId: EdgeId }\n\n/**\n * Returns the topmost edge hit by a world point, or null.\n * `selectedEdges` enables endpoint-handle detection (handles only show\n * when the edge is selected).\n */\nexport const hitTestEdge = (\n store: CanvasStore,\n worldPoint: Vec2,\n cameraZ: number,\n selectedEdges: ReadonlySet<EdgeId> = new Set(),\n): EdgeHit | null => {\n const slopWorld = EDGE_HIT_SLOP_PX / cameraZ\n const handleSlopWorld = EDGE_HANDLE_SLOP_PX / cameraZ\n\n // Endpoint handles win over body (interactive-over-background rule).\n // Midpoint handle slots between endpoint handles and the body.\n const midpointSlopWorld = EDGE_MIDPOINT_SLOP_PX / cameraZ\n for (const id of selectedEdges) {\n const geom = store.getEdgeGeometry(id)\n if (!geom) continue\n const dSource = distance(worldPoint, geom.source)\n if (dSource <= handleSlopWorld) {\n return { kind: 'source-handle', edgeId: id, distance: dSource }\n }\n const dTarget = distance(worldPoint, geom.target)\n if (dTarget <= handleSlopWorld) {\n return { kind: 'target-handle', edgeId: id, distance: dTarget }\n }\n const mid = getPointAndTangentAtArcLength(geom.samples, 0.5).point\n if (distance(worldPoint, mid) <= midpointSlopWorld) {\n return { kind: 'midpoint-handle', edgeId: id }\n }\n }\n\n // Body hits — broad-phase via spatial index, narrow via polyline.\n const queryRect = {\n x: worldPoint.x - slopWorld,\n y: worldPoint.y - slopWorld,\n w: slopWorld * 2,\n h: slopWorld * 2,\n }\n const candidates = store.querySpatial({ rect: queryRect }).edges\n\n // Label hits — checked before body so a click on a label doesn't\n // accidentally select the edge body underneath. Iterates candidates\n // again because labels can extend slightly beyond the body slop.\n for (const id of candidates) {\n const edge = store.getEdge(id)\n if (!edge || edge.hidden || !edge.content || !edge.content.trim()) continue\n const geom = store.getEdgeGeometry(id)\n if (!geom) continue\n const bounds = edgeLabelBoundsWorld(edge, geom)\n if (!bounds) continue\n if (\n worldPoint.x >= bounds.x &&\n worldPoint.x <= bounds.x + bounds.w &&\n worldPoint.y >= bounds.y &&\n worldPoint.y <= bounds.y + bounds.h\n ) {\n return { kind: 'label', edgeId: id }\n }\n }\n\n type BodyHit = Extract<EdgeHit, { kind: 'body' }>\n let best: { hit: BodyHit; z: number; edge: Edge } | null = null\n for (const id of candidates) {\n const edge = store.getEdge(id)\n if (!edge || edge.hidden) continue\n const geom = store.getEdgeGeometry(id)\n if (!geom) continue\n const result = nearestSampleDistance(worldPoint, geom)\n if (result.distance > slopWorld) continue\n if (\n !best ||\n edge.z > best.edge.z ||\n (edge.z === best.edge.z && result.distance < best.hit.distance)\n ) {\n best = {\n hit: { kind: 'body', edgeId: id, distance: result.distance, arcLength: result.arcLength },\n z: edge.z,\n edge,\n }\n }\n }\n\n return best ? best.hit : null\n}\n\n/**\n * Walks the polyline samples and finds the nearest segment to the point.\n * Returns the perpendicular distance + the arc-length parameter (0..1)\n * of the foot of perpendicular along the polyline. Callers use arcLength\n * to insert midpoints or anchor labels.\n */\nconst nearestSampleDistance = (\n p: Vec2,\n geom: EdgeGeometry,\n): { distance: number; arcLength: number } => {\n const samples = geom.samples\n if (samples.length < 2) return { distance: Number.POSITIVE_INFINITY, arcLength: 0 }\n\n const segmentLengths: number[] = []\n let totalLen = 0\n for (let i = 1; i < samples.length; i++) {\n const a = samples[i - 1]!\n const b = samples[i]!\n const len = Math.hypot(b.x - a.x, b.y - a.y)\n segmentLengths.push(len)\n totalLen += len\n }\n if (totalLen === 0) return { distance: distance(p, samples[0]!), arcLength: 0 }\n\n let bestD2 = Number.POSITIVE_INFINITY\n let bestArc = 0\n let cumLen = 0\n for (let i = 1; i < samples.length; i++) {\n const a = samples[i - 1]!\n const b = samples[i]!\n const segLen = segmentLengths[i - 1]!\n const { d2, t } = pointSegmentDistanceSq(p, a, b)\n if (d2 < bestD2) {\n bestD2 = d2\n bestArc = (cumLen + t * segLen) / totalLen\n }\n cumLen += segLen\n }\n return { distance: Math.sqrt(bestD2), arcLength: bestArc }\n}\n\nconst distance = (a: Vec2, b: Vec2): number => Math.hypot(b.x - a.x, b.y - a.y)\n\n/**\n * Squared distance from point p to segment ab, plus parametric t along ab.\n * Squared to avoid the sqrt in the inner loop.\n */\nconst pointSegmentDistanceSq = (p: Vec2, a: Vec2, b: Vec2): { d2: number; t: number } => {\n const dx = b.x - a.x\n const dy = b.y - a.y\n const len2 = dx * dx + dy * dy\n if (len2 === 0) {\n const ex = p.x - a.x\n const ey = p.y - a.y\n return { d2: ex * ex + ey * ey, t: 0 }\n }\n let t = ((p.x - a.x) * dx + (p.y - a.y) * dy) / len2\n t = Math.max(0, Math.min(1, t))\n const fx = a.x + dx * t\n const fy = a.y + dy * t\n const ex = p.x - fx\n const ey = p.y - fy\n return { d2: ex * ex + ey * ey, t }\n}\n","/**\n * Higher-level hit queries that combine the spatial index with per-shape\n * narrow-phase tests. Returns the topmost hit by z, or all hits inside a\n * marquee rect.\n */\nimport type { CanvasStore } from '../store'\nimport type { EdgeId, Node, NodeId, Vec2, WorldRect } from '../types'\nimport { type EdgeHit, hitTestEdge } from './edge'\nimport { type ResizeHandle, hitTestHandles, hitTestRotateHandle } from './handle'\nimport { nodeIntersectsRect, pointInNode } from './node'\n\nexport type NodeHit =\n | { kind: 'body'; nodeId: NodeId }\n | { kind: 'resize-handle'; nodeId: NodeId; handle: ResizeHandle }\n | { kind: 'rotate-handle'; nodeId: NodeId }\n\n/** A hit covers either a node or an edge sub-region. */\nexport type Hit = NodeHit | EdgeHit\n\n/**\n * Returns the topmost node hit by a world-space point, plus the part hit\n * (body or resize handle). Handles are tested before bodies (interactive\n * elements always win over background — see ARCHITECTURE.md §7).\n *\n * If `selectedIds` is provided, only those nodes' handles are considered\n * — handles only display when the node is selected.\n */\nexport const hitTestPoint = (\n store: CanvasStore,\n worldPoint: Vec2,\n cameraZ: number,\n selectedIds: ReadonlySet<NodeId> = new Set(),\n): NodeHit | null => {\n // First try rotation + resize handles on selected nodes (drawn above\n // bodies). Rotate handle sits OUTSIDE the node bounds so it gets\n // priority over neighboring bodies underneath.\n for (const id of selectedIds) {\n const n = store.getNode(id)\n if (!n) continue\n if (hitTestRotateHandle(n, worldPoint, cameraZ)) {\n return { kind: 'rotate-handle', nodeId: id }\n }\n const h = hitTestHandles(n, worldPoint, cameraZ)\n if (h) return { kind: 'resize-handle', nodeId: id, handle: h }\n }\n\n // Then bodies, topmost-z first. Tiebreak on id (lexically greater id\n // is painted later → sits on top → wins the hit) so hit-test matches\n // paint order exactly.\n const candidates = store.querySpatial({ point: worldPoint }).nodes\n let best: Node | null = null\n for (const id of candidates) {\n const n = store.getNode(id)\n if (!n) continue\n if (!pointInNode(worldPoint, n)) continue\n if (!best || n.z > best.z || (n.z === best.z && n.id > best.id)) {\n best = n\n }\n }\n return best ? { kind: 'body', nodeId: best.id } : null\n}\n\n/**\n * Combined node + edge hit testing. Order: node handles > edge endpoint\n * handles > visually-topmost body (node or edge, compared by z).\n *\n * For bodies, the rule is paint-order: whichever of (node body, edge\n * body) has the higher z wins, with ties going to edges (edges paint\n * over nodes by convention). This lets users click an edge that runs\n * visually over a large background-style node — the 8px polyline slop\n * keeps the edge's hit zone narrow, so clicks far from the polyline\n * still land on the node underneath.\n */\nexport const hitTestAny = (\n store: CanvasStore,\n worldPoint: Vec2,\n cameraZ: number,\n selectedNodes: ReadonlySet<NodeId> = new Set(),\n selectedEdges: ReadonlySet<EdgeId> = new Set(),\n): Hit | null => {\n // 1. node rotate + resize handles (selected only)\n for (const id of selectedNodes) {\n const n = store.getNode(id)\n if (!n) continue\n if (hitTestRotateHandle(n, worldPoint, cameraZ)) {\n return { kind: 'rotate-handle', nodeId: id }\n }\n const h = hitTestHandles(n, worldPoint, cameraZ)\n if (h) return { kind: 'resize-handle', nodeId: id, handle: h }\n }\n\n // 2. edge handles (selected only) — endpoint reconnect handles and\n // the midpoint reshape handle.\n for (const id of selectedEdges) {\n const partial = hitTestEdge(store, worldPoint, cameraZ, new Set([id]))\n if (\n partial &&\n (partial.kind === 'source-handle' ||\n partial.kind === 'target-handle' ||\n partial.kind === 'midpoint-handle')\n ) {\n return partial\n }\n }\n\n // 3. bodies — visually topmost wins. Edge body / label both expose\n // an `edgeId` field; either competes with the node body via z.\n const nodeHit = hitTestPoint(store, worldPoint, cameraZ, selectedNodes)\n const edgeHit = hitTestEdge(store, worldPoint, cameraZ)\n if (nodeHit && edgeHit && 'edgeId' in edgeHit) {\n const nodeZ = store.getNode(nodeHit.nodeId)?.z ?? 0\n const edgeZ = store.getEdge(edgeHit.edgeId)?.z ?? 0\n return edgeZ >= nodeZ ? edgeHit : nodeHit\n }\n return nodeHit ?? edgeHit\n}\n\n/**\n * Returns ids of all nodes whose (rotated) rect intersects the given rect.\n * Used for marquee selection.\n */\nexport const marqueeNodes = (store: CanvasStore, rect: WorldRect): NodeId[] => {\n const candidates = store.querySpatial({ rect }).nodes\n const result: NodeId[] = []\n for (const id of candidates) {\n const n = store.getNode(id)\n if (!n) continue\n if (nodeIntersectsRect(n, rect)) result.push(id)\n }\n return result\n}\n","import type { CanvasStore } from '../store'\nimport { SCHEMA_VERSION, asEdgeId, asNodeId, isAttached } from '../types'\nimport type { Edge, EdgeEnd, EdgeId, Node, NodeId, Vec2 } from '../types'\n\n/**\n * Clipboard serialization — see ARCHITECTURE.md §13 (copy/paste).\n *\n * Captures the selected nodes plus the edges *between* them (edges\n * crossing the selection are dropped — same rule as tldraw/excalidraw).\n * Pure functions; no clipboard-API I/O. The store wraps these with\n * `navigator.clipboard.{write,read}` calls.\n */\n\nexport type SerializedClipboard = {\n /** Schema version stamped at copy time. */\n v: number\n /** Source clientId — diagnostic only; not used for paste. */\n clientId: string\n /** Tagged so we can tell our payload apart from arbitrary JSON. */\n kind: 'canvas-harness/clipboard'\n nodes: Node[]\n edges: Edge[]\n}\n\n/**\n * Builds a clipboard payload from the store's current selection. Pure\n * — no I/O, no clipboard API. Useful for programmatic copy-paste\n * (snapshots, AI-driven duplication, drag-from-sidebar, ...).\n *\n * Edges crossing the selection boundary (only one endpoint in the\n * selection) are dropped. Edges with `worldPoint` endpoints are kept.\n *\n * @example\n * const clip = serializeSelection(store)\n * localStorage.setItem('clipboard', JSON.stringify(clip))\n */\nexport const serializeSelection = (store: CanvasStore): SerializedClipboard => {\n const selectedIds = store.getSelection()\n const selectedNodeIds = new Set<NodeId>()\n for (const id of selectedIds) {\n if (store.getNode(id as NodeId)) selectedNodeIds.add(id as NodeId)\n }\n const nodes: Node[] = []\n for (const id of selectedNodeIds) {\n const n = store.getNode(id)\n if (n) nodes.push(n)\n }\n // Edges: include if either both endpoints are in the selection (or\n // free-floating). Drop edges that cross the selection boundary.\n const edges: Edge[] = []\n for (const id of selectedIds) {\n const e = store.getEdge(id as EdgeId)\n if (e && bothEndsInsideSelection(e, selectedNodeIds)) edges.push(e)\n }\n // Also include any edges *between* selected nodes, even if not in the\n // selection itself — matches user expectation: \"copy this cluster\".\n for (const e of store.getAllEdges()) {\n if (edges.includes(e)) continue\n if (bothEndsInsideSelection(e, selectedNodeIds)) edges.push(e)\n }\n return {\n v: SCHEMA_VERSION,\n clientId: store.clientId,\n kind: 'canvas-harness/clipboard',\n nodes,\n edges,\n }\n}\n\nconst bothEndsInsideSelection = (edge: Edge, ids: ReadonlySet<NodeId>): boolean => {\n return endInside(edge.source, ids) && endInside(edge.target, ids)\n}\nconst endInside = (end: EdgeEnd, ids: ReadonlySet<NodeId>): boolean => {\n if (!isAttached(end)) return true // free-floating endpoint paste-safe\n return ids.has(end.nodeId)\n}\n\nexport type DeserializeOptions = {\n /**\n * Relative world-space offset added to every pasted node's `x/y`\n * (and to free-floating edge endpoints). Takes precedence over\n * `at` when both are passed. Default `(20, 20)` when neither is\n * given.\n */\n offset?: Vec2\n /**\n * Absolute world-space target — the *center* of the pasted bbox\n * lands here. Used by `paste()` to place the paste at the cursor;\n * pass directly for programmatic absolute placement. Ignored if\n * `offset` is also set.\n */\n at?: Vec2\n /** Override the selection on the store after applying. Default true. */\n select?: boolean\n}\n\n/**\n * Bounding-box center of a clip's node rects (pre-offset). Used to\n * translate an absolute `at` target into the per-node offset that\n * lands the paste's visual center on that point.\n */\nconst clipBboxCenter = (nodes: Node[]): Vec2 => {\n if (nodes.length === 0) return { x: 0, y: 0 }\n let minX = Number.POSITIVE_INFINITY\n let minY = Number.POSITIVE_INFINITY\n let maxX = Number.NEGATIVE_INFINITY\n let maxY = Number.NEGATIVE_INFINITY\n for (const n of nodes) {\n if (n.x < minX) minX = n.x\n if (n.y < minY) minY = n.y\n if (n.x + n.w > maxX) maxX = n.x + n.w\n if (n.y + n.h > maxY) maxY = n.y + n.h\n }\n return { x: (minX + maxX) / 2, y: (minY + maxY) / 2 }\n}\n\n/**\n * Applies a clipboard payload to the store. New ids are minted; edge\n * endpoints are rewired; the resulting nodes + edges become the new\n * selection by default. Positioning precedence:\n *\n * 1. `opts.offset` (relative) — used as-is.\n * 2. `opts.at` (absolute) — offset computed so the clip's bbox\n * center lands on this point.\n * 3. Default — relative `(20, 20)` offset.\n *\n * Free-floating edge endpoints (`{ worldPoint }`) also receive the\n * offset so an edge with an unattached end stays connected to the\n * surrounding nodes after the paste.\n *\n * One `store.batch` — one undo step.\n *\n * @example\n * // Restore from localStorage:\n * const clip = JSON.parse(localStorage.getItem('clipboard')!)\n * if (isCanvasHarnessClipboard(clip)) deserializeClipboard(store, clip)\n */\nexport const deserializeClipboard = (\n store: CanvasStore,\n clip: SerializedClipboard,\n opts: DeserializeOptions = {},\n): NodeId[] => {\n let offset: Vec2\n if (opts.offset) {\n offset = opts.offset\n } else if (opts.at && clip.nodes.length > 0) {\n const center = clipBboxCenter(clip.nodes)\n offset = { x: opts.at.x - center.x, y: opts.at.y - center.y }\n } else {\n offset = { x: 20, y: 20 }\n }\n const select = opts.select ?? true\n\n // Old → new id maps.\n const nodeMap = new Map<NodeId, NodeId>()\n const edgeMap = new Map<EdgeId, EdgeId>()\n for (const n of clip.nodes) nodeMap.set(n.id, asNodeId(store.generateId()))\n for (const e of clip.edges) edgeMap.set(e.id, asEdgeId(store.generateId()))\n\n const remappedNodes: Node[] = clip.nodes.map(n => ({\n ...n,\n id: nodeMap.get(n.id)!,\n x: n.x + offset.x,\n y: n.y + offset.y,\n }))\n const remapEnd = (end: EdgeEnd): EdgeEnd => {\n if (!isAttached(end)) {\n // Free-floating endpoint — keep it visually attached to the\n // pasted neighbourhood by applying the same offset the nodes\n // got. Without this, the edge end stays at the original world\n // point and the connection visually stretches.\n return { worldPoint: { x: end.worldPoint.x + offset.x, y: end.worldPoint.y + offset.y } }\n }\n const newId = nodeMap.get(end.nodeId)\n return newId ? { nodeId: newId, localOffset: end.localOffset } : end\n }\n const remappedEdges: Edge[] = clip.edges.map(e => ({\n ...e,\n id: edgeMap.get(e.id)!,\n source: remapEnd(e.source),\n target: remapEnd(e.target),\n }))\n\n store.batch(() => {\n for (const n of remappedNodes) store.addNode(n)\n for (const e of remappedEdges) store.addEdge(e)\n })\n\n const ids = remappedNodes.map(n => n.id)\n if (select) store.setSelection([...ids, ...remappedEdges.map(e => e.id)])\n return ids\n}\n\n/**\n * Type guard — verifies a parsed JSON blob is a clipboard payload from\n * this library, not arbitrary JSON pasted from elsewhere.\n */\nexport const isCanvasHarnessClipboard = (raw: unknown): raw is SerializedClipboard => {\n if (!raw || typeof raw !== 'object') return false\n const r = raw as Record<string, unknown>\n return r.kind === 'canvas-harness/clipboard' && Array.isArray(r.nodes) && Array.isArray(r.edges)\n}\n","import type { CanvasStore } from '../store'\nimport type { EdgeId, NodeId } from '../types'\nimport {\n type DeserializeOptions,\n type SerializedClipboard,\n deserializeClipboard,\n isCanvasHarnessClipboard,\n serializeSelection,\n} from './serialize'\n\nexport type {\n DeserializeOptions,\n SerializedClipboard,\n} from './serialize'\nexport { deserializeClipboard, isCanvasHarnessClipboard, serializeSelection } from './serialize'\n\nconst MIME_NATIVE = 'application/x-canvas-harness+json'\nconst MIME_TEXT = 'text/plain'\n\n/**\n * Copies the current selection to the system clipboard. Writes both a\n * native MIME (`application/x-canvas-harness+json`) and a `text/plain`\n * fallback (concatenated node contents) so paste works in non-canvas\n * destinations too.\n *\n * The `<Canvas>` component already wires this to Cmd/Ctrl+C — call\n * directly only if you're building a custom copy button.\n *\n * @example\n * <button onClick={() => copy(store)}>Copy</button>\n */\nexport const copy = async (store: CanvasStore): Promise<SerializedClipboard> => {\n const clip = serializeSelection(store)\n await writeClipboard(clip)\n return clip\n}\n\n/**\n * Copy + remove the selection in one undoable batch. Same as\n * Cmd/Ctrl+X.\n *\n * @example\n * <button onClick={() => cut(store)}>Cut</button>\n */\nexport const cut = async (store: CanvasStore): Promise<SerializedClipboard> => {\n const clip = await copy(store)\n store.batch(() => {\n for (const n of clip.nodes) store.removeNode(n.id)\n for (const e of clip.edges) store.removeEdge(e.id)\n })\n return clip\n}\n\n/**\n * Paste from the system clipboard (or a supplied payload). Every node\n * + edge gets a fresh id; edge endpoints rewire to the new ids; the\n * resulting nodes + edges become the new selection. Wrapped in one\n * undoable batch.\n *\n * Positioning, in precedence order:\n * 1. `opts.offset` — relative offset, used as-is.\n * 2. `opts.at` — absolute target; the paste's bbox center lands here.\n * 3. The store's current cursor (`interactionState.pointer`) — the\n * paste lands centered under the cursor. This is the default\n * `paste(store)` behavior on a Cmd+V keybind.\n * 4. Fallback `(20, 20)` relative offset when nothing else is known\n * (e.g. fresh session with no pointermove yet).\n *\n * Returns the new node ids on success, or `null` if the clipboard\n * didn't contain a canvas-harness payload.\n *\n * @example\n * <button onClick={() => paste(store)}>Paste</button>\n *\n * @example\n * // Programmatic paste at a specific world point:\n * paste(store, savedClip, { at: { x: 300, y: 200 }, select: false })\n */\nexport const paste = async (\n store: CanvasStore,\n payload?: SerializedClipboard,\n opts?: DeserializeOptions,\n): Promise<(NodeId | EdgeId)[] | null> => {\n const clip = payload ?? (await readClipboard())\n if (!clip) return null\n // Cursor-as-default: when the caller didn't specify positioning,\n // and the store has tracked the pointer at least once, paste at\n // the cursor's world position. deserializeClipboard handles the\n // bbox-center math.\n let effective = opts\n if (!opts?.offset && !opts?.at) {\n const pointer = store.getInteractionState().pointer\n if (pointer) {\n effective = { ...opts, at: { x: pointer.worldX, y: pointer.worldY } }\n }\n }\n const ids = deserializeClipboard(store, clip, effective)\n return ids\n}\n\nconst writeClipboard = async (clip: SerializedClipboard): Promise<void> => {\n if (typeof navigator === 'undefined' || !navigator.clipboard) return\n const json = JSON.stringify(clip)\n const text = clip.nodes\n .map(n => n.content ?? '')\n .filter(s => s.length > 0)\n .join('\\n')\n // navigator.clipboard.write expects ClipboardItem; not all engines\n // support arbitrary mime types. We dual-write best-effort.\n type ClipboardItemCtor = new (data: Record<string, Blob>) => ClipboardItem\n const W = (globalThis as { ClipboardItem?: ClipboardItemCtor }).ClipboardItem\n if (W && navigator.clipboard.write) {\n try {\n const item = new W({\n [MIME_NATIVE]: new Blob([json], { type: MIME_NATIVE }),\n [MIME_TEXT]: new Blob([text], { type: MIME_TEXT }),\n })\n await navigator.clipboard.write([item])\n return\n } catch {\n // Fall through to text-only writeText.\n }\n }\n if (navigator.clipboard.writeText) await navigator.clipboard.writeText(json)\n}\n\nconst readClipboard = async (): Promise<SerializedClipboard | null> => {\n if (typeof navigator === 'undefined' || !navigator.clipboard) return null\n // Prefer the native MIME via clipboard.read; fall back to readText.\n if (navigator.clipboard.read) {\n try {\n const items = await navigator.clipboard.read()\n for (const item of items) {\n if (item.types.includes(MIME_NATIVE)) {\n const blob = await item.getType(MIME_NATIVE)\n const text = await blob.text()\n const parsed = JSON.parse(text)\n if (isCanvasHarnessClipboard(parsed)) return parsed\n }\n }\n } catch {\n // Fall through to readText.\n }\n }\n if (navigator.clipboard.readText) {\n try {\n const text = await navigator.clipboard.readText()\n if (!text.trim().startsWith('{')) return null\n const parsed = JSON.parse(text)\n if (isCanvasHarnessClipboard(parsed)) return parsed\n } catch {\n return null\n }\n }\n return null\n}\n","import { computeEdgeGeometry } from '../edges'\nimport { drawEdge } from '../edges/draw'\nimport type { AssetCache } from '../render/assets'\nimport { paintIconNode, paintImageNode } from '../render/assets'\nimport { drawShape, isDrawablePrimitive } from '../render/shapes'\nimport type { ThemeResolver } from '../render/shapes'\nimport { drawWithNodeTransform } from '../render/transform'\nimport { nodeAABB } from '../spatial'\nimport type { CanvasStore } from '../store'\nimport {\n DEFAULT_HIGHLIGHT_COLOR,\n DEFAULT_TEXT_COLOR,\n FONT_SIZE_MAP,\n getOrRenderTextBitmap,\n} from '../text'\nimport type { Edge, Node, NodeId } from '../types'\n\n/**\n * PNG export — see ARCHITECTURE.md §13. Paints the requested set of\n * nodes + edges into an offscreen canvas at logical coords; returns a\n * Blob (image/png).\n */\nexport type ExportOptions = {\n /** Bitmap scale multiplier — defaults to 2 for retina-ish output. */\n scale?: number\n /** Padding (logical px) around the bounding rect. Default 16. */\n padding?: number\n /** Skip the background fill. Default false. */\n transparentBackground?: boolean\n /** Background color when not transparent. Default white. */\n backgroundColor?: string\n /** Theme resolver, same one passed to the live renderer. */\n theme?: ThemeResolver\n /**\n * Renderer-owned asset cache. When provided, `image` and `icon`\n * nodes paint from the same decoded bitmaps the live canvas uses.\n * When omitted, those node types are skipped (back-compat).\n *\n * Usage: `exportSelection(store, { assetCache: renderer.getAssetCache() })`.\n */\n assetCache?: AssetCache\n}\n\nconst DEFAULT_SCALE = 2\nconst DEFAULT_PADDING = 16\nconst DEFAULT_BACKGROUND = '#ffffff'\nconst MIN_READABLE_FONT_PX = 3\n\n/**\n * Renders the current selection to a PNG. Returns a `Blob` you can\n * download, upload, or paste somewhere.\n *\n * Bounding rect is computed from the selected nodes; edges between\n * selected nodes are included, edges crossing the boundary are\n * dropped.\n *\n * @example\n * // Download the selection as a PNG file.\n * const blob = await exportSelection(store, { scale: 2 })\n * const url = URL.createObjectURL(blob)\n * Object.assign(document.createElement('a'), {\n * href: url, download: 'scene.png',\n * }).click()\n * URL.revokeObjectURL(url)\n *\n * @example\n * // Transparent PNG for slide-deck overlays.\n * const blob = await exportSelection(store, { transparentBackground: true })\n */\nexport const exportSelection = async (\n store: CanvasStore,\n opts: ExportOptions = {},\n): Promise<Blob> => {\n const ids = store.getSelection()\n const nodeIds = new Set<NodeId>()\n for (const id of ids) {\n if (store.getNode(id as NodeId)) nodeIds.add(id as NodeId)\n }\n return exportNodeSet(store, nodeIds, opts)\n}\n\n/**\n * Renders an arbitrary world-space viewport to a PNG. Use to capture\n * the current screen, a minimap, or a specific region.\n *\n * @example\n * const viewport = worldViewport(staticSurface, store.getCamera())\n * const blob = await exportViewport(store, viewport)\n */\nexport const exportViewport = async (\n store: CanvasStore,\n viewport: { x: number; y: number; w: number; h: number },\n opts: ExportOptions = {},\n): Promise<Blob> => {\n const scale = opts.scale ?? DEFAULT_SCALE\n const padding = opts.padding ?? 0\n const ctx = makeContext(viewport.w + padding * 2, viewport.h + padding * 2, scale, opts)\n ctx.translate(-viewport.x + padding, -viewport.y + padding)\n paintScene(\n ctx,\n store,\n store.getAllNodes().filter((n: Node) => intersects(n, viewport)),\n scale,\n opts,\n )\n return toBlob(ctx.canvas)\n}\n\nconst exportNodeSet = async (\n store: CanvasStore,\n nodeIds: ReadonlySet<NodeId>,\n opts: ExportOptions,\n): Promise<Blob> => {\n if (nodeIds.size === 0) {\n // Empty selection — emit a 1×1 transparent png so callers don't crash.\n const c = document.createElement('canvas')\n c.width = 1\n c.height = 1\n return toBlob(c)\n }\n const nodes: Node[] = []\n for (const id of nodeIds) {\n const n = store.getNode(id)\n if (n) nodes.push(n)\n }\n const padding = opts.padding ?? DEFAULT_PADDING\n const scale = opts.scale ?? DEFAULT_SCALE\n const bbox = unionBounds(nodes)\n const w = bbox.w + padding * 2\n const h = bbox.h + padding * 2\n\n const ctx = makeContext(w, h, scale, opts)\n ctx.translate(-bbox.x + padding, -bbox.y + padding)\n\n // Edges that connect two selected nodes.\n const edges: Edge[] = []\n for (const e of store.getAllEdges()) {\n if (bothEndsInside(e, nodeIds)) edges.push(e)\n }\n paintScene(ctx, store, nodes, scale, opts, edges)\n return toBlob(ctx.canvas)\n}\n\nconst makeContext = (\n cssW: number,\n cssH: number,\n scale: number,\n opts: ExportOptions,\n): CanvasRenderingContext2D => {\n const canvas = document.createElement('canvas')\n canvas.width = Math.max(1, Math.ceil(cssW * scale))\n canvas.height = Math.max(1, Math.ceil(cssH * scale))\n const ctx = canvas.getContext('2d')\n if (!ctx) throw new Error('Canvas 2D context unavailable')\n if (!opts.transparentBackground) {\n ctx.fillStyle = opts.backgroundColor ?? DEFAULT_BACKGROUND\n ctx.fillRect(0, 0, canvas.width, canvas.height)\n }\n ctx.scale(scale, scale)\n return ctx\n}\n\n/**\n * Walks the node + edge set and paints them. Uses the same primitives\n * as the live renderer so output matches the canvas.\n */\nconst paintScene = (\n ctx: CanvasRenderingContext2D,\n store: CanvasStore,\n nodes: Node[],\n scale: number,\n opts: ExportOptions,\n edges?: Edge[],\n): void => {\n const theme = opts.theme\n const assetCache = opts.assetCache\n for (const node of nodes) {\n drawWithNodeTransform(ctx, node, () => {\n if (isDrawablePrimitive(node.type)) drawShape(ctx, node, scale, theme)\n if (assetCache) {\n if (node.type === 'image') paintImageNode(ctx, node, assetCache, theme)\n else if (node.type === 'icon') paintIconNode(ctx, node, assetCache, scale, theme)\n }\n paintContent(ctx, node)\n })\n }\n const edgeList = edges ?? store.getAllEdges()\n const getNode = (id: NodeId): Node | undefined => store.getNode(id)\n for (const edge of edgeList) {\n const geom = computeEdgeGeometry(edge, getNode)\n if (!geom) continue\n const sourceNode = geom.sourceNodeId ? (getNode(geom.sourceNodeId) ?? null) : null\n const targetNode = geom.targetNodeId ? (getNode(geom.targetNodeId) ?? null) : null\n drawEdge(ctx, edge, geom, sourceNode, targetNode, scale, theme)\n }\n}\n\nconst paintContent = (ctx: CanvasRenderingContext2D, node: Node): void => {\n if (!node.content || !node.content.trim()) return\n const style = node.style\n const fontSize = style?.fontSize ?? 'M'\n // Same readability skip as the live renderer.\n if (FONT_SIZE_MAP[fontSize] * 1 < MIN_READABLE_FONT_PX) return\n const bitmap = getOrRenderTextBitmap({\n id: node.id,\n text: node.content,\n width: node.w,\n height: node.h,\n zoom: 1,\n dpr: 2,\n isMoving: false,\n align: style?.textAlign ?? 'center',\n fontFamily: style?.fontFamily ?? 'handwriting',\n fontSize,\n textStyle: style?.textStyle ?? 'normal',\n textColor: style?.textColor ?? DEFAULT_TEXT_COLOR,\n highlightColor: DEFAULT_HIGHLIGHT_COLOR,\n })\n if (!bitmap) return\n ctx.drawImage(bitmap.canvas, 0, 0, node.w, node.h)\n}\n\nconst toBlob = (canvas: HTMLCanvasElement): Promise<Blob> =>\n new Promise((resolve, reject) => {\n canvas.toBlob(b => (b ? resolve(b) : reject(new Error('toBlob returned null'))), 'image/png')\n })\n\nconst unionBounds = (nodes: Node[]): { x: number; y: number; w: number; h: number } => {\n let minX = Number.POSITIVE_INFINITY\n let minY = Number.POSITIVE_INFINITY\n let maxX = Number.NEGATIVE_INFINITY\n let maxY = Number.NEGATIVE_INFINITY\n for (const n of nodes) {\n const r = nodeAABB(n)\n if (r.x < minX) minX = r.x\n if (r.y < minY) minY = r.y\n if (r.x + r.w > maxX) maxX = r.x + r.w\n if (r.y + r.h > maxY) maxY = r.y + r.h\n }\n return { x: minX, y: minY, w: maxX - minX, h: maxY - minY }\n}\n\nconst intersects = (n: Node, vp: { x: number; y: number; w: number; h: number }): boolean => {\n const a = nodeAABB(n)\n return a.x < vp.x + vp.w && a.x + a.w > vp.x && a.y < vp.y + vp.h && a.y + a.h > vp.y\n}\n\nconst bothEndsInside = (e: Edge, ids: ReadonlySet<NodeId>): boolean => {\n const inEnd = (end: typeof e.source): boolean => 'nodeId' in end && ids.has(end.nodeId)\n return inEnd(e.source) && inEnd(e.target)\n}\n","import { applySvgColor, extractSvgDimensions } from '../assets'\nimport { computeEdgeGeometry } from '../edges'\nimport { nodeAABB } from '../spatial'\nimport type { CanvasStore } from '../store'\nimport { FONT_FAMILY_MAP, FONT_SIZE_MAP } from '../text'\nimport type { Edge, IconNodeData, ImageNodeData, Node, NodeId } from '../types'\n\n/**\n * SVG export — see ARCHITECTURE.md §13.\n *\n * **Scope**: matches PNG export for shape geometry + edge geometry.\n * Image nodes are inlined as `<image href=\"…\">` (data URI passes\n * through verbatim). Icon nodes nest their sanitized SVG markup inside\n * a `<g transform>`, preserving vector quality and the `iconColor`\n * recolor knob.\n *\n * Markdown content is emitted as **plain text** (no inline bold /\n * italic / highlight). SVG `<text>` doesn't support our markdown\n * dialect without tspan positioning math; deferred to v2. PNG export\n * preserves all markdown styling via the bitmap pipeline.\n */\nexport type SvgExportOptions = {\n padding?: number\n transparentBackground?: boolean\n backgroundColor?: string\n}\n\nconst DEFAULT_PADDING = 16\nconst DEFAULT_BACKGROUND = '#ffffff'\n\n/**\n * Renders the current selection to an SVG string. Synchronous —\n * unlike PNG, no canvas roundtrip needed.\n *\n * **Caveat:** SVG `<text>` doesn't support our markdown dialect, so\n * `**bold**` / `==hl==` etc. render as plain text with the syntax\n * stripped. PNG export preserves all markdown via the bitmap pipeline.\n *\n * @example\n * const svg = exportSelectionSvg(store)\n * const blob = new Blob([svg], { type: 'image/svg+xml' })\n */\nexport const exportSelectionSvg = (store: CanvasStore, opts: SvgExportOptions = {}): string => {\n const ids = store.getSelection()\n const nodeIds = new Set<NodeId>()\n for (const id of ids) {\n if (store.getNode(id as NodeId)) nodeIds.add(id as NodeId)\n }\n return exportNodeSetSvg(store, nodeIds, opts)\n}\n\nconst exportNodeSetSvg = (\n store: CanvasStore,\n nodeIds: ReadonlySet<NodeId>,\n opts: SvgExportOptions,\n): string => {\n const padding = opts.padding ?? DEFAULT_PADDING\n if (nodeIds.size === 0) {\n return `<svg xmlns=\"http://www.w3.org/2000/svg\" width=\"1\" height=\"1\" />`\n }\n const nodes: Node[] = []\n for (const id of nodeIds) {\n const n = store.getNode(id)\n if (n) nodes.push(n)\n }\n const bbox = unionBounds(nodes)\n const w = Math.ceil(bbox.w + padding * 2)\n const h = Math.ceil(bbox.h + padding * 2)\n const tx = -bbox.x + padding\n const ty = -bbox.y + padding\n\n const bgRect = opts.transparentBackground\n ? ''\n : `<rect width=\"100%\" height=\"100%\" fill=\"${escapeAttr(opts.backgroundColor ?? DEFAULT_BACKGROUND)}\" />`\n\n const edges: Edge[] = []\n for (const e of store.getAllEdges()) {\n if (bothEndsInside(e, nodeIds)) edges.push(e)\n }\n\n const parts: string[] = []\n parts.push(\n `<svg xmlns=\"http://www.w3.org/2000/svg\" width=\"${w}\" height=\"${h}\" viewBox=\"0 0 ${w} ${h}\">`,\n )\n parts.push(bgRect)\n parts.push(`<g transform=\"translate(${tx} ${ty})\">`)\n for (const node of nodes) parts.push(renderNodeSvg(node))\n for (const edge of edges) parts.push(renderEdgeSvg(edge, store))\n parts.push('</g>')\n parts.push('</svg>')\n return parts.join('')\n}\n\nconst renderNodeSvg = (node: Node): string => {\n const fill = node.style?.backgroundColor ?? '#ffffff'\n const stroke = node.style?.strokeColor ?? '#0f172a'\n const strokeWidth = node.style?.strokeWidth ?? 1.5\n const opacity = node.style?.opacity ?? 1\n const rotate =\n node.angle !== 0\n ? ` transform=\"rotate(${(node.angle * 180) / Math.PI} ${node.x + node.w / 2} ${node.y + node.h / 2})\"`\n : ''\n\n const text = renderTextSvg(node)\n if (node.type === 'image') {\n return `<g${rotate}>${renderImageNodeSvg(node, opacity)}${text}</g>`\n }\n if (node.type === 'icon') {\n return `<g${rotate}>${renderIconNodeSvg(node, opacity)}${text}</g>`\n }\n\n const shape = renderShapeSvg(node, fill, stroke, strokeWidth, opacity)\n return `<g${rotate}>${shape}${text}</g>`\n}\n\nconst renderImageNodeSvg = (node: Node, opacity: number): string => {\n const data = node.data as ImageNodeData | undefined\n if (!data?.src) return ''\n // `<image href>` accepts data URIs directly; `preserveAspectRatio=\"none\"`\n // mirrors the live renderer's drawImage(0, 0, w, h) which stretches\n // the bitmap to the node rect (matches the no-default-aspect-lock\n // policy for image/icon resize).\n return `<image href=\"${escapeAttr(data.src)}\" x=\"${node.x}\" y=\"${node.y}\" width=\"${node.w}\" height=\"${node.h}\" preserveAspectRatio=\"none\" opacity=\"${opacity}\" />`\n}\n\nconst renderIconNodeSvg = (node: Node, opacity: number): string => {\n const data = node.data as IconNodeData | undefined\n if (!data?.src) return ''\n // Apply the same `currentColor` substitution the live renderer does\n // via getIcon(src, color, …). The sanitized markup is already\n // script-free (add-time guarantee).\n const colored = node.style?.iconColor ? applySvgColor(data.src, node.style.iconColor) : data.src\n // Nest the source <svg> inside a <g translate+scale>. The inner SVG\n // keeps its viewBox so vector content scales cleanly to the node\n // rect. extractSvgDimensions falls back to 24×24 if width/height/\n // viewBox are missing — same fallback the addSvg path uses.\n const dim = extractSvgDimensions(colored)\n const sx = node.w / dim.w\n const sy = node.h / dim.h\n return `<g transform=\"translate(${node.x} ${node.y}) scale(${sx} ${sy})\" opacity=\"${opacity}\">${colored}</g>`\n}\n\nconst renderShapeSvg = (\n node: Node,\n fill: string,\n stroke: string,\n strokeWidth: number,\n opacity: number,\n): string => {\n const attrs = (extra: string): string =>\n `fill=\"${escapeAttr(fill)}\" stroke=\"${escapeAttr(stroke)}\" stroke-width=\"${strokeWidth}\" opacity=\"${opacity}\"${extra}`\n switch (node.type) {\n case 'rect': {\n const r = (node.style?.roundness ?? 0) * 4\n return `<rect x=\"${node.x}\" y=\"${node.y}\" width=\"${node.w}\" height=\"${node.h}\" rx=\"${r}\" ry=\"${r}\" ${attrs('')} />`\n }\n case 'ellipse':\n return `<ellipse cx=\"${node.x + node.w / 2}\" cy=\"${node.y + node.h / 2}\" rx=\"${node.w / 2}\" ry=\"${node.h / 2}\" ${attrs('')} />`\n case 'diamond': {\n const cx = node.x + node.w / 2\n const cy = node.y + node.h / 2\n const pts = `${cx},${node.y} ${node.x + node.w},${cy} ${cx},${node.y + node.h} ${node.x},${cy}`\n return `<polygon points=\"${pts}\" ${attrs('')} />`\n }\n case 'tag': {\n // Approximate — emit the bounding rect. Full tag geometry is not\n // worth porting to the SVG export path.\n return `<rect x=\"${node.x}\" y=\"${node.y}\" width=\"${node.w}\" height=\"${node.h}\" rx=\"6\" ry=\"6\" ${attrs('')} />`\n }\n case 'capsule':\n case 'thought-cloud':\n case 'layered-rect':\n case 'layered-ellipse':\n case 'layered-diamond': {\n // Composites: emit a bounding rect placeholder. PNG export uses\n // the canvas renderer directly and renders these correctly.\n return `<rect x=\"${node.x}\" y=\"${node.y}\" width=\"${node.w}\" height=\"${node.h}\" rx=\"4\" ry=\"4\" ${attrs('')} />`\n }\n case 'text':\n return ''\n default:\n return `<rect x=\"${node.x}\" y=\"${node.y}\" width=\"${node.w}\" height=\"${node.h}\" fill=\"none\" stroke=\"${escapeAttr(stroke)}\" stroke-dasharray=\"4 4\" stroke-width=\"1\" opacity=\"0.5\" />`\n }\n}\n\nconst renderTextSvg = (node: Node): string => {\n if (!node.content || !node.content.trim()) return ''\n const fontSize = FONT_SIZE_MAP[node.style?.fontSize ?? 'M']\n const family = FONT_FAMILY_MAP[node.style?.fontFamily ?? 'handwriting']\n const color = node.style?.textColor ?? '#1f2937'\n const align = node.style?.textAlign ?? 'center'\n const anchor = align === 'left' ? 'start' : align === 'right' ? 'end' : 'middle'\n // Plain text — see header doc. Strip markdown syntax for legibility\n // (so '**bold**' renders as 'bold' not '**bold**').\n const lines = node.content.split('\\n').map(stripMarkdown)\n const cx = node.x + (align === 'left' ? 8 : align === 'right' ? node.w - 8 : node.w / 2)\n const totalH = lines.length * fontSize * 1.25\n const startY = node.y + (node.h - totalH) / 2 + fontSize * 0.8\n const tspans = lines\n .map(\n (line, i) =>\n `<tspan x=\"${cx}\" y=\"${startY + i * fontSize * 1.25}\">${escapeText(line)}</tspan>`,\n )\n .join('')\n return `<text fill=\"${escapeAttr(color)}\" font-family=\"${escapeAttr(family)}\" font-size=\"${fontSize}\" text-anchor=\"${anchor}\">${tspans}</text>`\n}\n\nconst renderEdgeSvg = (edge: Edge, store: CanvasStore): string => {\n const getNode = (id: NodeId): Node | undefined => store.getNode(id)\n const geom = computeEdgeGeometry(edge, getNode)\n if (!geom) return ''\n const samples = geom.samples\n if (samples.length < 2) return ''\n const d = samples\n .map((p, i) => `${i === 0 ? 'M' : 'L'}${p.x.toFixed(1)} ${p.y.toFixed(1)}`)\n .join(' ')\n const stroke = edge.style?.strokeColor ?? '#0f172a'\n const strokeWidth = edge.style?.strokeWidth ?? 1.5\n return `<path d=\"${d}\" fill=\"none\" stroke=\"${escapeAttr(stroke)}\" stroke-width=\"${strokeWidth}\" />`\n}\n\nconst stripMarkdown = (s: string): string =>\n s\n .replace(/\\*\\*(.*?)\\*\\*/g, '$1')\n .replace(/__(.*?)__/g, '$1')\n .replace(/~~(.*?)~~/g, '$1')\n .replace(/==(.*?)==/g, '$1')\n .replace(/`(.*?)`/g, '$1')\n .replace(/\\*(.*?)\\*/g, '$1')\n .replace(/\\[(.*?)\\]\\(.*?\\)/g, '$1')\n\nconst escapeText = (s: string): string =>\n s.replace(/&/g, '&amp;').replace(/</g, '&lt;').replace(/>/g, '&gt;')\nconst escapeAttr = (s: string): string => escapeText(s).replace(/\"/g, '&quot;')\n\nconst unionBounds = (nodes: Node[]): { x: number; y: number; w: number; h: number } => {\n let minX = Number.POSITIVE_INFINITY\n let minY = Number.POSITIVE_INFINITY\n let maxX = Number.NEGATIVE_INFINITY\n let maxY = Number.NEGATIVE_INFINITY\n for (const n of nodes) {\n const r = nodeAABB(n)\n if (r.x < minX) minX = r.x\n if (r.y < minY) minY = r.y\n if (r.x + r.w > maxX) maxX = r.x + r.w\n if (r.y + r.h > maxY) maxY = r.y + r.h\n }\n return { x: minX, y: minY, w: maxX - minX, h: maxY - minY }\n}\n\nconst bothEndsInside = (e: Edge, ids: ReadonlySet<NodeId>): boolean => {\n const inEnd = (end: typeof e.source): boolean => 'nodeId' in end && ids.has(end.nodeId)\n return inEnd(e.source) && inEnd(e.target)\n}\n","import type { CanvasStore } from '../store'\nimport { isAttached } from '../types'\nimport type { Edge, EdgeEnd, EdgeId, Node, NodeId } from '../types'\n\n/**\n * AI scene context — see ARCHITECTURE.md §13.\n *\n * Returns a human- or machine-readable snapshot of the scene for use\n * as a system-prompt payload or AI tool-call argument. **Markdown is\n * the prose form** (better for LLM comprehension token-per-token);\n * JSON is the structured form for downstream automation.\n *\n * Output keeps it tight: each node + edge becomes one line, with\n * truncation when the scene is large.\n */\nexport type GetContextOptions = {\n format?: 'markdown' | 'json'\n /** Restrict to the current selection. Default: include the whole scene. */\n selectionOnly?: boolean\n /** Truncate node list at this count. Default 500. */\n maxNodes?: number\n}\n\nconst DEFAULT_MAX_NODES = 500\n\n/**\n * Returns a snapshot of the scene suitable for an LLM system prompt or\n * a tool-call argument.\n *\n * - `format: 'markdown'` (default) — full-text prose summary. Better\n * for LLM token economy.\n * - `format: 'json'` — structured `SceneContextJson` shape; lighter\n * than `SerializedScene` (no internal fields).\n *\n * @example\n * // System prompt\n * const ctx = getContext(store) as string\n * await anthropic.messages.create({\n * system: `Current scene:\\n${ctx}`,\n * ...\n * })\n *\n * @example\n * // JSON for downstream automation\n * const ctx = getContext(store, { format: 'json', selectionOnly: true })\n */\nexport const getContext = (\n store: CanvasStore,\n opts: GetContextOptions = {},\n): string | SceneContextJson => {\n const format = opts.format ?? 'markdown'\n const maxNodes = opts.maxNodes ?? DEFAULT_MAX_NODES\n\n let nodes: Node[]\n let edges: Edge[]\n if (opts.selectionOnly) {\n const ids = new Set(store.getSelection())\n nodes = []\n edges = []\n for (const id of ids) {\n const n = store.getNode(id as NodeId)\n if (n) nodes.push(n)\n else {\n const e = store.getEdge(id as EdgeId)\n if (e) edges.push(e)\n }\n }\n } else {\n nodes = store.getAllNodes()\n edges = store.getAllEdges()\n }\n\n const truncated = nodes.length > maxNodes\n if (truncated) nodes = nodes.slice(0, maxNodes)\n\n if (format === 'json') return toJsonContext(nodes, edges, store, truncated)\n return toMarkdownContext(nodes, edges, store, truncated)\n}\n\n// ----- JSON output ------------------------------------------------------\n\nexport type SceneContextJson = {\n camera: { x: number; y: number; z: number }\n nodes: ContextNode[]\n edges: ContextEdge[]\n truncated: boolean\n}\n\nexport type ContextNode = {\n id: string\n type: string\n x: number\n y: number\n w: number\n h: number\n angle?: number\n content?: string\n style?: Record<string, unknown>\n}\n\nexport type ContextEdge = {\n id: string\n source: string | { x: number; y: number }\n target: string | { x: number; y: number }\n pathStyle?: string\n}\n\nconst toJsonContext = (\n nodes: Node[],\n edges: Edge[],\n store: CanvasStore,\n truncated: boolean,\n): SceneContextJson => {\n const camera = store.getCamera()\n return {\n camera: { x: camera.x, y: camera.y, z: camera.z },\n nodes: nodes.map(n => {\n const out: ContextNode = { id: n.id, type: n.type, x: n.x, y: n.y, w: n.w, h: n.h }\n if (n.angle !== 0) out.angle = n.angle\n if (n.content) out.content = n.content\n if (n.style && Object.keys(n.style).length > 0) out.style = n.style as Record<string, unknown>\n return out\n }),\n edges: edges.map(e => ({\n id: e.id,\n source: serializeEnd(e.source),\n target: serializeEnd(e.target),\n pathStyle: e.pathStyle,\n })),\n truncated,\n }\n}\n\nconst serializeEnd = (end: EdgeEnd): string | { x: number; y: number } => {\n if (isAttached(end)) return end.nodeId\n return { x: end.worldPoint.x, y: end.worldPoint.y }\n}\n\n// ----- Markdown output --------------------------------------------------\n\nconst toMarkdownContext = (\n nodes: Node[],\n edges: Edge[],\n store: CanvasStore,\n truncated: boolean,\n): string => {\n const lines: string[] = []\n const camera = store.getCamera()\n\n lines.push('# Canvas scene')\n lines.push('')\n lines.push(\n `camera at (${formatNumber(camera.x)}, ${formatNumber(camera.y)}) zoom ${formatNumber(camera.z)}`,\n )\n lines.push(`${nodes.length} node(s), ${edges.length} edge(s)`)\n if (truncated) lines.push(`_(truncated to first ${nodes.length} nodes)_`)\n lines.push('')\n\n if (nodes.length > 0) {\n lines.push('## Nodes')\n lines.push('')\n for (const n of nodes) lines.push(`- ${formatNode(n)}`)\n lines.push('')\n }\n\n if (edges.length > 0) {\n lines.push('## Edges')\n lines.push('')\n for (const e of edges) lines.push(`- ${formatEdge(e)}`)\n }\n\n return lines.join('\\n')\n}\n\nconst formatNode = (n: Node): string => {\n const pos = `at (${formatNumber(n.x)}, ${formatNumber(n.y)}) size ${formatNumber(n.w)}×${formatNumber(n.h)}`\n const angle = n.angle !== 0 ? ` rotated ${formatNumber((n.angle * 180) / Math.PI)}°` : ''\n const id = `\\`${n.id}\\``\n const type = `**${n.type}**`\n const content = n.content ? ` — \"${truncateText(n.content, 80)}\"` : ''\n return `${id} ${type} ${pos}${angle}${content}`\n}\n\nconst formatEdge = (e: Edge): string => {\n const id = `\\`${e.id}\\``\n const src = describeEnd(e.source)\n const tgt = describeEnd(e.target)\n const style = e.pathStyle !== 'bezier' ? ` (${e.pathStyle})` : ''\n return `${id} ${src} → ${tgt}${style}`\n}\n\nconst describeEnd = (end: EdgeEnd): string => {\n if (isAttached(end)) return `\\`${end.nodeId}\\``\n return `(${formatNumber(end.worldPoint.x)}, ${formatNumber(end.worldPoint.y)})`\n}\n\nconst formatNumber = (n: number): string => (Number.isInteger(n) ? String(n) : n.toFixed(1))\n\nconst truncateText = (s: string, max: number): string =>\n s.length <= max ? s.replace(/\\n/g, ' ↵ ') : `${s.slice(0, max - 1).replace(/\\n/g, ' ↵ ')}…`\n","/**\n * Op schemas — see ARCHITECTURE.md §13.\n *\n * Hand-written JSON-Schema definitions for the `Op` discriminated\n * union. AI agents use these to validate generated ops before calling\n * `store.applyOp`; tool-use frameworks (Anthropic, OpenAI, Vertex)\n * advertise the schemas as callable tool definitions.\n *\n * Hand-written (not derived from TS) so the schemas survive when the\n * runtime shape evolves without an explicit schema update.\n */\n\nconst Vec2 = {\n type: 'object',\n required: ['x', 'y'],\n properties: { x: { type: 'number' }, y: { type: 'number' } },\n} as const\n\nconst NodeBase = {\n type: 'object',\n required: ['id', 'type', 'x', 'y', 'w', 'h', 'angle', 'z', 'groups'],\n properties: {\n id: {\n type: 'string',\n description: 'Stable id (typically generated via `store.generateId()`).',\n },\n type: {\n type: 'string',\n description:\n 'Node type — rect / ellipse / diamond / tag / capsule / thought-cloud / layered-rect / layered-ellipse / layered-diamond / text / a registered custom type.',\n },\n x: { type: 'number' },\n y: { type: 'number' },\n w: { type: 'number', minimum: 0 },\n h: { type: 'number', minimum: 0 },\n angle: { type: 'number', description: 'Rotation in radians (clockwise).' },\n z: { type: 'number' },\n groups: { type: 'array', items: { type: 'string' } },\n content: { type: 'string', description: 'Markdown content (for text-bearing shapes).' },\n style: { type: 'object', description: 'Style bag — see ARCHITECTURE.md §3.4 (Style type).' },\n hidden: { type: 'boolean' },\n },\n} as const\n\nconst EdgeEnd = {\n oneOf: [\n {\n type: 'object',\n required: ['nodeId', 'localOffset'],\n properties: { nodeId: { type: 'string' }, localOffset: Vec2 },\n },\n {\n type: 'object',\n required: ['worldPoint'],\n properties: { worldPoint: Vec2 },\n },\n ],\n} as const\n\nconst EdgeBase = {\n type: 'object',\n required: ['id', 'source', 'target', 'pathStyle', 'z', 'groups'],\n properties: {\n id: { type: 'string' },\n source: EdgeEnd,\n target: EdgeEnd,\n pathStyle: { type: 'string', enum: ['bezier', 'straight', 'polyline'] },\n z: { type: 'number' },\n groups: { type: 'array', items: { type: 'string' } },\n style: { type: 'object' },\n hidden: { type: 'boolean' },\n },\n} as const\n\nconst GroupBase = {\n type: 'object',\n required: ['id', 'memberIds'],\n properties: {\n id: { type: 'string' },\n memberIds: { type: 'array', items: { type: 'string' } },\n name: { type: 'string' },\n },\n} as const\n\n/**\n * JSON-Schema definitions for every `Op` variant. Use to validate\n * agent-generated ops before calling `store.applyOp`, or to feed into\n * an LLM tool-use loop.\n *\n * @example\n * import Ajv from 'ajv'\n * const ajv = new Ajv()\n * const validate = ajv.compile(opSchemas.nodeAdd)\n * if (validate(generatedOp)) store.applyOp(generatedOp)\n */\nexport const opSchemas = {\n nodeAdd: {\n type: 'object',\n required: ['type', 'node'],\n properties: { type: { const: 'node.add' }, node: NodeBase },\n },\n nodeUpdate: {\n type: 'object',\n required: ['type', 'id', 'patch', 'prev'],\n properties: {\n type: { const: 'node.update' },\n id: { type: 'string' },\n patch: { type: 'object' },\n prev: { type: 'object' },\n },\n },\n nodeRemove: {\n type: 'object',\n required: ['type', 'node'],\n properties: { type: { const: 'node.remove' }, node: NodeBase },\n },\n edgeAdd: {\n type: 'object',\n required: ['type', 'edge'],\n properties: { type: { const: 'edge.add' }, edge: EdgeBase },\n },\n edgeUpdate: {\n type: 'object',\n required: ['type', 'id', 'patch', 'prev'],\n properties: {\n type: { const: 'edge.update' },\n id: { type: 'string' },\n patch: { type: 'object' },\n prev: { type: 'object' },\n },\n },\n edgeRemove: {\n type: 'object',\n required: ['type', 'edge'],\n properties: { type: { const: 'edge.remove' }, edge: EdgeBase },\n },\n groupUpsert: {\n type: 'object',\n required: ['type', 'group'],\n properties: { type: { const: 'group.upsert' }, group: GroupBase, prev: GroupBase },\n },\n groupRemove: {\n type: 'object',\n required: ['type', 'group'],\n properties: { type: { const: 'group.remove' }, group: GroupBase },\n },\n} as const\n\n/**\n * Tool definition in the Anthropic Messages API shape.\n */\nexport type AnthropicToolDef = {\n name: string\n description: string\n input_schema: object\n}\n\n/**\n * Returns op schemas wrapped as Anthropic Messages-API tool\n * definitions. Drop into the `tools` field of a `messages.create`\n * request to let an agent mutate the canvas directly.\n *\n * @example\n * const response = await anthropic.messages.create({\n * model: 'claude-opus-4-7',\n * tools: opSchemasAsAnthropicTools(),\n * messages: [{ role: 'user', content: 'Add a red sticky note' }],\n * })\n * for (const block of response.content) {\n * if (block.type === 'tool_use' && block.name.startsWith('canvas_')) {\n * const op = toOp(block.name, block.input)\n * store.applyOp(op)\n * }\n * }\n */\nexport const opSchemasAsAnthropicTools = (): AnthropicToolDef[] => [\n {\n name: 'canvas_node_add',\n description: 'Add a new node to the canvas.',\n input_schema: opSchemas.nodeAdd,\n },\n {\n name: 'canvas_node_update',\n description: 'Update fields on an existing node.',\n input_schema: opSchemas.nodeUpdate,\n },\n {\n name: 'canvas_node_remove',\n description: 'Remove an existing node (the previous snapshot must be supplied for undo).',\n input_schema: opSchemas.nodeRemove,\n },\n {\n name: 'canvas_edge_add',\n description: 'Add a new edge connecting two nodes (or free world points).',\n input_schema: opSchemas.edgeAdd,\n },\n {\n name: 'canvas_edge_update',\n description: 'Update fields on an existing edge.',\n input_schema: opSchemas.edgeUpdate,\n },\n {\n name: 'canvas_edge_remove',\n description: 'Remove an existing edge.',\n input_schema: opSchemas.edgeRemove,\n },\n]\n","import type { CanvasStore, StoreEventHandler, StoreEventName, Unsubscribe } from '../store'\n\n/**\n * Extension system — see ARCHITECTURE.md §13.9.\n *\n * The escape hatch for features the core won't ship: snap-to-grid,\n * alignment guides, minimap, autosave, AI plugins. Extensions get a\n * store handle + event subscription helper; they can mutate the store\n * (via the regular API), subscribe to events, and clean up on uninstall.\n *\n * Bare-bones by design — anything more (paint hooks, custom handles,\n * shortcut registration) is a v2 concern. Authors who need those today\n * can compose them inside `onInstall` against the store directly.\n */\nexport type ExtensionApi = {\n /** The store the extension is attached to. */\n store: CanvasStore\n /**\n * Subscribe to a store event with automatic cleanup on uninstall —\n * authors don't have to thread their own teardown.\n */\n on<E extends StoreEventName>(event: E, cb: StoreEventHandler<E>): Unsubscribe\n}\n\nexport type Extension = {\n /** Unique name; one extension per name per store. */\n name: string\n /**\n * Called when the extension is installed. May return a cleanup\n * function that runs on uninstall (in addition to auto-unsubscribed\n * listeners registered via `api.on`).\n *\n * `void` in the union is deliberate — extensions whose installer\n * does its work via `api.on` (auto-cleaned-up) don't need to return\n * anything. `undefined | (() => void)` would require an explicit\n * `return undefined`, which is noise. Biome's noConfusingVoidType\n * fires on this pattern; the suppression below is intentional.\n */\n // biome-ignore lint/suspicious/noConfusingVoidType: see comment above\n onInstall(api: ExtensionApi): void | (() => void)\n}\n\n/**\n * Defines an extension. Pure identity — exists for symmetry with\n * `defineNode` and to make call sites read nicely.\n *\n * @example\n * export const snapToGrid = defineExtension({\n * name: 'snap-to-grid',\n * onInstall: api => {\n * api.on('interaction', state => {\n * if (state.mode !== 'dragging') return\n * const snapped = {\n * x: Math.round(state.dragDelta.x / 20) * 20,\n * y: Math.round(state.dragDelta.y / 20) * 20,\n * }\n * api.store.setInteractionState({ dragDelta: snapped })\n * })\n * },\n * })\n */\nexport const defineExtension = (ext: Extension): Extension => ext\n\nconst installed = new WeakMap<CanvasStore, Map<string, () => void>>()\n\n/**\n * Installs an extension against a store. Returns an `uninstall()`\n * function. Re-installing the same name replaces the previous\n * instance.\n *\n * @example\n * useEffect(() => {\n * if (snapEnabled) return installExtension(store, snapToGrid)\n * }, [store, snapEnabled])\n */\nexport const installExtension = (store: CanvasStore, ext: Extension): Unsubscribe => {\n let registry = installed.get(store)\n if (!registry) {\n registry = new Map()\n installed.set(store, registry)\n }\n // Replace existing.\n const existing = registry.get(ext.name)\n if (existing) existing()\n\n const teardownFns: (() => void)[] = []\n const api: ExtensionApi = {\n store,\n on(event, cb) {\n const unsub = store.subscribe(event, cb)\n teardownFns.push(unsub)\n return unsub\n },\n }\n const userTeardown = ext.onInstall(api)\n if (typeof userTeardown === 'function') teardownFns.push(userTeardown)\n\n const teardown = (): void => {\n for (const fn of teardownFns) fn()\n teardownFns.length = 0\n registry?.delete(ext.name)\n }\n registry.set(ext.name, teardown)\n return teardown\n}\n\n/** Test / debug aid: list installed extension names for a store. */\nexport const installedExtensions = (store: CanvasStore): string[] => {\n const registry = installed.get(store)\n return registry ? [...registry.keys()] : []\n}\n","/**\n * @canvas-harness/core\n *\n * Framework-agnostic core for the canvas-harness library.\n * See ARCHITECTURE.md and IMPLEMENTATION.md at the repo root.\n *\n * Phase 1 ships: types, ids, camera, spatial index, store skeleton, codec.\n */\nexport const VERSION = '0.0.0'\n\nexport * from './types'\nexport * from './ids'\nexport * from './camera'\nexport * from './spatial'\nexport * from './edges'\nexport * from './node-types'\nexport * from './text'\nexport * from './edit'\nexport * from './store'\nexport * from './codec'\nexport * from './render'\nexport * from './hit-test'\nexport * from './clipboard'\nexport * from './export'\nexport * from './ai'\nexport * from './assets'\nexport * from './extension'\n"]}