From f34de9760850489d8f08eddb9bd33a41beda4771 Mon Sep 17 00:00:00 2001
From: Fuwn <contact@fuwn.net>
Date: Thu, 4 Jun 2026 09:28:32 +0000
Subject: fix(lists): tick count down when media leaves a list

On revalidation the {#await} branch swaps and remounts CleanAnimeList,
resetting NumberTicker's tween to 0 so it always counted up. Persist the
last displayed count in AnimeListTemplate (which survives the remount) and
feed it as the ticker's start, so the count animates in the real
direction: down when an item leaves due/upcoming, up when one arrives.
---
 src/lib/List/Anime/CleanAnimeList.svelte | 19 ++++++++++++++++---
 1 file changed, 16 insertions(+), 3 deletions(-)

(limited to 'src/lib/List/Anime/CleanAnimeList.svelte')

diff --git a/src/lib/List/Anime/CleanAnimeList.svelte b/src/lib/List/Anime/CleanAnimeList.svelte
index 0bc88489..f2077d20 100644
--- a/src/lib/List/Anime/CleanAnimeList.svelte
+++ b/src/lib/List/Anime/CleanAnimeList.svelte
@@ -30,6 +30,7 @@ export let endTime: number;
 export let lastUpdatedMedia: number;
 export let completed = false;
 export let previousAnimeList: Media[];
+export let previousCount: number | undefined = undefined;
 export let pendingUpdate: number | null;
 export let upcoming = false;
 export let notYetReleased = false;
@@ -37,6 +38,12 @@ export let dummy = false;
 export let disableFilter = false;
 export let limit: number | undefined = undefined;
 
+// This list remounts on every revalidation (the {#await} branch swaps),
+// which resets the count ticker's tween. Snapshot the count the user last
+// saw so the ticker animates from it — ticking down when an item leaves,
+// up when one arrives — instead of always counting up from zero.
+const startCount = previousCount;
+
 let showRoulette = false;
 let airingRefreshTimeout: ReturnType<typeof setTimeout> | undefined;
 let scheduledAiringAt: number | null = null;
@@ -111,6 +118,13 @@ $: filteredMedia =
 		? media
 		: media.filter((m) => m.mediaListEntry?.customLists?.[selectedList]);
 
+$: displayedCount =
+	$settings.displayTotalDueEpisodes || $settings.displayTotalEpisodes
+		? totalEpisodeDueCount
+		: filteredMedia.length;
+
+$: previousCount = displayedCount;
+
 $: if (browser && !dummy && media && previousAnimeList !== media)
 	previousAnimeList = media;
 
@@ -241,9 +255,8 @@ const increment = (anime: Media, progress: number) => {
 
 <ListTitle
   time={endTime / 1000}
-  count={$settings.displayTotalDueEpisodes || $settings.displayTotalEpisodes
-    ? totalEpisodeDueCount
-    : filteredMedia.length}
+  count={displayedCount}
+  start={startCount ?? 0}
   {title}
   hideTime={dummy}
   hideCount={dummy || media.length === 0}
-- 
cgit v1.2.3

