Status: backlog Priority: P1 Created: 2026-02-25 Blocked by: viz-labels-system
A browser-only simulator that lets users step through a statechart interactively. It uses the real CLJS processor but with a custom ExecutionModel where guard predicates are user-toggleable and other executable content is a noop. Uses its own simple-env (ManuallyPolledQueue, WorkingMemoryDataModel, etc.) — no Fulcro integration dependency.
sp/ExecutionModel protocolguard-values-atom, returns the toggled booleantrue (permissive, user can flip to false)nil)::sc/raw-result? in env to distinguish guard evaluation from script executionsimple/simple-env pattern (processor, data model, queue, registry, working memory store) with SimulatorExecutionModel instead of lambda modelstart-simulation! [chart] — registers chart, starts session, returns initial state (configuration + guard info)send-event! [sim event-name event-data] — processes event, returns new configurationtoggle-guard! [sim guard-fn new-value] — updates guard atomreset-simulation! [sim] — restarts from initial configurationextract-guards [chart] — walks ::sc/elements-by-id, finds all transitions with :cond, returns {fn-ref {:label str :transition-id keyword :default true}} using :diagram/condition for labelavailable-events [chart configuration] — returns set of event keywords from transitions on active statessrc/main/com/fulcrologic/statecharts/visualization/simulator.cljc (NEW)The simulator is a self-contained namespace. It creates a local statechart environment using the same simple-env pattern but swaps in SimulatorExecutionModel. The execution model wraps an atom of {fn-ref -> boolean}. When run-expression! is called, it checks if the expression fn is in the atom. The algorithm sets ::sc/raw-result? in env when evaluating conditions, which lets us distinguish guards from scripts.
State is held in a map/record containing the env, guard-values atom, session-id, and chart reference. All processing is synchronous (uses v20150901 sync processor).
SimulatorExecutionModel: toggled guard returns correct booleanSimulatorExecutionModel: unknown guards return true (permissive default)SimulatorExecutionModel: scripts return nil (noop)start-simulation!: produces valid initial configuration for a simple chartsend-event!: transitions to correct state when guard is truesend-event!: does NOT transition when guard is toggled to falsetoggle-guard!: flips value, subsequent send-event! respects new valueextract-guards: finds all unique guard fns with :diagram/condition labelsavailable-events: returns correct event set for a given configurationreset-simulation!: returns to initial configurationCan you improve this documentation?Edit on GitHub
cljdoc builds & hosts documentation for Clojure/Script libraries
| Ctrl+k | Jump to recent docs |
| ← | Move to previous article |
| → | Move to next article |
| Ctrl+/ | Jump to the search field |