# 问题 3:结束后未重置房间;德州补码/退出;其他游戏无限轮回 ## 现状 - **Holdem**:`showdown` 之后 `next: 'waiting'`,回到等待房主 `startHand`。但: - 任何人筹码 ≤ 0 时,没有“补码 / 退出房间”的入口,UI 只显示一个“出局”徽章(`HoldemBoard.tsx:147`)。 - 没有“重置房间”(把所有人筹码恢复到 `startingStack`、清空战绩)的按钮。 - **其他游戏(War / Mill / DragTest)**:`endIf` 一旦满足就 `gameover`,客户端停在“游戏结束”界面, 没有“再来一局 / 无限轮回”的自动重开。 ## 需求拆解 1. **Holdem**:有人筹码 ≤ 0 → 给他选择“补码(rebuy)”或“退出房间(leave)”。 2. **Holdem**:房主可“重置房间”(rebuy 所有人 / 重置到初始 setup)。 3. **通用(所有游戏)**:结束(gameover)后做一个“无限轮回”——自动或一键开下一局,而不是卡在结束页。 ## 拟采用方案 ### 3.1 Holdem —— 补码 / 退出 / 重置(engine + ui) - engine 新增 moves: - `rebuyMove({G, ctx, playerID}, amount?)`:把 `G.players[me].stack` 加回 `startingStack` (或指定补码额,默认补足到 `startingStack`);若之前 `seated && stack===0` 且已 `inHand=false`, 补码后恢复 `inHand=true` 以便下一手参与。`amount` 需 ≤ 上限(如 `startingStack`)且为 5 的倍数(呼应问题 9 的分段)。 - `leaveRoomMove({G, ctx, playerID})`:把该座位 `seated=false`(本地视图退出),不删房间。 (真正的“离开房间”仍走 lobby `leave`,这里是牌桌内的“退出本手/本房”语义。) - `resetRoomMove({G, ctx, playerID})`:**仅房主**:把所有 `seated` 玩家的 `stack` 重置为 `startingStack`、 `inHand/folded/allIn` 归位、清空 `pot/board/hands`、回到 `waiting`、可保留 `handNumber` 或清零。 - ui(`HoldemBoard`): - 当 `myPlayer.stack <= 0` 且 `seated` → 显示“补码”/“退出房间”两个按钮。 - 房主在 `waiting` 阶段增加“重置房间”按钮(调 `resetRoom`)。 - `waiting` 阶段已有“开始游戏”按钮(`HoldemBoard.tsx:287`),补码/重置与之并列。 ### 3.2 通用 —— 无限轮回(engine) 目标:游戏 `gameover` 后不要卡死,而是能“再来一局”。 - **方案 A(推荐,最小侵入)**:各游戏加一个通用 `playAgain`/`rematch` move(房主触发), 内部重新 `setup()` 并回到初始 phase。Holdem 的 `resetRoom` 已覆盖;War/Mill/DragTest 各加一个薄 `rematch`。 - **方案 B(自动轮回)**:`endIf` 命中后延迟 N 秒由房主/系统自动调用 `rematch`。 考虑到联机下需要权威端触发且避免“无人时自动开”,建议用**方案 A** + 在 UI 上把“再来一局”做成醒目的主按钮, 并允许房主开启“自动轮回”开关(可选)。 - 对 War/Mill:结算后 `waiting`/`rematch` phase 显示胜者 + “再来一局”按钮;不自动重开,避免误开。 > “无限轮回”理解为**可无限次重开同一房间**,而非同一对局逻辑无限循环。实现上就是“结束 → 一键重开”。 ## 与问题 2 的耦合 - 补码/重置/重开都是 **game move**,需经 boardgame.io(server 权威)。 - 房主判定的“房主专属权”(重置、rematch)依赖问题 2 中固化的 `hostId`(metadata `createdBy`)。 engine `host()` 应改为读 `G.hostId`(setup 时由房主座位写入),避免破产后 host 漂移导致重置按钮消失。 ## 验证 - Holdem:某人筹码 0 → 出现补码/退出;补码后 stack 回满、可继续;房主重置 → 全员回到初始。 - War/Mill:gameover → 显示“再来一局” → 点后回到初始可玩状态,房间不丢。 - 联机:补码/重置/rematch 在所有人客户端同步。