mirror of
https://github.com/Psychotoxical/psysonic.git
synced 2026-07-22 15:25:46 +00:00
feat(sidebar): add split Mix navigation mode with separate sidebar entries
Extract ALL_NAV_ITEMS to src/config/navItems.ts and add randomMix/randomAlbums nav items. A new toggle in Settings switches between a single "Build a Mix" hub and separate "Random Mix" / "Random Albums" sidebar entries (randomNavMode in authStore). Fixes reorder crash caused by hidden items being overwritten with undefined during the merge step. Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>
This commit is contained in:
@@ -212,6 +212,11 @@ interface AuthState {
|
||||
setMixMinRatingArtist: (v: number) => void;
|
||||
setMusicFolders: (folders: Array<{ id: string; name: string }>) => void;
|
||||
setMusicLibraryFilter: (folderId: 'all' | string) => void;
|
||||
|
||||
/** Navigation style for Mix pages: single hub ('hub') or separate sidebar entries ('separate'). */
|
||||
randomNavMode: 'hub' | 'separate';
|
||||
setRandomNavMode: (v: 'hub' | 'separate') => void;
|
||||
|
||||
logout: () => void;
|
||||
|
||||
// Derived
|
||||
@@ -304,6 +309,7 @@ export const useAuthStore = create<AuthState>()(
|
||||
mixMinRatingSong: 0,
|
||||
mixMinRatingAlbum: 0,
|
||||
mixMinRatingArtist: 0,
|
||||
randomNavMode: 'hub',
|
||||
musicFolders: [],
|
||||
musicLibraryFilterByServer: {},
|
||||
musicLibraryFilterVersion: 0,
|
||||
@@ -457,6 +463,7 @@ export const useAuthStore = create<AuthState>()(
|
||||
setMixMinRatingSong: (v) => set({ mixMinRatingSong: clampMixFilterMinStars(v) }),
|
||||
setMixMinRatingAlbum: (v) => set({ mixMinRatingAlbum: clampMixFilterMinStars(v) }),
|
||||
setMixMinRatingArtist: (v) => set({ mixMinRatingArtist: clampMixFilterMinStars(v) }),
|
||||
setRandomNavMode: (v) => set({ randomNavMode: v }),
|
||||
|
||||
setMusicFolders: (folders) => {
|
||||
const sid = get().activeServerId;
|
||||
|
||||
@@ -13,6 +13,8 @@ export const DEFAULT_SIDEBAR_ITEMS: SidebarItemConfig[] = [
|
||||
{ id: 'newReleases', visible: true },
|
||||
{ id: 'allAlbums', visible: true },
|
||||
{ id: 'randomPicker', visible: true },
|
||||
{ id: 'randomMix', visible: true },
|
||||
{ id: 'randomAlbums', visible: true },
|
||||
{ id: 'artists', visible: true },
|
||||
{ id: 'genres', visible: true },
|
||||
{ id: 'favorites', visible: true },
|
||||
@@ -49,11 +51,11 @@ export const useSidebarStore = create<SidebarStore>()(
|
||||
name: 'psysonic_sidebar',
|
||||
onRehydrateStorage: () => (state) => {
|
||||
if (!state) return;
|
||||
const known = new Set(state.items.map(i => i.id));
|
||||
// Sanitize: remove any null/corrupted entries that may have been persisted
|
||||
const safe = (state.items ?? []).filter((i): i is SidebarItemConfig => i != null && typeof i.id === 'string');
|
||||
const known = new Set(safe.map(i => i.id));
|
||||
const missing = DEFAULT_SIDEBAR_ITEMS.filter(i => !known.has(i.id));
|
||||
if (missing.length > 0) {
|
||||
state.items = [...state.items, ...missing];
|
||||
}
|
||||
state.items = missing.length > 0 ? [...safe, ...missing] : safe;
|
||||
},
|
||||
}
|
||||
)
|
||||
|
||||
Reference in New Issue
Block a user