diff --git a/frontend/src/html/pages/test-result.html b/frontend/src/html/pages/test-result.html
new file mode 100644
index 000000000000..14f4bbd3e81d
--- /dev/null
+++ b/frontend/src/html/pages/test-result.html
@@ -0,0 +1,317 @@
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
daily leaderboard
+
+ -
+
+
+
+
+
+ source
+
+
+
+
+
+
+
+
+
+
+
+
-
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
input history
+
+
+
+
+
+
+
+
+
+ watch replay
+
+
0s
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
monkeytype.com
+
+
+
diff --git a/frontend/src/html/pages/test.html b/frontend/src/html/pages/test.html
index f2d8f33c8140..a2cf8e5a2538 100644
--- a/frontend/src/html/pages/test.html
+++ b/frontend/src/html/pages/test.html
@@ -195,321 +195,5 @@
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
daily leaderboard
-
- -
-
-
-
-
-
- source
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
input history
-
-
-
-
-
-
-
-
-
- watch replay
-
-
0s
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
monkeytype.com
-
-
-
+
diff --git a/frontend/src/ts/controllers/page-controller.ts b/frontend/src/ts/controllers/page-controller.ts
index e60461598866..b191c40e5c99 100644
--- a/frontend/src/ts/controllers/page-controller.ts
+++ b/frontend/src/ts/controllers/page-controller.ts
@@ -275,9 +275,9 @@ export async function change(
typeof nextPageLoadingMode === "object" &&
nextPageLoadingMode.mode === "async"
) {
- nextPageLoadingMode.beforeLoading();
+ nextPageLoadingMode.beforeLoading?.();
void nextPage?.loadingOptions?.loadingPromise().then(() => {
- nextPageLoadingMode.afterLoading();
+ nextPageLoadingMode.afterLoading?.();
});
}
diff --git a/frontend/src/ts/pages/leaderboards.ts b/frontend/src/ts/pages/leaderboards.ts
index bb07897e9d89..d9c78c1b0414 100644
--- a/frontend/src/ts/pages/leaderboards.ts
+++ b/frontend/src/ts/pages/leaderboards.ts
@@ -1485,13 +1485,19 @@ export const page = new PageWithUrlParams({
element: qsr(".page.pageLeaderboards"),
path: "/leaderboards",
urlParamsSchema: UrlParameterSchema,
+ loadingOptions: {
+ style: "spinner",
+ loadingMode: () => "sync",
+ loadingPromise: async () => {
+ await ServerConfiguration.configurationPromise;
+ },
+ },
afterHide: async (): Promise => {
Skeleton.remove("pageLeaderboards");
stopTimer();
},
beforeShow: async (options): Promise => {
- await ServerConfiguration.configurationPromise;
Skeleton.append("pageLeaderboards", "main");
await updateValidDailyLeaderboards();
await appendModeAndLanguageButtons();
diff --git a/frontend/src/ts/pages/page.ts b/frontend/src/ts/pages/page.ts
index 70375c86fcb5..aa23f89e43b6 100644
--- a/frontend/src/ts/pages/page.ts
+++ b/frontend/src/ts/pages/page.ts
@@ -34,7 +34,7 @@ export type LoadingOptions = {
loadingMode: () =>
| "none"
| "sync"
- | { mode: "async"; beforeLoading: () => void; afterLoading: () => void };
+ | { mode: "async"; beforeLoading?: () => void; afterLoading?: () => void };
/**
* When this promise resolves, the loading screen will be hidden.
*/