simple-circuit-engine 0.0.11 → 0.0.13

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.
Files changed (161) hide show
  1. package/AGENTS.md +11 -7
  2. package/CLAUDE.md +6 -6
  3. package/README.md +5 -2
  4. package/dist/core/index.d.ts +0 -1
  5. package/dist/core/index.js +85 -2115
  6. package/dist/core/setup.d.ts +25 -0
  7. package/dist/core/simulation/CircuitRunner.d.ts +176 -0
  8. package/dist/core/simulation/DirtyTracker.d.ts +87 -0
  9. package/dist/core/simulation/EventQueue.d.ts +68 -0
  10. package/dist/core/simulation/StateManager.d.ts +100 -0
  11. package/dist/core/simulation/behaviors/BehaviorRegistry.d.ts +70 -0
  12. package/dist/core/simulation/behaviors/ComponentBehavior.d.ts +53 -0
  13. package/dist/core/simulation/behaviors/arithmetic/AdderBehavior.d.ts +28 -0
  14. package/dist/core/simulation/behaviors/arithmetic/ArithmeticBehaviorMixin.d.ts +63 -0
  15. package/dist/core/simulation/behaviors/arithmetic/EightBitAdderBehavior.d.ts +51 -0
  16. package/dist/core/simulation/behaviors/arithmetic/EightBitOnesComplementBehavior.d.ts +29 -0
  17. package/dist/core/simulation/behaviors/arithmetic/HalfAdderBehavior.d.ts +22 -0
  18. package/dist/core/simulation/behaviors/arithmetic/index.d.ts +7 -0
  19. package/dist/core/simulation/behaviors/basic/BatteryBehavior.d.ts +14 -0
  20. package/dist/core/simulation/behaviors/basic/ClockBehavior.d.ts +24 -0
  21. package/dist/core/simulation/behaviors/basic/DoubleThrowSwitchBehavior.d.ts +33 -0
  22. package/dist/core/simulation/behaviors/basic/LightbulbBehavior.d.ts +23 -0
  23. package/dist/core/simulation/behaviors/basic/RectangleLEDBehavior.d.ts +24 -0
  24. package/dist/core/simulation/behaviors/basic/RelayBehavior.d.ts +33 -0
  25. package/dist/core/simulation/behaviors/basic/SmallLEDBehavior.d.ts +24 -0
  26. package/dist/core/simulation/behaviors/basic/SwitchBehavior.d.ts +33 -0
  27. package/dist/core/simulation/behaviors/basic/index.d.ts +20 -0
  28. package/dist/core/simulation/behaviors/gates/InverterBehavior.d.ts +29 -0
  29. package/dist/core/simulation/behaviors/gates/Nand4GateBehavior.d.ts +18 -0
  30. package/dist/core/simulation/behaviors/gates/Nand8GateBehavior.d.ts +18 -0
  31. package/dist/core/simulation/behaviors/gates/NandGateBehavior.d.ts +28 -0
  32. package/dist/core/simulation/behaviors/gates/Nor4GateBehavior.d.ts +18 -0
  33. package/dist/core/simulation/behaviors/gates/Nor8GateBehavior.d.ts +18 -0
  34. package/dist/core/simulation/behaviors/gates/NorGateBehavior.d.ts +22 -0
  35. package/dist/core/simulation/behaviors/gates/Xor4GateBehavior.d.ts +18 -0
  36. package/dist/core/simulation/behaviors/gates/Xor8GateBehavior.d.ts +18 -0
  37. package/dist/core/simulation/behaviors/gates/XorGateBehavior.d.ts +22 -0
  38. package/dist/core/simulation/behaviors/gates/index.d.ts +34 -0
  39. package/dist/core/simulation/behaviors/index.d.ts +28 -0
  40. package/dist/core/simulation/behaviors/types.d.ts +101 -0
  41. package/dist/core/simulation/index.d.ts +18 -0
  42. package/dist/core/simulation/states/ComponentState.d.ts +57 -0
  43. package/dist/core/simulation/states/SimulationState.d.ts +46 -0
  44. package/dist/core/simulation/states/arithmetic/AdderState.d.ts +16 -0
  45. package/dist/core/simulation/states/arithmetic/ArithmeticState.d.ts +53 -0
  46. package/dist/core/simulation/states/arithmetic/EightBitAdderState.d.ts +25 -0
  47. package/dist/core/simulation/states/arithmetic/EightBitOnesComplementState.d.ts +18 -0
  48. package/dist/core/simulation/states/arithmetic/HalfAdderState.d.ts +16 -0
  49. package/dist/core/simulation/states/arithmetic/index.d.ts +7 -0
  50. package/dist/core/simulation/states/basic/BatteryState.d.ts +16 -0
  51. package/dist/core/simulation/states/basic/ClockState.d.ts +16 -0
  52. package/dist/core/simulation/states/basic/DoubleThrowSwitchState.d.ts +21 -0
  53. package/dist/core/simulation/states/basic/LightbulbState.d.ts +21 -0
  54. package/dist/core/simulation/states/basic/RectangleLEDState.d.ts +9 -0
  55. package/dist/core/simulation/states/basic/RelayState.d.ts +25 -0
  56. package/dist/core/simulation/states/basic/SmallLEDState.d.ts +21 -0
  57. package/dist/core/simulation/states/basic/SwitchState.d.ts +25 -0
  58. package/dist/core/simulation/states/gates/InverterState.d.ts +17 -0
  59. package/dist/core/simulation/states/gates/Nand4GateState.d.ts +10 -0
  60. package/dist/core/simulation/states/gates/Nand8GateState.d.ts +10 -0
  61. package/dist/core/simulation/states/gates/NandGateState.d.ts +16 -0
  62. package/dist/core/simulation/states/gates/Nor4GateState.d.ts +10 -0
  63. package/dist/core/simulation/states/gates/Nor8GateState.d.ts +10 -0
  64. package/dist/core/simulation/states/gates/NorGateState.d.ts +10 -0
  65. package/dist/core/simulation/states/gates/Xor4GateState.d.ts +10 -0
  66. package/dist/core/simulation/states/gates/Xor8GateState.d.ts +10 -0
  67. package/dist/core/simulation/states/gates/XorGateState.d.ts +10 -0
  68. package/dist/core/simulation/states/gates/index.d.ts +25 -0
  69. package/dist/core/simulation/states/index.d.ts +31 -0
  70. package/dist/core/simulation/states/types.d.ts +32 -0
  71. package/dist/core/simulation/types.d.ts +155 -0
  72. package/dist/core/topology/Circuit.d.ts +420 -0
  73. package/dist/core/topology/CircuitMetadata.d.ts +24 -0
  74. package/dist/core/topology/CircuitOptions.d.ts +14 -0
  75. package/dist/core/topology/Component.d.ts +153 -0
  76. package/dist/core/topology/ENode.d.ts +200 -0
  77. package/dist/core/topology/Wire.d.ts +130 -0
  78. package/dist/core/topology/delays.d.ts +52 -0
  79. package/dist/core/topology/index.d.ts +14 -0
  80. package/dist/core/topology/types.d.ts +189 -0
  81. package/dist/core/utils/CameraOptions.d.ts +83 -0
  82. package/dist/core/utils/MemoizeDecorator.d.ts +9 -0
  83. package/dist/core/utils/Position.d.ts +166 -0
  84. package/dist/core/utils/Position3D.d.ts +77 -0
  85. package/dist/core/utils/Rotation.d.ts +82 -0
  86. package/dist/core/utils/index.d.ts +24 -0
  87. package/dist/core/utils/types.d.ts +35 -0
  88. package/dist/core-b6Q8w2sn.js +3560 -0
  89. package/dist/core-b6Q8w2sn.js.map +1 -0
  90. package/dist/i18n/index.d.ts +882 -0
  91. package/dist/i18n/locales/en.json.d.ts +268 -0
  92. package/dist/i18n/locales/fr.json.d.ts +268 -0
  93. package/dist/index.d.ts +14 -6306
  94. package/dist/index.js +136 -112
  95. package/dist/scene/CircuitEngine.d.ts +283 -0
  96. package/dist/scene/index.d.ts +1 -2
  97. package/dist/scene/index.js +50 -41
  98. package/dist/scene/setup.d.ts +26 -0
  99. package/dist/scene/shared/AbstractCircuitController.d.ts +217 -0
  100. package/dist/scene/shared/BranchingPointVisualFactory.d.ts +70 -0
  101. package/dist/scene/shared/EventEmitter.d.ts +92 -0
  102. package/dist/scene/shared/HoverManager.d.ts +151 -0
  103. package/dist/scene/shared/SelectionManager.d.ts +159 -0
  104. package/dist/scene/shared/WireVisualManager.d.ts +242 -0
  105. package/dist/scene/shared/components/ComponentVisualFactory.d.ts +438 -0
  106. package/dist/scene/shared/components/DefaultVisualFactory.d.ts +51 -0
  107. package/dist/scene/shared/components/FactoryRegistry.d.ts +84 -0
  108. package/dist/scene/shared/components/GroupedFactoryRegistry.d.ts +153 -0
  109. package/dist/scene/shared/components/arithmetic/AdderVisualFactory.d.ts +54 -0
  110. package/dist/scene/shared/components/arithmetic/EightBitAdderVisualFactory.d.ts +45 -0
  111. package/dist/scene/shared/components/arithmetic/EightBitOnesComplementVisualFactory.d.ts +63 -0
  112. package/dist/scene/shared/components/arithmetic/HalfAdderVisualFactory.d.ts +55 -0
  113. package/dist/scene/shared/components/arithmetic/index.d.ts +4 -0
  114. package/dist/scene/shared/components/basic/BatteryVisualFactory.d.ts +13 -0
  115. package/dist/scene/shared/components/basic/ClockVisualFactory.d.ts +79 -0
  116. package/dist/scene/shared/components/basic/DoubleThrowSwitchVisualFactory.d.ts +87 -0
  117. package/dist/scene/shared/components/basic/LabelVisualFactory.d.ts +148 -0
  118. package/dist/scene/shared/components/basic/LightbulbVisualFactory.d.ts +72 -0
  119. package/dist/scene/shared/components/basic/RectangleLEDVisualFactory.d.ts +86 -0
  120. package/dist/scene/shared/components/basic/RelayVisualFactory.d.ts +92 -0
  121. package/dist/scene/shared/components/basic/SmallLEDVisualFactory.d.ts +86 -0
  122. package/dist/scene/shared/components/basic/SwitchVisualFactory.d.ts +85 -0
  123. package/dist/scene/shared/components/gates/InverterVisualFactory.d.ts +104 -0
  124. package/dist/scene/shared/components/gates/Nand4GateVisualFactory.d.ts +27 -0
  125. package/dist/scene/shared/components/gates/Nand8GateVisualFactory.d.ts +27 -0
  126. package/dist/scene/shared/components/gates/NandGateVisualFactory.d.ts +101 -0
  127. package/dist/scene/shared/components/gates/Nor4GateVisualFactory.d.ts +27 -0
  128. package/dist/scene/shared/components/gates/Nor8GateVisualFactory.d.ts +27 -0
  129. package/dist/scene/shared/components/gates/NorGateVisualFactory.d.ts +101 -0
  130. package/dist/scene/shared/components/gates/Xor4GateVisualFactory.d.ts +29 -0
  131. package/dist/scene/shared/components/gates/Xor8GateVisualFactory.d.ts +29 -0
  132. package/dist/scene/shared/components/gates/XorGateVisualFactory.d.ts +103 -0
  133. package/dist/scene/shared/components/index.d.ts +33 -0
  134. package/dist/scene/shared/components/types.d.ts +43 -0
  135. package/dist/scene/shared/types.d.ts +474 -0
  136. package/dist/scene/shared/utils/CameraUtils.d.ts +23 -0
  137. package/dist/scene/shared/utils/ColorUtils.d.ts +26 -0
  138. package/dist/scene/shared/utils/ControlsUtils.d.ts +8 -0
  139. package/dist/scene/shared/utils/GeometryUtils.d.ts +337 -0
  140. package/dist/scene/shared/utils/LayerConstants.d.ts +40 -0
  141. package/dist/scene/shared/utils/LightingUtils.d.ts +31 -0
  142. package/dist/scene/shared/utils/MaterialUtils.d.ts +73 -0
  143. package/dist/scene/shared/utils/Options.d.ts +16 -0
  144. package/dist/scene/simulation/CircuitRunnerController.d.ts +227 -0
  145. package/dist/scene/static/CircuitController.d.ts +228 -0
  146. package/dist/scene/static/CircuitWriter.d.ts +146 -0
  147. package/dist/scene/static/PinTooltipWidget.d.ts +31 -0
  148. package/dist/scene/static/tools/BuildTool.d.ts +290 -0
  149. package/dist/scene/static/tools/ComponentPickerWidget.d.ts +89 -0
  150. package/dist/scene/static/tools/ConfigPanelWidget.d.ts +107 -0
  151. package/dist/scene/static/tools/MultiSelectTool.d.ts +265 -0
  152. package/dist/scene-D4QcWeiq.js +8745 -0
  153. package/dist/scene-D4QcWeiq.js.map +1 -0
  154. package/package.json +29 -25
  155. package/dist/CircuitRunner-BQQlhwjD.js +0 -1981
  156. package/dist/CircuitRunner-BQQlhwjD.js.map +0 -1
  157. package/dist/core/index.js.map +0 -1
  158. package/dist/index.js.map +0 -1
  159. package/dist/scene/index.js.map +0 -1
  160. package/dist/setup-CIq_kgaw.js +0 -10230
  161. package/dist/setup-CIq_kgaw.js.map +0 -1
@@ -0,0 +1,25 @@
1
+ import { ComponentState } from '../ComponentState';
2
+ import { UUID } from '../../../utils/types';
3
+ /**
4
+ * Simulation state for Logic gates components
5
+ * Gates can be "low", "rising", "high", "falling" or "indeterminate" (if their input is not well-defined)
6
+ *
7
+ * @public
8
+ */
9
+ export declare abstract class LogicGateState extends ComponentState {
10
+ /**
11
+ * Create a new Inverter state.
12
+ *
13
+ * @param componentId - UUID of the Inverter component
14
+ * @param initialState - Initial operational state (default: "low")
15
+ */
16
+ protected constructor(componentId: UUID, initialState?: string);
17
+ /**
18
+ * Check if output is in a rising or falling transition
19
+ */
20
+ get isInTransition(): boolean;
21
+ /**
22
+ * Check if output is high
23
+ */
24
+ get isHigh(): boolean;
25
+ }
@@ -0,0 +1,31 @@
1
+ /**
2
+ * Simulation state definitions
3
+ * @module core/simulation/states
4
+ */
5
+ export type { INodeElectricalState } from './types';
6
+ export { unionElectricalStates } from './types';
7
+ export { SimulationState } from './SimulationState.js';
8
+ export { ComponentState } from './ComponentState.js';
9
+ export { BatteryState } from './basic/BatteryState';
10
+ export { LightbulbState } from './basic/LightbulbState';
11
+ export { RectangleLEDState } from './basic/RectangleLEDState';
12
+ export { RelayState } from './basic/RelayState';
13
+ export { SmallLEDState } from './basic/SmallLEDState';
14
+ export { SwitchState } from './basic/SwitchState';
15
+ export { DoubleThrowSwitchState } from './basic/DoubleThrowSwitchState';
16
+ export { ClockState } from './basic/ClockState';
17
+ export { InverterState } from './gates/InverterState';
18
+ export { NandGateState } from './gates/NandGateState';
19
+ export { Nand4GateState } from './gates/Nand4GateState';
20
+ export { Nand8GateState } from './gates/Nand8GateState';
21
+ export { NorGateState } from './gates/NorGateState';
22
+ export { Nor4GateState } from './gates/Nor4GateState';
23
+ export { Nor8GateState } from './gates/Nor8GateState';
24
+ export { XorGateState } from './gates/XorGateState';
25
+ export { Xor4GateState } from './gates/Xor4GateState';
26
+ export { Xor8GateState } from './gates/Xor8GateState';
27
+ export { ArithmeticState } from './arithmetic/ArithmeticState';
28
+ export { HalfAdderState } from './arithmetic/HalfAdderState';
29
+ export { AdderState } from './arithmetic/AdderState';
30
+ export { EightBitAdderState } from './arithmetic/EightBitAdderState';
31
+ export { EightBitOnesComplementState } from './arithmetic/EightBitOnesComplementState';
@@ -0,0 +1,32 @@
1
+ /**
2
+ * Binary electrical state for wires and enodes (connection points)
3
+ * @module core/simulation/states
4
+ * @public
5
+ */
6
+ export interface INodeElectricalState {
7
+ /**
8
+ * True if voltage is present at this node (potential > 0V).
9
+ * False if node is at ground potential or floating.
10
+ */
11
+ hasVoltage: boolean;
12
+ /**
13
+ * True if current is actively flowing through this node.
14
+ * False if no current flow (open circuit or equilibrium).
15
+ */
16
+ hasCurrent: boolean;
17
+ /**
18
+ * True only if the node is locked from state changes at circuit build time (ex: battery pins or other fixed-voltage/current pinSources).
19
+ * Important: Those nodes should never have their electrical state modified by the simulation controller!
20
+ * Always false for wires
21
+ */
22
+ locked: boolean;
23
+ }
24
+ /**
25
+ * Compute the union of multiple electrical states.
26
+ * Useful to derive a combined pin state from two or more pins
27
+ * (e.g. cmd_in + cmd_out → coil state).
28
+ *
29
+ * @param states - Two or more electrical states to combine
30
+ * @returns A new state where hasVoltage/hasCurrent are OR'd across inputs, locked is always false
31
+ */
32
+ export declare function unionElectricalStates(...states: INodeElectricalState[]): INodeElectricalState;
@@ -0,0 +1,155 @@
1
+ import { UUID } from '../utils';
2
+ /**
3
+ * Simulation speed bounds and defaults for ticks per second (TPS).
4
+ * @public
5
+ */
6
+ export declare const SIMULATION_SPEED: {
7
+ /**
8
+ * Minimum simulation speed in ticks per second
9
+ */
10
+ readonly MIN_TPS: 1;
11
+ /**
12
+ * Maximum simulation speed in ticks per second
13
+ */
14
+ readonly MAX_TPS: 100;
15
+ /**
16
+ * Default simulation speed in ticks per second
17
+ */
18
+ readonly DEFAULT_TPS: 3;
19
+ /**
20
+ * Default tick interval in milliseconds (1000 / DEFAULT_TPS)
21
+ */
22
+ readonly DEFAULT_INTERVAL_MS: 500;
23
+ };
24
+ /**
25
+ * Default transition timing values for components.
26
+ * @public
27
+ */
28
+ export declare const TRANSITION_DEFAULTS: {
29
+ /**
30
+ * Default transitionSpan for relays and transistors in ticks (instant transition)
31
+ */
32
+ readonly TRANSITION_SPAN_TICKS: 1;
33
+ /**
34
+ * Default transitionUserSpan for switches in milliseconds
35
+ */
36
+ readonly TRANSITION_USER_SPAN_MS: 200;
37
+ };
38
+ /**
39
+ * User command to be executed during simulation.
40
+ * Commands can be queued for future ticks or executed immediately.
41
+ *
42
+ * @public
43
+ */
44
+ export interface IUserCommand {
45
+ /**
46
+ * Type of command.
47
+ */
48
+ readonly type: 'toggle_switch';
49
+ /**
50
+ * UUID of target component.
51
+ */
52
+ readonly targetId: UUID;
53
+ /**
54
+ * tick when this command was scheduled.
55
+ */
56
+ scheduledAtTick: number;
57
+ /**
58
+ * Extra parameters associated with this command.
59
+ *
60
+ * For `toggle_switch` commands:
61
+ * - `tickCount`: Number of ticks for the switch transition. Computed at toggle time
62
+ * using the formula: `ceil(transitionUserSpan × simulationSpeed / 1000)` with minimum of 1.
63
+ * If not provided, behavior uses default transition timing.
64
+ */
65
+ readonly parameters?: Map<string, string> | null;
66
+ }
67
+ /**
68
+ * all reachable nodes and wires from a seed
69
+ */
70
+ export type IReachabilityResult = {
71
+ nodes: Set<UUID>;
72
+ wires: Set<UUID>;
73
+ };
74
+ /**
75
+ * Configuration options for CircuitRunner
76
+ */
77
+ export interface IRunnerOptions {
78
+ /**
79
+ * Enable historical state tracking.
80
+ * When true, past simulation states are preserved up to historyLimit.
81
+ * When false (default), only current state is retained for better performance.
82
+ * @default false
83
+ */
84
+ enableHistory?: boolean;
85
+ /**
86
+ * Maximum number of historical states to retain when enableHistory is true.
87
+ * Uses circular buffer—oldest states are overwritten when limit is reached.
88
+ * Must be a positive integer.
89
+ * @default 1000
90
+ */
91
+ historyLimit?: number;
92
+ }
93
+ /**
94
+ * Result statistics of one simulation tick run
95
+ */
96
+ export interface IRunnerResult {
97
+ startTick: number;
98
+ endTick: number;
99
+ componentUpdateCount: number;
100
+ nodeUpdateCount: number;
101
+ wireUpdateCount: number;
102
+ processedCommandCount: number;
103
+ scheduledEventCount: number;
104
+ firedEventCount: number;
105
+ }
106
+ /**
107
+ * Scheduled event for delayed component transitions.
108
+ * Events are ordered by readyAtTick in a min-heap priority queue.
109
+ * Events with same readyAtTick are processed in FIFO order (by scheduledAtTick).
110
+ *
111
+ * @public
112
+ */
113
+ export interface IScheduledEvent {
114
+ /**
115
+ * UUID of target component.
116
+ */
117
+ readonly targetId: UUID;
118
+ /**
119
+ * Tick when this event was scheduled (for FIFO ordering).
120
+ * @readonly
121
+ */
122
+ readonly scheduledAtTick: number;
123
+ /**
124
+ * Tick when this event should be processed.
125
+ * @readonly
126
+ */
127
+ readonly readyAtTick: number;
128
+ /**
129
+ * Indicates the type of this event, eg 'ClosingEnd', 'OpeningEnd', etc.
130
+ */
131
+ readonly type: string;
132
+ /**
133
+ * extra parameters associated with this event.
134
+ */
135
+ readonly parameters?: Map<string, string> | undefined;
136
+ }
137
+ /**
138
+ * Dirty elements collected during a tick, returned by getDirtyElements().
139
+ *
140
+ * @public
141
+ */
142
+ export interface IDirtyElements {
143
+ /**
144
+ * Components that changed state.
145
+ */
146
+ readonly components: ReadonlySet<UUID>;
147
+ /**
148
+ * Wires that changed electrical state.
149
+ */
150
+ readonly wires: ReadonlySet<UUID>;
151
+ /**
152
+ * ENodes that changed electrical state.
153
+ */
154
+ readonly enodes: ReadonlySet<UUID>;
155
+ }
@@ -0,0 +1,420 @@
1
+ import { UUID, Rotation, Position } from '../utils';
2
+ import { ComponentType, ENodeSourceType, ICircuit } from './types';
3
+ import { CircuitOptions } from './CircuitOptions';
4
+ import { CircuitMetadata } from './CircuitMetadata';
5
+ import { Component } from './Component';
6
+ import { ENode } from './ENode';
7
+ import { Wire } from './Wire';
8
+ /**
9
+ * Circuit container managing components, ENodes, and wires.
10
+ *
11
+ * The Circuit class provides:
12
+ * - Component management (add/remove with automatic pin ENode creation)
13
+ * - Topology queries (get by ID, enumerate all)
14
+ * - Automatic lifecycle management (cascade deletion, orphan cleanup)
15
+ * - JSON serialization for persistence
16
+ *
17
+ * **Key Principles**:
18
+ * - Users manage Components and Wires; ENodes are managed automatically
19
+ * - Removing a Component cascades to remove its pins and connected wires
20
+ * - Orphaned branching ENodes (no wires) are automatically removed
21
+ * - All operations maintain bidirectional consistency
22
+ *
23
+ * @example
24
+ * ```typescript
25
+ * const circuit = new Circuit();
26
+ *
27
+ * // Add a component at position (10, 20) with 2 pins
28
+ * const lightbulb = circuit.addComponent(
29
+ * new Position(10, 20),
30
+ * new Rotation(90),
31
+ * 2
32
+ * );
33
+ *
34
+ * console.log(lightbulb.id); // UUID
35
+ * console.log(lightbulb.pins); // [pin-uuid-1, pin-uuid-2]
36
+ *
37
+ * // Query components
38
+ * const comp = circuit.getComponent(lightbulb.id);
39
+ * const all = circuit.getAllComponents();
40
+ *
41
+ * // Remove component (cascade deletes pins and wires)
42
+ * circuit.removeComponent(lightbulb.id);
43
+ * ```
44
+ */
45
+ export declare class Circuit {
46
+ /**
47
+ * Circuit metadata holding general information.
48
+ * @private
49
+ */
50
+ metadata: CircuitMetadata;
51
+ /**
52
+ * Map of all components in the circuit (UUID → Component).
53
+ * @private
54
+ */
55
+ private components;
56
+ /**
57
+ * Map of all electrical nodes in the circuit (UUID → ENode).
58
+ * Includes both pin nodes and branching point nodes.
59
+ * @private
60
+ */
61
+ private enodes;
62
+ /**
63
+ * Map of all wires in the circuit (UUID → Wire).
64
+ * @private
65
+ */
66
+ private wires;
67
+ /**
68
+ * Create a new empty circuit.
69
+ */
70
+ constructor(options: CircuitOptions);
71
+ get name(): string;
72
+ set name(value: string);
73
+ /**
74
+ * Add a new component to the circuit.
75
+ *
76
+ * Automatically creates pin ENodes for the component and links them
77
+ * bidirectionally. Pin ENode UUIDs are stored in the component's pins array.
78
+ * Pin labels are derived from the ComponentType metadata.
79
+ *
80
+ * @param type - Component type (Battery, Switch, LED, etc.)
81
+ * @param position - Grid position (x, y integers)
82
+ * @param rotation - Orientation angle (integer degrees)
83
+ * @param config - Optional configuration map for component-specific settings
84
+ * @returns The created Component
85
+ * @throws {TypeError} If position/rotation coordinates are not integers
86
+ *
87
+ * @example
88
+ * ```typescript
89
+ * const lightbulb = circuit.addComponent(
90
+ * new Position(10, 20),
91
+ * new Rotation(90),
92
+ * ComponentType.Lightbulb
93
+ * );
94
+ *
95
+ * console.log(lightbulb.type); // ComponentType.Lightbulb
96
+ * console.log(lightbulb.pins.length); // 2
97
+ * console.log(lightbulb.position.x); // 10
98
+ * ```
99
+ */
100
+ addComponent(type: ComponentType, position: Position, rotation: Rotation, config?: Map<string, string> | undefined): Component;
101
+ /**
102
+ * Resolve and update the transitionSpan config for a component
103
+ * if automatic resolution returns undefined nothing is done on the component
104
+ *
105
+ * @param component - Component to resolve transitionSpan for
106
+ */
107
+ resolveTransitionSpan(component: Component): void;
108
+ /**
109
+ * Remove a component from the circuit.
110
+ *
111
+ * **Cascade deletion** removes:
112
+ * - All pin ENodes belonging to the component
113
+ * - All Wires connected to those pins
114
+ *
115
+ * @param id - Component UUID
116
+ * @throws {Error} If component does not exist
117
+ * @returns Object containing arrays of deleted Wires and ENodes IDs
118
+ *
119
+ * @example
120
+ * ```typescript
121
+ * circuit.removeComponent(componentId);
122
+ * // Component, its pins, and connected wires are all removed
123
+ * ```
124
+ */
125
+ removeComponent(id: UUID): {
126
+ deletedWires: UUID[];
127
+ deletedENodes: UUID[];
128
+ };
129
+ hasComponent(id: UUID): boolean;
130
+ /**
131
+ * Get a component by ID.
132
+ *
133
+ * @param id - Component UUID
134
+ * @returns The Component or undefined if not found
135
+ *
136
+ * @example
137
+ * ```typescript
138
+ * const component = circuit.getComponent(componentId);
139
+ * if (component) {
140
+ * console.log(component.position);
141
+ * }
142
+ * ```
143
+ */
144
+ getComponent(id: UUID): Component | undefined;
145
+ /**
146
+ * Get all components in the circuit.
147
+ *
148
+ * Returns a new array on each call (defensive copy).
149
+ *
150
+ * @returns Array of all Components
151
+ *
152
+ * @example
153
+ * ```typescript
154
+ * const components = circuit.getAllComponents();
155
+ * console.log(`Circuit has ${components.length} components`);
156
+ *
157
+ * for (const comp of components) {
158
+ * console.log(comp.id, comp.position);
159
+ * }
160
+ * ```
161
+ */
162
+ getAllComponents(): Component[];
163
+ getAllComponentsByType(type: ComponentType): Component[];
164
+ getFirstComponentOfType(type: ComponentType): Component | undefined;
165
+ /**
166
+ * Get an electrical node by ID.
167
+ *
168
+ * Note: ENodes are automatically managed and not directly created
169
+ * or removed by users.
170
+ *
171
+ * @param id - ENode UUID
172
+ * @returns The ENode or undefined if not found
173
+ *
174
+ * @example
175
+ * ```typescript
176
+ * const component = circuit.addComponent(
177
+ * new Position(10, 20),
178
+ * new Rotation(0),
179
+ * 2
180
+ * );
181
+ *
182
+ * const pinId = component.pins[0];
183
+ * const enode = circuit.getENode(pinId);
184
+ * console.log(enode.type); // ENodeType.Pin
185
+ * ```
186
+ */
187
+ getENode(id: UUID): ENode | undefined;
188
+ /**
189
+ * Get all electrical nodes in the circuit.
190
+ *
191
+ * Includes both pin nodes (from components) and branching point nodes
192
+ * (from wire splits).
193
+ *
194
+ * Returns a new array on each call (defensive copy).
195
+ *
196
+ * @returns Array of all ENodes
197
+ *
198
+ * @example
199
+ * ```typescript
200
+ * const enodes = circuit.getAllENodes();
201
+ * console.log(`Circuit has ${enodes.length} electrical nodes`);
202
+ *
203
+ * for (const enode of enodes) {
204
+ * console.log(enode.id, enode.type);
205
+ * }
206
+ * ```
207
+ */
208
+ getAllENodes(): ENode[];
209
+ /**
210
+ * Add a branching point electrical node at a specific position.
211
+ *
212
+ * Branching points are used to split wires and create junctions.
213
+ * @param position - Grid position for the branching point
214
+ * @param sourceType - Optional source type (voltage/current)
215
+ * @returns The created ENode
216
+ */
217
+ addBranchingPoint(position: Position, sourceType?: ENodeSourceType): ENode;
218
+ /**
219
+ * Remove a branching point electrical node from the circuit.
220
+ * Also removes all wires connected to this branching point if there are ony one or more than 2.
221
+ * In the case there are exactly two wires, they will be merged before removing the branching point.
222
+ *
223
+ * @param id - Branching point ENode UUID
224
+ * @throws {Error} If ENode does not exist or is not a branching point
225
+ */
226
+ removeBranchingPoint(id: UUID): {
227
+ deletedWires?: UUID[] | undefined;
228
+ mergedWires?: UUID[] | undefined;
229
+ newWire?: Wire | undefined;
230
+ };
231
+ /**
232
+ * Add a wire connecting two electrical nodes.
233
+ *
234
+ * Validates that both nodes exist, not a self-connection, and no duplicate.
235
+ * Updates bidirectional references (Wire ↔ ENodes).
236
+ *
237
+ * @param node1 - First ENode UUID
238
+ * @param node2 - Second ENode UUID
239
+ * @param intermediatePositions - Optional path waypoints for rendering
240
+ * @returns The created Wire, or Error if validation fails
241
+ *
242
+ * @example
243
+ * ```typescript
244
+ * const comp1 = circuit.addComponent(new Position(0, 0), new Rotation(0), 1);
245
+ * const comp2 = circuit.addComponent(new Position(10, 10), new Rotation(0), 1);
246
+ *
247
+ * const wire = circuit.addWire(comp1.pins[0], comp2.pins[0]);
248
+ * if (wire instanceof Error) {
249
+ * console.error('Failed:', wire.message);
250
+ * }
251
+ * ```
252
+ */
253
+ addWire(node1: UUID, node2: UUID, intermediatePositions?: Position[]): Wire | Error;
254
+ /**
255
+ * Remove a wire from the circuit.
256
+ *
257
+ * @param id - Wire UUID
258
+ * @throws {Error} If wire does not exist
259
+ *
260
+ * @example
261
+ * ```typescript
262
+ * circuit.removeWire(wireId);
263
+ * // Wire is removed
264
+ * ```
265
+ */
266
+ removeWire(id: UUID): void;
267
+ /**
268
+ * Split a wire in the circuit.
269
+ *
270
+ * It creates two new wires connected by either the target enode or a new branching point ENode at the specified position.
271
+ * Returns 2 UUIDS of the new wires.
272
+ *
273
+ * @param id - Wire UUID
274
+ * @param position
275
+ * @throws {Error} If wire does not exist
276
+ *
277
+ * @example
278
+ * ```typescript
279
+ * circuit.splitWire(wireId);
280
+ * // Wire and any orphaned branching points are removed
281
+ * ```
282
+ */
283
+ /**
284
+ * Split an existing wire at a position, creating a branching point.
285
+ * The original wire is removed and replaced with two new wires
286
+ * connecting through the new branching point.
287
+ * NB : in the special case where targetEnode belongs to a component where the wire is already connected
288
+ * only one new wire will be created as this method don't allow a wire directly connecting two pins of the same component.
289
+ *
290
+ * @param wireId - Wire to split
291
+ * @param position - Position for the new branching point : no effect if targetEnodeId provided
292
+ * @param targetEnodeId - if provided, the existing enode to split the wire at
293
+ * @returns Object containing the new branching point and an array of the two new wires
294
+ * @throws Error if wireId not found
295
+ */
296
+ splitWire(wireId: UUID, position: Position, targetEnodeId?: UUID | null): {
297
+ branchingPoint: ENode;
298
+ wires: Array<Wire>;
299
+ };
300
+ getWireBetweenNodes(node1: UUID, node2: UUID): Wire | undefined;
301
+ /**
302
+ * Get a wire by ID.
303
+ *
304
+ * @param id - Wire UUID
305
+ * @returns The Wire or undefined if not found
306
+ */
307
+ getWire(id: UUID): Wire | undefined;
308
+ /**
309
+ * Get all wires in the circuit.
310
+ *
311
+ * Returns a new array on each call (defensive copy).
312
+ *
313
+ * @returns Array of all Wires
314
+ */
315
+ getAllWires(): Wire[];
316
+ /**
317
+ * Get all wires connected to a specific ENode.
318
+ *
319
+ * @param nodeId - ENode UUID
320
+ * @returns Array of connected Wires, or empty array if node not found
321
+ */
322
+ getWiresByNode(nodeId: UUID): Wire[];
323
+ /**
324
+ * Get all wires connected to a component, e.g to any pin enode of the component.
325
+ *
326
+ * @param componentId - Component UUID
327
+ * @returns Array of connected Wires, or empty array if component not found
328
+ */
329
+ getWiresByComponent(componentId: UUID): Wire[];
330
+ /**
331
+ * Get both ENodes connected by a wire.
332
+ *
333
+ * @param wireId - Wire UUID
334
+ * @returns Tuple [node1, node2] or undefined if wire not found
335
+ */
336
+ getNodesByWire(wireId: UUID): [ENode, ENode] | undefined;
337
+ /**
338
+ * Check if a wire already exists between two nodes.
339
+ *
340
+ * Order-independent: returns true for (A, B) or (B, A).
341
+ *
342
+ * @param node1 - First ENode UUID
343
+ * @param node2 - Second ENode UUID
344
+ * @returns true if wire exists, false otherwise
345
+ */
346
+ hasWireBetween(node1: UUID, node2: UUID): boolean;
347
+ /**
348
+ * Find all components with pins among the provided enode IDs set.
349
+ *
350
+ * @param pinIds - Set of pins UUIDs
351
+ * @returns Set of components UUIDs
352
+ */
353
+ getComponentsOfPins(pinIds: Set<UUID>): Set<UUID>;
354
+ /**
355
+ * Get a component's pin ENode by its label.
356
+ * @param component
357
+ * @param pinLabel
358
+ */
359
+ getComponentPinByLabel(component: Component, pinLabel: string): ENode | undefined;
360
+ /**
361
+ * Update the intermediate positions of a wire.
362
+ * Update the wire in place.
363
+ *
364
+ * @param wireId - Wire to update
365
+ * @param intermediatePositions - New intermediate positions
366
+ * @param simplify - Whether to simplify positions by removing collinear points : useful when finalizing wire routing
367
+ * @returns The updated Wire
368
+ * @throws Error if wireId not found
369
+ */
370
+ updateWireIntermediatePositions(wireId: UUID, intermediatePositions: Position[], simplify?: boolean): Wire;
371
+ /**
372
+ * Simplify intermediate positions of a wire.
373
+ * Update the wire in place.
374
+ * @param wireId - Wire to simplify
375
+ * @returns The updated Wire
376
+ * @throws Error if wireId not found
377
+ */
378
+ simplifyWireIntermediatePositions(wireId: UUID): Wire;
379
+ /**
380
+ * Update the source type of an ENode (branching point or component pin).
381
+ * @param enodeId - ENode to update
382
+ * @param sourceType - New source type (null to clear)
383
+ * @throws Error if enodeId not found
384
+ */
385
+ updateENodeSourceType(enodeId: UUID, sourceType: ENodeSourceType | null): void;
386
+ /**
387
+ * iterate through all components, enodes and wires positions to get the size that allows to enclose all elements.
388
+ * @param margin - optional margin to add to the size
389
+ * @returns size that allows to enclose all elements plus margin
390
+ * @todo if calls to this method at each build operation ends causes slowness see to optimize by restricting checked elements
391
+ */
392
+ getEnclosingSize(margin?: number): number;
393
+ /**
394
+ * Serialize circuit to JSON.
395
+ *
396
+ * @returns JSON-serializable object containing all components, enodes, and wires
397
+ *
398
+ * @example
399
+ * ```typescript
400
+ * const json = circuit.toJSON();
401
+ * localStorage.setItem('my-circuit', JSON.stringify(json));
402
+ * ```
403
+ */
404
+ toJSON(): ICircuit;
405
+ /**
406
+ * Deserialize circuit from JSON.
407
+ *
408
+ * @param json - Circuit data
409
+ * @returns Circuit instance
410
+ * @throws {Error} If JSON is invalid or violates invariants
411
+ *
412
+ * @example
413
+ * ```typescript
414
+ * const jsonStr = localStorage.getItem('my-circuit');
415
+ * const json = JSON.parse(jsonStr);
416
+ * const circuit = Circuit.fromJSON(json);
417
+ * ```
418
+ */
419
+ static fromJSON(json: ICircuit): Circuit;
420
+ }
@@ -0,0 +1,24 @@
1
+ import { CameraOptions } from '../utils';
2
+ import { CircuitOptions } from './CircuitOptions';
3
+ import { ICircuitMetadata } from './types';
4
+ export declare class CircuitMetadata implements ICircuitMetadata {
5
+ version: string;
6
+ options: CircuitOptions;
7
+ size: number;
8
+ divisions: number;
9
+ cameraOptions: CameraOptions;
10
+ /**
11
+ * Create a new CircuitMetadata holding general information about the Circuit.
12
+ *
13
+ * @param version - Circuit version
14
+ * @param options - Circuit options
15
+ * @param size - Size of the circuit grid
16
+ * @param divisions - Divisions in the circuit grid
17
+ * @param cameraOptions - Camera Options at startup
18
+ * @throws {TypeError} If size or divisions are not integers
19
+ */
20
+ constructor(version: string, options: CircuitOptions, size: number, divisions: number, cameraOptions: CameraOptions);
21
+ toJSON(): ICircuitMetadata;
22
+ static fromJSON(json: ICircuitMetadata): CircuitMetadata;
23
+ toString(): string;
24
+ }