/** * Diagram wire-flow animation: marching dashes, traveling packets, node highlight. * Supports loop/once playback, pause, explicit paths, and path status tinting. */ import type { App } from '../App'; import type { Node } from '../Node'; import type { Group } from '../shapes/Group'; export type DiagramFlowMode = 'dash' | 'packet' | 'both'; export type DiagramFlowHighlight = 'pulse' | 'breathe' | 'flash' | 'none'; export type DiagramFlowPlayback = 'loop' | 'once'; export type DiagramFlowNodeStatus = 'idle' | 'active' | 'done' | 'error'; /** Built-in overlay toolbar: `true` / omit = auto when flow on; `false` = hide; object = granular. */ export type DiagramFlowChrome = boolean | { /** Play / pause / replay. Default true when flow is enabled. */ flow?: boolean; /** Zoom − / % / + / Fit. Default true when toolbar is shown. */ zoom?: boolean; }; export interface DiagramFlowHop { from: string; to: string; } /** Soft status tint colors (path-driven runs). Partial overrides merge with defaults. */ export interface DiagramFlowStatusColors { idle?: string; active?: string; done?: string; error?: string; } export interface DiagramFlowOptions { /** When false, clears animation and keeps options in state. Default true when apply is called. */ enabled?: boolean; /** Playback rate: 0 = paused (same as paused:true), 1 = default, 2 = 2×. */ speed?: number; /** Soft pause without clearing chrome / options. */ paused?: boolean; /** `loop` (default) or `once` then stop. */ playback?: DiagramFlowPlayback; /** Wire motion style. Default `both`. */ mode?: DiagramFlowMode; /** Motion chrome while a step is active / on packet arrival. Default `pulse`. */ highlight?: DiagramFlowHighlight; /** * Soft idle/active/done/error tint on path nodes (additive with `highlight`). * Defaults to `true` when a path/`paths`/`pathEdges` run is configured; otherwise `false`. * Requires `mode: 'packet' | 'both'` so hops advance. */ statusHighlight?: boolean; /** * Tint path edge strokes with the same status palette (idle / active / done). * Defaults to `true` when `statusHighlight` is on. */ statusEdges?: boolean; /** Override status tint colors (`idle` grey, `active` yellow, `done` green, `error` red). */ statusColors?: DiagramFlowStatusColors; /** * Force status for specific node ids (merged after lifecycle paint). * Useful for JSON snapshots or pinning an `error` node. */ statusOverrides?: Record; /** * When a declared hop has no matching edge, mark the source node `error` and pause. * Default `true`. */ statusPauseOnError?: boolean; /** diagramIds that show continuous pulse/breathe (when no path is driving highlight). */ activeNodes?: string[]; /** * Edge ids (`edgeId` or `from->to`) that get ambient packets when no path runs. * When omitted, all edges animate. */ activeEdges?: string[]; /** * Single run: ordered node ids (consecutive pairs become hops). * Example: `['start','check','process','end']` * Also accepts `string[][]` as a shorthand for `paths`. */ path?: string[] | string[][]; /** * Multiple runs in index order. Each entry is a node-id path. * After run `i` finishes, run `i+1` starts (after `pathGapMs`). * Takes precedence over `path` when both are set. */ paths?: string[][]; /** * Explicit hops for a single run. Used when no `paths` / `path` node lists. * Alias: `edges`. */ pathEdges?: DiagramFlowHop[]; /** Alias for `pathEdges` (builder-friendly). */ edges?: DiagramFlowHop[]; /** * Multiple hop-lists in index order (like `paths`, but as `{from,to}` hops). * Takes precedence over single `pathEdges` when set. */ pathsEdges?: DiagramFlowHop[][]; /** Pause between consecutive path runs (ms). Default 450. */ pathGapMs?: number; /** Dash pattern applied when an edge has no existing dash. */ dashPattern?: number[]; /** * Built-in HTML toolbar (play/pause/replay + zoom). * Default: shown when flow is enabled. Set `false` to hide (e.g. custom demo chrome). */ chrome?: DiagramFlowChrome; } interface ResolvedStatusColors { idle: string; active: string; done: string; error: string; } /** Default path-status tint palette. */ export declare const DEFAULT_FLOW_STATUS_COLORS: ResolvedStatusColors; export declare function resolveFlowStatusColors(raw?: DiagramFlowStatusColors | null): ResolvedStatusColors; /** Ordered unique node ids from a hop list (stable first-seen order). */ export declare function nodeIdsFromHops(hops: DiagramFlowHop[]): string[]; /** Stable edge key for status maps (`from->to`). */ export declare function flowEdgeKey(from: string, to: string): string; export declare function isDiagramFlowNodeStatus(v: unknown): v is DiagramFlowNodeStatus; export declare function sanitizeStatusOverrides(raw: unknown): Record | undefined; /** * Pure idle → active → done transitions for a path run (no canvas). * Used by the runtime and unit tests. */ export declare function createFlowStatusMap(): { states: Map; edgeStates: Map; beginRun(ids: string[], edgeKeys?: string[]): void; hopStart(from: string, to: string): void; hopArrive(from: string, to: string, isLast: boolean): void; setError(nodeId: string): void; applyOverrides(overrides?: Record): void; reset(): void; snapshot(): Record; edgeSnapshot(): Record; }; /** Flat polyline points → SVG path `d` for motionPath. */ export declare function edgePointsToPathD(points: number[]): string; /** Visible stroke polyline inside an edge group (not hit-target / packet). */ export declare function getEdgeStrokePolyline(edge: Group): Node | undefined; /** Stop running flow animations; keep `diagramState.flow` unless `clearState`. */ export declare function stopDiagramFlow(root: Group, opts?: { clearState?: boolean; }): void; /** * Apply (or re-apply) flow animation on a diagram root. * Persists options under `diagramState.flow`. */ export declare function applyDiagramFlow(app: App, root: Group, options?: DiagramFlowOptions): void; /** Re-apply flow from `diagramState.flow` after reroute / rebuild. */ export declare function refreshDiagramFlow(app: App, root: Group): void; /** If builder options include `flow`, start animation and persist on the group. */ export declare function maybeApplyDiagramFlow(app: App, root: Group, options: Record): void; /** Pause flow in place (packet / dashes / status keep position; resume continues). */ export declare function pauseDiagramFlow(app: App, root: Group): void; /** Resume flow from the paused step (soft pause) or restart if no live runtime. */ export declare function resumeDiagramFlow(app: App, root: Group): void; /** Toggle pause / resume. Returns whether flow is playing after the call. */ export declare function toggleDiagramFlowPause(app: App, root: Group): boolean; /** Replay from the start (clears pause; useful after `playback: 'once'`). */ export declare function replayDiagramFlow(app: App, root: Group): void; /** Whether flow is currently animating. */ export declare function isDiagramFlowPlaying(root: Group): boolean; export {};