# To-Do List This file tracks prioritized tasks with detailed attack plans. ## Recently Completed (February 4, 2026) - [x] **Task #51.3 & #51.4: Tracker Test Suite & Build Integration**: - [x] **Comprehensive Test Suite**: Created `test_tracker_timing.cc` with 7 test scenarios using MockAudioBackend. - [x] **Simultaneous Trigger Verification**: Confirmed multiple patterns at same time trigger with **0.000ms delta** (perfect sync). - [x] **Test Coverage**: Basic recording, progressive triggering, simultaneous triggers, monotonicity, seek/fast-forward, timestamp clustering, render integration. - [x] **Real Music Data**: Tests use generated tracker music data for realistic validation. - [x] **Build Integration**: Added to CMake with proper dependencies on generated music data. - [x] **All Tests Pass**: 15/15 tests passing (100% success rate). - [x] **Task #51.2: Mock Audio Backend**: - [x] **Event Recording**: Created `VoiceTriggerEvent` structure to capture timestamp, spectrogram_id, volume, and pan. - [x] **MockAudioBackend Class**: Implemented test-only backend with event recording and time tracking capabilities. - [x] **Time Management**: Added `advance_time()`, `set_time()`, and `get_current_time()` for deterministic testing. - [x] **Frame Rendering Hook**: Implemented `on_frames_rendered()` to automatically update time based on audio frames (32kHz). - [x] **Synth Integration**: Verified mock backend correctly captures voice triggers from synth engine. - [x] **Comprehensive Tests**: Created `test_mock_backend.cc` with 6 test scenarios covering all mock functionality. - [x] **Build Integration**: Added mock backend to test builds, all 14 tests pass. - [x] **Task #51.1: Audio Backend Abstraction**: - [x] **Interface Created**: Defined `AudioBackend` interface in `src/audio/audio_backend.h` with hooks for voice triggering and frame rendering. - [x] **Production Backend**: Moved miniaudio implementation to `MiniaudioBackend` class, maintaining backward compatibility. - [x] **Audio Refactoring**: Updated `audio.cc` to use backend abstraction with automatic fallback to `MiniaudioBackend`. - [x] **Event Hooks**: Added time tracking to `synth.cc` with `on_voice_triggered()` callbacks (guarded by `!STRIP_ALL`). - [x] **Verification Test**: Created `test_audio_backend.cc` to verify backend injection and event recording work correctly. - [x] **Build Integration**: Updated CMakeLists.txt to include new backend files and link audio tests properly with util/procedural dependencies. - [x] **Zero Size Impact**: All test infrastructure under `#if !defined(STRIP_ALL)`, production path unchanged. - [x] **Task #50: WGSL Modularization**: - [x] **Recursive Composition**: Updated `ShaderComposer` to support recursive `#include "snippet_name"` directives with cycle detection. - [x] **Granular SDF Library**: Extracted `math/sdf_shapes.wgsl`, `math/sdf_utils.wgsl`, `render/shadows.wgsl`, `render/scene_query.wgsl`, and `render/lighting_utils.wgsl`. - [x] **Pipeline Update**: Refactored `Renderer3D` and `renderer_3d.wgsl` to use the new modular system, reducing C++-side dependency management. - [x] **Platform Fix**: Resolved `WGPUShaderSourceWGSL` usage on macOS to ensure compatibility with composed shader strings. - [x] **Task #48: Improve Audio Coverage**: - [x] **New Tests**: Added `test_dct` (100% coverage for transforms) and `test_audio_gen` (94% coverage for procedural audio). - [x] **Enhanced Tests**: Updated `test_synth` to cover rendering loop, double-buffering, and resource exhaustion. - [x] **Coverage Boost**: Increased `src/audio/` coverage from ~42% to 93%. - [x] **Task #47: Improve Asset Manager Coverage**: - [x] **New Tests**: Added tests for unknown procedural functions, generation failures, and edge cases in `src/tests/test_assets.cc`. - [x] **Tooling Update**: Downgraded `asset_packer` validation error to warning to allow testing invalid assets. - [x] **Coverage Boost**: Increased `src/util/asset_manager.cc` coverage from 71% to 88%. - [x] **Task #46: Enhance Coverage Script**: Updated `scripts/gen_coverage_report.sh` to accept an optional directory argument for targeted coverage reports (e.g., `src/procedural`). - [x] **Task #45: Improve Procedural Generation Coverage**: - [x] **Unit Tests:** Implemented comprehensive tests for `gen_perlin`, `make_periodic`, and default parameter handling in `src/tests/test_procedural.cc`. - [x] **Coverage Boost:** Increased `src/procedural/generator.cc` coverage from 38% to 96%. - [x] **Task #44: Developer Tooling (Coverage)**: - [x] **Implement Code Coverage:** Added `DEMO_ENABLE_COVERAGE` CMake option and created `scripts/gen_coverage_report.sh` to generate HTML coverage reports using `lcov` on macOS. - [x] **Documentation:** Updated `doc/HOWTO.md` with usage instructions. - [x] **Skybox & Two-pass Rendering Stability**: - [x] **Fixed Two-pass Rendering:** Implemented mandatory clear operations for color and depth when the skybox is absent, preventing black screens and depth validation errors. - [x] **Implemented Rotating Skybox:** Added `inv_view_proj` to `GlobalUniforms` and updated the skybox shader to perform world-space ray unprojection, enabling correct rotation with the camera. - [x] **Enhanced Procedural Noise:** Implemented a multi-octave Value Noise generator for higher-quality skybox textures. - [x] **Scene Integrity:** Restored proper object indexing and removed redundant geometry, ensuring the floor grid and objects render correctly. ## Priority 1: Physics & Collision (Task #49) **Goal**: Implement a lightweight physics engine using SDFs and BVH acceleration. (See `doc/3D.md` for design). - [ ] **Task #49.1: CPU-Side SDF Library**: - [ ] Create `src/3d/sdf_cpu.h` implementing `sdSphere`, `sdBox`, `sdTorus`, `sdPlane` using `mini_math.h`. - [ ] Implement `calc_normal` (numerical gradient) for these SDFs. - [ ] Add unit tests in `src/tests/test_physics.cc` to verify CPU SDFs match ground truth. - [ ] **Task #49.2: BVH Construction**: - [ ] Define `BVHNode` struct in `src/3d/bvh.h` (shared/compatible with GPU layout). - [ ] Implement `BVHBuilder::Build(const std::vector&)` in `src/3d/bvh.cc`. - [ ] Implement `BVH::Query(AABB)` for broad-phase collision detection. - [ ] Visualize BVH in `src/tests/test_3d_render.cc` (using `VisualDebug`). - [ ] **Task #49.3: Physics Loop**: - [ ] Create `PhysicsSystem` class in `src/3d/physics.h`. - [ ] Implement `Update(dt)`: Integration -> Broad Phase -> Narrow Phase (SDF Probe) -> Resolution. - [ ] Add `velocity`, `mass`, `restitution` fields to `Object3D`. - [ ] Integrate into `test_3d_render.cc` main loop. ## Priority 2: 3D System Enhancements (Task #18) **Goal:** Establish a pipeline for importing complex 3D scenes to replace hardcoded geometry. - [ ] **Task #36: Blender Exporter:** Create a Python script (`tools/blender_export.py`) to export meshes/cameras/lights to a binary asset format. - [ ] **Task #37: Asset Ingestion:** Update `asset_packer` to handle the new 3D binary format. - [ ] **Task #38: Runtime Loader:** Implement a minimal C++ parser to load the scene data into the ECS/Renderer. ## Priority 3: WGSL Modularization (Task #50) [RECURRENT] **Goal**: Refactor `ShaderComposer` and WGSL assets to support granular, reusable snippets and `#include` directives. This is an ongoing task to maintain shader code hygiene as new features are added. ## Priority 4: Developer Tooling & CI **Goal**: Improve developer workflows, code quality, and release processes. - [ ] **Task #51: Tracker Timing Verification** - [x] **Task #51.1: Audio Backend Abstraction**: Create an interface to separate audio output from synth logic, enabling testable backends. - [x] **Task #51.2: Mock Audio Backend**: Implement a test backend that records voice trigger events with precise timestamps. - [x] **Task #51.3: Tracker Test Suite**: Create `test_tracker.cc` to verify pattern triggering, timing accuracy, and synchronization. - [x] **Task #51.4: Integration with Build**: Wire up tests to CMake and ensure they run in CI. ## Phase 2: Size Optimization (Final Goal) - [ ] **Task #34: Full STL Removal**: Replace all remaining `std::vector`, `std::map`, and `std::string` usage with custom minimal containers or C-style arrays to allow for CRT replacement. (Minimal Priority - deferred to end). - [ ] **Task #22: Windows Native Platform**: Replace GLFW with direct Win32 API calls for the final 64k push. - [ ] **Task #28: Spectrogram Quantization**: Research optimal frequency bin distribution and implement quantization. - [ ] **Task #35: CRT Replacement**: investigation and implementation of CRT-free entry point. --- ## Task #51: Tracker Timing Verification - Detailed Attack Plan **Problem Statement**: The tracker and synthesizer have audio sync issues. There's no robust way to verify that tracker patterns trigger at the correct timestamps without running the full audio hardware stack. **Goal**: Implement a testable audio backend abstraction with event recording capabilities to verify tracker timing accuracy. ### Task #51.1: Audio Backend Abstraction **Objective**: Decouple audio output from synthesis logic to enable testing without hardware. **Implementation Steps**: - [ ] **Create `src/audio/audio_backend.h`**: - Define `AudioBackend` interface with pure virtual methods: - `init()`: Initialize backend resources - `start()`: Start audio playback/recording - `shutdown()`: Clean up resources - `on_voice_triggered(timestamp, spec_id, volume, pan)`: Hook for voice events - Add `#if !defined(STRIP_ALL)` guards around test-only methods - [ ] **Create `src/audio/miniaudio_backend.h` and `.cc`**: - Move current miniaudio implementation from `audio.cc` to `MiniaudioBackend` class - Implement `AudioBackend` interface - Keep production behavior identical (no regressions) - This backend does NOT record events (production path) - [ ] **Refactor `src/audio/audio.cc`**: - Add global `AudioBackend* g_audio_backend` pointer - Add `void audio_set_backend(AudioBackend* backend)` function (under `!STRIP_ALL`) - Default to `MiniaudioBackend` if no backend is set - Replace direct miniaudio calls with backend interface calls - [ ] **Update `src/audio/synth.cc`**: - Add external hook: `extern AudioBackend* g_audio_backend_for_events` - In `synth_trigger_voice()`, call `backend->on_voice_triggered()` if backend exists - Ensure hook is `#if !defined(STRIP_ALL)` guarded **Size Impact**: Zero (test code stripped in final build). **Validation**: Existing tests (`test_synth.cc`) must pass unchanged. --- ### Task #51.2: Mock Audio Backend **Objective**: Create a test-only backend that records all audio events with timestamps. **Implementation Steps**: - [ ] **Create `src/audio/mock_audio_backend.h` and `.cc`** (under `#if !defined(STRIP_ALL)`): - Define `struct VoiceTriggerEvent`: ```cpp struct VoiceTriggerEvent { float timestamp_sec; int spectrogram_id; float volume; float pan; }; ``` - Implement `MockAudioBackend` class: - Maintain `std::vector recorded_events` - Override `on_voice_triggered()` to record events with current time - Add `const std::vector& get_events() const` - Add `void clear_events()` - Add `void advance_time(float delta_sec)` to simulate time progression - Implement `init()`, `start()`, `shutdown()` as no-ops - [ ] **Time Tracking**: - Add `float current_time_sec` member to `MockAudioBackend` - Increment `current_time_sec` in `advance_time()` - Use `current_time_sec` as timestamp when recording events - [ ] **Synth Integration**: - When `synth_render()` is called, calculate frames rendered - Notify backend of time elapsed: `frames / sample_rate` - Update mock's internal clock accordingly **Testing**: Create minimal unit test in `test_tracker.cc` to verify event recording works. --- ### Task #51.3: Tracker Test Suite **Objective**: Comprehensive tests for tracker pattern triggering and timing accuracy. **Implementation Steps**: - [ ] **Create `src/tests/test_tracker.cc`**: - **Test 1: Single Pattern Trigger** - Define a minimal `TrackerScore` with 1 pattern at `t=1.0s` - Set up mock backend - Call `tracker_update(0.5)` → verify no events - Call `tracker_update(1.0)` → verify 1 event recorded - Validate event timestamp matches expected trigger time - **Test 2: Multiple Pattern Triggers** - Score with 3 patterns at `t=0.5s, 1.0s, 2.0s` - Progressively call `tracker_update()` with increasing times - Verify each pattern triggers exactly once at correct time - **Test 3: Event Timing Accuracy** - Pattern with multiple events at different beat offsets - Verify each event's timestamp matches: `pattern_start_time + (beat * beat_duration)` - Use tolerance: `±1 frame` (1/32000 sec ≈ 31.25µs) - **Test 4: BPM Scaling** - Same pattern tested at different BPMs (60, 120, 180) - Verify beat-to-time conversion is accurate: `beat_sec = 60.0 / bpm` - **Test 5: Pattern Overlap** - Two patterns with overlapping time ranges - Verify both trigger correctly without interference - **Test 6: Asset vs Procedural Samples** - Pattern using both asset-based spectrograms and procedural notes - Verify both types render and trigger correctly - **Test 7: Seek/Fast-Forward Simulation** - Simulate `audio_render_silent()` behavior - Start at `t=0`, fast-forward to `t=10.0s` - Verify all patterns in range [0, 10] triggered correctly - [ ] **Helper Functions**: ```cpp void assert_event_at_time(const std::vector& events, float expected_time, float tolerance = 0.001f); void assert_event_count(const std::vector& events, int expected_count); TrackerScore create_test_score(const std::vector& trigger_times, float bpm = 120.0f); ``` **Coverage Target**: 95%+ for `src/audio/tracker.cc`. --- ### Task #51.4: Integration with Build **Objective**: Wire up tests to CMake and ensure they run automatically. **Implementation Steps**: - [ ] **Update `src/CMakeLists.txt`**: - Add `mock_audio_backend.cc` to test-only sources (under `DEMO_BUILD_TESTS`) - Link `test_tracker` executable with audio subsystem library - [ ] **Add test to CTest**: ```cmake if(DEMO_BUILD_TESTS) add_executable(test_tracker tests/test_tracker.cc audio/mock_audio_backend.cc) target_link_libraries(test_tracker PRIVATE audio_lib util_lib) add_test(NAME TrackerTest COMMAND test_tracker) endif() ``` - [ ] **Verify in CI**: - Run `cmake --build build && cd build && ctest` - Ensure `test_tracker` runs and passes - Check coverage report includes tracker.cc **Validation**: `ctest` output shows `TrackerTest: PASSED`. --- ## Implementation Layout Summary ### New Files ``` src/audio/audio_backend.h # Interface definition src/audio/miniaudio_backend.h # Production backend (header) src/audio/miniaudio_backend.cc # Production backend (impl) src/audio/mock_audio_backend.h # Test backend (header, !STRIP_ALL) src/audio/mock_audio_backend.cc # Test backend (impl, !STRIP_ALL) src/tests/test_tracker.cc # Comprehensive tracker tests ``` ### Modified Files ``` src/audio/audio.cc # Backend abstraction layer src/audio/synth.cc # Add event hooks src/CMakeLists.txt # Add new files and tests ``` ### File Structure ``` src/audio/ ├── audio_backend.h [NEW] Interface (50 lines) ├── miniaudio_backend.h [NEW] Header (30 lines) ├── miniaudio_backend.cc [NEW] Production impl (~100 lines, moved from audio.cc) ├── mock_audio_backend.h [NEW] Test header (60 lines) ├── mock_audio_backend.cc [NEW] Test impl (~120 lines) ├── audio.h [MODIFIED] Add backend setter ├── audio.cc [MODIFIED] Use backend abstraction (~30 lines changed) ├── synth.cc [MODIFIED] Add event hook (~10 lines) └── tracker.cc [NO CHANGE] src/tests/ └── test_tracker.cc [NEW] Test suite (~400 lines) ``` ### Code Organization Principles 1. **Zero Size Impact**: All test infrastructure under `#if !defined(STRIP_ALL)` 2. **Backward Compatible**: Production path unchanged, existing tests pass 3. **Clean Separation**: Interface-based design, easy to add more backends later 4. **Testable**: Mock backend has minimal dependencies (no hardware/threads) --- ## Future Goals