gostations/todo/queued/per-station-volume.md

75 lines
4.8 KiB
Markdown
Raw Permalink Normal View History

# Per-station volume savings (favorites only)
**Description**: Persist the last-used volume level *only for stations in your favorites list* (keyed by stream URL). When you return to a favorited station, it restores the volume you last set for *that specific station* (falling back to the global last-volume if none saved for it). Non-favorited stations always use the global last-volume.
## Problem It Solves
Currently only a single global `player.last_volume` is saved in `radiostations.ini`. When a user fine-tunes the volume while listening to a favorited Station A (e.g. to 35), stops, then plays another favorited Station B, the volume resets to the global value (or default 70). Users have to re-adjust every time they switch between their own favorites. We deliberately limit this to favorited stations only (no unbounded per-station data for the entire radio-browser corpus).
## Benefits
- **Natural UX**: Volume preference is specific to your favorited stations (e.g. a quiet classical vs. a loud rock station).
- **Seamless resumption**: Pick a favorite from your list → volume is already where you left it for *that* station.
- **Low friction**: No extra UI; the existing volume controls + persistence just become smarter for your own list.
- **Backward compatible**: Non-favorites always use global last-volume. Falls back gracefully.
- **Leverages existing patterns**: Volumes live inside the favorites data (no new file or unbounded store). Same atomic JSON + XDG path.
## High-Level Implementation
1. **Extend the existing Favorites store** (no new file needed):
- Add `Volume int `json:"volume,omitempty"`` field to `radio.Station`.
- Add `SetVolume(url string, vol int)` and `GetVolume(url string) int` to `*data.Favorites`.
- When `Add`ing or updating a favorite while a volume is active, capture it on the station.
- Volumes are automatically persisted inside `favorites.json` (only for stations you have favorited).
- `Remove` naturally drops the volume data for that station.
2. **Wire into TUI / playback** (in `internal/ui/ui.go`):
- On entering playback for a station (Enter in list):
- `desired := config.LastVolume()`
- `if v := a.favs.GetVolume(station.Url); v > 0 { desired = v }`
- Prefer live `a.currentVolume` for session stickiness across s/x within the same run.
- Pass `desired` via `--volume=...` extra arg to `Play()`.
- On volume change (key handler and `volumeMsg`):
- After updating `currentVolume`, if the current station's URL is in favorites: `a.favs.SetVolume(url, currentVolume)` and `Save()`.
- Always still call `config.SetLastVolume` for the global fallback.
- On `s`/`x` stop or quit: ensure the current station's per-fav volume (if any) is saved via `favs.SetVolume` + `Save()`.
3. **Player interface**:
- No new methods required for basic functionality (we pass `--volume` on `Play`).
- (Optional future) Add `SetVolume` for runtime adjustment after start.
4. **Scope is deliberately narrow**:
- Only stations that exist in the user's favorites list get per-station volumes.
- No unbounded storage for the entire radio-browser catalog.
- When you unfavorite a station, its volume preference is dropped.
- Non-favorites always use global `last_volume` (or 70).
## Flags / Config
| Key | Description |
|-----|-------------|
| (none yet) | Could add `player.per_station_volume=true` (default on) in future |
## Implementation Notes
- **Key choice**: Use the station's `Url` (same as Favorites). Volumes only exist for stations the user has explicitly favorited.
- **When to persist**: Save on volume change for the favorite (immediate, like global), plus on stop/quit. Non-favorites never create per-station entries.
- **mpv timing**: The `--volume=XX` extra arg passed to `Play()` is the simplest reliable way (command-line wins for the launch of that station).
- **Legacy player**: Per-station volumes are ignored (documented limitation).
- **First-time migration**: Existing global last-volume is the fallback. No per-station entries until the user actually changes volume while playing a favorite.
- **Tests**: Extend existing favorites tests and playback tests.
- **Effort**: Low-to-medium. Reuses the Favorites store and persistence; mostly wiring in the TUI playback entry and volume handlers. No new files.
## ROI
**High**. Volume is one of the most frequently adjusted controls. Making it "stick" for the stations *you actually care about* (your favorites) removes friction without the complexity of tracking every station ever played.
| Stage | Covered |
|-------|---------|
| Global last-volume | ✓ (already shipped) |
| Per-favorite volume | **new** (narrowed scope) |
| Favorites integration | ✓ (reuses existing store) |
| TUI playback | ✓ |
Users will notice it immediately the second time they return to a station they previously tuned.