@classytic/labs 0.1.0 → 0.2.0

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (455) hide show
  1. package/dist/_virtual/_rolldown/runtime.mjs +18 -0
  2. package/dist/biology/enzyme-rate/preset.mjs +5 -5
  3. package/dist/biology/genetic-cross/core.d.mts +7 -7
  4. package/dist/biology/genetic-cross/core.mjs +4 -4
  5. package/dist/biology/genetic-cross/grid.mjs +132 -123
  6. package/dist/biology/genetic-cross/preset.mjs +4 -4
  7. package/dist/biology/genetic-cross/sex-linked.mjs +7 -7
  8. package/dist/biology/photosynthesis-factors/preset.mjs +8 -8
  9. package/dist/biology/respiration/preset.mjs +4 -4
  10. package/dist/biology/sequence/central-dogma.mjs +5 -5
  11. package/dist/biology/sequence/core.d.mts +6 -6
  12. package/dist/biology/sequence/core.mjs +1 -1
  13. package/dist/biology/sequence/preset.mjs +6 -6
  14. package/dist/blocks/authoring.mjs +5 -5
  15. package/dist/blocks/biology.d.mts +2 -2
  16. package/dist/blocks/biology.mjs +5 -5
  17. package/dist/blocks/chem.d.mts +2 -2
  18. package/dist/blocks/chem.mjs +13 -13
  19. package/dist/blocks/circuits.d.mts +293 -4
  20. package/dist/blocks/circuits.mjs +874 -9
  21. package/dist/blocks/discrete.d.mts +30 -2
  22. package/dist/blocks/discrete.mjs +74 -4
  23. package/dist/blocks/economics.mjs +1 -1
  24. package/dist/blocks/geography.mjs +1 -1
  25. package/dist/blocks/geometry.mjs +3 -3
  26. package/dist/blocks/ict.d.mts +90 -1
  27. package/dist/blocks/ict.mjs +217 -7
  28. package/dist/blocks/index.d.mts +3064 -657
  29. package/dist/blocks/index.mjs +9 -9
  30. package/dist/blocks/lab-block.mjs +5 -5
  31. package/dist/blocks/lab-config.d.mts +1 -1
  32. package/dist/blocks/lab-config.mjs +4 -4
  33. package/dist/blocks/lab-gallery.d.mts +1 -1
  34. package/dist/blocks/lab-gallery.mjs +2 -2
  35. package/dist/blocks/language.d.mts +6 -6
  36. package/dist/blocks/language.mjs +12 -12
  37. package/dist/blocks/lesson.mjs +4 -4
  38. package/dist/blocks/math.d.mts +577 -11
  39. package/dist/blocks/math.mjs +1648 -14
  40. package/dist/blocks/ml.d.mts +45 -1
  41. package/dist/blocks/ml.mjs +80 -6
  42. package/dist/blocks/physics.d.mts +9 -4
  43. package/dist/blocks/physics.mjs +75 -28
  44. package/dist/blocks/statistics.mjs +1 -1
  45. package/dist/build/CircuitEditor.d.mts +14 -0
  46. package/dist/build/CircuitEditor.mjs +787 -0
  47. package/dist/build/CircuitPlayer.d.mts +19 -0
  48. package/dist/build/CircuitPlayer.mjs +53 -0
  49. package/dist/build/CircuitScene.d.mts +61 -0
  50. package/dist/build/CircuitScene.mjs +383 -0
  51. package/dist/build/contract.d.mts +116 -0
  52. package/dist/build/editor-ops.d.mts +65 -0
  53. package/dist/build/editor-ops.mjs +306 -0
  54. package/dist/build/editor-ui.mjs +121 -0
  55. package/dist/build/flow.d.mts +14 -0
  56. package/dist/build/flow.mjs +119 -0
  57. package/dist/build/index.d.mts +10 -0
  58. package/dist/build/index.mjs +10 -0
  59. package/dist/build/parts/ammeter.d.mts +1 -0
  60. package/dist/build/parts/ammeter.mjs +32 -0
  61. package/dist/build/parts/bulb.d.mts +1 -0
  62. package/dist/build/parts/bulb.mjs +50 -0
  63. package/dist/build/parts/capacitor.d.mts +1 -0
  64. package/dist/build/parts/capacitor.mjs +26 -0
  65. package/dist/build/parts/cell.d.mts +1 -0
  66. package/dist/build/parts/cell.mjs +40 -0
  67. package/dist/build/parts/diode.d.mts +1 -0
  68. package/dist/build/parts/diode.mjs +33 -0
  69. package/dist/build/parts/index.d.mts +5 -0
  70. package/dist/build/parts/index.mjs +43 -0
  71. package/dist/build/parts/mosfet.d.mts +1 -0
  72. package/dist/build/parts/mosfet.mjs +95 -0
  73. package/dist/build/parts/node.d.mts +1 -0
  74. package/dist/build/parts/node.mjs +32 -0
  75. package/dist/build/parts/resistor.d.mts +1 -0
  76. package/dist/build/parts/resistor.mjs +49 -0
  77. package/dist/build/parts/shared.mjs +42 -0
  78. package/dist/build/parts/switch.d.mts +1 -0
  79. package/dist/build/parts/switch.mjs +34 -0
  80. package/dist/build/parts.d.mts +1 -0
  81. package/dist/build/registry.d.mts +9 -0
  82. package/dist/build/registry.mjs +15 -0
  83. package/dist/build/solve.d.mts +8 -0
  84. package/dist/build/solve.mjs +0 -0
  85. package/dist/catalog/registry.d.mts +2 -2
  86. package/dist/catalog/templates.d.mts +1 -1
  87. package/dist/catalog/templates.mjs +6 -6
  88. package/dist/chem/battery.mjs +1 -1
  89. package/dist/chem/bohr-atom.mjs +4 -4
  90. package/dist/chem/diffusion/preset.mjs +4 -4
  91. package/dist/chem/electrochem/preset.mjs +5 -5
  92. package/dist/chem/equilibrium/preset.d.mts +1 -1
  93. package/dist/chem/equilibrium/preset.mjs +6 -6
  94. package/dist/chem/gas-box/preset.mjs +6 -6
  95. package/dist/chem/kinetics/preset.mjs +6 -6
  96. package/dist/chem/periodic-trends/preset.mjs +7 -7
  97. package/dist/chem/reaction-lab.mjs +3 -3
  98. package/dist/chem/reaction-profile.mjs +4 -4
  99. package/dist/chem/solution/dilution.mjs +6 -6
  100. package/dist/chem/solution/field.d.mts +2 -2
  101. package/dist/chem/solution/field.mjs +2 -2
  102. package/dist/chem/solution/solution-box.mjs +7 -7
  103. package/dist/chem/stoichiometry/preset.mjs +5 -5
  104. package/dist/chem/titration/preset.mjs +5 -5
  105. package/dist/circuits/ac-dc/asset.mjs +1 -1
  106. package/dist/circuits/ac-dc/preset.mjs +2 -2
  107. package/dist/circuits/brownout/index.d.mts +1 -0
  108. package/dist/circuits/brownout/preset.d.mts +22 -0
  109. package/dist/circuits/brownout/preset.mjs +399 -0
  110. package/dist/circuits/capacitor-leak/preset.mjs +13 -8
  111. package/dist/circuits/circuit/asset.mjs +71 -14
  112. package/dist/circuits/circuit/preset.mjs +23 -5
  113. package/dist/circuits/circuit-builder.mjs +60 -132
  114. package/dist/circuits/circuit-lab.mjs +60 -40
  115. package/dist/circuits/cmos-gate/index.d.mts +1 -0
  116. package/dist/circuits/cmos-gate/preset.d.mts +75 -0
  117. package/dist/circuits/cmos-gate/preset.mjs +1491 -0
  118. package/dist/circuits/diode/index.d.mts +1 -0
  119. package/dist/circuits/diode/preset.d.mts +25 -0
  120. package/dist/circuits/diode/preset.mjs +266 -0
  121. package/dist/circuits/index.d.mts +7 -1
  122. package/dist/circuits/index.mjs +7 -1
  123. package/dist/circuits/rc-charging/index.d.mts +1 -0
  124. package/dist/circuits/rc-charging/preset.d.mts +27 -0
  125. package/dist/circuits/rc-charging/preset.mjs +329 -0
  126. package/dist/circuits/semiconductor/index.d.mts +1 -0
  127. package/dist/circuits/semiconductor/preset.d.mts +102 -0
  128. package/dist/circuits/semiconductor/preset.mjs +1855 -0
  129. package/dist/circuits/transistor/index.d.mts +1 -0
  130. package/dist/circuits/transistor/preset.d.mts +27 -0
  131. package/dist/circuits/transistor/preset.mjs +329 -0
  132. package/dist/commerce/accounting/core.d.mts +1 -1
  133. package/dist/commerce/accounting/equation-balance.mjs +5 -5
  134. package/dist/commerce/accounting/journal-poster.mjs +8 -8
  135. package/dist/commerce/accounting/statement-sorter.mjs +4 -4
  136. package/dist/commerce/economics/core.d.mts +2 -2
  137. package/dist/commerce/economics/core.mjs +1 -1
  138. package/dist/commerce/economics/demand-shift-vs-move.mjs +6 -6
  139. package/dist/commerce/economics/elasticity-revenue.mjs +6 -6
  140. package/dist/commerce/economics/market-equilibrium.mjs +5 -5
  141. package/dist/core/easing.d.mts +3 -3
  142. package/dist/core/easing.mjs +2 -2
  143. package/dist/core/numeric.d.mts +3 -3
  144. package/dist/core/numeric.mjs +2 -2
  145. package/dist/core/reactive.d.mts +1 -1
  146. package/dist/core/reactive.mjs +1 -1
  147. package/dist/core/rng.d.mts +2 -2
  148. package/dist/core/rng.mjs +1 -1
  149. package/dist/core/tex.mjs +2 -2
  150. package/dist/core/timeline.d.mts +1 -1
  151. package/dist/core/timeline.mjs +1 -1
  152. package/dist/core/util.mjs +11 -1
  153. package/dist/discrete/arrangements/preset.mjs +6 -14
  154. package/dist/discrete/bayes/preset.mjs +43 -35
  155. package/dist/discrete/binomial/preset.mjs +2 -2
  156. package/dist/discrete/combination-studio/figure.d.mts +6 -0
  157. package/dist/discrete/combination-studio/figure.mjs +159 -0
  158. package/dist/discrete/combination-studio/index.d.mts +2 -0
  159. package/dist/discrete/combination-studio/preset.d.mts +44 -0
  160. package/dist/discrete/combination-studio/preset.mjs +440 -0
  161. package/dist/discrete/core/combinatorics.d.mts +23 -3
  162. package/dist/discrete/core/combinatorics.mjs +38 -3
  163. package/dist/discrete/core/pigeonhole.d.mts +1 -1
  164. package/dist/discrete/core/pigeonhole.mjs +1 -1
  165. package/dist/discrete/core/probability.d.mts +3 -3
  166. package/dist/discrete/core/probability.mjs +3 -3
  167. package/dist/discrete/core/sets.d.mts +1 -1
  168. package/dist/discrete/counting-slots/preset.mjs +8 -8
  169. package/dist/discrete/counting-tree/preset.mjs +65 -8
  170. package/dist/discrete/expected-value/preset.mjs +13 -13
  171. package/dist/discrete/hypergeometric/preset.mjs +48 -15
  172. package/dist/discrete/index.d.mts +4 -2
  173. package/dist/discrete/index.mjs +4 -2
  174. package/dist/discrete/karnaugh/preset.mjs +26 -20
  175. package/dist/discrete/lln/preset.mjs +44 -3
  176. package/dist/discrete/logic-circuit/preset.mjs +2 -2
  177. package/dist/discrete/monte-carlo/preset.d.mts +1 -1
  178. package/dist/discrete/monte-carlo/preset.mjs +14 -14
  179. package/dist/discrete/monty-hall/preset.mjs +6 -6
  180. package/dist/discrete/outcome-builder/preset.mjs +3 -3
  181. package/dist/discrete/pascal/preset.mjs +37 -7
  182. package/dist/discrete/rules.d.mts +20 -0
  183. package/dist/discrete/rules.mjs +264 -0
  184. package/dist/discrete/sample-space/preset.mjs +4 -4
  185. package/dist/discrete/selection/preset.mjs +7 -13
  186. package/dist/discrete/truth-table/preset.mjs +32 -9
  187. package/dist/discrete/venn/preset.mjs +71 -48
  188. package/dist/geography/cycle-lab/preset.mjs +17 -10
  189. package/dist/geography/cycles.d.mts +3 -3
  190. package/dist/geography/cycles.mjs +3 -3
  191. package/dist/geometry/board/preset.d.mts +2 -0
  192. package/dist/geometry/board/preset.mjs +11 -15
  193. package/dist/geometry/builder.mjs +3 -3
  194. package/dist/ict/number-systems/base-odometer.mjs +4 -4
  195. package/dist/ict/number-systems/bit-grouper.d.mts +1 -1
  196. package/dist/ict/number-systems/bit-grouper.mjs +4 -4
  197. package/dist/ict/number-systems/place-value-dial.d.mts +1 -1
  198. package/dist/ict/number-systems/place-value-dial.mjs +3 -3
  199. package/dist/ict/number-systems/wheel.d.mts +3 -3
  200. package/dist/ict/number-systems/wheel.mjs +4 -4
  201. package/dist/kit/annotate.mjs +3 -3
  202. package/dist/kit/answer-check.d.mts +2 -2
  203. package/dist/kit/answer-check.mjs +34 -6
  204. package/dist/kit/ask.d.mts +19 -0
  205. package/dist/kit/ask.mjs +46 -0
  206. package/dist/kit/bar-strip.mjs +53 -0
  207. package/dist/kit/calc.d.mts +33 -0
  208. package/dist/kit/calc.mjs +27 -0
  209. package/dist/kit/carrier-engine.mjs +147 -0
  210. package/dist/kit/clue-scene.d.mts +86 -0
  211. package/dist/kit/clue-scene.mjs +424 -0
  212. package/dist/kit/cluster.d.mts +30 -0
  213. package/dist/kit/cluster.mjs +81 -0
  214. package/dist/kit/controls.mjs +11 -5
  215. package/dist/kit/coords.d.mts +88 -0
  216. package/dist/kit/coords.mjs +192 -0
  217. package/dist/kit/data-scene.d.mts +27 -0
  218. package/dist/kit/data-scene.mjs +199 -0
  219. package/dist/kit/diagram.mjs +111 -50
  220. package/dist/kit/electronics.mjs +552 -60
  221. package/dist/kit/expr-analysis.d.mts +18 -6
  222. package/dist/kit/expr-analysis.mjs +82 -28
  223. package/dist/kit/frame.d.mts +3 -3
  224. package/dist/kit/frame.mjs +25 -6
  225. package/dist/kit/gameshow.mjs +2 -2
  226. package/dist/kit/index.d.mts +14 -2
  227. package/dist/kit/index.mjs +13 -1
  228. package/dist/kit/logic-gates.mjs +246 -47
  229. package/dist/kit/palette.mjs +26 -0
  230. package/dist/kit/pedagogy.d.mts +4 -4
  231. package/dist/kit/pedagogy.mjs +21 -17
  232. package/dist/kit/play.d.mts +1 -1
  233. package/dist/kit/play.mjs +3 -3
  234. package/dist/kit/predict.d.mts +55 -0
  235. package/dist/kit/predict.mjs +146 -0
  236. package/dist/kit/receipt.d.mts +29 -0
  237. package/dist/kit/receipt.mjs +94 -0
  238. package/dist/kit/rich.mjs +2 -2
  239. package/dist/kit/rule.d.mts +59 -0
  240. package/dist/kit/rule.mjs +215 -0
  241. package/dist/kit/scale.mjs +1 -1
  242. package/dist/kit/scene-library.d.mts +22 -0
  243. package/dist/kit/scene-library.mjs +311 -0
  244. package/dist/kit/scene-studio.d.mts +14 -0
  245. package/dist/kit/scene-studio.mjs +338 -0
  246. package/dist/kit/scenes.d.mts +31 -0
  247. package/dist/kit/scenes.mjs +569 -0
  248. package/dist/kit/slot-fill.d.mts +61 -0
  249. package/dist/kit/slot-fill.mjs +207 -0
  250. package/dist/kit/solve.d.mts +21 -0
  251. package/dist/kit/solve.mjs +75 -0
  252. package/dist/kit/space.mjs +5 -5
  253. package/dist/kit/steps.mjs +2 -2
  254. package/dist/kit/vessel.d.mts +69 -0
  255. package/dist/kit/vessel.mjs +191 -0
  256. package/dist/language/agreement/preset.mjs +2 -2
  257. package/dist/language/article-lens/preset.d.mts +1 -1
  258. package/dist/language/article-lens/preset.mjs +8 -8
  259. package/dist/language/deck.d.mts +3 -3
  260. package/dist/language/deck.mjs +1 -1
  261. package/dist/language/preposition-scene/preset.d.mts +2 -2
  262. package/dist/language/preposition-scene/preset.mjs +5 -5
  263. package/dist/language/sentence-builder/preset.mjs +5 -5
  264. package/dist/language/transform/preset.d.mts +2 -2
  265. package/dist/language/transform/preset.mjs +5 -5
  266. package/dist/language/ui.d.mts +3 -3
  267. package/dist/language/ui.mjs +4 -4
  268. package/dist/language/word-match/preset.mjs +3 -3
  269. package/dist/logic/LogicBuildLab.d.mts +22 -0
  270. package/dist/logic/LogicBuildLab.mjs +170 -0
  271. package/dist/logic/LogicEditScene.d.mts +31 -0
  272. package/dist/logic/LogicEditScene.mjs +276 -0
  273. package/dist/logic/LogicEditor.d.mts +14 -0
  274. package/dist/logic/LogicEditor.mjs +413 -0
  275. package/dist/logic/LogicScene.d.mts +32 -0
  276. package/dist/logic/LogicScene.mjs +277 -0
  277. package/dist/logic/contract.d.mts +72 -0
  278. package/dist/logic/display.d.mts +24 -0
  279. package/dist/logic/display.mjs +127 -0
  280. package/dist/logic/edit-ops.d.mts +44 -0
  281. package/dist/logic/edit-ops.mjs +177 -0
  282. package/dist/logic/evaluate.d.mts +11 -0
  283. package/dist/logic/evaluate.mjs +93 -0
  284. package/dist/logic/gates.d.mts +10 -0
  285. package/dist/logic/gates.mjs +73 -0
  286. package/dist/logic/index.d.mts +14 -0
  287. package/dist/logic/index.mjs +13 -0
  288. package/dist/logic/lab.d.mts +32 -0
  289. package/dist/logic/lab.mjs +160 -0
  290. package/dist/logic/presets.d.mts +12 -0
  291. package/dist/logic/presets.mjs +241 -0
  292. package/dist/logic/registry.d.mts +9 -0
  293. package/dist/logic/registry.mjs +15 -0
  294. package/dist/math/area-model/preset.mjs +70 -44
  295. package/dist/math/balance-algebra/preset.mjs +14 -5
  296. package/dist/math/broken-tree/index.d.mts +1 -0
  297. package/dist/math/broken-tree/preset.d.mts +26 -0
  298. package/dist/math/broken-tree/preset.mjs +435 -0
  299. package/dist/math/circle/index.d.mts +1 -0
  300. package/dist/math/circle/preset.d.mts +44 -0
  301. package/dist/math/circle/preset.mjs +198 -0
  302. package/dist/math/complex/core.d.mts +93 -0
  303. package/dist/math/complex/core.mjs +239 -0
  304. package/dist/math/complex/index.d.mts +3 -0
  305. package/dist/math/complex/preset.d.mts +31 -0
  306. package/dist/math/complex/preset.mjs +377 -0
  307. package/dist/math/complex/rules.d.mts +6 -0
  308. package/dist/math/complex/rules.mjs +121 -0
  309. package/dist/math/conic/index.d.mts +1 -0
  310. package/dist/math/conic/preset.d.mts +30 -0
  311. package/dist/math/conic/preset.mjs +334 -0
  312. package/dist/math/derivation.mjs +5 -5
  313. package/dist/math/derivative-explorer/preset.mjs +5 -5
  314. package/dist/math/domain-range/index.d.mts +1 -0
  315. package/dist/math/domain-range/preset.d.mts +33 -0
  316. package/dist/math/domain-range/preset.mjs +313 -0
  317. package/dist/math/fraction-bar/index.d.mts +1 -0
  318. package/dist/math/fraction-bar/preset.d.mts +27 -0
  319. package/dist/math/fraction-bar/preset.mjs +197 -0
  320. package/dist/math/function-machine/preset.mjs +2 -2
  321. package/dist/math/gradient-descent.mjs +6 -6
  322. package/dist/math/grapher/preset.d.mts +1 -1
  323. package/dist/math/grapher/preset.mjs +4 -4
  324. package/dist/math/harmonic-form/preset.mjs +6 -6
  325. package/dist/math/index.d.mts +27 -2
  326. package/dist/math/index.mjs +27 -2
  327. package/dist/math/integral-explorer/preset.mjs +2 -2
  328. package/dist/math/interactive/preset.mjs +3 -3
  329. package/dist/math/limit-explorer/preset.mjs +4 -4
  330. package/dist/math/linear-model/index.d.mts +1 -0
  331. package/dist/math/linear-model/preset.d.mts +53 -0
  332. package/dist/math/linear-model/preset.mjs +164 -0
  333. package/dist/math/linear-system/preset.mjs +4 -4
  334. package/dist/math/mystery-bucket/preset.mjs +6 -6
  335. package/dist/math/number-line/preset.mjs +3 -2
  336. package/dist/math/parabola/preset.mjs +4 -3
  337. package/dist/math/pattern/preset.mjs +7 -13
  338. package/dist/math/percent-bar/index.d.mts +1 -0
  339. package/dist/math/percent-bar/preset.d.mts +37 -0
  340. package/dist/math/percent-bar/preset.mjs +275 -0
  341. package/dist/math/poly/core.d.mts +50 -0
  342. package/dist/math/poly/core.mjs +268 -0
  343. package/dist/math/poly/index.d.mts +3 -0
  344. package/dist/math/poly/preset.d.mts +23 -0
  345. package/dist/math/poly/preset.mjs +141 -0
  346. package/dist/math/poly/steps.d.mts +10 -0
  347. package/dist/math/poly/steps.mjs +99 -0
  348. package/dist/math/rate-machine/index.d.mts +1 -0
  349. package/dist/math/rate-machine/preset.d.mts +35 -0
  350. package/dist/math/rate-machine/preset.mjs +281 -0
  351. package/dist/math/ratio-share/index.d.mts +1 -0
  352. package/dist/math/ratio-share/preset.d.mts +24 -0
  353. package/dist/math/ratio-share/preset.mjs +204 -0
  354. package/dist/math/receipt/index.d.mts +1 -0
  355. package/dist/math/receipt/preset.d.mts +22 -0
  356. package/dist/math/receipt/preset.mjs +137 -0
  357. package/dist/math/sequence-predict/index.d.mts +1 -0
  358. package/dist/math/sequence-predict/preset.d.mts +34 -0
  359. package/dist/math/sequence-predict/preset.mjs +130 -0
  360. package/dist/math/straight-line/index.d.mts +1 -0
  361. package/dist/math/straight-line/preset.d.mts +37 -0
  362. package/dist/math/straight-line/preset.mjs +374 -0
  363. package/dist/math/system-solve/index.d.mts +1 -0
  364. package/dist/math/system-solve/preset.d.mts +21 -0
  365. package/dist/math/system-solve/preset.mjs +227 -0
  366. package/dist/math/transform/index.d.mts +1 -0
  367. package/dist/math/transform/preset.d.mts +41 -0
  368. package/dist/math/transform/preset.mjs +343 -0
  369. package/dist/math/triangle-trig/preset.mjs +12 -9
  370. package/dist/math/trig/core.d.mts +37 -0
  371. package/dist/math/trig/core.mjs +150 -0
  372. package/dist/math/trig/diagrams.d.mts +1 -0
  373. package/dist/math/trig/diagrams.mjs +321 -0
  374. package/dist/math/trig/index.d.mts +3 -0
  375. package/dist/math/trig/preset.d.mts +25 -0
  376. package/dist/math/trig/preset.mjs +260 -0
  377. package/dist/math/trig/rules.d.mts +6 -0
  378. package/dist/math/trig/rules.mjs +159 -0
  379. package/dist/math/trig-explorer.mjs +4 -4
  380. package/dist/ml/boundary/preset.mjs +8 -3
  381. package/dist/ml/classifier/preset.mjs +31 -6
  382. package/dist/ml/kmeans/preset.mjs +4 -4
  383. package/dist/ml/knn/preset.mjs +47 -12
  384. package/dist/ml/regression/preset.mjs +36 -7
  385. package/dist/physics/atwood/preset.mjs +4 -4
  386. package/dist/physics/bullet-walls/preset.d.mts +1 -1
  387. package/dist/physics/bullet-walls/preset.mjs +7 -7
  388. package/dist/physics/carnot/preset.mjs +6 -6
  389. package/dist/physics/circular-motion/preset.mjs +36 -5
  390. package/dist/physics/collision-track/preset.mjs +35 -5
  391. package/dist/physics/efficiency/preset.d.mts +2 -2
  392. package/dist/physics/efficiency/preset.mjs +5 -5
  393. package/dist/physics/electric-field/preset.mjs +32 -23
  394. package/dist/physics/electric-flux/index.d.mts +1 -0
  395. package/dist/physics/electric-flux/preset.d.mts +29 -0
  396. package/dist/physics/electric-flux/preset.mjs +264 -0
  397. package/dist/physics/energy-skate/preset.mjs +5 -5
  398. package/dist/physics/entropy/preset.mjs +7 -7
  399. package/dist/physics/expansion/preset.mjs +13 -13
  400. package/dist/physics/exponential/asset.mjs +1 -1
  401. package/dist/physics/exponential/preset.mjs +4 -4
  402. package/dist/physics/gas-process/preset.mjs +3 -3
  403. package/dist/physics/gauss-law/index.d.mts +1 -0
  404. package/dist/physics/gauss-law/preset.d.mts +20 -0
  405. package/dist/physics/gauss-law/preset.mjs +286 -0
  406. package/dist/physics/gravitation/preset.mjs +7 -7
  407. package/dist/physics/gravity-drop.mjs +4 -4
  408. package/dist/physics/heat-transfer/preset.d.mts +1 -1
  409. package/dist/physics/heat-transfer/preset.mjs +10 -10
  410. package/dist/physics/impulse/preset.mjs +5 -5
  411. package/dist/physics/index.d.mts +4 -1
  412. package/dist/physics/index.mjs +4 -1
  413. package/dist/physics/kepler/preset.mjs +4 -4
  414. package/dist/physics/lever/preset.mjs +3 -3
  415. package/dist/physics/lorentz/preset.mjs +11 -11
  416. package/dist/physics/magnetism/preset.mjs +3 -3
  417. package/dist/physics/optics/preset.mjs +2 -2
  418. package/dist/physics/orbit-lab.mjs +5 -5
  419. package/dist/physics/projectile-lab.mjs +4 -4
  420. package/dist/physics/rain-relative/preset.mjs +5 -5
  421. package/dist/physics/ramp-forces/preset.mjs +5 -5
  422. package/dist/physics/river-boat.mjs +6 -6
  423. package/dist/physics/shm/preset.mjs +9 -9
  424. package/dist/physics/stopping-distance/preset.mjs +3 -3
  425. package/dist/physics/temperature-scales/preset.mjs +105 -116
  426. package/dist/physics/terminal-velocity/preset.mjs +5 -5
  427. package/dist/physics/thermal/preset.mjs +5 -5
  428. package/dist/physics/vector-board/preset.mjs +7 -6
  429. package/dist/physics/vector-scene.mjs +2 -2
  430. package/dist/physics/vector-types/preset.mjs +37 -3
  431. package/dist/physics/water-density/preset.mjs +12 -12
  432. package/dist/physics/waves/doppler.mjs +2 -2
  433. package/dist/physics/waves/preset.mjs +4 -4
  434. package/dist/physics/waves/ripple.mjs +6 -6
  435. package/dist/physics/waves/string.mjs +5 -5
  436. package/dist/physics/work-energy/preset.mjs +4 -4
  437. package/dist/physics/work-potential/index.d.mts +1 -0
  438. package/dist/physics/work-potential/preset.d.mts +20 -0
  439. package/dist/physics/work-potential/preset.mjs +276 -0
  440. package/dist/schemas/index.d.mts +6 -6
  441. package/dist/schemas/index.mjs +3 -3
  442. package/dist/statistics/center-spread/preset.mjs +3 -3
  443. package/dist/statistics/core/descriptive.d.mts +2 -2
  444. package/dist/statistics/core/descriptive.mjs +2 -2
  445. package/dist/statistics/core/normal.d.mts +3 -3
  446. package/dist/statistics/core/normal.mjs +3 -3
  447. package/dist/statistics/core/sequences.d.mts +1 -1
  448. package/dist/statistics/galton/preset.mjs +2 -2
  449. package/dist/statistics/histogram/preset.mjs +6 -6
  450. package/dist/statistics/normal/preset.mjs +2 -2
  451. package/dist/statistics/sampling/preset.mjs +4 -4
  452. package/dist/statistics/sequence/preset.mjs +58 -15
  453. package/dist/statistics/z-table/preset.mjs +17 -4
  454. package/package.json +11 -3
  455. package/styles.css +4 -1
@@ -10,63 +10,82 @@ const BG = "var(--stage-bg)";
10
10
  const FG = "var(--stage-fg)";
11
11
  const CHARGE = "var(--stage-charge)";
12
12
  const SHEEN = "color-mix(in oklab, var(--stage-sheen) 45%, transparent)";
13
- /** The two leads + terminal nubs from each terminal to the body edge at ±bodyHalf. */
13
+ const C_RESISTOR = "var(--stage-resistor, oklch(0.74 0.09 70))";
14
+ const C_CAP = "var(--stage-capacitor, oklch(0.6 0.14 250))";
15
+ const C_DIODE = "var(--stage-diode, oklch(0.56 0.16 290))";
16
+ const C_CELL = "var(--stage-cell, oklch(0.58 0.18 28))";
17
+ const C_LAMP = "var(--stage-warn, oklch(0.78 0.15 75))";
18
+ const C_SWITCH = "var(--stage-switch, oklch(0.6 0.04 250))";
19
+ const C_MOS = "var(--stage-mosfet, oklch(0.57 0.13 300))";
20
+ const C_BAND = [
21
+ "oklch(0.45 0.08 50)",
22
+ "oklch(0.55 0.18 28)",
23
+ "oklch(0.6 0.15 75)"
24
+ ];
25
+ const tint = (c, pct = 12) => `color-mix(in oklab, ${c} ${pct}%, ${BG})`;
26
+ /** The two clean leads from each terminal to the body edge at ±bodyHalf (no nubs, no bloat). */
14
27
  function Leads({ cx, cy, half, bodyHalf, live }) {
15
28
  const wire = live ? LIVE : WIRE;
16
- return /* @__PURE__ */ jsxs("g", { children: [
17
- /* @__PURE__ */ jsx("line", {
18
- x1: cx - half,
19
- y1: cy,
20
- x2: cx - bodyHalf,
21
- y2: cy,
22
- stroke: wire,
23
- strokeWidth: 2.5,
24
- strokeLinecap: "round"
25
- }),
26
- /* @__PURE__ */ jsx("line", {
27
- x1: cx + bodyHalf,
28
- y1: cy,
29
- x2: cx + half,
30
- y2: cy,
31
- stroke: wire,
32
- strokeWidth: 2.5,
33
- strokeLinecap: "round"
34
- }),
35
- /* @__PURE__ */ jsx("circle", {
36
- cx: cx - half,
37
- cy,
38
- r: 2.6,
39
- fill: METAL
40
- }),
41
- /* @__PURE__ */ jsx("circle", {
42
- cx: cx + half,
43
- cy,
44
- r: 2.6,
45
- fill: METAL
46
- })
47
- ] });
29
+ return /* @__PURE__ */ jsxs("g", { children: [/* @__PURE__ */ jsx("line", {
30
+ x1: cx - half,
31
+ y1: cy,
32
+ x2: cx - bodyHalf,
33
+ y2: cy,
34
+ stroke: wire,
35
+ strokeWidth: 2,
36
+ strokeLinecap: "round"
37
+ }), /* @__PURE__ */ jsx("line", {
38
+ x1: cx + bodyHalf,
39
+ y1: cy,
40
+ x2: cx + half,
41
+ y2: cy,
42
+ stroke: wire,
43
+ strokeWidth: 2,
44
+ strokeLinecap: "round"
45
+ })] });
46
+ }
47
+ /**
48
+ * Tag — an SVG text label with a background HALO (a stroke in the bg colour painted under
49
+ * the fill). ALWAYS use this instead of a bare <text> in a schematic: it keeps labels
50
+ * readable wherever they land, so a label crossing a wire or sitting on a fill never turns
51
+ * into mud. (This is the same paint-order trick the stage axis labels use.)
52
+ */
53
+ function Tag({ x, y, text, color = FG, size = 11, weight = 600, anchor = "middle", halo = BG }) {
54
+ return /* @__PURE__ */ jsx("text", {
55
+ x,
56
+ y,
57
+ fill: color,
58
+ fontSize: size,
59
+ fontWeight: weight,
60
+ textAnchor: anchor,
61
+ style: {
62
+ pointerEvents: "none",
63
+ paintOrder: "stroke",
64
+ stroke: halo,
65
+ strokeWidth: 3.5,
66
+ strokeLinejoin: "round"
67
+ },
68
+ children: text
69
+ });
48
70
  }
49
- /** Value/name label above a body of half-height `bodyH`. */
71
+ /** Value/name label above a body of half-height `bodyH` (haloed via Tag). */
50
72
  function GlyphLabel({ cx, cy, bodyH, label }) {
51
73
  if (!label) return null;
52
- return /* @__PURE__ */ jsx("text", {
74
+ return /* @__PURE__ */ jsx(Tag, {
53
75
  x: cx,
54
76
  y: cy - bodyH - 7,
55
- fill: FG,
56
- fontSize: 11,
57
- fontWeight: 600,
58
- textAnchor: "middle",
59
- style: { pointerEvents: "none" },
60
- children: label
77
+ text: label
61
78
  });
62
79
  }
63
80
  /**
64
- * RESISTOR — the IEC/CAIE rectangle (an open box interrupting the wire). The
81
+ * RESISTOR, the IEC/CAIE rectangle (an open box interrupting the wire). The
65
82
  * exam-standard symbol; clean token fill + metal outline + a top-edge sheen.
66
83
  */
67
84
  function ResistorGlyph({ cx, cy, half, live, label }) {
68
- const bw = 21;
69
- const bh = 10;
85
+ const bw = 22;
86
+ const bh = 11;
87
+ const body = `color-mix(in oklab, ${C_RESISTOR} 78%, ${BG})`;
88
+ const edge = `color-mix(in oklab, ${C_RESISTOR} 60%, #000)`;
70
89
  return /* @__PURE__ */ jsxs("g", { children: [
71
90
  /* @__PURE__ */ jsx(Leads, {
72
91
  cx,
@@ -80,16 +99,24 @@ function ResistorGlyph({ cx, cy, half, live, label }) {
80
99
  y: cy - bh,
81
100
  width: bw * 2,
82
101
  height: bh * 2,
83
- rx: 3,
84
- fill: BG,
85
- stroke: live ? LIVE : METAL,
86
- strokeWidth: 2
102
+ rx: bh * .85,
103
+ fill: body,
104
+ stroke: edge,
105
+ strokeWidth: 1.5
87
106
  }),
107
+ C_BAND.map((c, i) => /* @__PURE__ */ jsx("rect", {
108
+ x: cx - 8 + i * 7,
109
+ y: cy - bh + 2,
110
+ width: 3,
111
+ height: bh * 2 - 4,
112
+ rx: 1,
113
+ fill: c
114
+ }, i)),
88
115
  /* @__PURE__ */ jsx("line", {
89
116
  x1: cx - bw * .7,
90
- y1: cy - bh + 1.5,
117
+ y1: cy - bh + 2.5,
91
118
  x2: cx + bw * .7,
92
- y2: cy - bh + 1.5,
119
+ y2: cy - bh + 2.5,
93
120
  stroke: SHEEN,
94
121
  strokeWidth: 1.4,
95
122
  strokeLinecap: "round"
@@ -103,7 +130,7 @@ function ResistorGlyph({ cx, cy, half, live, label }) {
103
130
  ] });
104
131
  }
105
132
  /**
106
- * CELL / BATTERY — one long thin plate (+) and one short thick plate (−). Pass
133
+ * CELL / BATTERY, one long thin plate (+) and one short thick plate (−). Pass
107
134
  * `cells` > 1 to draw a battery (repeated plate pairs). EMF label above.
108
135
  */
109
136
  function CellGlyph({ cx, cy, half, live, label, cells = 1 }) {
@@ -121,7 +148,7 @@ function CellGlyph({ cx, cy, half, live, label, cells = 1 }) {
121
148
  y1: cy - longH,
122
149
  x2: x,
123
150
  y2: cy + longH,
124
- stroke: METAL,
151
+ stroke: C_CELL,
125
152
  strokeWidth: 2,
126
153
  strokeLinecap: "round"
127
154
  }, `l${i}`));
@@ -131,7 +158,7 @@ function CellGlyph({ cx, cy, half, live, label, cells = 1 }) {
131
158
  y1: cy - shortH,
132
159
  x2: x,
133
160
  y2: cy + shortH,
134
- stroke: METAL,
161
+ stroke: C_CELL,
135
162
  strokeWidth: 4.5,
136
163
  strokeLinecap: "round"
137
164
  }, `s${i}`));
@@ -155,12 +182,12 @@ function CellGlyph({ cx, cy, half, live, label, cells = 1 }) {
155
182
  ] });
156
183
  }
157
184
  /**
158
- * CAPACITOR — two parallel plates with a visible STORED-CHARGE field between them
185
+ * CAPACITOR, two parallel plates with a visible STORED-CHARGE field between them
159
186
  * and an optional LEAK. This is the centerpiece glyph: `charge` (0..1) sets how
160
187
  * many field lines bridge the plates and their intensity, so a charging cap fills
161
188
  * and a leaking cap visibly empties; `leaking` + `leakPhase` drip charge off the
162
189
  * lower plate (the "why capacitors don't hold charge forever" picture). All motion
163
- * is data — the lab's RC integrator lowers `charge` and advances `leakPhase`.
190
+ * is data, the lab's RC integrator lowers `charge` and advances `leakPhase`.
164
191
  */
165
192
  function CapacitorGlyph({ cx, cy, half, live, label, charge = 0, leaking, leakPhase = 0, polarised }) {
166
193
  const q = Math.max(0, Math.min(1, charge));
@@ -204,20 +231,29 @@ function CapacitorGlyph({ cx, cy, half, live, label, charge = 0, leaking, leakPh
204
231
  bodyHalf,
205
232
  live
206
233
  }),
234
+ q > .02 && /* @__PURE__ */ jsx("rect", {
235
+ x: lx + 1,
236
+ y: cy - plateH,
237
+ width: rx - lx - 2,
238
+ height: plateH * 2,
239
+ fill: C_CAP,
240
+ opacity: .12 + .4 * q,
241
+ rx: 1
242
+ }),
207
243
  field,
208
244
  /* @__PURE__ */ jsx("line", {
209
245
  x1: lx,
210
246
  y1: cy - plateH,
211
247
  x2: lx,
212
248
  y2: cy + plateH,
213
- stroke: METAL,
214
- strokeWidth: 3.5,
249
+ stroke: C_CAP,
250
+ strokeWidth: 4,
215
251
  strokeLinecap: "round"
216
252
  }),
217
253
  polarised ? /* @__PURE__ */ jsx("path", {
218
254
  d: `M ${rx} ${cy - plateH} Q ${rx + 5} ${cy} ${rx} ${cy + plateH}`,
219
255
  fill: "none",
220
- stroke: METAL,
256
+ stroke: C_CAP,
221
257
  strokeWidth: 3.5,
222
258
  strokeLinecap: "round"
223
259
  }) : /* @__PURE__ */ jsx("line", {
@@ -225,7 +261,7 @@ function CapacitorGlyph({ cx, cy, half, live, label, charge = 0, leaking, leakPh
225
261
  y1: cy - plateH,
226
262
  x2: rx,
227
263
  y2: cy + plateH,
228
- stroke: METAL,
264
+ stroke: C_CAP,
229
265
  strokeWidth: 3.5,
230
266
  strokeLinecap: "round"
231
267
  }),
@@ -248,6 +284,462 @@ function CapacitorGlyph({ cx, cy, half, live, label, charge = 0, leaking, leakPh
248
284
  })
249
285
  ] });
250
286
  }
287
+ /**
288
+ * SWITCH (SPST), the exam-standard open/closed switch: two terminal contacts and
289
+ * a hinged lever off the left contact. Closed → lever lies horizontal onto the
290
+ * right contact (energised path picks up the live colour); open → lever lifts
291
+ * ~40° and the gap is drawn in the warn/neutral colour.
292
+ */
293
+ function SwitchGlyph({ cx, cy, half, live, label, closed }) {
294
+ const bw = 18;
295
+ const hx = cx - bw;
296
+ const tx = cx + bw;
297
+ const len = bw * 2;
298
+ const ang = closed ? 0 : -40 * (Math.PI / 180);
299
+ const ex = hx + len * Math.cos(ang);
300
+ const ey = cy + len * Math.sin(ang);
301
+ const lever = closed ? C_SWITCH : "var(--stage-warn)";
302
+ const bodyH = closed ? 4 : len * Math.sin(-ang) + 4;
303
+ return /* @__PURE__ */ jsxs("g", { children: [
304
+ /* @__PURE__ */ jsx(Leads, {
305
+ cx,
306
+ cy,
307
+ half,
308
+ bodyHalf: bw,
309
+ live
310
+ }),
311
+ /* @__PURE__ */ jsx("circle", {
312
+ cx: hx,
313
+ cy,
314
+ r: 3.4,
315
+ fill: C_SWITCH
316
+ }),
317
+ /* @__PURE__ */ jsx("circle", {
318
+ cx: tx,
319
+ cy,
320
+ r: 3.4,
321
+ fill: C_SWITCH
322
+ }),
323
+ /* @__PURE__ */ jsx("line", {
324
+ x1: hx,
325
+ y1: cy,
326
+ x2: ex,
327
+ y2: ey,
328
+ stroke: lever,
329
+ strokeWidth: 3.6,
330
+ strokeLinecap: "round"
331
+ }),
332
+ /* @__PURE__ */ jsx("line", {
333
+ x1: hx,
334
+ y1: cy - 1.4,
335
+ x2: ex,
336
+ y2: ey - 1.4,
337
+ stroke: SHEEN,
338
+ strokeWidth: 1.2,
339
+ strokeLinecap: "round"
340
+ }),
341
+ /* @__PURE__ */ jsx(GlyphLabel, {
342
+ cx,
343
+ cy,
344
+ bodyH,
345
+ label
346
+ })
347
+ ] });
348
+ }
349
+ /**
350
+ * FILAMENT LAMP, the exam-standard circle with an inscribed × cross (NOT a ~,
351
+ * which is the AC-source mark). When `live`, a warm glow halo (var(--stage-warn))
352
+ * whose radius + opacity scale with `brightness` blooms behind the bulb and the
353
+ * cross brightens; when dark, the cross is neutral metal. `bodyHalf` ≈ the circle
354
+ * radius, so it lines up with ResistorGlyph. Glow is DATA, the host drives
355
+ * `brightness` from the circuit's power.
356
+ */
357
+ function BulbGlyph({ cx, cy, half, live, label, brightness = 0 }) {
358
+ const r = 16;
359
+ const b = Math.max(0, Math.min(1, brightness));
360
+ const lit = live && b > .02;
361
+ const k = r * Math.SQRT1_2;
362
+ const crossStroke = lit ? C_LAMP : METAL;
363
+ const ring = lit ? C_LAMP : METAL;
364
+ return /* @__PURE__ */ jsxs("g", { children: [
365
+ lit && /* @__PURE__ */ jsx("circle", {
366
+ cx,
367
+ cy,
368
+ r: 20 + b * 12,
369
+ fill: "var(--stage-warn)",
370
+ opacity: .12 + .32 * b,
371
+ style: { pointerEvents: "none" }
372
+ }),
373
+ /* @__PURE__ */ jsx(Leads, {
374
+ cx,
375
+ cy,
376
+ half,
377
+ bodyHalf: r,
378
+ live
379
+ }),
380
+ /* @__PURE__ */ jsx("circle", {
381
+ cx,
382
+ cy,
383
+ r,
384
+ fill: lit ? tint(C_LAMP, 18) : BG,
385
+ stroke: ring,
386
+ strokeWidth: 2
387
+ }),
388
+ /* @__PURE__ */ jsx("line", {
389
+ x1: cx - k,
390
+ y1: cy - k,
391
+ x2: cx + k,
392
+ y2: cy + k,
393
+ stroke: crossStroke,
394
+ strokeWidth: 2.5,
395
+ strokeLinecap: "round"
396
+ }),
397
+ /* @__PURE__ */ jsx("line", {
398
+ x1: cx - k,
399
+ y1: cy + k,
400
+ x2: cx + k,
401
+ y2: cy - k,
402
+ stroke: crossStroke,
403
+ strokeWidth: 2.5,
404
+ strokeLinecap: "round"
405
+ }),
406
+ /* @__PURE__ */ jsx("path", {
407
+ d: `M ${cx - r * .62} ${cy - r * .62} A ${r} ${r} 0 0 1 ${cx + r * .18} ${cy - r * .86}`,
408
+ fill: "none",
409
+ stroke: SHEEN,
410
+ strokeWidth: 1.4,
411
+ strokeLinecap: "round"
412
+ }),
413
+ /* @__PURE__ */ jsx(GlyphLabel, {
414
+ cx,
415
+ cy,
416
+ bodyH: r,
417
+ label
418
+ })
419
+ ] });
420
+ }
421
+ /**
422
+ * DIODE, the exam-standard symbol: a filled triangle (anode, current →) pointing
423
+ * right into a vertical bar (cathode). Current flows anode→cathode only; when it is
424
+ * forward-biased and `live`, the triangle, bar and leads light up (`conducting`).
425
+ */
426
+ function DiodeGlyph({ cx, cy, half, live, label, conducting }) {
427
+ const bw = 16;
428
+ const bh = 13;
429
+ const on = !!(conducting && live);
430
+ const accent = C_DIODE;
431
+ const apex = cx + bw;
432
+ return /* @__PURE__ */ jsxs("g", { children: [
433
+ /* @__PURE__ */ jsx(Leads, {
434
+ cx,
435
+ cy,
436
+ half,
437
+ bodyHalf: bw,
438
+ live: on
439
+ }),
440
+ /* @__PURE__ */ jsx("path", {
441
+ d: `M ${cx - bw} ${cy - bh} L ${apex} ${cy} L ${cx - bw} ${cy + bh} Z`,
442
+ fill: tint(C_DIODE, on ? 38 : 14),
443
+ stroke: accent,
444
+ strokeWidth: 2,
445
+ strokeLinejoin: "round"
446
+ }),
447
+ /* @__PURE__ */ jsx("line", {
448
+ x1: apex,
449
+ y1: cy - bh,
450
+ x2: apex,
451
+ y2: cy + bh,
452
+ stroke: accent,
453
+ strokeWidth: 3,
454
+ strokeLinecap: "round"
455
+ }),
456
+ /* @__PURE__ */ jsx("line", {
457
+ x1: cx - bw + 1.5,
458
+ y1: cy - bh + 1.5,
459
+ x2: apex - 1.5,
460
+ y2: cy - 1,
461
+ stroke: SHEEN,
462
+ strokeWidth: 1.4,
463
+ strokeLinecap: "round"
464
+ }),
465
+ /* @__PURE__ */ jsx(GlyphLabel, {
466
+ cx,
467
+ cy,
468
+ bodyH: bh,
469
+ label
470
+ })
471
+ ] });
472
+ }
473
+ /**
474
+ * AMMETER, the exam-standard meter symbol: a circle on the wire with a centered
475
+ * capital "A". Energised circle picks up the live colour; the `reading` (e.g.
476
+ * "0.5 A") sits above the body as the value label.
477
+ */
478
+ function AmmeterGlyph({ cx, cy, half, live, label, reading }) {
479
+ const r = 17;
480
+ const ring = live ? LIVE : METAL;
481
+ return /* @__PURE__ */ jsxs("g", { children: [
482
+ /* @__PURE__ */ jsx(Leads, {
483
+ cx,
484
+ cy,
485
+ half,
486
+ bodyHalf: r,
487
+ live
488
+ }),
489
+ /* @__PURE__ */ jsx("circle", {
490
+ cx,
491
+ cy,
492
+ r,
493
+ fill: BG,
494
+ stroke: ring,
495
+ strokeWidth: 2
496
+ }),
497
+ /* @__PURE__ */ jsx("path", {
498
+ d: `M ${cx - r * .6} ${cy - r * .45} A ${r} ${r} 0 0 1 ${cx + r * .6} ${cy - r * .45}`,
499
+ fill: "none",
500
+ stroke: SHEEN,
501
+ strokeWidth: 1.4,
502
+ strokeLinecap: "round"
503
+ }),
504
+ /* @__PURE__ */ jsx("text", {
505
+ x: cx,
506
+ y: cy,
507
+ fill: ring,
508
+ fontSize: 16,
509
+ fontWeight: 700,
510
+ textAnchor: "middle",
511
+ dominantBaseline: "central",
512
+ style: { pointerEvents: "none" },
513
+ children: "A"
514
+ }),
515
+ /* @__PURE__ */ jsx(GlyphLabel, {
516
+ cx,
517
+ cy,
518
+ bodyH: r,
519
+ label: reading ?? label
520
+ })
521
+ ] });
522
+ }
523
+ /**
524
+ * JUNCTION DOT, the wire-junction marker: a single filled node placed where
525
+ * wires meet to show they are electrically connected (vs. a crossing). Not a
526
+ * two-terminal device, so no `Leads`; energised junctions pick up the live colour.
527
+ */
528
+ function JunctionDot({ x, y, r = 4, live, color }) {
529
+ return /* @__PURE__ */ jsxs("g", { children: [/* @__PURE__ */ jsx("circle", {
530
+ cx: x,
531
+ cy: y,
532
+ r,
533
+ fill: live ? color ?? LIVE : METAL
534
+ }), /* @__PURE__ */ jsx("path", {
535
+ d: `M ${x - r * .55} ${y - r * .55} A ${r} ${r} 0 0 1 ${x + r * .55} ${y - r * .55}`,
536
+ fill: "none",
537
+ stroke: SHEEN,
538
+ strokeWidth: 1.2,
539
+ strokeLinecap: "round"
540
+ })] });
541
+ }
542
+ /**
543
+ * NMOS (enhancement) transistor, the exam-standard symbol turned for a circuit:
544
+ * DRAIN at top, SOURCE at bottom, GATE out the left. The gate bar is separated from
545
+ * the channel by the oxide gap; the channel is the three dashes of an enhancement
546
+ * device (normally off); the body arrow points inward (NMOS). When `on`, the channel
547
+ * and drain-source path pick up the live colour.
548
+ */
549
+ function MosfetGlyph({ cx, cy, half, gateLen = 24, on, live, pmos, label, labelPos = "right" }) {
550
+ const ch = on && live ? LIVE : C_MOS;
551
+ const wire = live ? LIVE : WIRE;
552
+ const gx = cx - 13;
553
+ const chx = cx - 4;
554
+ const ext = cx + 9;
555
+ const top = cy - half, bot = cy + half;
556
+ const gateTermX = gx - gateLen;
557
+ return /* @__PURE__ */ jsxs("g", { children: [
558
+ /* @__PURE__ */ jsx("line", {
559
+ x1: gateTermX,
560
+ y1: cy,
561
+ x2: pmos ? gx - 9 : gx,
562
+ y2: cy,
563
+ stroke: wire,
564
+ strokeWidth: 2.5,
565
+ strokeLinecap: "round"
566
+ }),
567
+ pmos && /* @__PURE__ */ jsx("circle", {
568
+ cx: gx - 5,
569
+ cy,
570
+ r: 4,
571
+ fill: BG,
572
+ stroke: C_MOS,
573
+ strokeWidth: 1.6
574
+ }),
575
+ /* @__PURE__ */ jsx("line", {
576
+ x1: gx,
577
+ y1: cy - 13,
578
+ x2: gx,
579
+ y2: cy + 13,
580
+ stroke: C_MOS,
581
+ strokeWidth: 2.5,
582
+ strokeLinecap: "round"
583
+ }),
584
+ [
585
+ [-13, -5],
586
+ [-3, 5],
587
+ [7, 13]
588
+ ].map(([a, b], i) => /* @__PURE__ */ jsx("line", {
589
+ x1: chx,
590
+ y1: cy + a,
591
+ x2: chx,
592
+ y2: cy + b,
593
+ stroke: ch,
594
+ strokeWidth: 3,
595
+ strokeLinecap: "round"
596
+ }, i)),
597
+ /* @__PURE__ */ jsx("line", {
598
+ x1: chx,
599
+ y1: cy - 9,
600
+ x2: ext,
601
+ y2: cy - 9,
602
+ stroke: ch,
603
+ strokeWidth: 2.5,
604
+ strokeLinecap: "round"
605
+ }),
606
+ /* @__PURE__ */ jsx("line", {
607
+ x1: ext,
608
+ y1: cy - 9,
609
+ x2: ext,
610
+ y2: top,
611
+ stroke: wire,
612
+ strokeWidth: 2.5,
613
+ strokeLinecap: "round"
614
+ }),
615
+ /* @__PURE__ */ jsx("line", {
616
+ x1: chx,
617
+ y1: cy + 9,
618
+ x2: ext,
619
+ y2: cy + 9,
620
+ stroke: ch,
621
+ strokeWidth: 2.5,
622
+ strokeLinecap: "round"
623
+ }),
624
+ /* @__PURE__ */ jsx("line", {
625
+ x1: ext,
626
+ y1: cy + 9,
627
+ x2: ext,
628
+ y2: bot,
629
+ stroke: wire,
630
+ strokeWidth: 2.5,
631
+ strokeLinecap: "round"
632
+ }),
633
+ /* @__PURE__ */ jsx("path", {
634
+ d: `M ${chx + 9} ${cy + 6} L ${chx + 2} ${cy + 9} L ${chx + 9} ${cy + 12} Z`,
635
+ fill: ch
636
+ }),
637
+ /* @__PURE__ */ jsx("circle", {
638
+ cx: ext,
639
+ cy: top,
640
+ r: 2.6,
641
+ fill: METAL
642
+ }),
643
+ /* @__PURE__ */ jsx("circle", {
644
+ cx: ext,
645
+ cy: bot,
646
+ r: 2.6,
647
+ fill: METAL
648
+ }),
649
+ /* @__PURE__ */ jsx("circle", {
650
+ cx: gateTermX,
651
+ cy,
652
+ r: 2.6,
653
+ fill: METAL
654
+ }),
655
+ label && (labelPos === "top" ? /* @__PURE__ */ jsx("text", {
656
+ x: cx,
657
+ y: top - 7,
658
+ fill: FG,
659
+ fontSize: 11,
660
+ fontWeight: 600,
661
+ textAnchor: "middle",
662
+ style: { pointerEvents: "none" },
663
+ children: label
664
+ }) : /* @__PURE__ */ jsx("text", {
665
+ x: ext + 7,
666
+ y: cy,
667
+ fill: FG,
668
+ fontSize: 11,
669
+ fontWeight: 600,
670
+ textAnchor: "start",
671
+ dominantBaseline: "central",
672
+ style: { pointerEvents: "none" },
673
+ children: label
674
+ }))
675
+ ] });
676
+ }
677
+ /** A thin, crisp wire polyline through pixel points; energised path picks up the live colour (or a
678
+ * per-net `color` override, so a scene can colour each signal so it stays traceable where wires cross). */
679
+ function Wire({ points, live, color }) {
680
+ return /* @__PURE__ */ jsx("polyline", {
681
+ points: points.map((p) => `${p[0]},${p[1]}`).join(" "),
682
+ fill: "none",
683
+ stroke: live ? color ?? LIVE : WIRE,
684
+ strokeWidth: 2,
685
+ strokeLinejoin: "round",
686
+ strokeLinecap: "round"
687
+ });
688
+ }
689
+ /** Orthogonal (right-angle) route from a left source to a right sink, as polyline points for
690
+ * `Wire`: straight when aligned, otherwise out to a mid-x, vertical, then in. One wire model
691
+ * shared by the electronics and logic scenes (no second wire primitive). */
692
+ function orthPoints(a, b) {
693
+ if (Math.abs(a.y - b.y) < 1.5) return [[a.x, a.y], [b.x, b.y]];
694
+ const midX = a.x + Math.max(14, (b.x - a.x) * .5);
695
+ return [
696
+ [a.x, a.y],
697
+ [midX, a.y],
698
+ [midX, b.y],
699
+ [b.x, b.y]
700
+ ];
701
+ }
702
+ function pathLength(points) {
703
+ let t = 0;
704
+ for (let i = 1; i < points.length; i++) t += Math.hypot(points[i][0] - points[i - 1][0], points[i][1] - points[i - 1][1]);
705
+ return t;
706
+ }
707
+ /** Point a fraction t∈[0,1] along a pixel polyline (for placing current dots). */
708
+ function pointAlong(points, t) {
709
+ if (points.length < 2) return points[0] ?? [0, 0];
710
+ const segs = points.slice(1).map((p, i) => Math.hypot(p[0] - points[i][0], p[1] - points[i][1]));
711
+ const total = segs.reduce((a, b) => a + b, 0) || 1;
712
+ let d = (t % 1 + 1) % 1 * total;
713
+ for (let i = 0; i < segs.length; i++) {
714
+ if (d <= segs[i]) {
715
+ const f = segs[i] ? d / segs[i] : 0;
716
+ const a = points[i], b = points[i + 1];
717
+ return [a[0] + (b[0] - a[0]) * f, a[1] + (b[1] - a[1]) * f];
718
+ }
719
+ d -= segs[i];
720
+ }
721
+ return points[points.length - 1];
722
+ }
723
+ /**
724
+ * Conventional current as clean, evenly-spaced dots drifting along a wire path.
725
+ * Auto-spaces by arc length (one dot per ~`spacing` px) so it reads as flow, not
726
+ * noise — Brilliant-style. `phase` (0..1) animates them.
727
+ */
728
+ function FlowDots({ points, phase = 0, spacing = 60, r = 3.5 }) {
729
+ const n = Math.max(3, Math.round(pathLength(points) / spacing));
730
+ return /* @__PURE__ */ jsx("g", {
731
+ style: { pointerEvents: "none" },
732
+ children: Array.from({ length: n }, (_, i) => {
733
+ const [x, y] = pointAlong(points, phase + i / n);
734
+ return /* @__PURE__ */ jsx("circle", {
735
+ cx: x,
736
+ cy: y,
737
+ r,
738
+ fill: LIVE
739
+ }, i);
740
+ })
741
+ });
742
+ }
251
743
  function LampGlyph({ cx, cy, brightness, r = 30 }) {
252
744
  const b = Math.max(0, Math.min(1, brightness));
253
745
  const hot = b > .04;
@@ -354,4 +846,4 @@ function AcDcSourceGlyph({ cx, cy, mode, level, r = 30 }) {
354
846
  }
355
847
 
356
848
  //#endregion
357
- export { AcDcSourceGlyph, CapacitorGlyph, CellGlyph, LampGlyph, ResistorGlyph };
849
+ export { AcDcSourceGlyph, AmmeterGlyph, BulbGlyph, CapacitorGlyph, CellGlyph, DiodeGlyph, FlowDots, JunctionDot, LampGlyph, MosfetGlyph, ResistorGlyph, SwitchGlyph, Tag, Wire, orthPoints };