feat(presenter): 实例清单改并集(档案 ∪ versions/*)+ 空态接导入向导(M273)
用户实测:HMCL 能看见 `.minecraft/versions/樱落怡然客户端`,ULL 的实例页是空的 (日志 `instances=0`)。根因不是路径找错,而是 `host::game::instances()` 只列 `profiles.json` 里的档案,第三方启动器装好的版本在界面上根本不存在。 ## 列表改并集(presenter/src/host/game.rs) - `versions/*` 里**能解析出清单**(`<id>/<id>.json` 的 id 与目录名一致、继承链走到底、 符号链接不越界)且没有被任何档案绑定的版本,就地合成一条实例视图: 显示名 = 目录名、`version_id` = 目录名。扫描复用 `core::game::adopt::scan`, 没有另写一套目录遍历。 - 只读:合成视图不建目录、不写 profiles.json、不碰 versions/ 一个字节。 - 档案优先:某版本已被档案绑定时只按档案出一条(名字/隔离档/启动参数都保留),不重复列。 - 坏目录(无清单 / JSON 坏 / id 不符 / 缺父 / 越界)不当实例;`versions/` 读不出来也只是 退回「只有档案」的旧行为,不让实例页报错。 - 外部实例的视图 id 用 `ext-<fnv64>`:`is_valid_instance_id` 只收 `[A-Za-z0-9_-]`, 而版本目录名可以是中文(现场就是),直接沿用版本 id 会让**启动**在读实例设置时就失败。 ## 懒创建档案(只有第一次改它才写盘) `set_isolation()` 与 `apply_launch_args()` 的「找不到实例」改成 `game::ensure_profile()`: 外部实例第一次改隔离档 / 启动参数时才写 profiles.json(幂等,id 与视图 id 相同)。 ## 空态可见入口 + 文案(app-iced / i18n) - 空态分两种:列表里有东西但没选中(原「未选择实例」)与**一个实例都没有** (新:「还没有实例」+ 实心主行动「导入已有版本」)。用户现场看不到任何入口正是前一种文案 在误导。 - `adopt_action()` 成为「导入已有版本」意图的唯一产地,页头按钮与空态主行动共用它。 ## 门禁 `cargo test -p unlucky-app-iced --lib` 971 passed / `cargo test -p unlucky-presenter --all-targets` 384 passed / `cargo test -p unlucky-i18n` 36 passed / `cargo fmt --all --check` 0 / `cargo clippy -p unlucky-presenter -p unlucky-app-iced --all-targets -- -D warnings` 0。
This commit is contained in:
1 parent
751ae80f28
commit
5479f25068
11 files changed
+574
-46
No files matched your search
@@ -154,6 +154,9 @@ pub(super) const GOLDEN: &[(&str, &str, &str)] = &[
|
||||
("InstancesSavesPreviewTooLarge", "too large for a preview (over 8 MiB)", "文件过大,未生成预览(超过 8 MiB)"),
|
||||
("InstancesSavesPreviewUnreadable", "the file could not be read", "读不出这张图"),
|
||||
("InstancesSavesPreviewDecode", "not a decodable image", "解不出这张图(可能已损坏或格式不支持)"),
|
||||
("InstancesEmptyNoneTitle", "No instances yet", "还没有实例"),
|
||||
("InstancesEmptyNoneBody", "Nothing has been registered yet. Import a version that is already on disk to get started.", "这里还没有实例。导入一个已经装在盘上的版本就能开始。"),
|
||||
("InstancesAdoptCta", "Import existing version", "导入已有版本"),
|
||||
];
|
||||
|
||||
/// 金表的**全量**行(本文件 → [`tail`] → [`tail_ai`] → [`tail2`],顺序即 `Key::ALL`)。
|
||||
|
||||
@@ -216,6 +216,14 @@ macro_rules! instances_entries {
|
||||
InstancesSavesPreviewTooLarge => ("too large for a preview (over 8 MiB)", "文件过大,未生成预览(超过 8 MiB)"),
|
||||
InstancesSavesPreviewUnreadable => ("the file could not be read", "读不出这张图"),
|
||||
InstancesSavesPreviewDecode => ("not a decodable image", "解不出这张图(可能已损坏或格式不支持)"),
|
||||
// ── 空态(M273 · ADOPTWIRE)。
|
||||
// 原来空态只有一句「未选择实例」——那是对「有实例但没点」说的。**一个实例都没有**时
|
||||
// 同一条文案在骗人:用户看到的是「未选择」,以为自己漏点了什么。现在两种空态分开,
|
||||
// 「一个都没有」那一态给一条主行动(导入已有版本),否则用户根本不知道还能接管
|
||||
// 别人 `.minecraft` 里已经装好的实例。
|
||||
InstancesEmptyNoneTitle => ("No instances yet", "还没有实例"),
|
||||
InstancesEmptyNoneBody => ("Nothing has been registered yet. Import a version that is already on disk to get started.", "这里还没有实例。导入一个已经装在盘上的版本就能开始。"),
|
||||
InstancesAdoptCta => ("Import existing version", "导入已有版本"),
|
||||
} }
|
||||
};
|
||||
}
|
||||
|
||||
Reference in new issue
Block a user