# 1.2.0 客户端自动化验证记录 环境:Windows,DSH Desktop `desktop` profile,PCL2 + Java 版 `26.1.2-Fabric 0.19.5`,HubSuite dev 服务端 `localhost:25566`(RCON `25575`),Java 25。测试时间 2026-10-18。 ## 1. 窗口识别与聚焦 | 测试 | 结果 | |---|---| | 无游戏时 `mc_status` | `windows: []`,DSH 窗口被标记 `excluded:true`、`isGame:false`,不进入可操控列表 | | 启动游戏后 `mc_status` | 只返回 `process:"java", class:"GLFW30", title:"Minecraft* 26.1.2 - 单人游戏"` 的游戏窗口;`foregroundWindow` 可单独查看 | | 把 DSH 窗口置前后 `mc_screenshot` | 仍返回 `method:"printwindow"`、游戏窗口 `hwnd`,截图中没有 DSH/桌面内容(证据:`docs/window-capture-overlap.png`) | | 把 DSH 窗口置前后发送 `w` | 助手先恢复并验证游戏窗口焦点;随后 `mc_status.foregroundIsGame == true`、`foreground == 游戏 hwnd` | | 聚焦失败路径 | 代码在 `GetForegroundWindow()` 校验失败时返回 `ok:false, code:"focus-failed"`,不会继续发送键鼠输入 | ## 2. 聊天、日志、截图 | 测试 | 结果 | |---|---| | `mc_control {action:"chat", text:"hello from plugin readback"}` | 返回 `chatLines:[{time:"14:29:33", text:" hello from dsh-mc-client"}]`,`chatSource.method:"appended"` | | `mc_control {action:"chat", text:"/time set day"}` | 命令自动用 Unicode 输入保留 `/`,回读 `已将minecraft:overworld调至时间标记minecraft:day的时刻` | | `mc_client_log {grep:"HubSuite", tail:8}` | 自动选中 PCL 当前版本日志 `E:\Minecraft\.minecraft\versions\26.1.2-Fabric 0.19.5\logs\latest.log`,返回匹配行与来源、mtime、总行数 | | `mc_screenshot {scope:"window"}` | 返回 `path/width/height/method:"printwindow"/hwnd/title`;图片只有游戏窗口 | | `mc_screenshot {scope:"window", region:{x:240,y:310,width:280,height:110}}` | 返回裁剪后 280×110 的 PNG、`region` 和 `captureOrigin`;证据:`docs/hubsuite-region-test.png` | ## 3. 启动并自动进服(P1-1) ### 3.1 新启动 + Quick Play ```text mc_launch {edition:"java", server:"localhost:25566", waitInGame:true, waitGameSeconds:120} ``` 返回 `ok:true`、`inGame:true`、`quickPlay:{attempted:true, argument:"--quickPlayMultiplayer", value:"localhost:25566"}`,窗口标题变为 `Minecraft* 26.1.2 - 多人游戏(第三方服务器)`。从启动到判定进服约 60 秒(其中窗口出现约 26 秒,modded 客户端加载 + 连接约 34 秒)。 ### 3.2 已运行客户端 + OCR 菜单回退 先不带 `server` 启动客户端到主菜单,再调用: ```text mc_launch {edition:"java", server:"localhost:25566", waitInGame:true, waitGameSeconds:120} ``` 返回 `ok:true`、`inGame:true`、`alreadyRunning:true`,`menuFallback.steps` 记录了真实点击序列: 1. OCR 找到并点击 `一 多 人 游 戏`(显示文字带空格也能匹配); 2. OCR 找到并点击“直连”; 3. 点击服务器地址输入框,全选、输入 `localhost:25566`; 4. 点击“加入服务器”; 5. 轮询窗口标题/日志,确认进入 HubSuite 登录界面后报告 `inGame:true`。 失败时返回 `code:"not-in-game"`、`state` 和逐步 `menuFallback.steps`,不会声称成功。 ## 4. 客户端状态(P1-2) `mc_control {action:"state", visual:true}` 实测: - 主菜单:`inGame:false`, `screen:"mainmenu"`(OCR 识别“单 人 游 戏 / 多人 游 戏”); - 进服/进世界:`inGame:true`, `inGameSource:"window-title"`;日志连接标记也可作为备用来源; - F3 打开时:`position:{x:7.7,y:64,z:6.569}`, `positionSource:"f3-ocr"`, `biome:"minecraft:forest"`, `facing:{name:"south",axis:"positive Z"}`, `blockPosition`, `chunk`; - 打开背包:`screen:"inventory"`(OCR 识别物品提示“12 个组件”/`minecraft:white_wool` 等);证据:`docs/inventory-test.png`; - `chatLast` 返回最近一条 `[CHAT]`,`chatLines` 返回最近 ≤10 条。 HubSuite 自动进服后的游戏画面(服务端登录界面):`docs/hubsuite-ingame.png`。 `visual:false` 时只读窗口标题与日志,速度快、无需 OCR。 ## 5. 绝对视角与按住鼠标(P2) ```text mc_control {action:"look", yaw:90, pitch:0} ``` 返回 `ok:true, method:"tp-command", command:"/tp @s ~ ~ ~ 90.00 0.00"`,聊天回读 `已将DRheEheAM传送至527.597937, 125.775194, -439.310912`,F3 面向随后变为 `west`。说明:窗口版没有客户端 API 可直接设置相机,因此用 `/tp` 设置服务端玩家旋转;**需要 op 或开启作弊**,无权限时返回 `code:"command-rejected"`;若 GUI 挡住聊天或服务器关闭了命令反馈,返回 `code:"command-not-observed"`,不会假装成功。执行前会先检查背包/容器界面和自定义登录框,避免把 `/tp` 打进密码框。 `rightclick_hold` / `leftclick_hold` 实测返回 `ok:true`、`button`、`durationMs`;按下后会在 `durationMs` 后释放。 ## 6. 未覆盖/限制 - 绝对视角的成功路径只在单人创造模式(有命令权限)实测;HubSuite 登录前无法发命令,登录后是否有 op 取决于账号权限,失败会明确报错。 - 物品栏/容器识别依赖 OCR 关键词和物品提示;不同 GUI 缩放、语言、资源包下可能识别为 `screen:"none"`,此时用截图 + `read_image` 判断。 - HubSuite 的登录/注册界面属于服务端自定义 GUI,`screen` 目前不会单列为登录态;截图仍可正常看到。 - 窗口版 PCL 客户端登录 HubSuite 时需要用户手动输入密码;插件不会保存或猜测账号密码。