aboutsummaryrefslogtreecommitdiff
path: root/src/lib/Hololive/Lives.svelte
diff options
context:
space:
mode:
Diffstat (limited to 'src/lib/Hololive/Lives.svelte')
-rw-r--r--src/lib/Hololive/Lives.svelte168
1 files changed, 53 insertions, 115 deletions
diff --git a/src/lib/Hololive/Lives.svelte b/src/lib/Hololive/Lives.svelte
index c7ecfdf8..38def6fa 100644
--- a/src/lib/Hololive/Lives.svelte
+++ b/src/lib/Hololive/Lives.svelte
@@ -1,10 +1,8 @@
<script lang="ts">
import Message from '$lib/Loading/Message.svelte';
import root from '$lib/Utility/root';
- import identity from '$stores/identity';
- import locale from '$stores/locale';
- import Icon from '@iconify/svelte';
- import type { ParseResult } from './hololive';
+ import type { Live, ParseResult } from './hololive';
+ import Stream from './Stream.svelte';
export let schedule: ParseResult;
export let closestUpcomingPinnedStreams: Map<string, any>;
@@ -18,23 +16,8 @@
'Content-Type': 'application/json'
}
}).then(getPinnedStreams);
-</script>
-
-{#if schedule.lives.length === 0}
- <Message message="No upcoming streams." loader="ripple" />
-{/if}
-<div class="container">
- {#each schedule.lives
- .filter((live) => {
- try {
- $locale().hololive.dateFormatter(new Date(live.time));
-
- return true;
- } catch {
- return false;
- }
- })
+ $: categorisedStreams = schedule.lives
.sort((a, b) => new Date(a.time).getTime() - new Date(b.time).getTime())
.sort((a, b) => {
const now = Date.now();
@@ -58,111 +41,66 @@
if (bTime > now && !(bTime < now && !bIsLive)) return 1;
return bTime - aTime;
- }) as live}
- <div class="stream card">
- {#if $identity.id !== -2}
- <div class="pin-icon">
- <a
- href={'#'}
- on:click={(e) => {
- e.preventDefault();
- pinStream(live.streamer);
- }}
- >
- <Icon
- icon={`pajamas:thumbtack${pinnedStreams.includes(live.streamer) ? '-solid' : ''}`}
- width="1em"
- />
- </a>
- </div>
- {/if}
-
- <p class="stream-heading">
- [{#if live.streaming}
- <b class="live">{$locale().hololive.live}</b
- >{:else if new Date(live.time).getTime() < Date.now()}
- <span class="ended">{$locale().hololive.ended}</span>{:else}
- <span class="upcoming">{$locale().hololive.upcoming}</span>{/if}]
- <b>{live.streamer}</b> <span class="opaque">|</span>
- {$locale().hololive.dateFormatter(new Date(live.time))}
- {#if live.guests.length > 0}
- <br />
- <small>
- {$locale().hololive.with}{live.guests
- .join($locale().hololive.comma)
- .replace(
- new RegExp(
- `${$locale().hololive.comma}([^${$locale().hololive.commaNoSpace}]+)$`,
- 'g'
- ),
- `${$locale().hololive.comma}${$locale().hololive.ampersand}$1`
- )}
- </small>
- {/if}
- </p>
-
- <a href={live.link} class="preview" target="_blank">
- <img src={live.livePreviewImage} alt="Stream Thumbnail" />
- </a>
- </div>
+ })
+ .reduce(
+ (
+ acc: {
+ live: Live[];
+ upcoming: Live[];
+ ended: Live[];
+ },
+ live
+ ) => {
+ const now = Date.now();
+ const time = new Date(live.time).getTime();
+ const isLive = live.streaming;
+ const isUpcoming = time > now && !isLive;
+ const isEnded = time < now && !isLive;
+
+ if (isLive) {
+ acc.live.push(live);
+ } else if (isUpcoming) {
+ acc.upcoming.push(live);
+ } else if (isEnded) {
+ acc.ended.push(live);
+ }
+
+ return acc;
+ },
+ { live: [], upcoming: [], ended: [] }
+ );
+</script>
+
+{#if schedule.lives.length === 0}
+ <Message message="No upcoming streams." loader="ripple" />
+{/if}
+
+<div class="container">
+ {#each categorisedStreams.live as live}
+ <Stream {live} {pinStream} {pinnedStreams} />
{/each}
</div>
-<style lang="scss">
- .preview {
- // margin: 0.15rem;
-
- img {
- border-radius: 8px;
- height: 20vh;
- object-fit: cover;
- transition: transform 0.3s ease;
- }
-
- &:hover {
- img {
- position: relative;
- z-index: 2;
- transition: transform 0.3s ease;
- transform: scale(1.05);
- }
- }
-
- display: flex;
- justify-content: center;
- align-items: center;
- }
+<p />
- .live {
- color: var(--base0F);
- }
+<div class="container">
+ {#each categorisedStreams.upcoming as live}
+ <Stream {live} {pinStream} {pinnedStreams} />
+ {/each}
+</div>
- .upcoming {
- color: var(--base0C);
- }
+<p />
- .ended {
- color: var(--base0D);
- }
+<div class="container">
+ {#each categorisedStreams.ended as live}
+ <Stream {live} {pinStream} {pinnedStreams} />
+ {/each}
+</div>
+<style lang="scss">
.container {
display: grid;
grid-template-columns: repeat(auto-fill, minmax(22.5em, 1fr));
gap: 0.5em;
}
-
- .pin-icon {
- position: absolute;
- right: 0;
- top: 0;
- padding: 0.75rem;
- }
-
- .stream {
- position: relative;
- }
-
- .stream-heading {
- padding-right: 2em;
- }
</style>