diff --git a/MyMusicClientSveltePwa/package-lock.json b/MyMusicClientSveltePwa/package-lock.json index 3d4884b..6a35c8b 100644 --- a/MyMusicClientSveltePwa/package-lock.json +++ b/MyMusicClientSveltePwa/package-lock.json @@ -1,12 +1,12 @@ { "name": "mymusicclientsveltepwa", - "version": "0.1.11", + "version": "0.1.12", "lockfileVersion": 3, "requires": true, "packages": { "": { "name": "mymusicclientsveltepwa", - "version": "0.1.11", + "version": "0.1.12", "dependencies": { "@sveltejs/svelte-virtual-list": "^3.0.1", "@sveltestrap/sveltestrap": "^7.1.0" diff --git a/MyMusicClientSveltePwa/package.json b/MyMusicClientSveltePwa/package.json index 5815fb6..562abf4 100644 --- a/MyMusicClientSveltePwa/package.json +++ b/MyMusicClientSveltePwa/package.json @@ -1,7 +1,7 @@ { "name": "mymusicclientsveltepwa", "private": true, - "version": "0.1.11-beta", + "version": "0.1.12", "type": "module", "scripts": { "dev": "vite --host", diff --git a/MyMusicClientSveltePwa/src/App.svelte b/MyMusicClientSveltePwa/src/App.svelte index b497fed..efcfc87 100644 --- a/MyMusicClientSveltePwa/src/App.svelte +++ b/MyMusicClientSveltePwa/src/App.svelte @@ -4,7 +4,7 @@ import { onMount, onDestroy, setContext } from "svelte"; import { get, writable } from "svelte/store"; - import { initializeRouteService, pathName, navigateTo, component, componentParams } from "./lib/scripts/routeService.js"; + import { initializeRouteService, pathName, navigateTo, component as currentView, componentParams } from "./lib/scripts/routeService.js"; import PlayerBar from "./lib/components/PlayerBar.svelte"; import Modals from "./lib/components/Modals.svelte"; import { initializePlaylistService, deleteCurrentPlaylist } from "./lib/scripts/playlistService.js"; @@ -14,7 +14,7 @@ import SearchBar from "./lib/components/SearchBar.svelte"; $: $pathName; - $: $component; + $: $currentView; // @ts-ignore export const version = __APP_VERSION__; @@ -33,7 +33,7 @@ } onMount(() => { - component.subscribe((value) => { + currentView.subscribe((value) => { // Whenever the component changes, enable auto scroll preventAutoScroll() }); @@ -59,6 +59,7 @@
MyMusicBox(v{version})
+
@@ -69,7 +70,7 @@
- +
diff --git a/MyMusicClientSveltePwa/src/lib/components/Playlist.svelte b/MyMusicClientSveltePwa/src/lib/components/Playlist.svelte index f61b493..509842b 100644 --- a/MyMusicClientSveltePwa/src/lib/components/Playlist.svelte +++ b/MyMusicClientSveltePwa/src/lib/components/Playlist.svelte @@ -23,7 +23,6 @@ songCount = getCachedPlaylistSongs(playlist.id).length; }); - {#if playlist} @@ -38,7 +37,7 @@
{:else} -

No playlist available.

+

No playlist founnd with id: {playlist.id}.

{/if} diff --git a/MyMusicClientSveltePwa/src/lib/scripts/storageService.js b/MyMusicClientSveltePwa/src/lib/scripts/storageService.js index 0e390a5..9410046 100644 --- a/MyMusicClientSveltePwa/src/lib/scripts/storageService.js +++ b/MyMusicClientSveltePwa/src/lib/scripts/storageService.js @@ -10,6 +10,7 @@ const CurrentSongIndexKey = "currentSongIndex"; const CurrentShuffeldPlaylistKey = "currentShuffledPlaylist"; const CurrentSongTimeKey = "currentSongTime"; const ConfigKey = "appConfig"; +const ConfigKeySearchQyery = "searchQuery"; export let appConfiguration = writable(getConfiguration()); @@ -18,6 +19,14 @@ export function setConfiguration(config) { setItem(ConfigKey, config); } +export function setSearchQueryInStorage(query) { + setItem(ConfigKeySearchQyery, query); +} + +export function getSearchQueryFromStorage() { + return getItem(ConfigKeySearchQyery) || ''; +} + export function setCachedPlaylists(playlists) { setItem(PlaylistsKey, playlists); } diff --git a/MyMusicClientSveltePwa/src/lib/scripts/util.js b/MyMusicClientSveltePwa/src/lib/scripts/util.js index c658af1..132ec8e 100644 --- a/MyMusicClientSveltePwa/src/lib/scripts/util.js +++ b/MyMusicClientSveltePwa/src/lib/scripts/util.js @@ -1,6 +1,6 @@ import { writable } from "svelte/store"; -export let searchQuery = writable(); +export let searchQuery = writable(''); // Mulberry32 PRNG function mulberry32(seed) { @@ -8,7 +8,7 @@ function mulberry32(seed) { let t = (seed += 0x6d2b79f5); t = Math.imul(t ^ (t >>> 15), t | 1); t ^= t + Math.imul(t ^ (t >>> 7), t | 61); - return ((t ^ (t >>> 14)) >>> 0) / 4294967296; + return ((t ^ (t >>> 16)) >>> 0) / 4294967296; }; } @@ -25,45 +25,58 @@ function generateSeed() { // Fisher-Yates shuffle with optional seed export function shuffleArray(array) { - const seed = generateSeed(); - const rng = mulberry32(seed); - - for (let i = array.length - 1; i > 0; i--) { - const j = Math.floor(rng() * (i + 1)); + const rng = mulberry32(generateSeed()); + let i = array.length; + while (i > 1) { + const j = Math.floor(rng() * i--); [array[i], array[j]] = [array[j], array[i]]; } - return array; } export function getSearchParameters() { - const searchParams = new URLSearchParams(window.location.search); const result = {}; - for (const [key, value] of searchParams.entries()) { - if (result[key]) { - // If key already exists, convert to array or push into existing array - result[key] = Array.isArray(result[key]) ? [...result[key], parseValue(value)] : [result[key], parseValue(value)]; + for (const [key, value] of new URLSearchParams(window.location.search)) { + const parsed = parseValue(value); + if (key in result) { + result[key] = Array.isArray(result[key]) ? [...result[key], parsed] : [result[key], parsed]; } else { - result[key] = parseValue(value); + result[key] = parsed; } } return result; } +/** + * Parses a string value to its appropriate type. + * @param {string} value + * @returns {boolean|number|string|null|undefined} + */ export function parseValue(value) { if (value === "true") return true; if (value === "false") return false; - if (!isNaN(value) && value.trim() !== "") return Number(value); + if (value == null) return value; + const trimmed = value.trim(); + if (/^-?\d+(\.\d+)?$/.test(trimmed)) return Number(trimmed); return value; } +/** + * Creates a URL search string from an object of parameters. + * @param {Object} params + * @returns {string} + */ export function createSearchParameters(params) { const searchParams = new URLSearchParams(); for (const key in params) { - if (Array.isArray(params[key])) { - params[key].forEach((value) => searchParams.append(key, value)); + const val = params[key]; + if (val == null) continue; + if (Array.isArray(val)) { + for (const v of val) searchParams.append(key, v); + } else if (typeof val === "object") { + searchParams.set(key, JSON.stringify(val)); } else { - searchParams.set(key, params[key]); + searchParams.set(key, val); } } return searchParams.toString();