aboutsummaryrefslogtreecommitdiff
path: root/src
diff options
context:
space:
mode:
authorFuwn <[email protected]>2025-04-10 17:41:57 -0700
committerFuwn <[email protected]>2025-04-10 17:41:57 -0700
commit4d133fedb749437cdaff24d7d69c9a3ffdb42dd3 (patch)
treea417473fea32dd918f0bf192ab406a80b5cf725b /src
parentfeat: Add AniList Badges Easter Event 2025 demo (diff)
downloaddue.moe-4d133fedb749437cdaff24d7d69c9a3ffdb42dd3.tar.xz
due.moe-4d133fedb749437cdaff24d7d69c9a3ffdb42dd3.zip
feat: Add AniList Badges Easter Event 2025 demo #2
Diffstat (limited to 'src')
-rw-r--r--src/lib/Events/AniListBadges/EasterEvent2025/EasterEgg.svelte111
-rw-r--r--src/routes/+page.svelte9
-rw-r--r--src/routes/completed/+page.svelte5
-rw-r--r--src/routes/settings/+page.svelte7
4 files changed, 129 insertions, 3 deletions
diff --git a/src/lib/Events/AniListBadges/EasterEvent2025/EasterEgg.svelte b/src/lib/Events/AniListBadges/EasterEvent2025/EasterEgg.svelte
new file mode 100644
index 00000000..ac747aba
--- /dev/null
+++ b/src/lib/Events/AniListBadges/EasterEvent2025/EasterEgg.svelte
@@ -0,0 +1,111 @@
+<script lang="ts">
+ import { onMount } from 'svelte';
+ import { goto } from '$app/navigation';
+ import root from '$lib/Utility/root';
+
+ export let targetID = 'easter-target';
+ export let id: number;
+
+ let eggCount = 0;
+ let visible = false;
+
+ onMount(() => {
+ const storedEggCount = localStorage.getItem('easter2025Eggs');
+ const targetElement = document.getElementById(targetID);
+ const urlParameters = new URLSearchParams(window.location.search);
+ const hasPreviewParameter = urlParameters.get('preview') === 'easter-2025';
+
+ eggCount = storedEggCount ? parseInt(storedEggCount) : 0;
+
+ if (targetElement) {
+ const updatePosition = () => {
+ const eggVisual = document.getElementById(`egg-visual-${targetID}-${id}`);
+ const eggClick = document.getElementById(`egg-click-${targetID}-${id}`);
+ const pageWidth = document.documentElement.clientWidth;
+ const storedClickedEggs = localStorage.getItem('easter2025ClickedEggs');
+ const clickedEggs = storedClickedEggs ? JSON.parse(storedClickedEggs) : [];
+
+ visible = hasPreviewParameter && !clickedEggs.includes(id);
+
+ if (eggVisual && eggClick) {
+ const verticalPosition = targetElement.offsetHeight * 0.9;
+ const eggWidthPercent = (100 / pageWidth) * 100;
+ const horizontalPosition = targetElement.offsetWidth - eggWidthPercent / 2;
+
+ eggVisual.style.top = `${verticalPosition}px`;
+ eggVisual.style.left = `${horizontalPosition}px`;
+ eggVisual.style.zIndex = '-1';
+ eggClick.style.top = `${verticalPosition}px`;
+ eggClick.style.left = `${horizontalPosition}px`;
+ eggClick.style.zIndex = '9999';
+ }
+ };
+
+ window.addEventListener('resize', updatePosition);
+ window.addEventListener('scroll', updatePosition);
+
+ return () => {
+ window.removeEventListener('resize', updatePosition);
+ window.removeEventListener('scroll', updatePosition);
+ };
+ }
+ });
+
+ function handleClick(event: MouseEvent) {
+ if (event.button === 0) {
+ eggCount += 1;
+
+ localStorage.setItem('easter2025Eggs', eggCount.toString());
+
+ const storedClickedEggs = localStorage.getItem('easter2025ClickedEggs');
+ const clickedEggs = storedClickedEggs ? JSON.parse(storedClickedEggs) : [];
+
+ if (!clickedEggs.includes(id)) {
+ clickedEggs.push(id);
+ localStorage.setItem('easter2025ClickedEggs', JSON.stringify(clickedEggs));
+ }
+
+ visible = false;
+
+ if (eggCount >= 3) goto(root('/anilist-badges-easter-event-2025?page=4'));
+ } else if (event.button === 1) {
+ eggCount = 0;
+ visible = true;
+
+ localStorage.setItem('easter2025Eggs', '0');
+ localStorage.setItem('easter2025ClickedEggs', '[]');
+ }
+ }
+</script>
+
+{#if visible}
+ <img
+ id="egg-visual-{targetID}-{id}"
+ src="https://images.vexels.com/media/users/3/162149/isolated/preview/7f9f0546b21308e4851956e9c15313c9-egg-easter-painted-easter-egg-easter-egg-spot-pattern-stripe-flat.png"
+ alt="Easter Egg"
+ class="egg"
+ />
+
+ <div
+ id="egg-click-{targetID}-{id}"
+ role="button"
+ tabindex="0"
+ on:mousedown={handleClick}
+ class="egg click-layer"
+ />
+{/if}
+
+<style>
+ .egg {
+ position: absolute;
+ width: 100px;
+ height: 100px;
+ transform: rotate(15deg);
+ }
+
+ .click-layer {
+ cursor: pointer;
+ background: transparent;
+ z-index: 9999;
+ }
+</style>
diff --git a/src/routes/+page.svelte b/src/routes/+page.svelte
index 653c3836..daf51739 100644
--- a/src/routes/+page.svelte
+++ b/src/routes/+page.svelte
@@ -12,6 +12,7 @@
import locale from '$stores/locale.js';
import Landing from '$lib/Landing.svelte';
import IndexColumn from '$lib/List/Anime/DueIndexColumn.svelte';
+ import EasterEgg from '$lib/Events/AniListBadges/EasterEvent2025/EasterEgg.svelte';
export let data;
@@ -47,7 +48,11 @@
>
<div class="left-column">
{#if !$settings.disableUpcomingAnime}
- <details open={!$settings.displayUpcomingAnimeCollapsed} class="list list-upcoming">
+ <details
+ open={!$settings.displayUpcomingAnimeCollapsed}
+ class="list list-upcoming"
+ id="easter-target"
+ >
{#if $userIdentity.id !== -2}
<UpcomingAnimeList user={data.user} />
{:else}
@@ -63,6 +68,8 @@
{/if}
</div>
+ <EasterEgg id={0} />
+
<div class="right-column">
{#if !$settings.disableAnime && $settings.disableManga}
<IndexColumn user={data.user} userIdentity={$userIdentity} />
diff --git a/src/routes/completed/+page.svelte b/src/routes/completed/+page.svelte
index d483d7fe..26eaa0ec 100644
--- a/src/routes/completed/+page.svelte
+++ b/src/routes/completed/+page.svelte
@@ -11,6 +11,7 @@
import Skeleton from '$lib/Loading/Skeleton.svelte';
import locale from '$stores/locale.js';
import Landing from '$lib/Landing.svelte';
+ import EasterEgg from '$lib/Events/AniListBadges/EasterEvent2025/EasterEgg.svelte';
export let data;
@@ -34,7 +35,7 @@
{:else}
<div class="list-container">
{#if !$settings.displayFiltersIncludeCompleted || !$settings.disableAnime}
- <details open={!$settings.displayAnimeCollapsed} class="list">
+ <details open={!$settings.displayAnimeCollapsed} class="list" id="easter-target">
{#if $userIdentity.id !== -2}
<WatchingAnimeList user={data.user} />
{:else}
@@ -63,6 +64,8 @@
</div>
{/if}
+<EasterEgg id={1} />
+
<style>
.list-container {
display: flex;
diff --git a/src/routes/settings/+page.svelte b/src/routes/settings/+page.svelte
index 42ee4edd..1302b3ea 100644
--- a/src/routes/settings/+page.svelte
+++ b/src/routes/settings/+page.svelte
@@ -14,6 +14,7 @@
import LogInRestricted from '$lib/Error/LogInRestricted.svelte';
import SettingSync from '$lib/Settings/Categories/SettingSync.svelte';
import RssFeeds from '$lib/Settings/Categories/RSSFeeds.svelte';
+ import EasterEgg from '$lib/Events/AniListBadges/EasterEvent2025/EasterEgg.svelte';
export let data;
@@ -64,7 +65,9 @@
{:else}
<div class="small-categories">
<Category title={$locale().settings.settingsSync.title} id="sync" newLine={false}>
- <SettingSync />
+ <div id="easter-target">
+ <SettingSync />
+ </div>
</Category>
<Category title={$locale().settings.rssFeeds.title} id="feeds" newLine={false}>
<RssFeeds user={data.user} />
@@ -93,6 +96,8 @@
<Category title={$locale().settings.attributions.title} open={false}><Attributions /></Category>
{/if}
+<EasterEgg id={2} />
+
<style>
.small-categories {
display: grid;