refact store again

This commit is contained in:
wryk 2020-02-14 16:48:49 +01:00
parent 9b87708077
commit dacc31ce77
6 changed files with 99 additions and 85 deletions

3
.gitignore vendored
View File

@ -2,4 +2,5 @@ node_modules
dist
public
.cache
.env
.env
.now

View File

@ -21,11 +21,65 @@
<script>
import { onMount, onDestroy } from 'svelte'
import { get } from 'svelte/store'
import Controls from '/components/Controls.svelte'
import Queue from '/components/Queue.svelte'
import Viewer from '/components/Viewer.svelte'
import { hashtagIterator } from '/services/mastodon.js'
import { mkTracksIterator } from '/services/misc.js'
import { current } from '/store.js'
import { domain, hashtags, queue, next, current, enqueueing, select } from '/store.js'
let nextUnsubcribe = null
let currentUnsubcribe = null
onMount(async () => {
const iterator = mkTracksIterator(hashtagIterator(get(domain), get(hashtags)[0]))
const { value: first } = await iterator.next()
queue.set([first])
select(first)
nextUnsubcribe = next.subscribe(async nextValue => {
if (nextValue === null) {
if (!get(enqueueing)) {
enqueueing.set(true)
const { value: newTrack } = await iterator.next()
if (newTrack) {
queue.update(queueValue => [...queueValue, newTrack])
next.set(newTrack)
}
enqueueing.set(false)
}
}
})
currentUnsubcribe = current.subscribe(currentValue => {
if (currentValue !== null) {
next.update(nextValue => {
if (nextValue === currentValue) {
return null
} else {
return nextValue
}
})
}
})
})
onDestroy(() => {
for (const unsubcribe of [nextUnsubcribe, currentUnsubcribe]) {
if (unsubcribe) {
unsubcribe()
}
}
})
</script>
<style>

View File

@ -19,7 +19,7 @@
<button class:cant={!$canPrevious} on:click={() => selectPrevious()}>⏮️</button>
<button on:click={() => $paused = !$paused}>
{#if $index === null}
{#if $current === null}
▶️
{:else if $loading}
🕒
@ -44,7 +44,7 @@
paused,
muted,
volume,
index,
current,
queue,
canPrevious,
canNext,

View File

@ -1,7 +1,8 @@
<div>
<h6>PLAY NEXT</h6>
{#if $next}
<div class="entry">
<div class="entry" on:click={() => select($next)}>
<div class="title">{$next.metadata.title}</div>
<div class="user">by {$next.status.account.acct}</div>
</div>
@ -13,54 +14,32 @@
<h6>HISTORY</h6>
{#each $queue as track, i (track.status.id)}
<div class="entry" class:active={i === $index}>
<div>
<button on:click={() => toggle(i)}>
{#if i != $index}
▶️
{:else if $loading}
🕒
{:else if $paused}
▶️
{:else}
⏸️
{/if}
</button>
</div>
<div class="title">{track.metadata.title}</div>
<div class="user">by {track.status.account.acct}</div>
{#each history as track (track.status.id)}
<div class="entry" class:active={track === $current} on:click={() => select(track)}>
<div class>{track.metadata.title}</div>
<div class>shared by {track.status.account.acct}</div>
</div>
{/each}
</div>
<script>
import { onMount } from 'svelte'
import { next, enqueueing, queue, index, paused, loading, canNext, selectNext } from '/store.js'
import { queue, next, current, enqueueing, select } from '/store.js'
const toggle = i => {
if (i === $index) {
$paused = !$paused
} else {
$index = i
$paused = false
}
}
$: if ($queue.length === 0 && $index === null && $next !== null) {
$queue = [$next]
$next = null
$index = 0
}
$: history = $queue.filter(x => x !== $next).reverse()
</script>
<style>
.entry {
padding: 1em 2em;
cursor: pointer;
}
.entry.active {
background-color: plum;
}
.entry.active::before {
content: "▶️";
}
</style>

View File

@ -20,20 +20,22 @@
LOADING TRACK
{/if}
{#if duration}
<div>
{currentTimeText}
<input
type="range"
min="0"
max={duration}
value="0"
value="{currentTime}"
on:input={event => updateCurrentTime(event.target.value, false)}
on:change={event => updateCurrentTime(event.target.value, true)}
disabled={currentTime === null || duration === null}
>
{durationText}
{/if}
</div>
</div>
<script>
@ -49,8 +51,8 @@
let duration = null
let seek = null
$: currentTimeText = currentTime !== null ? secondsToElapsedTime(currentTime) : null
$: durationText = duration !== null ? secondsToElapsedTime(duration) : null
$: currentTimeText = currentTime !== null ? secondsToElapsedTime(currentTime) : '--:--'
$: durationText = duration !== null ? secondsToElapsedTime(duration) : '--:--'
$: if (ended || error) {
selectNext()

View File

@ -1,7 +1,5 @@
import { writable, derived, get } from 'svelte/store'
import { writableLocalStorage } from '/services/svelte.js'
import { hashtagIterator } from '/services/mastodon.js'
import { mkTracksIterator } from '/services/misc.js'
export const domain = writableLocalStorage('domain', 'eldritch.cafe')
@ -12,63 +10,43 @@ export const hashtags = writableLocalStorage('hashtags', [
'pouetradio'
])
const tracksIterator = mkTracksIterator(hashtagIterator(get(domain), get(hashtags)[0]))
export const paused = writable(true)
export const muted = writableLocalStorage('muted', false)
export const volume = writableLocalStorage('volume', 100)
export const next = writable(null)
export const enqueueing = writable(false)
export const queue = writable([])
export const index = writable(null)
export const current = derived([queue, index], ([$queue, $index]) => $queue[$index])
export const canPrevious = derived([index, queue], ([$index, $queue]) => $index !== null && $index < $queue.length - 1)
export const canNext = derived([index, next], ([$index, $next]) => $index !== null && ($index > 0 || $next !== null))
export const next = writable(null)
export const current = writable(null)
export const enqueueing = writable(false)
export const loading = writable(false)
next.subscribe(async $next => {
if ($next === null) {
if (!get(enqueueing)) {
enqueueing.set(true)
const { value: newTrack } = await tracksIterator.next()
if (newTrack) {
next.set(newTrack)
}
enqueueing.set(false)
}
}
const index = derived([queue, current], ([$queue, $current]) => {
const i = $queue.indexOf($current)
return i === -1 ? null : i
})
export const canPrevious = derived([queue, index], ([$queue, $index]) => $index !== null && $index > 0)
export const canNext = derived([queue, index], ([$queue, $index]) => $index !== null && $index < $queue.length - 1)
export const select = track => {
console.log(`Select ${track.metadata.title}`)
current.set(track)
}
export const selectPrevious = () => {
if (get(canPrevious)) {
index.update($index => $index + 1)
const $queue = get(queue)
const $index = get(index)
select($queue[$index - 1])
}
}
export const selectNext = () => {
if (get(canNext)) {
const $queue = get(queue)
const $index = get(index)
if ($index === 0) {
queue.update($queue => {
const $next = get(next)
next.set(null)
return [$next, ...$queue]
})
} else {
index.update($index => $index - 1)
}
select($queue[$index + 1])
}
}