diff --git a/AGENTS.md b/AGENTS.md index 422b873..ce8aa2a 100644 --- a/AGENTS.md +++ b/AGENTS.md @@ -30,7 +30,7 @@ Windows 上的 Dota 2 **天梯选将识别**工具:用 GSI 感知选将阶段 运行时产物(**勿提交**,见 `.gitignore`): -- `samples/raw/` — 截图 +- `samples/raw//` — GSI 会话截图;手动 `capture.py` 可写在 `raw/` 根下 - `preview/` — 标定 / sheet 预览 - `results/` — 每局 JSON - `failures/` — `--truth` 调试用错识裁切 @@ -39,7 +39,7 @@ Windows 上的 Dota 2 **天梯选将识别**工具:用 GSI 感知选将阶段 ``` Dota 2 GSI → gsi_watch.py (:3223) - → DraftSession 轮询截屏 + → DraftSession 轮询截屏 → samples/raw// → recognize_image (CDN 模板 + 可选天梯遮罩) → roles / grid / modes(辅助) → results/draft_*.json + 终端时间线 @@ -48,8 +48,9 @@ Dota 2 GSI → gsi_watch.py (:3223) ## 技术约束(修改前必读) - **合规**:仅 GSI + 屏幕截图;**禁止**读进程内存、注入、绕过 VAC。 -- **GSI 范围**:普通玩家视角拿不到双方 pick;GSI 只作阶段触发与 `team_slot` 等自身信息。 -- **模板策略**:只维护 CDN 层。皮肤问题用会话策略(选人可改判、决策 `allow_revise=False`、best 帧偏 HERO_SELECTION),不要为皮肤加模板库。 +- **GSI 范围**:普通玩家视角拿不到双方 pick;GSI 只作阶段触发、`team_slot`、本人 `hero`。 +- **模板策略**:只维护 CDN 层。皮肤问题用会话策略(选人可改判、决策 `allow_revise=False`、best 帧偏 HERO_SELECTION),不要为皮肤加模板库,也不要复活 real 双层库。 +- **顶栏时机**:皮肤在**全员选完后**才上顶栏;本机进决策时别人可能还在选——须保持 `strategy_tail` 视觉,禁止「一进 STRATEGY 就永久停读」。 - **坐标**:一律相对坐标(相对屏幕高 / 相对中心),勿写死像素分辨率。 - **宁可不认,不可乱认**:`min_score` + `min_margin` 双门控;不确定就 `null`。 - **平台**:面向 Windows;截屏依赖无边框/窗口模式。 diff --git a/CHANGELOG.md b/CHANGELOG.md index 8bf6e28..ef9b8dd 100644 --- a/CHANGELOG.md +++ b/CHANGELOG.md @@ -10,8 +10,11 @@ - **放弃 real 实拍模板库**:删除 `build_library.py`、`templates/real/`;匹配仅使用 CDN 层。 - 移除 `match.cdn_penalty` 与 `evaluate.py --cdn-only`(双层库对比已无意义)。 - 模板加载 API 简化为 `(hero_key, image)`。 +- GSI 会话截图按对局写入 `samples/raw//`。 - 运行产物纳入 `.gitignore`:`preview/`、`results/`、`failures/`、`samples/raw/`。 - 文档拆分为 `README`(操作)、`DESIGN`(决策)、`AGENTS`(协作)、`CHANGELOG`(变更)。 +- `DESIGN.md` / `AGENTS.md` 补录原型会话结论:顶栏皮肤时机、决策禁改判原因、 + real 库审计结论、无法靠 GSI 卡「皮肤前」单帧等。 ### Removed @@ -21,7 +24,8 @@ ### Fixed - (继承自原型)CDN 头像按顶栏窗口裁切,而非中心正方形;CDN-only 即可高准确率。 -- (继承自原型)天梯段位条 / 勋章遮罩匹配;选人多帧 + 决策禁改判规避皮肤。 +- (继承自原型)天梯段位条 / 勋章遮罩匹配;选人多帧 + 决策禁改判规避皮肤; + best 帧优先选人阶段;本人英雄以 GSI 覆盖。 ## [0.1.0] - 2026-07-25 diff --git a/DESIGN.md b/DESIGN.md index 48b6bab..6adbcf3 100644 --- a/DESIGN.md +++ b/DESIGN.md @@ -68,7 +68,13 @@ Valve 已明确关闭普通玩家视角的实时 draft - 选人阶段:多帧确认、允许更高分改判(`revise_gain`) - 决策阶段:只补空槽、禁止改判(避免皮肤顶栏覆盖默认脸结论) -- best 帧优先选人阶段默认脸 +- best 帧优先选人阶段默认脸(`recognized` 相同时) +- 本人英雄以 GSI `hero` 覆盖视觉结果(只覆盖自己的槽) + +**⑤ 截图按对局归档** + +GSI 会话写入 `samples/raw/{matchid}/`;手动 `capture.py` 仍写 `samples/raw/` 根目录。 +结果 JSON 仍为 `results/draft_<时间戳>.json`(内含 `match_id`)。 --- @@ -88,6 +94,15 @@ Valve 已明确关闭普通玩家视角的实时 draft CDN-only 开箱即用后,「打几十局攒默认脸」不再是主路径。项目改为只维护 CDN。 +后续审计(迁出前原型库)进一步确认: + +- 标注集上大量 `score=1.000` 往往是「从同帧裁进 real 再评同帧」的自证,夸大了 real 贡献。 +- 剩余 real 与 CDN(天梯遮罩)多数 ≥0.85,近乎 CDN 副本;明显偏离的极少(如军团指挥官一类边缘格)。 +- **近期问题局**(宙斯缺槽、斯拉达 CDN 分低、敌法末位、皮肤帧风行者 0.415)主要靠 + **多帧会话 + 决策禁改判 + GSI 补自己** 凑齐,不是靠 real。 +- 皮肤变体极多,入库皮肤模板不合理;段位条/徽章每人不同,匹配时已用遮罩忽略, + 也不该为不同段位重复存图。 + ### 发现三:自动标定靠玩家颜色条 10 条固定玩家色定位槽位;中心用中位数槽距拟合(剔除被身后头像污染的宽条); @@ -109,6 +124,27 @@ GSI 不含可靠 lobby 类型时,用右下金色勋章检测(`has_ranked_ove 定位局位置字用二值 IoU(非 OCR)。「我」优先 GSI `team_slot`; 否则姓名亮度相对差(最亮比次亮 ≥ 25)兜底。 +### 发现七:客户端顶栏时机(会话策略前提) + +这些是实战纠正后的事实,改 `DraftSession` 时不要违背: + +| 现象 | 含义 | +|------|------| +| 顶栏默认脸 → 皮肤 | **全员选完后**才换皮肤立绘,不是一进决策就换 | +| 本机已进 `STRATEGY_TIME` | 别人可能还在选;**不能**一进决策就永久停视觉 | +| 空槽红旗倒计时 | 只出现在**未选**槽;揭晓后消失,不是挡脸主因 | +| GSI | **没有**「皮肤已加载」字段;无法精确卡「人选完、皮肤前」单帧 | + +因此正确节奏是:选人 + 决策前期持续读,直到确认 10/10 或 `strategy_tail_polls` 用尽; +凑齐后停视觉,再短等 GSI 补本人英雄。单帧皮肤弱识别(如决策 3D 模型挡顶栏)属预期, +靠会话回填,不靠降阈值或堆皮肤模板。 + +### 发现八:揭晓淡入需要可改判 + +首帧揭晓常半透明 + 段位条,易误认(例:剑圣揭晓瞬间被认成幽鬼)。 +`confirm_polls` 后若仍禁止改判会锁死错误。选人阶段允许 +`score ≥ was_score + revise_gain` 的稳定新结果覆盖;决策阶段则关闭改判。 + --- ## 4. 代码结构 @@ -122,10 +158,10 @@ climperor/ ├── autocalibrate.py / calibrate.py / capture.py ├── evaluate.py / roles.py / grid.py / modes.py ├── templates/cdn|roles|modes/ -└── samples/labels.json # 评测真值;raw/ 见 .gitignore +└── samples/labels.json # 评测真值;raw// 见 .gitignore ``` -运行时目录 `preview/`、`results/`、`failures/`、`samples/raw/` 不入库。 +运行时目录 `preview/`、`results/`、`failures/`、`samples/raw/`(含按对局子目录)不入库。 ### 主要配置 @@ -135,8 +171,9 @@ climperor/ | `match.ranked_mask` | 天梯遮罩比例 | bottom 0.32, right 0.22 | | `gsi.port` | 监听端口 | 3223 | | `gsi.confirm_polls` | 连续同结果帧数 | 2 | -| `gsi.revise_gain` | 改判所需分数增益 | 0.15 | +| `gsi.revise_gain` | 选人阶段改判所需分数增益 | 0.15 | | `gsi.strategy_tail_polls` | 决策阶段继续视觉轮询 | 8 | +| `gsi.strategy_gsi_wait` | 视觉结束后等待本人 GSI 英雄 | 3.0 | --- @@ -149,10 +186,12 @@ Dota 2 (-gamestateintegration) → results/draft_*.json ``` -要点:按 `matchid` 去重;识别在工作线程;未标定时降级为只截图。 +要点:按 `matchid` 去重;截图进 `samples/raw/{matchid}/`;识别在工作线程; +未标定时降级为只截图。 天梯 AP 选人按 2/2/1 成批揭晓,本轮结束前互不可见——因此必须在 -**HERO_SELECTION** 跟踪,不能只在决策时间截一张终局图。 +**HERO_SELECTION** 跟踪,不能只在决策时间截一张终局图;决策前期仍读几帧 +以吃到最后一人揭晓(见发现七)。 --- diff --git a/README.md b/README.md index 72b55af..af98a76 100644 --- a/README.md +++ b/README.md @@ -34,6 +34,7 @@ python gsi_watch.py ``` 进入英雄选择后自动跟踪;凑齐 10 人或超时后写出 `results/draft_<时间戳>.json`(该目录已 gitignore)。 +会话截图按对局落在 `samples/raw//`。 > 主菜单收不到 GSI 是正常的:客户端**第一次载入对局后**才开始推送。看到 `[gsi] connected` 才算链路通。 @@ -46,21 +47,22 @@ python capture.py # 单张 → samples/raw/ python capture.py --loop 300 3 # 每 3 秒一张,持续 300 秒 ``` +GSI 跟踪时自动写入 `samples/raw//draft_*.png`(含 milestone / best)。 需无边框窗口或窗口模式(独占全屏可能黑帧)。 ### 标定 ROI(一次性) ```powershell -python autocalibrate.py samples/raw/<某帧>.png -# 失败时退路:python calibrate.py samples/raw/<某帧>.png +python autocalibrate.py samples/raw//<某帧>.png +# 失败时退路:python calibrate.py samples/raw//<某帧>.png ``` ### 识别 / 评测 ```powershell -python recognize.py samples/raw/<帧>.png -python recognize.py samples/raw/<帧>.png --sheet -python recognize.py samples/raw/<帧>.png --truth hero1,...,hero10 +python recognize.py samples/raw//<帧>.png +python recognize.py samples/raw//<帧>.png --sheet +python recognize.py samples/raw//<帧>.png --truth hero1,...,hero10 python evaluate.py # 按 samples/labels.json 批量评测 ``` @@ -70,7 +72,7 @@ python evaluate.py # 按 samples/labels.json 批量评测 - PNG、原始分辨率(勿经聊天工具压缩) - 顶栏 10 个英雄完整可见 -- 优先选人阶段默认脸帧(皮肤尚未上顶栏) +- 优先选人阶段默认脸帧(全员选完后顶栏才会换皮肤;GSI 无「皮肤已加载」信号) ## 已知限制 @@ -78,6 +80,8 @@ python evaluate.py # 按 samples/labels.json 批量评测 - 客户端改网格排序后 `grid.py` 会 `ok=False`,不会瞎报禁用名单 - 新英雄上线后重跑 `fetch_cdn_templates.py` - 位置文字模板取自简体中文客户端 +- 决策界面 3D 模型挡住顶栏时单帧会很弱,依赖会话多帧回填 +- 普通玩家 GSI 只有自己的英雄 id,不能代替读顶栏 ## 相关项目