diff --git a/src/components/Radio.svelte b/src/components/Radio.svelte index e8c97fd..b763350 100644 --- a/src/components/Radio.svelte +++ b/src/components/Radio.svelte @@ -23,7 +23,7 @@ import Footer from '/components/layout/Footer.svelte' import Queue from '/components/Queue.svelte' import Viewer from '/components/Viewer.svelte' - import { get, writable, writableLocalStorage, derived, scan, wait, startWith, distinct } from '/services/store.js' + import { get, writable, writableStorage, derived, scan, wait, startWith } from '/services/store.js' import { radioIterator, radioShareIterator } from '/services/radio.js' import DeepSet from '/services/deep-set.js' @@ -34,9 +34,9 @@ const cache = new DeepSet() - const domain = writableLocalStorage('domain', 'eldritch.cafe') + const domain = writableStorage(localStorage, 'domain', 'eldritch.cafe') - const hashtags = writableLocalStorage('hashtags', [ + const hashtags = writableStorage(localStorage, 'hashtags', [ 'np', 'nowplaying', 'tootradio', @@ -44,7 +44,7 @@ ]) const paused = writable(true) - const volume = writableLocalStorage('volume', 100) + const volume = writableStorage(localStorage, 'volume', 100) const current = writable(null) const enqueueing = writable(false) @@ -66,22 +66,28 @@ }, null) const next = derived([iterator, current], ([$iterator, $current]) => ({ $iterator, $current })) - .pipe(scan(($nextPromise, { $iterator, $current }) => { - return $nextPromise.then($next => { - if ($next == null || $next === $current) { - enqueueing.set(true) - return $iterator.next().then(({ done, value }) => { - enqueueing.set(false) - return value - }).catch(console.error) - } else { - return $nextPromise - } + .pipe(source => { + let $next = null + + return writable(undefined, set => { + source.subscribe(({ $iterator, $current }) => { + if ($current !== null && $next === $current) { + $next = null + set($next) + } + + if ($next === null) { + enqueueing.set(true) + + $iterator.next().then(({ done, value }) => { + enqueueing.set(false) + $next = value + set($next) + }).catch(console.error) + } + }) }) - }, Promise.resolve(null))) - .pipe(wait(x => x)) - // distinct but with strict check - .pipe(distinct()) + }) .pipe(startWith(null)) @@ -139,9 +145,9 @@ } onMount(() => { - const stickyObserver = new IntersectionObserver( + const stickyObserver = new IntersectionObserver( ([e]) => { - sticky = (e.intersectionRatio === 0) + sticky = (e.intersectionRatio === 0) }, {threshold: [0]} ) diff --git a/src/services/store.js b/src/services/store.js index 5b952a2..bf0595d 100644 --- a/src/services/store.js +++ b/src/services/store.js @@ -1,26 +1,12 @@ -import { writable, readable } from 'svelte-pipeable-store' +import { writable, tap } from 'svelte-pipeable-store' export { get } from 'svelte/store' export * from 'svelte-pipeable-store' -export const writableLocalStorage = (key, value) => { - const item = JSON.parse(localStorage.getItem(key)) - const store = writable(item === null ? value : item) +export const writableStorage = (storage, storageKey, defaultValue) => { + const item = storage.getItem(storageKey) + const value = item === null ? defaultValue : JSON.parse(item) - store.subscribe(x => localStorage.setItem(key, JSON.stringify(x))) - - return store -} - -export const distinct = () => { - return ({ subscribe }) => readable(undefined, set => { - let last - - return subscribe(v => { - if (last !== v) { - set(v) - last = v - } - }) - }) + return writable(value) + .pipe(tap(value => storage.setItem(storageKey, JSON.stringify(value)))) } \ No newline at end of file