From e326481f2fc43cf649f95a757b6dbb117629473d Mon Sep 17 00:00:00 2001 From: Joywayer Date: Wed, 26 Aug 2026 18:55:26 +0800 Subject: [PATCH] =?UTF-8?q?=E4=BA=8C=E4=B8=83=E7=8E=8B=EF=BC=9A=E5=89=8D?= =?UTF-8?q?=E7=AB=AF=E5=AD=90=E9=A1=B9=E7=9B=AE=20A=20=E5=AE=9E=E6=96=BD?= =?UTF-8?q?=E8=AE=A1=E5=88=92?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit 14 个任务,每个自带 TDD 循环与提交:shared 抽取与同步(1-2)、 单测框架与漂移守卫(3)、core 四个纯逻辑模块(4-7)、布局求解器(8)、 常量层三批(9/10/12)、精灵索引(11)、常量机械守卫(13)、接入骨架(14)。 顺带修订设计文档两处:shared 抽取函数数量 7→8(原文列了 8 个名字), CardMark.markOf 签名与计划对齐(拖拉机判定需整手牌作上下文)。 Co-Authored-By: Claude Opus 5 (1M context) --- .../2026-08-26-二七王前端A-地基与逻辑层.md | 2237 +++++++++++++++++ ...6-08-26-二七王前端A-地基与逻辑层-design.md | 7 +- 2 files changed, 2240 insertions(+), 4 deletions(-) create mode 100644 docs/superpowers/plans/2026-08-26-二七王前端A-地基与逻辑层.md diff --git a/docs/superpowers/plans/2026-08-26-二七王前端A-地基与逻辑层.md b/docs/superpowers/plans/2026-08-26-二七王前端A-地基与逻辑层.md new file mode 100644 index 0000000..d73f6cd --- /dev/null +++ b/docs/superpowers/plans/2026-08-26-二七王前端A-地基与逻辑层.md @@ -0,0 +1,2237 @@ +# 二七王前端 · 子项目 A:地基与逻辑层 · 实施计划 + +> **For agentic workers:** REQUIRED SUB-SKILL: Use superpowers:subagent-driven-development (recommended) or superpowers:executing-plans to implement this plan task-by-task. Steps use checkbox (`- [ ]`) syntax for tracking. + +**Goal:** 搭出二七王前端的地基——常量层全量、纯逻辑核心、布局求解器、前后端共享算法同源机制、单测框架与平台接入骨架,使后续 B–F 的界面开发不再受任何前置条件阻塞。 + +**Architecture:** 三层单向依赖 `config`(纯数据,无依赖)← `core`(纯逻辑,可 Node 单测)← `ui`(布局求解)。前后端共享的牌值算法抽到服务端 `shared/`,经根目录脚本单向同步为前端只读副本,字节一致由测试守卫。资源与精灵的 ID 全部先在常量文件里定义,常量文件即后期在编辑器里建资源的规格书。 + +**Tech Stack:** 纯静态 ES5 JavaScript(浏览器 ` + + + + + + + + + + + + + + + + + + + + + + + + + + + +``` + +- [ ] **Step 3: 浏览器验证** + +Run: `npx http-server client -p 8080`(另开一个终端),浏览器打开 `http://localhost:8080/index.html`,看控制台。 +Expected: **无报错**。在控制台逐个求值确认已就绪: + +```js +[EQW_Layers, EQW_Groups, EQW_Images, EQW_Sounds, EQW_Sprites, EQW_Layout, + EQW_RoomOptions, EQW_Anim, EQW_CardCodec, EQW_SeatMap, EQW_CardOrder, + EQW_CardMark, EQW_SpriteIndex, EQW_LayoutSolver, youle_erqiwang_shared_cards, + SubGameHooks].every(x => !!x) +// → true +EQW_CardCodec.cardIdToFrame(39) // → 1(黑桃A) +EQW_SpriteIndex.init() // 不抛错,返回索引对象 +``` + +若报 404,核对 `index.html` 里的路径与实际文件名大小写。 + +- [ ] **Step 4: 跑两端全套测试** + +Run: `node client/tests/run.js && node server/games/erqiwang/test/run.js` +Expected: 两个都是 `===== 全部单测通过 =====`。 + +- [ ] **Step 5: 提交** + +```bash +git add client/js/01_SubGame/codes/SubGameHooks.js client/index.html +git commit -F - <<'EOF' +二七王:前端接入骨架与 index.html 加载段 + +SubGameHooks 从模板复制、本阶段保持空骨架(无 hook 时转发壳走平台默认)。 +index.html 按 client 06 §3 的顺序加入 codes 段:config → shared → core → ui +→ SubGameHooks → 三文件转发壳,三个转发壳一字未动。 +浏览器打开无报错,全部 EQW_* 就绪。 + +Co-Authored-By: Claude Opus 5 (1M context) +EOF +``` + +--- + +## 完成检查 + +全部任务做完后逐条核对(对应 spec §10 验收标准): + +- [ ] `node client/tests/run.js` 全绿(8 个用例文件) +- [ ] `node server/games/erqiwang/test/run.js` 全绿(shared 抽取的安全网) +- [ ] HTTP 打开 `client/index.html` 控制台无报错,全部 `EQW_*` 与 `SubGameHooks` 就绪 +- [ ] 提交全部通过 `.githooks/pre-commit` 的机械红线校验(严格 ES5、可编辑范围) +- [ ] 常量层与清单 §3 / §5 / §6 逐条对应,无遗漏、无臆造条目 +- [ ] `core/`、`ui/` 里不出现任何精灵 ID、坐标、时长的字面量 +- [ ] `CLAUDE.md`「常用命令」已收录 `sync_shared.cmd` +- [ ] 三个转发壳 `00_/01_/02_SubGame_*.js` 一字未动(`git log --oneline -- client/js/01_SubGame/0*.js` 无本次提交) diff --git a/docs/superpowers/specs/2026-08-26-二七王前端A-地基与逻辑层-design.md b/docs/superpowers/specs/2026-08-26-二七王前端A-地基与逻辑层-design.md index aaf31c5..328a2bc 100644 --- a/docs/superpowers/specs/2026-08-26-二七王前端A-地基与逻辑层-design.md +++ b/docs/superpowers/specs/2026-08-26-二七王前端A-地基与逻辑层-design.md @@ -164,9 +164,8 @@ EQW_CardOrder.sort(cards, mainflower) // 返回新数组,从大到小,与 清单 §1.6 T-8 的三种牌面标记,前端据 `flower` 本地推导,服务端不下发: ```js -EQW_CardMark.markOf(cardId, mainflower, handCards) -// → 'tractor' | 'zheng' | 'zhu' | null (三者互斥,每张牌至多一个) -EQW_CardMark.marksOfHand(handCards, mainflower) // 批量,返回 { cardId: mark } +EQW_CardMark.marksOfHand(cards, mainflower) // 批量,返回 { cardId: mark };无标记的牌不出现 +EQW_CardMark.markOf(cardId, cards, mainflower) // 单张 → 'tractor'|'zheng'|'zhu'|null(互斥,至多一个) EQW_CardMark.countByFlower(cards) // 选主面板:{ flower: {count, pairs} } ``` @@ -275,7 +274,7 @@ get_tuolaji_list ─→ id_to_code trump_rank ───────→ id_to_code ``` -共 7 个:`id_to_flower`、`id_to_number`、`id_to_code`、`order_cards`、`is_continuous`、`get_pairlist`、`get_tuolaji_list`、`trump_rank`。 +共 8 个:`id_to_flower`、`id_to_number`、`id_to_code`、`order_cards`、`is_continuous`、`get_pairlist`、`get_tuolaji_list`、`trump_rank`。它们在 `class.arith.js` 里正好是**连续的一整段**(第 62–289 行),中间不夹杂其他函数,可整段搬运。 ### 7.3 服务端改动