ai.md: Key patterns gains the 'true decomposition beats partial-shuffling' rule + the glue-vs-component diagnostic (count OnPropertyChanged/SetProperty; extract only zero/low-glue cohesive state blobs like chat's; leave binding glue over already-extracted services alone; line count is a guideline not a goal). ViewModels table row notes Chat.cs is now a thin facade over ChatOverlayLayer. HANDOFF: everything through Commit G is pushed (origin/main=85893ea); the remaining big decomposition is the scene-graph segment, flagged as design-needed (not an unsupervised peel).
6.9 KiB
HANDOFF — Session State
Branch / Commit State
main, working tree is CLEAN. origin/main == 85893ea (pushed).
Pushed (reached origin/main == 85893ea, incl. tags): Phase 1 commit 0 +
refactor commits 1..11 + Phase 2 commits 12..18 + the Controls/index.md
docs commit cb54637 + Phase 3 splits A–E (tags refactor-commit-A..E) +
Commit F (Recording, refactor-commit-F) + Commit G (ChatOverlayLayer,
refactor-commit-G). Everything is pushed; nothing local-only.
Commit log (all pushed):
| Commit | Hash | Tag | Payload |
|---|---|---|---|
| docs | cb54637 |
— | Controls/index.md |
| A | 6944db8 |
refactor-commit-A |
split MainViewModel.cs core → 495 |
| B | 31362d1 |
refactor-commit-B |
split MainViewModel.Streaming.cs → 330 |
| C | fab2e09 |
refactor-commit-C |
split MainViewModel.Background.cs → 418 |
| D | d3271a0 |
refactor-commit-D |
trim SocialsDialogViewModel.cs → 334 |
| E | dcb3637 |
refactor-commit-E |
split LayoutStore.cs → 6 partials |
| F | 3107f92 |
refactor-commit-F |
extract recording concern → MainViewModel.Recording.cs |
| G | 85893ea |
refactor-commit-G |
first true decomposition → Services/ChatOverlayLayer.cs |
What's In Flight
Nothing code-in-flight — working tree clean.
The directive (2026-08-31, user): rewrite the project, breaking files into functional components to compliment AI retrieval/processing — NOT line-count chasing. Line count is a guideline for context management, not a design goal.
What was done:
- Phase 3 (A–E): every production
.cs≤ 500, grouped by concern. These are partial shuffles — same class, same shared state. Marginal for retrieval. - Commit F: recording-output concern →
MainViewModel.Recording.cs(partial). - Commit G — the real win:
Services/ChatOverlayLayer.csis a genuine owner-state component (buffer + renderer + timers + preview + liveRenderFrame);MainViewModel.Chat.cs194 → 44 (thin binding facade). First true decomposition.
Expert diagnostic (recorded in ai.md → Key patterns): the remaining partials
(Audio, Webcam, Background, Scenes, Socials…) are binding glue over already-
extracted services (AudioMixer, CameraManager, ScreenCaptureManager,
ChatBoxRenderer, SocialValidator). They have no cohesive owner-state blob to
peel — forcing extraction adds coupling. Chat was the one clean peel.
Next (recommended): the one remaining genuine big decomposition is the
scene-graph segment (the Scenes/StagedScene/element-inventory backbone
every feature hangs off). This is a real architectural redesign — a SceneGraph
owner-object with narrow seams — that touches the binding surface and needs
design review, NOT an unsupervised autonomous peel. Do not attempt it blind pre-1.0.
Pending bus: ViewModels/index.md Phase 3 tracker has rows A–E (closed);
Phase 3 marked COMPLETE. Watch-list (under limit, no action): Controls/PreviewPane.xaml.cs
(464), ViewModels/MainViewModel.Audio.cs (408).
Landmines
- Pre-existing test failures (do not chase):
AudioPipelineTests.Mix_HonorsProviderGains_AndGameMute_KillsTheLoopback+RoundClipInteractionTests.Round_Clip_Corner_Is_Grabbable_And_Shape_Is_Circle. - Tests occasionally abort early (236/237) — known flake, accepted by
verify.sh. - App running locks
ytLive.exe→ build fails MSB3027. Kill PID before building. - WinForm crash from
Window_PreviewMouseLeftButtonDown— handled in-side the preview/left panel; don't add handlers that derefOriginalSourceunguarded. - Controls cannot see
Window.Resources(converter rule, Commit 13): any StaticResource the window once supplied must live at app level inThemes/Controls.xaml. The 7 converters were promoted there. - Some control XAML needs its own
xmlns:models/xmlns:Helpers— a moved block lost its namespace when it left MainWindow's root (LeftPanel hit this, MC2000 "key null"). Always add the model/helper xmlns on each control root. - Name-looked-up host stubs must stay in the window:
WebViewHostPanel(ctorInitWebView2(WebViewHostPanel)) andToastArea(NotificationService.InArea("ToastArea")) are resolved by name from the window — keep them as window-root children, don't bury them in a control. OverlayHost deliberately left them in place (Commit 18) for this reason. - Pre-commit gate:
scripts/verify.sh(0-warning build + full tests) andscripts/scope-check.sh "file1" …— scope-check REQUIRES explicit file args. - Build from WSL with the Windows dotnet host only (see
AGENTS.md).
Todo state
- MainViewModel refactor: Phase 1 complete (11/11 partials), pushed.
- MainWindow.xaml refactor: Phase 2 complete (6/6 controls), pushed at
1f4624c. - 500-line compliance: Phase 3 complete (A–E, all ≤500), pushed.
- True decomposition: Commit G —
Services/ChatOverlayLayer.csshipped + pushed (first owner-state component; pattern recorded inai.md). - Next (design-needed, do NOT blind-peel): the scene-graph segment (
SceneGraphowner-object) — the one remaining genuine big decomposition; touches binding surface, needs review. - TASK 3: 27/30 (preview compositor 16, text source 17, alerts 20 still open).
- TASK 4: ✅ shipped. TASK 9: items 1–3 shipped; 4–7 open. TASK 10: steps 1–7; Velopack pending.
- TASK 18: shipped, creator verification pending. TASK 19/23, 20, 21-A: shipped.
- TASK 22 (audio sync offset): not started — required for v1.
Session summary (2026-08-31)
- Ran the 500-line Phase 3 split to completion (A–E), then the continuation.
- Re-structuring principle (user correction, 2026-08-31): split by functionality, so an AI can process one concern per file; the 500-line count is a ceiling, NOT the target. Do not pad or reshape code to a number.
- Correction of a false premise: my plan to "extract FFmpegEncoder /
StreamHealthMonitor / FramePump" was a no-op — those already exist as
Services/Encoder/*. The honest seams were (F) the recording concern and (G) the chat overlay. - Commit G = first TRUE decomposition:
ChatOverlayLayerowns chat state + behavior;MainViewModel.Chat.cs194 → 44 thin facade. This is the pattern that actually compliments AI retrieval (one self-contained unit per feature), unlike the partial shuffles of A–E, which only marginalize context because every partial still shares the god-object's state. - Accident caught & recovered (Commit D): a
> ViewModels/SocialsDialogViewModel.cswrite that truncated the file it was reading left it at 1 line; restored viagit checkout --, re-ran from temp files. Lesson inMyMistakes.md: neverawk … > SRCwhile awking SRC; stage cuts into temp files, then assemble. - Everything through G is pushed to
origin/main(85893ea) with tags A–G.