web-a2e 1.0.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 (295) hide show
  1. package/.clangd +5 -0
  2. package/.mcp.json +12 -0
  3. package/CLAUDE.md +362 -0
  4. package/CMakeLists.txt +774 -0
  5. package/LICENSE +21 -0
  6. package/README.md +392 -0
  7. package/build-wasm/generated/roms.cpp +2447 -0
  8. package/docker-compose.staging.yml +9 -0
  9. package/docs/basic-rom-disassembly.md +6663 -0
  10. package/docs/softswitch-comparison.md +273 -0
  11. package/docs/thunderclock-debug.md +89 -0
  12. package/examples/cube.bas +72 -0
  13. package/examples/hello.s +55 -0
  14. package/examples/scroll.s +140 -0
  15. package/package.json +18 -0
  16. package/public/assets/apple-logo-old.png +0 -0
  17. package/public/assets/apple-logo.png +0 -0
  18. package/public/assets/drive-closed-light-on.png +0 -0
  19. package/public/assets/drive-closed.png +0 -0
  20. package/public/assets/drive-open-light-on.png +0 -0
  21. package/public/assets/drive-open.png +0 -0
  22. package/public/audio-worklet.js +82 -0
  23. package/public/disks/Apple DOS 3.3 January 1983.dsk +0 -0
  24. package/public/disks/ProDOS 2.4.3.po +0 -0
  25. package/public/disks/h32mb.2mg +0 -0
  26. package/public/disks/library.json +26 -0
  27. package/public/docs/llms/llm-assembler.txt +90 -0
  28. package/public/docs/llms/llm-basic-program.txt +256 -0
  29. package/public/docs/llms/llm-disk-drives.txt +72 -0
  30. package/public/docs/llms/llm-file-explorer.txt +50 -0
  31. package/public/docs/llms/llm-hard-drives.txt +80 -0
  32. package/public/docs/llms/llm-main.txt +51 -0
  33. package/public/docs/llms/llm-slot-configuration.txt +66 -0
  34. package/public/icons/icon-192.svg +4 -0
  35. package/public/icons/icon-512.svg +4 -0
  36. package/public/index.html +661 -0
  37. package/public/llms.txt +49 -0
  38. package/public/manifest.json +29 -0
  39. package/public/shaders/burnin.glsl +22 -0
  40. package/public/shaders/crt.glsl +706 -0
  41. package/public/shaders/edge.glsl +109 -0
  42. package/public/shaders/vertex.glsl +8 -0
  43. package/public/sw.js +186 -0
  44. package/roms/341-0027.bin +0 -0
  45. package/roms/341-0160-A-US-UK.bin +0 -0
  46. package/roms/341-0160-A.bin +0 -0
  47. package/roms/342-0273-A-US-UK.bin +0 -0
  48. package/roms/342-0349-B-C0-FF.bin +0 -0
  49. package/roms/Apple Mouse Interface Card ROM - 342-0270-C.bin +0 -0
  50. package/roms/Thunderclock Plus ROM.bin +0 -0
  51. package/scripts/generate_roms.sh +69 -0
  52. package/src/bindings/wasm_interface.cpp +1940 -0
  53. package/src/core/assembler/assembler.cpp +1239 -0
  54. package/src/core/assembler/assembler.hpp +115 -0
  55. package/src/core/audio/audio.cpp +160 -0
  56. package/src/core/audio/audio.hpp +81 -0
  57. package/src/core/basic/basic_detokenizer.cpp +436 -0
  58. package/src/core/basic/basic_detokenizer.hpp +41 -0
  59. package/src/core/basic/basic_tokenizer.cpp +286 -0
  60. package/src/core/basic/basic_tokenizer.hpp +26 -0
  61. package/src/core/basic/basic_tokens.hpp +295 -0
  62. package/src/core/cards/disk2_card.cpp +568 -0
  63. package/src/core/cards/disk2_card.hpp +316 -0
  64. package/src/core/cards/expansion_card.hpp +185 -0
  65. package/src/core/cards/mockingboard/ay8910.cpp +616 -0
  66. package/src/core/cards/mockingboard/ay8910.hpp +159 -0
  67. package/src/core/cards/mockingboard/via6522.cpp +530 -0
  68. package/src/core/cards/mockingboard/via6522.hpp +163 -0
  69. package/src/core/cards/mockingboard_card.cpp +312 -0
  70. package/src/core/cards/mockingboard_card.hpp +159 -0
  71. package/src/core/cards/mouse_card.cpp +654 -0
  72. package/src/core/cards/mouse_card.hpp +190 -0
  73. package/src/core/cards/smartport/block_device.cpp +202 -0
  74. package/src/core/cards/smartport/block_device.hpp +60 -0
  75. package/src/core/cards/smartport/smartport_card.cpp +603 -0
  76. package/src/core/cards/smartport/smartport_card.hpp +120 -0
  77. package/src/core/cards/thunderclock_card.cpp +237 -0
  78. package/src/core/cards/thunderclock_card.hpp +122 -0
  79. package/src/core/cpu/cpu6502.cpp +1609 -0
  80. package/src/core/cpu/cpu6502.hpp +203 -0
  81. package/src/core/debug/condition_evaluator.cpp +470 -0
  82. package/src/core/debug/condition_evaluator.hpp +87 -0
  83. package/src/core/disassembler/disassembler.cpp +552 -0
  84. package/src/core/disassembler/disassembler.hpp +171 -0
  85. package/src/core/disk-image/disk_image.hpp +267 -0
  86. package/src/core/disk-image/dsk_disk_image.cpp +827 -0
  87. package/src/core/disk-image/dsk_disk_image.hpp +204 -0
  88. package/src/core/disk-image/gcr_encoding.cpp +147 -0
  89. package/src/core/disk-image/gcr_encoding.hpp +78 -0
  90. package/src/core/disk-image/woz_disk_image.cpp +1049 -0
  91. package/src/core/disk-image/woz_disk_image.hpp +343 -0
  92. package/src/core/emulator.cpp +2126 -0
  93. package/src/core/emulator.hpp +434 -0
  94. package/src/core/filesystem/dos33.cpp +178 -0
  95. package/src/core/filesystem/dos33.hpp +66 -0
  96. package/src/core/filesystem/pascal.cpp +262 -0
  97. package/src/core/filesystem/pascal.hpp +87 -0
  98. package/src/core/filesystem/prodos.cpp +369 -0
  99. package/src/core/filesystem/prodos.hpp +119 -0
  100. package/src/core/input/keyboard.cpp +227 -0
  101. package/src/core/input/keyboard.hpp +111 -0
  102. package/src/core/mmu/mmu.cpp +1387 -0
  103. package/src/core/mmu/mmu.hpp +236 -0
  104. package/src/core/types.hpp +196 -0
  105. package/src/core/video/video.cpp +680 -0
  106. package/src/core/video/video.hpp +156 -0
  107. package/src/css/assembler-editor.css +1617 -0
  108. package/src/css/base.css +470 -0
  109. package/src/css/basic-debugger.css +791 -0
  110. package/src/css/basic-editor.css +792 -0
  111. package/src/css/controls.css +783 -0
  112. package/src/css/cpu-debugger.css +1413 -0
  113. package/src/css/debug-base.css +160 -0
  114. package/src/css/debug-windows.css +6455 -0
  115. package/src/css/disk-drives.css +406 -0
  116. package/src/css/documentation.css +392 -0
  117. package/src/css/file-explorer.css +867 -0
  118. package/src/css/hard-drive.css +180 -0
  119. package/src/css/layout.css +217 -0
  120. package/src/css/memory-windows.css +798 -0
  121. package/src/css/modals.css +510 -0
  122. package/src/css/monitor.css +425 -0
  123. package/src/css/release-notes.css +101 -0
  124. package/src/css/responsive.css +400 -0
  125. package/src/css/rule-builder.css +340 -0
  126. package/src/css/save-states.css +201 -0
  127. package/src/css/settings-windows.css +1231 -0
  128. package/src/css/window-switcher.css +150 -0
  129. package/src/js/agent/agent-manager.js +643 -0
  130. package/src/js/agent/agent-tools.js +293 -0
  131. package/src/js/agent/agent-version-tools.js +131 -0
  132. package/src/js/agent/assembler-tools.js +357 -0
  133. package/src/js/agent/basic-program-tools.js +894 -0
  134. package/src/js/agent/disk-tools.js +417 -0
  135. package/src/js/agent/file-explorer-tools.js +269 -0
  136. package/src/js/agent/index.js +13 -0
  137. package/src/js/agent/main-tools.js +222 -0
  138. package/src/js/agent/slot-tools.js +303 -0
  139. package/src/js/agent/smartport-tools.js +257 -0
  140. package/src/js/agent/window-tools.js +80 -0
  141. package/src/js/audio/audio-driver.js +417 -0
  142. package/src/js/audio/audio-worklet.js +85 -0
  143. package/src/js/audio/index.js +8 -0
  144. package/src/js/config/default-layout.js +34 -0
  145. package/src/js/config/version.js +8 -0
  146. package/src/js/data/apple2-rom-routines.js +577 -0
  147. package/src/js/debug/assembler-editor-window.js +2993 -0
  148. package/src/js/debug/basic-breakpoint-manager.js +529 -0
  149. package/src/js/debug/basic-program-parser.js +436 -0
  150. package/src/js/debug/basic-program-window.js +2594 -0
  151. package/src/js/debug/basic-variable-inspector.js +447 -0
  152. package/src/js/debug/breakpoint-manager.js +472 -0
  153. package/src/js/debug/cpu-debugger-window.js +2396 -0
  154. package/src/js/debug/index.js +22 -0
  155. package/src/js/debug/label-manager.js +238 -0
  156. package/src/js/debug/memory-browser-window.js +416 -0
  157. package/src/js/debug/memory-heat-map-window.js +481 -0
  158. package/src/js/debug/memory-map-window.js +206 -0
  159. package/src/js/debug/mockingboard-window.js +882 -0
  160. package/src/js/debug/mouse-card-window.js +355 -0
  161. package/src/js/debug/rule-builder-window.js +648 -0
  162. package/src/js/debug/soft-switch-window.js +458 -0
  163. package/src/js/debug/stack-viewer-window.js +221 -0
  164. package/src/js/debug/symbols.js +416 -0
  165. package/src/js/debug/trace-panel.js +291 -0
  166. package/src/js/debug/zero-page-watch-window.js +297 -0
  167. package/src/js/disk-manager/disk-drives-window.js +212 -0
  168. package/src/js/disk-manager/disk-operations.js +284 -0
  169. package/src/js/disk-manager/disk-persistence.js +301 -0
  170. package/src/js/disk-manager/disk-surface-renderer.js +388 -0
  171. package/src/js/disk-manager/drive-sounds.js +139 -0
  172. package/src/js/disk-manager/hard-drive-manager.js +481 -0
  173. package/src/js/disk-manager/hard-drive-persistence.js +187 -0
  174. package/src/js/disk-manager/hard-drive-window.js +57 -0
  175. package/src/js/disk-manager/index.js +890 -0
  176. package/src/js/display/display-settings-window.js +383 -0
  177. package/src/js/display/index.js +10 -0
  178. package/src/js/display/screen-window.js +342 -0
  179. package/src/js/display/webgl-renderer.js +705 -0
  180. package/src/js/file-explorer/disassembler.js +574 -0
  181. package/src/js/file-explorer/dos33.js +266 -0
  182. package/src/js/file-explorer/file-viewer.js +359 -0
  183. package/src/js/file-explorer/index.js +1261 -0
  184. package/src/js/file-explorer/prodos.js +549 -0
  185. package/src/js/file-explorer/utils.js +67 -0
  186. package/src/js/help/documentation-window.js +1096 -0
  187. package/src/js/help/index.js +10 -0
  188. package/src/js/help/release-notes-window.js +85 -0
  189. package/src/js/help/release-notes.js +612 -0
  190. package/src/js/input/gamepad-handler.js +176 -0
  191. package/src/js/input/index.js +12 -0
  192. package/src/js/input/input-handler.js +396 -0
  193. package/src/js/input/joystick-window.js +404 -0
  194. package/src/js/input/mouse-handler.js +99 -0
  195. package/src/js/input/text-selection.js +462 -0
  196. package/src/js/main.js +653 -0
  197. package/src/js/state/index.js +15 -0
  198. package/src/js/state/save-states-window.js +393 -0
  199. package/src/js/state/state-manager.js +409 -0
  200. package/src/js/state/state-persistence.js +218 -0
  201. package/src/js/ui/confirm.js +43 -0
  202. package/src/js/ui/disk-drive-positioner.js +347 -0
  203. package/src/js/ui/reminder-controller.js +129 -0
  204. package/src/js/ui/slot-configuration-window.js +560 -0
  205. package/src/js/ui/theme-manager.js +61 -0
  206. package/src/js/ui/toast.js +44 -0
  207. package/src/js/ui/ui-controller.js +897 -0
  208. package/src/js/ui/window-switcher.js +275 -0
  209. package/src/js/utils/basic-autocomplete.js +832 -0
  210. package/src/js/utils/basic-highlighting.js +473 -0
  211. package/src/js/utils/basic-tokenizer.js +153 -0
  212. package/src/js/utils/basic-tokens.js +117 -0
  213. package/src/js/utils/constants.js +28 -0
  214. package/src/js/utils/indexeddb-helper.js +225 -0
  215. package/src/js/utils/merlin-editor-support.js +905 -0
  216. package/src/js/utils/merlin-highlighting.js +551 -0
  217. package/src/js/utils/storage.js +125 -0
  218. package/src/js/utils/string-utils.js +19 -0
  219. package/src/js/utils/wasm-memory.js +54 -0
  220. package/src/js/windows/base-window.js +690 -0
  221. package/src/js/windows/index.js +9 -0
  222. package/src/js/windows/window-manager.js +375 -0
  223. package/tests/catch2/catch.hpp +17976 -0
  224. package/tests/common/basic_program_builder.cpp +119 -0
  225. package/tests/common/basic_program_builder.hpp +209 -0
  226. package/tests/common/disk_image_builder.cpp +444 -0
  227. package/tests/common/disk_image_builder.hpp +141 -0
  228. package/tests/common/test_helpers.hpp +118 -0
  229. package/tests/gcr/gcr-test.cpp +142 -0
  230. package/tests/integration/check-rom.js +70 -0
  231. package/tests/integration/compare-boot.js +239 -0
  232. package/tests/integration/crash-trace.js +102 -0
  233. package/tests/integration/disk-boot-test.js +264 -0
  234. package/tests/integration/memory-crash.js +108 -0
  235. package/tests/integration/nibble-read-test.js +249 -0
  236. package/tests/integration/phase-test.js +159 -0
  237. package/tests/integration/test_emulator.cpp +291 -0
  238. package/tests/integration/test_emulator_basic.cpp +91 -0
  239. package/tests/integration/test_emulator_debug.cpp +344 -0
  240. package/tests/integration/test_emulator_disk.cpp +153 -0
  241. package/tests/integration/test_emulator_state.cpp +163 -0
  242. package/tests/klaus/6502_functional_test.bin +0 -0
  243. package/tests/klaus/65C02_extended_opcodes_test.bin +0 -0
  244. package/tests/klaus/klaus_6502_test.cpp +184 -0
  245. package/tests/klaus/klaus_65c02_test.cpp +197 -0
  246. package/tests/thunderclock/thunderclock_mmu_test.cpp +304 -0
  247. package/tests/thunderclock/thunderclock_test.cpp +550 -0
  248. package/tests/unit/test_assembler.cpp +521 -0
  249. package/tests/unit/test_audio.cpp +196 -0
  250. package/tests/unit/test_ay8910.cpp +311 -0
  251. package/tests/unit/test_basic_detokenizer.cpp +265 -0
  252. package/tests/unit/test_basic_tokenizer.cpp +382 -0
  253. package/tests/unit/test_block_device.cpp +259 -0
  254. package/tests/unit/test_condition_evaluator.cpp +219 -0
  255. package/tests/unit/test_cpu6502.cpp +1301 -0
  256. package/tests/unit/test_cpu_addressing.cpp +361 -0
  257. package/tests/unit/test_cpu_cycle_counts.cpp +409 -0
  258. package/tests/unit/test_cpu_decimal.cpp +166 -0
  259. package/tests/unit/test_cpu_interrupts.cpp +285 -0
  260. package/tests/unit/test_disassembler.cpp +323 -0
  261. package/tests/unit/test_disk2_card.cpp +330 -0
  262. package/tests/unit/test_dos33.cpp +273 -0
  263. package/tests/unit/test_dsk_disk_image.cpp +315 -0
  264. package/tests/unit/test_expansion_card.cpp +178 -0
  265. package/tests/unit/test_gcr_encoding.cpp +232 -0
  266. package/tests/unit/test_keyboard.cpp +262 -0
  267. package/tests/unit/test_mmu.cpp +555 -0
  268. package/tests/unit/test_mmu_slots.cpp +323 -0
  269. package/tests/unit/test_mockingboard.cpp +352 -0
  270. package/tests/unit/test_mouse_card.cpp +386 -0
  271. package/tests/unit/test_pascal.cpp +248 -0
  272. package/tests/unit/test_prodos.cpp +259 -0
  273. package/tests/unit/test_smartport_card.cpp +321 -0
  274. package/tests/unit/test_thunderclock.cpp +354 -0
  275. package/tests/unit/test_via6522.cpp +323 -0
  276. package/tests/unit/test_video.cpp +319 -0
  277. package/tests/unit/test_woz_disk_image.cpp +257 -0
  278. package/vite.config.js +96 -0
  279. package/wiki/AI-Agent.md +372 -0
  280. package/wiki/Architecture-Overview.md +303 -0
  281. package/wiki/Audio-System.md +449 -0
  282. package/wiki/CPU-Emulation.md +477 -0
  283. package/wiki/Debugger.md +516 -0
  284. package/wiki/Disk-Drives.md +161 -0
  285. package/wiki/Disk-System-Internals.md +547 -0
  286. package/wiki/Display-Settings.md +88 -0
  287. package/wiki/Expansion-Slots.md +187 -0
  288. package/wiki/File-Explorer.md +259 -0
  289. package/wiki/Getting-Started.md +156 -0
  290. package/wiki/Home.md +69 -0
  291. package/wiki/Input-Devices.md +183 -0
  292. package/wiki/Keyboard-Shortcuts.md +158 -0
  293. package/wiki/Memory-System.md +364 -0
  294. package/wiki/Save-States.md +172 -0
  295. package/wiki/Video-Rendering.md +658 -0
@@ -0,0 +1,791 @@
1
+ /* ============================================
2
+ BASIC DEBUGGER STYLES (within unified window)
3
+ ============================================ */
4
+
5
+ /* Toolbar */
6
+ .basic-dbg-toolbar {
7
+ display: flex;
8
+ align-items: center;
9
+ flex-wrap: wrap;
10
+ gap: 6px;
11
+ padding: 4px 0 6px;
12
+ border-bottom: 1px solid var(--separator-bg);
13
+ margin-bottom: 6px;
14
+ }
15
+
16
+ .basic-dbg-btn {
17
+ display: inline-flex;
18
+ align-items: center;
19
+ gap: 4px;
20
+ padding: 4px 8px;
21
+ font-family: var(--font-mono);
22
+ font-size: 10px;
23
+ font-weight: 500;
24
+ background: var(--control-bg);
25
+ border: 1px solid var(--control-border);
26
+ border-radius: 3px;
27
+ color: var(--text-secondary);
28
+ cursor: pointer;
29
+ transition: all 0.12s;
30
+ white-space: nowrap;
31
+ }
32
+
33
+ .basic-dbg-btn:hover {
34
+ background: var(--control-hover);
35
+ color: var(--text-primary);
36
+ }
37
+
38
+ .basic-dbg-btn:active {
39
+ background: var(--control-active);
40
+ }
41
+
42
+ .basic-dbg-icon {
43
+ font-size: 9px;
44
+ }
45
+
46
+ .basic-dbg-run {
47
+ background: var(--accent-green-bg);
48
+ border-color: var(--accent-green-border);
49
+ color: var(--accent-green);
50
+ }
51
+
52
+ .basic-dbg-run:hover {
53
+ background: var(--accent-green-bg-strong);
54
+ border-color: var(--accent-green-border);
55
+ color: var(--accent-green);
56
+ }
57
+
58
+ .basic-dbg-stop {
59
+ background: var(--accent-orange-bg);
60
+ border-color: var(--accent-orange-border);
61
+ color: var(--accent-orange);
62
+ }
63
+
64
+ .basic-dbg-stop:hover {
65
+ background: var(--accent-orange-bg-strong);
66
+ border-color: var(--accent-orange-border);
67
+ color: var(--accent-orange);
68
+ }
69
+
70
+ .basic-dbg-pause {
71
+ background: var(--accent-red-bg);
72
+ border-color: var(--accent-red-border);
73
+ color: var(--accent-red);
74
+ }
75
+
76
+ .basic-dbg-pause:hover {
77
+ background: var(--accent-red-bg-strong);
78
+ border-color: var(--accent-red-border);
79
+ color: var(--accent-red);
80
+ }
81
+
82
+ .basic-dbg-step-line,
83
+ .basic-dbg-step-stmt {
84
+ background: var(--accent-orange-bg);
85
+ border-color: var(--accent-orange-border);
86
+ color: var(--accent-orange);
87
+ }
88
+
89
+ .basic-dbg-step-line:hover,
90
+ .basic-dbg-step-stmt:hover {
91
+ background: var(--accent-orange-bg-strong);
92
+ border-color: var(--accent-orange-border);
93
+ color: var(--accent-orange);
94
+ }
95
+
96
+ /* Status Bar - matches CPU debugger status bar */
97
+ .basic-dbg-status-bar {
98
+ display: flex;
99
+ align-items: center;
100
+ justify-content: space-between;
101
+ padding: 3px 6px;
102
+ background: var(--input-bg);
103
+ border: 1px solid var(--glass-border-subtle);
104
+ border-radius: 4px;
105
+ margin-bottom: 4px;
106
+ flex-shrink: 0;
107
+ }
108
+
109
+ /* Status Dot */
110
+ .basic-dbg-status-dot {
111
+ width: 6px;
112
+ height: 6px;
113
+ border-radius: 50%;
114
+ background: var(--text-muted);
115
+ flex-shrink: 0;
116
+ }
117
+
118
+ .basic-dbg-status-bar[data-state="running"] .basic-dbg-status-dot {
119
+ background: var(--accent-green);
120
+ animation: basic-status-dot-pulse 1.5s ease-in-out infinite;
121
+ }
122
+
123
+ .basic-dbg-status-bar[data-state="paused"] .basic-dbg-status-dot {
124
+ background: var(--accent-orange);
125
+ animation: none;
126
+ }
127
+
128
+ .basic-dbg-status-bar[data-state="error"] .basic-dbg-status-dot {
129
+ background: var(--accent-red);
130
+ animation: none;
131
+ }
132
+
133
+ .basic-dbg-status-bar[data-state="idle"] .basic-dbg-status-dot {
134
+ background: var(--text-muted);
135
+ animation: none;
136
+ }
137
+
138
+ @keyframes basic-status-dot-pulse {
139
+ 0%, 100% { opacity: 1; transform: scale(1); }
140
+ 50% { opacity: 0.4; transform: scale(0.75); }
141
+ }
142
+
143
+ /* Status Chip */
144
+ .basic-dbg-status {
145
+ display: inline-flex;
146
+ align-items: center;
147
+ gap: 6px;
148
+ }
149
+
150
+ .basic-dbg-status-chip {
151
+ font-family: var(--font-mono);
152
+ font-size: 9px;
153
+ font-weight: 700;
154
+ letter-spacing: 0.06em;
155
+ text-transform: uppercase;
156
+ transition: color 0.15s;
157
+ color: var(--text-muted);
158
+ }
159
+
160
+ .basic-dbg-status-idle {
161
+ color: var(--text-muted);
162
+ }
163
+
164
+ .basic-dbg-status-running {
165
+ color: var(--accent-green);
166
+ }
167
+
168
+ .basic-dbg-status-paused {
169
+ color: var(--accent-orange);
170
+ }
171
+
172
+ .basic-dbg-status-error {
173
+ color: var(--accent-red);
174
+ }
175
+
176
+ /* Info Bar (inline with toolbar) */
177
+ .basic-dbg-info {
178
+ display: flex;
179
+ gap: 12px;
180
+ font-family: var(--font-mono);
181
+ font-size: 10px;
182
+ color: var(--text-muted);
183
+ }
184
+
185
+ .basic-dbg-line,
186
+ .basic-dbg-ptr {
187
+ color: var(--text-secondary);
188
+ }
189
+
190
+ .basic-dbg-listing::-webkit-scrollbar {
191
+ width: 5px;
192
+ height: 5px;
193
+ }
194
+
195
+ .basic-dbg-listing::-webkit-scrollbar-track {
196
+ background: transparent;
197
+ }
198
+
199
+ .basic-dbg-listing::-webkit-scrollbar-thumb {
200
+ background: var(--overlay-active);
201
+ border-radius: 3px;
202
+ }
203
+
204
+ .basic-dbg-line-row {
205
+ display: flex;
206
+ align-items: baseline;
207
+ padding: 1px 6px;
208
+ font-family: var(--font-mono);
209
+ font-size: 11px;
210
+ line-height: 1.4;
211
+ cursor: default;
212
+ }
213
+
214
+ .basic-dbg-line-row:hover {
215
+ background: var(--overlay-hover);
216
+ }
217
+
218
+ .basic-dbg-line-row.current-line {
219
+ background: var(--accent-blue-bg);
220
+ }
221
+
222
+ .basic-dbg-line-row.has-breakpoint {
223
+ background: rgba(224, 58, 62, 0.08);
224
+ }
225
+
226
+ .basic-dbg-line-row.has-breakpoint.current-line {
227
+ background: linear-gradient(
228
+ 90deg,
229
+ rgba(224, 58, 62, 0.12) 0%,
230
+ var(--accent-blue-bg) 30%
231
+ );
232
+ }
233
+
234
+ .basic-dbg-bp-marker {
235
+ width: 14px;
236
+ text-align: center;
237
+ color: var(--accent-red);
238
+ font-size: 10px;
239
+ cursor: pointer;
240
+ flex-shrink: 0;
241
+ }
242
+
243
+ .basic-dbg-bp-marker:hover {
244
+ opacity: 0.7;
245
+ }
246
+
247
+ .basic-dbg-line-row:not(.has-breakpoint) .basic-dbg-bp-marker:hover::before {
248
+ content: "\25CB";
249
+ color: var(--text-muted);
250
+ }
251
+
252
+ .basic-dbg-current-marker {
253
+ width: 12px;
254
+ text-align: center;
255
+ color: var(--accent-blue);
256
+ font-size: 10px;
257
+ flex-shrink: 0;
258
+ }
259
+
260
+ .basic-dbg-linenum {
261
+ width: 45px;
262
+ text-align: right;
263
+ padding-right: 8px;
264
+ color: var(--text-muted);
265
+ flex-shrink: 0;
266
+ cursor: pointer;
267
+ }
268
+
269
+ .basic-dbg-linenum:hover {
270
+ color: var(--text-secondary);
271
+ }
272
+
273
+ .basic-dbg-text {
274
+ color: var(--text-primary);
275
+ white-space: pre;
276
+ }
277
+
278
+ .basic-dbg-empty {
279
+ color: var(--text-muted);
280
+ font-style: italic;
281
+ padding: 12px;
282
+ text-align: center;
283
+ }
284
+
285
+ .basic-dbg-var-header {
286
+ padding: 4px 8px;
287
+ font-family: var(--font-mono);
288
+ font-size: 10px;
289
+ font-weight: 500;
290
+ color: var(--text-muted);
291
+ border-bottom: 1px solid var(--separator-bg);
292
+ background: var(--overlay-subtle);
293
+ }
294
+
295
+ .basic-dbg-var-panel {
296
+ flex: 1;
297
+ min-height: 0;
298
+ overflow-y: auto;
299
+ padding: 4px;
300
+ }
301
+
302
+ .basic-dbg-var-panel::-webkit-scrollbar {
303
+ width: 5px;
304
+ }
305
+
306
+ .basic-dbg-var-panel::-webkit-scrollbar-track {
307
+ background: transparent;
308
+ }
309
+
310
+ .basic-dbg-var-panel::-webkit-scrollbar-thumb {
311
+ background: var(--overlay-active);
312
+ border-radius: 3px;
313
+ }
314
+
315
+ .basic-dbg-var-list {
316
+ display: flex;
317
+ flex-direction: column;
318
+ gap: 2px;
319
+ }
320
+
321
+ .basic-dbg-var-row {
322
+ display: flex;
323
+ justify-content: space-between;
324
+ padding: 2px 4px;
325
+ font-family: var(--font-mono);
326
+ font-size: 10px;
327
+ border-radius: 2px;
328
+ transition: background 0.3s;
329
+ }
330
+
331
+ .basic-dbg-var-row:hover {
332
+ background: var(--overlay-hover);
333
+ }
334
+
335
+ .basic-dbg-var-row.changed .basic-dbg-var-value {
336
+ animation: reg-flash 0.6s ease-out;
337
+ }
338
+
339
+ .basic-dbg-arr-val.changed {
340
+ animation: reg-flash 0.6s ease-out;
341
+ }
342
+
343
+ .basic-dbg-var-name {
344
+ color: var(--text-primary);
345
+ font-weight: 500;
346
+ }
347
+
348
+ .basic-dbg-var-value {
349
+ color: var(--text-secondary);
350
+ text-align: right;
351
+ overflow: hidden;
352
+ text-overflow: ellipsis;
353
+ }
354
+
355
+ .basic-dbg-var-row.var-type-string .basic-dbg-var-value {
356
+ color: var(--syntax-string);
357
+ }
358
+
359
+ .basic-dbg-var-row.var-type-integer .basic-dbg-var-value {
360
+ color: var(--syntax-flag);
361
+ }
362
+
363
+ .basic-dbg-var-value.editable {
364
+ cursor: pointer;
365
+ border-radius: 2px;
366
+ }
367
+
368
+ .basic-dbg-var-value.editable:hover {
369
+ background: var(--overlay-hover);
370
+ }
371
+
372
+ .basic-dbg-arr-val.editable {
373
+ cursor: pointer;
374
+ border-radius: 2px;
375
+ }
376
+
377
+ .basic-dbg-arr-val.editable:hover {
378
+ background: var(--overlay-hover);
379
+ }
380
+
381
+ .basic-dbg-var-edit {
382
+ width: 100%;
383
+ background: var(--editor-bg);
384
+ color: inherit;
385
+ border: 1px solid var(--accent-blue-border);
386
+ border-radius: 2px;
387
+ font-family: var(--font-mono);
388
+ font-size: 10px;
389
+ padding: 0 2px;
390
+ text-align: right;
391
+ outline: none;
392
+ }
393
+
394
+ /* Array display - expandable list */
395
+ /* Spacing between variables and arrays */
396
+ .basic-dbg-var-list + .basic-dbg-arr-list {
397
+ margin-top: 8px;
398
+ padding-top: 8px;
399
+ border-top: 1px solid var(--separator-bg);
400
+ }
401
+
402
+ .basic-dbg-arr-list {
403
+ display: flex;
404
+ flex-direction: column;
405
+ gap: 2px;
406
+ }
407
+
408
+ .basic-dbg-arr-item {
409
+ font-family: var(--font-mono);
410
+ font-size: 10px;
411
+ border-radius: 3px;
412
+ background: var(--overlay-subtle);
413
+ overflow: hidden;
414
+ }
415
+
416
+ .basic-dbg-arr-header {
417
+ display: flex;
418
+ align-items: center;
419
+ gap: 6px;
420
+ padding: 5px 6px;
421
+ cursor: pointer;
422
+ user-select: none;
423
+ }
424
+
425
+ .basic-dbg-arr-header:hover {
426
+ background: var(--overlay-hover);
427
+ }
428
+
429
+ .basic-dbg-arr-toggle {
430
+ color: var(--text-muted);
431
+ font-size: 8px;
432
+ width: 10px;
433
+ }
434
+
435
+ .basic-dbg-arr-name {
436
+ color: var(--text-primary);
437
+ font-weight: 500;
438
+ }
439
+
440
+ .basic-dbg-arr-info {
441
+ color: var(--text-muted);
442
+ font-size: 9px;
443
+ margin-left: auto;
444
+ }
445
+
446
+ /* Array body wrapper (for expand/collapse) */
447
+ .basic-dbg-arr-body {
448
+ overflow: hidden;
449
+ }
450
+
451
+ /* Array contents container */
452
+ .basic-dbg-arr-contents {
453
+ max-height: 400px;
454
+ overflow: auto;
455
+ background: var(--panel-bg);
456
+ border-top: 1px solid var(--control-border);
457
+ padding: 4px;
458
+ }
459
+
460
+ /* 1D array - grid of cells */
461
+ .basic-dbg-arr-1d {
462
+ display: grid;
463
+ grid-template-columns: repeat(auto-fill, minmax(70px, 1fr));
464
+ gap: 2px;
465
+ }
466
+
467
+ .basic-dbg-arr-1d .basic-dbg-arr-cell {
468
+ display: flex;
469
+ align-items: center;
470
+ gap: 4px;
471
+ padding: 2px 4px;
472
+ background: var(--overlay-subtle);
473
+ border-radius: 2px;
474
+ }
475
+
476
+ .basic-dbg-arr-idx {
477
+ color: var(--text-muted);
478
+ font-size: 9px;
479
+ min-width: 16px;
480
+ }
481
+
482
+ .basic-dbg-arr-val {
483
+ color: var(--syntax-load);
484
+ font-size: 10px;
485
+ }
486
+
487
+ /* 2D array - table */
488
+ .basic-dbg-arr-2d {
489
+ overflow: auto;
490
+ }
491
+
492
+ .basic-dbg-arr-table {
493
+ border-collapse: collapse;
494
+ font-size: 10px;
495
+ width: auto;
496
+ }
497
+
498
+ .basic-dbg-arr-table th,
499
+ .basic-dbg-arr-table td {
500
+ padding: 2px 6px;
501
+ border: 1px solid var(--control-border);
502
+ text-align: right;
503
+ min-width: 40px;
504
+ }
505
+
506
+ .basic-dbg-arr-table th {
507
+ background: var(--overlay-subtle);
508
+ color: var(--text-muted);
509
+ font-weight: normal;
510
+ font-size: 9px;
511
+ position: sticky;
512
+ }
513
+
514
+ .basic-dbg-arr-table thead th {
515
+ top: 0;
516
+ z-index: 2;
517
+ }
518
+
519
+ .basic-dbg-arr-table tbody th {
520
+ left: 0;
521
+ z-index: 1;
522
+ }
523
+
524
+ .basic-dbg-arr-table thead th:first-child {
525
+ z-index: 3;
526
+ }
527
+
528
+ .basic-dbg-arr-table td {
529
+ color: var(--syntax-load);
530
+ }
531
+
532
+ /* 3D+ array - indexed list */
533
+ .basic-dbg-arr-nd {
534
+ display: grid;
535
+ grid-template-columns: repeat(auto-fill, minmax(90px, 1fr));
536
+ gap: 2px;
537
+ }
538
+
539
+ .basic-dbg-arr-nd .basic-dbg-arr-cell {
540
+ display: flex;
541
+ align-items: center;
542
+ gap: 4px;
543
+ padding: 2px 4px;
544
+ background: var(--overlay-subtle);
545
+ border-radius: 2px;
546
+ }
547
+
548
+ .basic-dbg-arr-nd .basic-dbg-arr-idx {
549
+ min-width: 32px;
550
+ }
551
+
552
+ /* Breakpoints Panel */
553
+ .basic-dbg-breakpoints {
554
+ display: flex;
555
+ flex-direction: column;
556
+ height: 150px;
557
+ min-height: 80px;
558
+ border: 1px solid var(--control-border);
559
+ border-radius: 4px;
560
+ background: var(--control-bg);
561
+ overflow: hidden;
562
+ flex-shrink: 0;
563
+ }
564
+
565
+ .basic-dbg-bp-header {
566
+ display: flex;
567
+ justify-content: space-between;
568
+ align-items: center;
569
+ padding: 4px 8px;
570
+ font-family: var(--font-mono);
571
+ font-size: 10px;
572
+ font-weight: 500;
573
+ color: var(--text-muted);
574
+ border-bottom: 1px solid var(--separator-bg);
575
+ background: var(--overlay-subtle);
576
+ }
577
+
578
+ .basic-dbg-bp-toolbar {
579
+ display: flex;
580
+ gap: 3px;
581
+ padding: 4px;
582
+ flex-shrink: 0;
583
+ }
584
+
585
+ .basic-dbg-bp-input {
586
+ flex: 1;
587
+ min-width: 0;
588
+ padding: 2px 5px;
589
+ font-family: var(--font-mono);
590
+ font-size: 10px;
591
+ background: var(--input-bg-deep);
592
+ border: 1px solid var(--control-border);
593
+ border-radius: 3px;
594
+ color: var(--text-primary);
595
+ }
596
+
597
+ .basic-dbg-bp-input:focus {
598
+ outline: none;
599
+ border-color: var(--accent-blue-border);
600
+ }
601
+
602
+ .basic-dbg-bp-input.error {
603
+ border-color: var(--accent-red);
604
+ animation: shake 0.3s;
605
+ }
606
+
607
+ @keyframes shake {
608
+ 0%,
609
+ 100% {
610
+ transform: translateX(0);
611
+ }
612
+ 25% {
613
+ transform: translateX(-4px);
614
+ }
615
+ 75% {
616
+ transform: translateX(4px);
617
+ }
618
+ }
619
+
620
+ .basic-dbg-bp-add-btn {
621
+ padding: 2px 7px;
622
+ font-family: var(--font-mono);
623
+ font-size: 11px;
624
+ font-weight: 600;
625
+ background: var(--control-bg);
626
+ border: 1px solid var(--control-border);
627
+ border-radius: 3px;
628
+ color: var(--text-secondary);
629
+ cursor: pointer;
630
+ transition: all 0.12s;
631
+ }
632
+
633
+ .basic-dbg-bp-add-btn:hover {
634
+ background: var(--accent-green-bg-strong);
635
+ border-color: var(--accent-green-border);
636
+ color: var(--accent-green);
637
+ }
638
+
639
+ .basic-dbg-bp-list {
640
+ flex: 1;
641
+ overflow-y: auto;
642
+ }
643
+
644
+ .basic-dbg-bp-empty {
645
+ padding: 12px 8px;
646
+ text-align: center;
647
+ color: var(--text-muted);
648
+ font-size: 10px;
649
+ font-style: italic;
650
+ opacity: 0.7;
651
+ }
652
+
653
+ .basic-dbg-bp-item {
654
+ display: flex;
655
+ align-items: center;
656
+ gap: 4px;
657
+ padding: 4px 4px;
658
+ font-family: var(--font-mono);
659
+ font-size: 10px;
660
+ border-radius: 3px;
661
+ }
662
+
663
+ .basic-dbg-bp-item.bp-triggered {
664
+ animation: bp-pulse-red 0.8s ease-in-out infinite;
665
+ }
666
+
667
+ @keyframes bp-pulse-red {
668
+ 0%, 100% { background: rgba(224, 58, 62, 0.15); }
669
+ 50% { background: rgba(224, 58, 62, 0.35); }
670
+ }
671
+
672
+ .basic-dbg-bp-item:hover {
673
+ background: var(--overlay-faint);
674
+ }
675
+
676
+ .basic-dbg-bp-item.disabled {
677
+ opacity: 0.45;
678
+ }
679
+
680
+ .basic-dbg-bp-enabled {
681
+ width: 10px;
682
+ height: 10px;
683
+ margin: 0;
684
+ cursor: pointer;
685
+ flex-shrink: 0;
686
+ }
687
+
688
+ .basic-dbg-bp-line {
689
+ color: var(--accent-red);
690
+ flex-shrink: 0;
691
+ }
692
+
693
+ .basic-dbg-bp-cond {
694
+ color: var(--accent-orange);
695
+ font-size: 9px;
696
+ font-weight: 600;
697
+ text-transform: uppercase;
698
+ letter-spacing: 0.5px;
699
+ padding: 1px 4px;
700
+ background: var(--accent-orange-bg, rgba(245, 130, 31, 0.1));
701
+ border-radius: 3px;
702
+ flex-shrink: 0;
703
+ }
704
+
705
+ .basic-dbg-bp-edit {
706
+ background: var(--accent-blue-bg);
707
+ border: 1px solid var(--accent-blue-bg-stronger);
708
+ color: var(--accent-blue);
709
+ font-size: 9px;
710
+ font-family: var(--font-mono);
711
+ cursor: pointer;
712
+ padding: 1px 5px;
713
+ border-radius: 3px;
714
+ opacity: 0;
715
+ transition: all 0.12s;
716
+ flex-shrink: 0;
717
+ }
718
+
719
+ .basic-dbg-bp-item:hover .basic-dbg-bp-edit {
720
+ opacity: 1;
721
+ }
722
+
723
+ .basic-dbg-bp-edit:hover {
724
+ background: var(--accent-blue-bg-strong);
725
+ border-color: rgba(88, 166, 255, 0.6);
726
+ }
727
+
728
+ .basic-dbg-bp-remove {
729
+ background: none;
730
+ border: none;
731
+ color: var(--text-muted);
732
+ font-size: 13px;
733
+ cursor: pointer;
734
+ padding: 0 4px;
735
+ line-height: 1;
736
+ opacity: 0;
737
+ margin-left: auto;
738
+ transition: all 0.12s;
739
+ }
740
+
741
+ .basic-dbg-bp-item:hover .basic-dbg-bp-remove {
742
+ opacity: 0.6;
743
+ }
744
+
745
+ .basic-dbg-bp-remove:hover {
746
+ opacity: 1;
747
+ color: var(--accent-red);
748
+ }
749
+
750
+ /* Condition-only rule items */
751
+ .basic-dbg-bp-item.condition-rule {
752
+ background: var(--accent-orange-bg, rgba(245, 130, 31, 0.05));
753
+ }
754
+
755
+ .basic-dbg-bp-rule-badge {
756
+ color: var(--accent-orange);
757
+ font-size: 9px;
758
+ font-weight: 600;
759
+ text-transform: uppercase;
760
+ padding: 1px 4px;
761
+ background: var(--accent-orange-bg, rgba(245, 130, 31, 0.1));
762
+ border-radius: 3px;
763
+ flex-shrink: 0;
764
+ }
765
+
766
+ .basic-dbg-bp-rule-expr {
767
+ color: var(--accent-orange) !important;
768
+ overflow: hidden;
769
+ text-overflow: ellipsis;
770
+ white-space: nowrap;
771
+ flex: 1;
772
+ min-width: 0;
773
+ }
774
+
775
+ /* Add rule button in toolbar */
776
+ .basic-dbg-bp-add-rule-btn {
777
+ background: var(--accent-orange-bg, rgba(245, 130, 31, 0.1));
778
+ border: 1px solid var(--accent-orange-border, rgba(245, 130, 31, 0.3));
779
+ color: var(--accent-orange);
780
+ font-size: 10px;
781
+ font-family: var(--font-mono);
782
+ cursor: pointer;
783
+ padding: 2px 6px;
784
+ border-radius: 3px;
785
+ transition: all 0.12s;
786
+ }
787
+
788
+ .basic-dbg-bp-add-rule-btn:hover {
789
+ background: rgba(245, 130, 31, 0.2);
790
+ border-color: rgba(245, 130, 31, 0.5);
791
+ }