Commit Graph
3 Commits
Author SHA1 Message Date
vicrodh b8b493bd59 fix(qt): persist the player volume, so a launch stops starting at 100%
PARITY-DEBT #3 — the cheapest AUDIBLE row in the inventory. Volume was never
written and never restored: `setVolume` reached the engine and stopped there.
Set it to 15%, quit, relaunch, and playback came back at full scale. On an
exclusive-mode DAC at night that is not a cosmetic default.

1:1 with the Slint: persist on drag-END only (`NowPlayingState.persist-volume`,
PlayerBar.slint:864-866 -> qbz/src/main.rs:14413-14417), restore at shell entry
(qbz/src/main.rs:220-227), and let the poll loop mirror the engine back onto the
slider so nothing else has to publish it.

Drag-end matters here rather than being a nicety: ui_prefs.json is co-owned with
the running Slint app and both processes do a whole-document read-modify-write,
so a write per drag tick is a write per pixel into a shared file. `QbzSlider`
only had `changed`, which fires on every tick, so it gains a `released` signal
carrying the settled value — both now-playing bars use it.

Two supporting bits: `QbzPlayer.persistVolume` (the engine setter stays
per-tick, only the persist is debounced by the signal), and
`settings_qt::read_pref_f32` — the crate had no public ui_prefs reader, theme_qt
kept a private one, and a third private copy is exactly what the write
discipline at the top of settings_qt exists to prevent.

Verified the key name against the live file: `volume` is already present in the
shared ui_prefs.json alongside 60 other keys, so this reads and writes what the
Slint build reads and writes.

cc
2026-07-30 09:46:19 -06:00
vicrodh c8a5b03aee fix(qbz-qt): live output LEDs, closer stamp, and a volume lock on ALSA direct
The LEDs only changed when the user navigated. They were published from the
settings snapshot, so they refreshed when that document republished rather
than when playback started — which is exactly when the backend and mode are
decided, a moment after "now playing" in the log. They publish on the stream
edge now, without polling and without republishing settings.

The stamp itself was close but not 1:1, so it went back against
shell/AudioStamp.slint, primitives/QualityBadgeFull.slint and shell/SongCard.slint
line by line; the divergences in sizes, weights, spacing and the inactive LED
colour are corrected.

Volume is locked while the bit-perfect ALSA direct path is engaged. Software
volume there is meaningless and applying it would not be bit-perfect, so the
control now reads as inert rather than silently doing nothing. Slint has the
same gap and no lock to copy, so this is new: the condition comes from the
output state already published, and no audio behaviour changed — only the UI
reflects it.

cc
2026-07-28 16:22:48 -06:00
vicrodh 9a4fec6b70 refactor(qbz-qt): phase 23 part 1 — QML module layout + first five domain bridges
Two fronts of the modularization, both gated green before this commit.

QML leaves the flat qml/ directory for seven modules: cards, controls,
rows, settings, shell, theme, views. Only Main.qml and LoginScreen.qml
stay at the root. build.rs matches the tree exactly (55 files), relative
imports and asset paths were re-anchored for the new depth.

The QbzBridge God-object starts breaking up: QbzSession, QbzShell,
QbzPlayer, QbzQueue and QbzHome are now their own #[cxx_qt::bridge]
singletons, each with its own OnceLock<CxxQtThread> and ui() hop, booted
in order from Main.qml. Bridge files stay directly under src/ because
cxx-qt-build only accepts rust_files from one directory (QTBUG-93443).

bridge.rs keeps 5.5 domains (library, album/artist, settings,
integrations, search, playlist) and dies once they are split out.

cc
2026-07-28 11:08:20 -06:00