Files

112 lines
4.6 KiB
TypeScript

import { cn } from "@/lib/utils";
import { grades, pkPageCursorClass } from "../constants";
import type { ClassType, Grade } from "../types";
type StartScreenProps = {
selectedGrade: Grade;
classTypes: ClassType[];
selectedClassTypeId: number;
selectedClassTypeName?: string;
availableWordCount: number;
plannedRoundCount: number;
loadingSetup: boolean;
scorePerCorrect: number;
scorePerWrong: number;
onSelectGrade: (grade: Grade) => void;
onSelectClassType: (classTypeId: number) => void;
onStartGame: () => void;
};
export function StartScreen({
selectedGrade,
classTypes,
selectedClassTypeId,
selectedClassTypeName,
availableWordCount,
plannedRoundCount,
loadingSetup,
scorePerCorrect,
scorePerWrong,
onSelectGrade,
onSelectClassType,
onStartGame,
}: StartScreenProps) {
return (
<main
className={cn(
pkPageCursorClass,
"pk-start-stage mx-auto grid min-h-[calc(100vh-60px)] max-w-5xl place-items-center px-4 py-4",
)}
>
<section className="pk-start-card w-full rounded-[24px] bg-white p-[clamp(18px,3vw,36px)] text-center shadow-soft">
<div className="pk-start-visual mb-2 text-[clamp(54px,8vw,92px)] leading-none">🦊 VS 🦓</div>
<h1 className="pk-start-title text-balance text-[clamp(28px,4vw,44px)] font-black text-rose-500">字母单词PK赛</h1>
<p className="pk-start-subtitle mt-2 text-[clamp(15px,1.6vw,19px)] text-slate-600">
红队蓝队轮流答题,答对加{scorePerCorrect}
{scorePerWrong > 0 ? `,答错扣${scorePerWrong}分。` : ",答错不扣分。"}
</p>
<div className="pk-start-panel mx-auto mt-5 grid max-w-3xl gap-3 rounded-2xl border bg-slate-50 p-4 text-left">
<div>
<div className="mb-2 text-xs font-semibold text-slate-600">选择年级</div>
<div className="grid grid-cols-3 gap-3">
{grades.map((grade) => (
<button
key={grade}
onClick={() => onSelectGrade(grade)}
className={cn(
"pk-start-choice rounded-lg border bg-white px-4 py-2.5 text-center text-base font-bold transition hover:border-rose-300",
selectedGrade === grade && "border-rose-500 bg-rose-50 text-rose-700 shadow-sm",
)}
>
{grade}
</button>
))}
</div>
</div>
<div>
<div className="mb-2 text-xs font-semibold text-slate-600">选择班级类型</div>
<div className="grid grid-cols-1 gap-3 sm:grid-cols-3">
{classTypes.map((classType) => (
<button
key={classType.id}
onClick={() => onSelectClassType(classType.id)}
className={cn(
"pk-start-choice rounded-lg border bg-white px-4 py-2.5 text-center text-base font-bold transition hover:border-blue-300",
selectedClassTypeId === classType.id && "border-blue-500 bg-blue-50 text-blue-700 shadow-sm",
)}
>
{classType.name}
</button>
))}
</div>
</div>
<div className="pk-start-summary rounded-lg bg-white px-4 py-2 text-center text-sm text-slate-600">
当前选择:<span className="font-bold text-slate-900">{selectedGrade}</span>
<span className="mx-2 text-slate-300">/</span>
<span className="font-bold text-slate-900">{selectedClassTypeName ?? "未选择班型"}</span>
<span className="mx-2 text-slate-300">/</span>
本轮题目 <span className="font-bold text-emerald-600">{plannedRoundCount}</span>
<span className="mx-2 text-slate-300">/</span>
题库可用 <span className="font-bold text-slate-900">{availableWordCount}</span>
</div>
</div>
{!loadingSetup && availableWordCount === 0 && (
<p className="pk-start-warning mt-4 text-sm font-medium text-red-500">当前年级和班级类型没有启用题目,请先到后台管理启用词库。</p>
)}
<button
onClick={onStartGame}
disabled={loadingSetup || availableWordCount === 0}
className="pk-start-button mt-5 rounded-full bg-rose-500 px-10 py-3 text-[clamp(17px,1.8vw,21px)] font-bold text-white shadow-lg transition hover:bg-rose-600 disabled:cursor-not-allowed disabled:bg-slate-300 disabled:shadow-none"
>
{loadingSetup ? "加载中..." : "开始PK"}
</button>
</section>
</main>
);
}