diff --git a/typescript/client/src/app/pages/LandingPage.tsx b/typescript/client/src/app/pages/LandingPage.tsx
index c5fc0f851..9c4e2bcbb 100644
--- a/typescript/client/src/app/pages/LandingPage.tsx
+++ b/typescript/client/src/app/pages/LandingPage.tsx
@@ -3,6 +3,7 @@ import Divider from "#components/util/Divider";
import LinkButton from "#components/util/LinkButton";
import { TachiConfig } from "#lib/config";
import { ToCDNURL } from "#util/api";
+import { DEFAULT_GAME_BANNER_REL_PATH } from "#util/game-group-banner-counts";
import React from "react";
// This page is currently unused,
@@ -17,7 +18,7 @@ export default function LandingPage() {
(null);
diff --git a/typescript/client/src/util/game-group-banner-counts.ts b/typescript/client/src/util/game-group-banner-counts.ts
new file mode 100644
index 000000000..3404c9246
--- /dev/null
+++ b/typescript/client/src/util/game-group-banner-counts.ts
@@ -0,0 +1,51 @@
+import type { GameGroup } from "tachi-common";
+
+/** Fallback hero/background when no game is selected or a group has no variants. */
+export const DEFAULT_GAME_BANNER_REL_PATH = "/game-banners/default.webp";
+
+/**
+ * How many CDN banner variants exist per game group, named
+ * `{gameGroup}-{n}.webp` with `n` in `[1, count]` (one-based).
+ *
+ * Bump the count when new banner images are added for a group on the CDN.
+ */
+export const GAME_GROUP_BANNER_COUNTS = {
+ iidx: 1,
+ museca: 1,
+ chunithm: 1,
+ bms: 1,
+ gitadora: 1,
+ jubeat: 1,
+ maimai: 1,
+ maimaidx: 1,
+ popn: 1,
+ sdvx: 1,
+ usc: 1,
+ wacca: 1,
+ pms: 1,
+ itg: 1,
+ arcaea: 1,
+ ongeki: 1,
+ ddr: 1,
+} as const satisfies Record;
+
+export function getGameGroupBannerCount(gameGroup: GameGroup): number {
+ return GAME_GROUP_BANNER_COUNTS[gameGroup];
+}
+
+/**
+ * CDN-relative path for this group's banner. Picks `{gameGroup}-n.webp` where
+ * `n = ((local weekday from Date#getDay()) % count) + 1` — same backdrop all Sunday, etc.
+ *
+ * Bump GAME_GROUP_BANNER_COUNTS when adding images; weekdays cycle indices in `[1, count]`.
+ */
+export function getGameGroupBannerRelPathForWeekday(gameGroup: GameGroup): string {
+ const count = GAME_GROUP_BANNER_COUNTS[gameGroup];
+ if (count <= 0) {
+ return DEFAULT_GAME_BANNER_REL_PATH;
+ }
+
+ const weekday = new Date().getDay(); // 0 = Sunday … 6 = Saturday
+ const n = (weekday % count) + 1;
+ return `/game-banners/${gameGroup}-${n}.webp`;
+}
diff --git a/typescript/server/example/default-cdn-contents/game-banners/arcaea b/typescript/server/example/default-cdn-contents/game-banners/arcaea
deleted file mode 100644
index 4a4e21a83..000000000
Binary files a/typescript/server/example/default-cdn-contents/game-banners/arcaea and /dev/null differ
diff --git a/typescript/server/example/default-cdn-contents/game-banners/arcaea-1.webp b/typescript/server/example/default-cdn-contents/game-banners/arcaea-1.webp
new file mode 100644
index 000000000..b777a70de
Binary files /dev/null and b/typescript/server/example/default-cdn-contents/game-banners/arcaea-1.webp differ
diff --git a/typescript/server/example/default-cdn-contents/game-banners/bms-1.webp b/typescript/server/example/default-cdn-contents/game-banners/bms-1.webp
new file mode 100644
index 000000000..5804fd644
Binary files /dev/null and b/typescript/server/example/default-cdn-contents/game-banners/bms-1.webp differ
diff --git a/typescript/server/example/default-cdn-contents/game-banners/chunithm b/typescript/server/example/default-cdn-contents/game-banners/chunithm
deleted file mode 100755
index 8aa5158e1..000000000
Binary files a/typescript/server/example/default-cdn-contents/game-banners/chunithm and /dev/null differ
diff --git a/typescript/server/example/default-cdn-contents/game-banners/chunithm-1.webp b/typescript/server/example/default-cdn-contents/game-banners/chunithm-1.webp
new file mode 100644
index 000000000..f380030ac
Binary files /dev/null and b/typescript/server/example/default-cdn-contents/game-banners/chunithm-1.webp differ
diff --git a/typescript/server/example/default-cdn-contents/game-banners/ddr b/typescript/server/example/default-cdn-contents/game-banners/ddr
deleted file mode 100644
index b7c4a0b65..000000000
Binary files a/typescript/server/example/default-cdn-contents/game-banners/ddr and /dev/null differ
diff --git a/typescript/server/example/default-cdn-contents/game-banners/ddr-1.webp b/typescript/server/example/default-cdn-contents/game-banners/ddr-1.webp
new file mode 100644
index 000000000..63d961fe7
Binary files /dev/null and b/typescript/server/example/default-cdn-contents/game-banners/ddr-1.webp differ
diff --git a/typescript/server/example/default-cdn-contents/game-banners/default b/typescript/server/example/default-cdn-contents/game-banners/default
deleted file mode 100755
index 78ab46d5c..000000000
Binary files a/typescript/server/example/default-cdn-contents/game-banners/default and /dev/null differ
diff --git a/typescript/server/example/default-cdn-contents/game-banners/bms b/typescript/server/example/default-cdn-contents/game-banners/default.png
similarity index 100%
rename from typescript/server/example/default-cdn-contents/game-banners/bms
rename to typescript/server/example/default-cdn-contents/game-banners/default.png
diff --git a/typescript/server/example/default-cdn-contents/game-banners/default.webp b/typescript/server/example/default-cdn-contents/game-banners/default.webp
new file mode 100644
index 000000000..5804fd644
Binary files /dev/null and b/typescript/server/example/default-cdn-contents/game-banners/default.webp differ
diff --git a/typescript/server/example/default-cdn-contents/game-banners/gitadora b/typescript/server/example/default-cdn-contents/game-banners/gitadora
deleted file mode 100755
index 86c974404..000000000
Binary files a/typescript/server/example/default-cdn-contents/game-banners/gitadora and /dev/null differ
diff --git a/typescript/server/example/default-cdn-contents/game-banners/gitadora-1.webp b/typescript/server/example/default-cdn-contents/game-banners/gitadora-1.webp
new file mode 100644
index 000000000..cc9903263
Binary files /dev/null and b/typescript/server/example/default-cdn-contents/game-banners/gitadora-1.webp differ
diff --git a/typescript/server/example/default-cdn-contents/game-banners/iidx b/typescript/server/example/default-cdn-contents/game-banners/iidx
deleted file mode 100755
index d4930f4e9..000000000
Binary files a/typescript/server/example/default-cdn-contents/game-banners/iidx and /dev/null differ
diff --git a/typescript/server/example/default-cdn-contents/game-banners/iidx-1.webp b/typescript/server/example/default-cdn-contents/game-banners/iidx-1.webp
new file mode 100644
index 000000000..89365c873
Binary files /dev/null and b/typescript/server/example/default-cdn-contents/game-banners/iidx-1.webp differ
diff --git a/typescript/server/example/default-cdn-contents/game-banners/jubeat b/typescript/server/example/default-cdn-contents/game-banners/jubeat
deleted file mode 100644
index 6da4e9ffc..000000000
Binary files a/typescript/server/example/default-cdn-contents/game-banners/jubeat and /dev/null differ
diff --git a/typescript/server/example/default-cdn-contents/game-banners/jubeat-1.webp b/typescript/server/example/default-cdn-contents/game-banners/jubeat-1.webp
new file mode 100644
index 000000000..38ab564de
Binary files /dev/null and b/typescript/server/example/default-cdn-contents/game-banners/jubeat-1.webp differ
diff --git a/typescript/server/example/default-cdn-contents/game-banners/maimai b/typescript/server/example/default-cdn-contents/game-banners/maimai
deleted file mode 100755
index ad2bba578..000000000
Binary files a/typescript/server/example/default-cdn-contents/game-banners/maimai and /dev/null differ
diff --git a/typescript/server/example/default-cdn-contents/game-banners/maimai-1.webp b/typescript/server/example/default-cdn-contents/game-banners/maimai-1.webp
new file mode 100644
index 000000000..195a355a0
Binary files /dev/null and b/typescript/server/example/default-cdn-contents/game-banners/maimai-1.webp differ
diff --git a/typescript/server/example/default-cdn-contents/game-banners/maimaidx-1.webp b/typescript/server/example/default-cdn-contents/game-banners/maimaidx-1.webp
new file mode 100644
index 000000000..c51b25407
Binary files /dev/null and b/typescript/server/example/default-cdn-contents/game-banners/maimaidx-1.webp differ
diff --git a/typescript/server/example/default-cdn-contents/game-banners/museca b/typescript/server/example/default-cdn-contents/game-banners/museca
deleted file mode 100755
index 769b0b3dc..000000000
Binary files a/typescript/server/example/default-cdn-contents/game-banners/museca and /dev/null differ
diff --git a/typescript/server/example/default-cdn-contents/game-banners/museca-1.webp b/typescript/server/example/default-cdn-contents/game-banners/museca-1.webp
new file mode 100644
index 000000000..dcaf3b832
Binary files /dev/null and b/typescript/server/example/default-cdn-contents/game-banners/museca-1.webp differ
diff --git a/typescript/server/example/default-cdn-contents/game-banners/ongeki b/typescript/server/example/default-cdn-contents/game-banners/ongeki
deleted file mode 100644
index 14a05e18e..000000000
Binary files a/typescript/server/example/default-cdn-contents/game-banners/ongeki and /dev/null differ
diff --git a/typescript/server/example/default-cdn-contents/game-banners/ongeki-1.webp b/typescript/server/example/default-cdn-contents/game-banners/ongeki-1.webp
new file mode 100644
index 000000000..09feb3a07
Binary files /dev/null and b/typescript/server/example/default-cdn-contents/game-banners/ongeki-1.webp differ
diff --git a/typescript/server/example/default-cdn-contents/game-banners/pms b/typescript/server/example/default-cdn-contents/game-banners/pms
deleted file mode 100644
index 418aa001d..000000000
Binary files a/typescript/server/example/default-cdn-contents/game-banners/pms and /dev/null differ
diff --git a/typescript/server/example/default-cdn-contents/game-banners/pms-1.webp b/typescript/server/example/default-cdn-contents/game-banners/pms-1.webp
new file mode 100644
index 000000000..043e10ccd
Binary files /dev/null and b/typescript/server/example/default-cdn-contents/game-banners/pms-1.webp differ
diff --git a/typescript/server/example/default-cdn-contents/game-banners/popn b/typescript/server/example/default-cdn-contents/game-banners/popn
deleted file mode 100755
index 633859fe9..000000000
Binary files a/typescript/server/example/default-cdn-contents/game-banners/popn and /dev/null differ
diff --git a/typescript/server/example/default-cdn-contents/game-banners/popn-1.webp b/typescript/server/example/default-cdn-contents/game-banners/popn-1.webp
new file mode 100644
index 000000000..425628ace
Binary files /dev/null and b/typescript/server/example/default-cdn-contents/game-banners/popn-1.webp differ
diff --git a/typescript/server/example/default-cdn-contents/game-banners/sdvx b/typescript/server/example/default-cdn-contents/game-banners/sdvx
deleted file mode 100755
index 69aa8bbfb..000000000
Binary files a/typescript/server/example/default-cdn-contents/game-banners/sdvx and /dev/null differ
diff --git a/typescript/server/example/default-cdn-contents/game-banners/sdvx-1.webp b/typescript/server/example/default-cdn-contents/game-banners/sdvx-1.webp
new file mode 100644
index 000000000..9f5965ae0
Binary files /dev/null and b/typescript/server/example/default-cdn-contents/game-banners/sdvx-1.webp differ
diff --git a/typescript/server/example/default-cdn-contents/game-banners/usc b/typescript/server/example/default-cdn-contents/game-banners/usc
deleted file mode 100644
index 361d965a2..000000000
Binary files a/typescript/server/example/default-cdn-contents/game-banners/usc and /dev/null differ
diff --git a/typescript/server/example/default-cdn-contents/game-banners/usc-1.webp b/typescript/server/example/default-cdn-contents/game-banners/usc-1.webp
new file mode 100644
index 000000000..ddd5e7247
Binary files /dev/null and b/typescript/server/example/default-cdn-contents/game-banners/usc-1.webp differ
diff --git a/typescript/server/example/default-cdn-contents/game-banners/wacca b/typescript/server/example/default-cdn-contents/game-banners/wacca
deleted file mode 100644
index 5a97228a2..000000000
Binary files a/typescript/server/example/default-cdn-contents/game-banners/wacca and /dev/null differ
diff --git a/typescript/server/example/default-cdn-contents/game-banners/wacca-1.webp b/typescript/server/example/default-cdn-contents/game-banners/wacca-1.webp
new file mode 100644
index 000000000..3ffb4a0ca
Binary files /dev/null and b/typescript/server/example/default-cdn-contents/game-banners/wacca-1.webp differ