fix(locallibrary): track-row source indicator (drop fav/offline) + AlbumView favorite item
LocalLibrary track rows (Tracks tab + local album detail) no longer carry the favorite or offline-cache columns — they don't apply to local content. Instead they show a subtle per-source indicator (local -> hard-drive tinted; qobuz offline / plex -> their mark), small + flat rather than the bold album-card badge (mirrors Tauri's track-row local indicator). TrackItem gains a `source` field, set by every constructor (Qobuz surfaces -> "qobuz"; map_local_track -> local/qobuz/plex); TrackRow gains `show-source`. Also fixes Qobuz AlbumView: the track list had a Favorite column header but the rows never rendered the heart (show-favorite defaulted false). AlbumPageView now sets show-favorite + show-download for Qobuz albums (matching the header) and the source indicator for local albums, with the column header switched to match each. cc
This commit is contained in:
12 files changed
+60
-6
No files matched your search
@@ -259,6 +259,8 @@ pub fn apply_album(window: &AppWindow, data: AlbumData) {
|
||||
removing: false,
|
||||
cache_status: if crate::offline_cache::is_cached(&track.id) { 3 } else { 0 },
|
||||
cache_progress: 0.0,
|
||||
// Qobuz album-detail rows; local albums override via map_local_track.
|
||||
source: "qobuz".into(),
|
||||
unlocking: false,
|
||||
})
|
||||
.collect();
|
||||
|
||||
@@ -505,6 +505,7 @@ pub fn apply_artist(window: &AppWindow, data: ArtistData) {
|
||||
removing: false,
|
||||
cache_status: if crate::offline_cache::is_cached(&track.id) { 3 } else { 0 },
|
||||
cache_progress: 0.0,
|
||||
source: "qobuz".into(),
|
||||
unlocking: false,
|
||||
})
|
||||
.collect();
|
||||
|
||||
@@ -421,6 +421,7 @@ pub fn apply_favorites(window: &AppWindow, data: FavData) {
|
||||
removing: false,
|
||||
cache_status: if crate::offline_cache::is_cached(&t.id) { 3 } else { 0 },
|
||||
cache_progress: 0.0,
|
||||
source: "qobuz".into(),
|
||||
unlocking: false,
|
||||
})
|
||||
.collect();
|
||||
|
||||
@@ -765,6 +765,7 @@ fn top_track_to_item(t: &TopTrack) -> TrackItem {
|
||||
removing: false,
|
||||
cache_status: if crate::offline_cache::is_cached(&t.id) { 3 } else { 0 },
|
||||
cache_progress: 0.0,
|
||||
source: "qobuz".into(),
|
||||
unlocking: false,
|
||||
}
|
||||
}
|
||||
|
||||
@@ -454,6 +454,13 @@ fn map_local_track(t: qbz_library::LocalTrack) -> TrackItem {
|
||||
removing: false,
|
||||
cache_status: 0,
|
||||
cache_progress: 0.0,
|
||||
// Source indicator: offline copies read as Qobuz, user files as local.
|
||||
source: match t.source.as_deref() {
|
||||
Some("qobuz_download") => "qobuz",
|
||||
Some("plex") => "plex",
|
||||
_ => "local",
|
||||
}
|
||||
.into(),
|
||||
unlocking: false,
|
||||
}
|
||||
}
|
||||
|
||||
@@ -177,6 +177,7 @@ fn to_item(track: &Track) -> TrackItem {
|
||||
removing: false,
|
||||
cache_status: if crate::offline_cache::is_cached(&track.id.to_string()) { 3 } else { 0 },
|
||||
cache_progress: 0.0,
|
||||
source: "qobuz".into(),
|
||||
unlocking: false,
|
||||
}
|
||||
}
|
||||
|
||||
@@ -384,6 +384,7 @@ fn to_item(track: &Track) -> TrackItem {
|
||||
removing: false,
|
||||
cache_status: if crate::offline_cache::is_cached(&track.id.to_string()) { 3 } else { 0 },
|
||||
cache_progress: 0.0,
|
||||
source: "qobuz".into(),
|
||||
unlocking: false,
|
||||
}
|
||||
}
|
||||
|
||||
@@ -375,6 +375,7 @@ fn track_item(row: TrackRowData) -> TrackItem {
|
||||
removing: false,
|
||||
cache_status: if is_cached { 3 } else { 0 },
|
||||
cache_progress: 0.0,
|
||||
source: "qobuz".into(),
|
||||
unlocking: false,
|
||||
}
|
||||
}
|
||||
|
||||
@@ -529,8 +529,10 @@ export component AlbumPageView inherits Rectangle {
|
||||
horizontal-alignment: center;
|
||||
vertical-alignment: center;
|
||||
}
|
||||
// Favorite / offline-cache column headers.
|
||||
Rectangle {
|
||||
// Favorite / offline-cache column headers (Qobuz). For
|
||||
// a local album the rows show a source indicator
|
||||
// instead, so one unlabeled column keeps alignment.
|
||||
if !AlbumState.is-local: Rectangle {
|
||||
width: 28px;
|
||||
QbzIcon {
|
||||
source: @image-url("../assets/icons/heart.svg");
|
||||
@@ -541,7 +543,7 @@ export component AlbumPageView inherits Rectangle {
|
||||
tint: Theme.text-muted;
|
||||
}
|
||||
}
|
||||
Rectangle {
|
||||
if !AlbumState.is-local: Rectangle {
|
||||
width: 28px;
|
||||
QbzIcon {
|
||||
source: @image-url("../assets/icons/cloud-download.svg");
|
||||
@@ -552,6 +554,7 @@ export component AlbumPageView inherits Rectangle {
|
||||
tint: Theme.text-muted;
|
||||
}
|
||||
}
|
||||
if AlbumState.is-local: Rectangle { width: 28px; }
|
||||
// Aligns with the per-row more-button slot.
|
||||
Rectangle { width: 32px; }
|
||||
}
|
||||
@@ -559,10 +562,14 @@ export component AlbumPageView inherits Rectangle {
|
||||
for track[index] in AlbumState.tracks: TrackRow {
|
||||
track: track;
|
||||
index: index;
|
||||
// Album context: number cell (no cover), with the
|
||||
// offline-cache button.
|
||||
// Number cell (no cover). Qobuz albums carry the
|
||||
// favorite heart (matching the column header) + the
|
||||
// offline-cache button; local albums show the source
|
||||
// indicator instead.
|
||||
show-artwork: false;
|
||||
show-download: true;
|
||||
show-favorite: !AlbumState.is-local;
|
||||
show-download: !AlbumState.is-local;
|
||||
show-source: AlbumState.is-local;
|
||||
media-action(kind, id, action) => {
|
||||
root.media-action(kind, id, action);
|
||||
}
|
||||
|
||||
@@ -513,6 +513,7 @@ export component LocalLibraryView inherits Rectangle {
|
||||
show-album: true;
|
||||
show-favorite: false;
|
||||
show-download: false;
|
||||
show-source: true;
|
||||
media-action(kind, id, action) => {
|
||||
if (kind == "album" && action == "open") {
|
||||
LocalLibraryActions.open-album(id);
|
||||
|
||||
@@ -36,6 +36,9 @@ export component TrackRow inherits Rectangle {
|
||||
// button. A non-Qobuz surface (future Local Library / Plex rows, which are
|
||||
// already local) should set this false.
|
||||
in property <bool> show-download: true;
|
||||
// Local Library: a subtle per-source indicator (local / qobuz / plex)
|
||||
// shown INSTEAD of the favorite + offline columns.
|
||||
in property <bool> show-source: false;
|
||||
in property <bool> multi-select-mode: false;
|
||||
// Custom-order reorder controls (up/down chevrons) at the leading
|
||||
// edge — used by the playlist custom sort.
|
||||
@@ -451,6 +454,31 @@ export component TrackRow inherits Rectangle {
|
||||
}
|
||||
}
|
||||
|
||||
// Source indicator (Local Library) — a subtle per-source glyph shown
|
||||
// instead of the favorite/offline columns. local -> hard-drive
|
||||
// (tinted), plex / qobuz(offline) -> their mark; small + flat, not the
|
||||
// bold album-card badge.
|
||||
if root.show-source && root.track.source != "": VerticalLayout {
|
||||
alignment: center;
|
||||
Rectangle {
|
||||
width: 28px;
|
||||
height: 28px;
|
||||
Image {
|
||||
source: root.track.source == "plex"
|
||||
? @image-url("../assets/icons/plex-logo.svg")
|
||||
: (root.track.source == "qobuz"
|
||||
? @image-url("../assets/icons/qobuz-logo-filled.svg")
|
||||
: @image-url("../assets/icons/hard-drive.svg"));
|
||||
colorize: root.track.source == "local" ? Theme.text-muted : transparent;
|
||||
width: root.track.source == "local" ? 15px : 16px;
|
||||
height: self.width;
|
||||
x: (parent.width - self.width) / 2;
|
||||
y: (parent.height - self.height) / 2;
|
||||
image-fit: contain;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
// Context menu.
|
||||
VerticalLayout {
|
||||
alignment: center;
|
||||
|
||||
@@ -251,6 +251,9 @@ export struct TrackItem {
|
||||
// album view, both via the media-action bubble channel.
|
||||
artist-id: string,
|
||||
album-id: string,
|
||||
// "qobuz" | "local" | "plex" | "" — drives the Local Library source
|
||||
// indicator (shown instead of the favorite/offline columns).
|
||||
source: string,
|
||||
// Fading out (un-favorited in the favorites view) before removal.
|
||||
removing: bool,
|
||||
// Offline-cache status: 0 none, 1 queued, 2 downloading, 3 ready, 4 failed.
|
||||
|
||||
Reference in new issue
Block a user