feat: add unified contest pool and realtime game modes

This commit is contained in:
2026-08-10 00:31:21 +08:00
parent 97ca20413e
commit 40e9462842
18 changed files with 822 additions and 152 deletions
+5 -24
View File
@@ -14,23 +14,6 @@
},
};
function difficultySelect() {
const select = document.createElement("select");
select.className = "game-difficulty";
[
["easy", "入门"],
["standard", "标准"],
["hard", "进阶"],
].forEach(([value, label]) => {
const option = document.createElement("option");
option.value = value;
option.textContent = label;
if (value === "standard") option.selected = true;
select.append(option);
});
return select;
}
function gameCard(game) {
const meta = GAME_META[game.kind];
const article = document.createElement("article");
@@ -50,12 +33,11 @@
summary.textContent = game.summary;
const controls = document.createElement("div");
controls.className = "game-card-controls";
const difficulty = difficultySelect();
const start = document.createElement("button");
start.className = "primary-button";
start.textContent = meta.action;
start.addEventListener("click", () => startGame(game.kind, difficulty.value));
controls.append(difficulty, start);
start.addEventListener("click", () => startGame(game.kind));
controls.append(start);
article.append(top, kicker, title, summary, controls);
return article;
}
@@ -70,12 +52,12 @@
}
}
async function startGame(kind, difficulty) {
async function startGame(kind) {
if (!requireAuth()) return;
try {
const attempt = await api(`contests/games/${kind}/start/`, {
method: "POST",
body: { difficulty },
body: {},
});
renderGame(attempt);
$game("#experience-dialog").showModal();
@@ -88,8 +70,7 @@
const fragment = document.createDocumentFragment();
const label = document.createElement("span");
label.className = "kicker";
label.textContent =
`${GAME_META[attempt.kind].kicker} · ${attempt.difficulty.toUpperCase()}`;
label.textContent = GAME_META[attempt.kind].kicker;
const title = document.createElement("h2");
title.textContent = GAME_META[attempt.kind].title;
fragment.append(label, title);