Update .gitignore to include build and coverage directories; add initial project plan and expand TODO list with new items and bugs

Signed-off-by: Hans Kokx <hans.d.kokx@gmail.com>
This commit is contained in:
2026-08-09 21:14:38 +02:00
parent 4f4f7bffdf
commit 55c396b2a2
3 changed files with 113 additions and 7 deletions
+5 -5
View File
@@ -30,8 +30,8 @@ migrate_working_dir/
.flutter-plugins-dependencies
.pub-cache/
.pub/
/build/
/coverage/
**/build/
**/coverage/
# Symbolication related
app.*.symbols
@@ -40,6 +40,6 @@ app.*.symbols
app.*.map.json
# Android Studio will place build artifacts here
/android/app/debug
/android/app/profile
/android/app/release
**/android/app/debug
**/android/app/profile
**/android/app/release
+99
View File
@@ -0,0 +1,99 @@
# PLAN.md — Winamp Desktop (dartamp) work plan
Order: A -> B -> C -> D (confirmed). Docking uses a custom in-Dart drag loop.
Prefs window matches the full original tab set. Resumable across sessions; mark
items `[x]` as done.
## Phase A — Skin subsystem (TODO items 5, 3, 4)
### A1. Extract classic-skin code into a project-level package (task 5)
- [x] New package `dartamp_skin` at `packages/dartamp_skin/`.
- [x] Moved `classic_skin.dart`, `skin_loader.dart`, `bmp_decoder.dart`,
`skin_image.dart`, `skin_slider.dart`, `text_font.dart`, and
`assets/skins/base/` into the package; added barrel + pubspec +
analysis_options.
- [x] Moved skin-debugging tooling (`tool/`) and `text_font_test.dart` into the
package; added `base_skin_test.dart` (loadBaseSkin smoke test).
- [x] App keeps all window/UI logic; imports `package:dartamp_skin/...`;
`archive` dep moved to the package; app gained `path_provider` (for A2).
- [x] Verify: `dart format`, `flutter analyze` (app + package clean),
`flutter test` (7 tests green), `flutter build macos --debug` succeeds
and bundles `packages/dartamp_skin/assets/...`. Note: package assets
resolve at `packages/dartamp_skin/assets/skins/base/` in the bundle, so
`loadBaseSkin` uses that path.
### A2. Self-contained storage + .wsz import (task 3)
- [x] `SkinRegistry` in the package (`skin_registry.dart`): scans a directory for
extracted skins, holds a `manifest.json` per skin (name + import time),
`importArchive()` unzips a `.wsz` into `skins/<name>/` (flat top-level
files only), `loadSkin()` overlays on the bundled base. Base is NOT
extracted to disk: it stays bundled in app assets and is served directly
by `loadBaseSkin()` (registry lists it first), so a first-run extraction
is unnecessary. Imported skins never touch original Winamp files.
- [x] App-side `SkinManager` (`lib/src/skin/skin_manager.dart`): owns the
registry + active skin + loaded `ClassicSkin`; `apply()`/`importArchive()`
persist `winamp.active_skin` and reload; sub-windows load their own skin
by name via `loadAppSkin()`.
- [x] Main window renders the manager's skin; EQ/PL sub-windows receive the skin
name in `SubWindowArgs` at spawn and live `setSkin` pushes over
`winamp.subwindows` control channel.
- [x] Import UI: "Load Skin…" item added to the app menu (MainMenu.xib +
AppDelegate `importSkin:`), wired to Dart `FilePicker` -> import + apply.
- [x] Verify: `flutter analyze` (app + package clean), package tests green
(11 incl. `skin_registry_test.dart`), `flutter build macos --debug` ok.
### A3. Cursors (task 4)
- `ClassicSkin` exposes cursor bitmaps (`cursor.bmp`/`.cur`) + hotspot (default
skin included).
- Native `NSCursor` from skin bitmap via the `winamp` channel; applied with
`MouseRegion` over the windows.
## Phase B — Docking & window management (new `lib/src/docking/`)
### B1. Plumbing
- Persist per-window positions (`winamp.window_<name>_x/y` in PlayerState);
sub-windows spawn at saved positions instead of `center()`.
- Sub-windows report bounds over `winamp.subwindows`; main holds the
authoritative rect map; main -> sub pushes on demand.
- Add `getScreenBounds` to AppDelegate's `winamp` channel.
- Replace `DragSurface.startDragging()` with a custom drag loop: pointer-down
records start pos + grab; move computes delta -> snap -> `setPosition`;
dragged window moves attached windows via relayed delta; drag-end persists
positions + recomputes attachments.
### B2. Dock logic (task 1) — port from DOCK.cpp / Set.cpp / ui.cpp
- `IsWindowAttached` (dynamic geometry), `SnapWindowToWindow`, `SnapToScreen`,
`AdjustSnap`, `FixOverlaps`.
- Shade-toggle re-pin (`doMyDirtyShitholeDockingShit`) when main/EQ/PL sizes
change; docking severs automatically on window close.
- Verify vs original: stacked main->PL->EQ moves together; moving a docked
window undocks it; shade toggle keeps below-windows pinned; closing middle
PL severs the chain.
### B3. Playlist resize from bottom-right (task 6)
- Custom bottom-right resize handle (window_manager startResizing is
Win/Linux-only).
- Verify original row-snapping constraints; reuse re-pin for windows docked
below PL.
## Phase C — UI fixes
### C1. EQ presets window (task 7)
- Implement the presets window, wire the presets button, load/save to prefs.
### C2. PL bottom action buttons (task 8)
- Research original `button.bmp` regions + popup behavior; clipped sprites +
long-press full-sheet popup with release-to-activate; verify vs original.
## Phase D — Preferences + dock menu
### D1. Preferences window (task 2)
- Match original classic layout (Setup, Audio, Visualization, Plug-ins,
Skins, Titles, Directories, etc.); all tabs no-op except Skins (registry
list + active selection).
### D2. Dock icon menu (task 9)
- `applicationDockMenu(_:)` with Main/EQ/PL visibility toggles; add missing
main-window item to the Window menu; flip
`applicationShouldTerminateAfterLastWindowClosed` -> `false` so closing all
windows keeps the app alive.
+9 -2
View File
@@ -1,5 +1,4 @@
TODO
====
# TODO
- [ ] The EQ and playlist windows should be "dockable" to each other. Dragging, for example, the playlist window to the bottom of the main window would "dock" the playlist window to the bottom window, at which point moving the main window would also move the playlist window. This should allow you to dock all the main windows (main, playlist, equalizer) atop each other, or any two of the windows should be dockable to each other. If, for example, the playlist window is docked between the main and equalizer windows, then the playlist window is closed, the "docking" should be severed for the windows that are no longer touching. The current window-snapping feature should be retained, as it helps you align the windows with each other. Moving docked windows is accomplished by moving the window on the "top" of the stack. So, if the playlist is docked below the main window, moving the playlist window will undock it from the main window, but moving the main window will move both windows together. Toggling window-shade mode on a docked window will reposition windows below it to keep them pinned to the bottom. Verify all of this behavior against the original source.
- [ ] There should be a preferences window that matches the original application's look/feel/layout. The options can be no-op stubs, except for the skins.
@@ -10,3 +9,11 @@ TODO
- [ ] The presets button on the equalizer doesn't open the presets window as it should.
- [ ] The playlist window has 5 action buttons along the bottom that are currently implemented incorrectly. Right now, the sprites are drawn full-size, but they should be clipped. However, when you tap and hold on the button, it should open the full sprite sheet as a pop-up. Releasing the cursor on any of the items should trigger the action. Verify this against the original source.
- [ ] Right-clicking the dock icon should give us the same window menu options for the main window, equalizer, and playlist window visibility. The window menu currently lacks an option for the main window, so it should be added. Closing all windows shouldn't exit the program.
## New Items
- [ ] Equalizier and playlist windows should remember position when opening/closing, even between launches. This should also include window-docking and window-shade.
- [ ] BUG: I can no longer move the main window unless it is in window-shade mode or until I've toggled window shade mode on/off.
- [ ] BUG: The main screen's un-window-shade button is not wired up.
- [ ] BUG: The windows take a long time to toggle window shade mode on/off.
- [ ] BUG: The main screen has 4 buttons on the top-right: the first one is currently bugged with the incorrect sprite, minimize (which doesn't work), window shade (works), and close (which doesn't work).