feat(library): genre sliders, artist links, and navigation utils
- music landing: diverse per-genre album sliders (online counts / offline wide-probe fallback) and home-screen library shortcuts - add ArtistLinks component and shared navigation/genreDiversity utils - player/playback-mode refinements across Rust and frontend
This commit is contained in:
@@ -8,7 +8,7 @@
|
||||
import type { MediaItem } from "$lib/api/types";
|
||||
import { auth } from "$lib/stores/auth";
|
||||
import { library } from "$lib/stores/library";
|
||||
import { queue, currentQueueItem } from "$lib/stores/queue";
|
||||
import { queue, currentQueueItem, isShuffle, repeatMode, hasNext as hasNextStore, hasPrevious as hasPreviousStore } from "$lib/stores/queue";
|
||||
import { downloads, type DownloadInfo } from "$lib/stores/downloads";
|
||||
import { playbackPosition, playbackDuration, currentMedia as storeCurrentMedia } from "$lib/stores/player";
|
||||
import { get } from "svelte/store";
|
||||
@@ -47,10 +47,12 @@
|
||||
const position = $derived($playbackPosition);
|
||||
const duration = $derived($playbackDuration);
|
||||
let isPlaying = $state(false);
|
||||
let shuffle = $state(false);
|
||||
let repeat = $state<"off" | "all" | "one">("off");
|
||||
let hasNext = $state(false);
|
||||
let hasPrevious = $state(false);
|
||||
// Shuffle/repeat/next/previous are event-driven via the queue store (instant
|
||||
// update on queue_changed), not polled.
|
||||
const shuffle = $derived($isShuffle);
|
||||
const repeat = $derived($repeatMode);
|
||||
const hasNext = $derived($hasNextStore);
|
||||
const hasPrevious = $derived($hasPreviousStore);
|
||||
let currentMedia = $state<MediaItem | null>(null);
|
||||
let streamUrl = $state<string | null>(null);
|
||||
let mediaSourceId = $state<string | null>(null);
|
||||
@@ -133,14 +135,7 @@
|
||||
isVideo = item.type === "Movie" || item.type === "Episode";
|
||||
isPlaying = true;
|
||||
loading = false;
|
||||
// Sync queue status
|
||||
try {
|
||||
const queueStatus = await commands.playerGetQueue();
|
||||
hasNext = queueStatus.hasNext;
|
||||
hasPrevious = queueStatus.hasPrevious;
|
||||
} catch (e) {
|
||||
// Ignore - queue status will update via polling
|
||||
}
|
||||
// hasNext/hasPrevious come from the event-driven queue store.
|
||||
// Fetch next episode for video skip button
|
||||
if (isVideo) {
|
||||
fetchNextEpisode(item);
|
||||
@@ -446,13 +441,7 @@
|
||||
isPlaying = status.state.kind === "playing";
|
||||
// Note: position/duration are now derived from player store (updated by events)
|
||||
}
|
||||
shuffle = status.shuffle;
|
||||
repeat = status.repeat;
|
||||
|
||||
// Update queue status
|
||||
const queue = await commands.playerGetQueue();
|
||||
hasNext = queue.hasNext;
|
||||
hasPrevious = queue.hasPrevious;
|
||||
// shuffle/repeat/hasNext/hasPrevious come from the queue store (event-driven).
|
||||
} catch (e) {
|
||||
// Ignore polling errors
|
||||
}
|
||||
|
||||
Reference in New Issue
Block a user