文档
工作原理
MTR Surveyor 背后的架构 — 客户端数据访问、mixin 与安全的依赖加载。
MTR Surveyor 是一个小型 mod,职责清晰:读取 MTR 客户端数据,写入 Xaero 路径点,并在 Xaero’s World Map 上画路线。下面是各部分如何协作。
纯客户端运行
本 mod 实际上是纯客户端的:
- 命令通过
RegisterClientCommandsEvent注册,进入客户端命令分发器。 - 同步触发是一个对 MTR
MinecraftClientData.sync()的@Mixin— 客户端类。 - 路线叠加层是对 Xaero
GuiMap的@Mixin— 客户端界面。 - 原项目中服务端广播逻辑已被移除:
MTRSimulatorMixin用空实现覆盖Simulator.sync(),玩家登录钩子是空桩。
这意味着你可以装在客户端上,在任何服务器使用 — 包括运行 MTR 但没装 MTR Surveyor 的服务器。
数据源
MTR 维护两个客户端数据实例:
| 实例 | 何时被填充 |
|---|---|
MinecraftClientData.getInstance() | 持续填充,由服务器把 MTR 数据流式同步到你的客户端。 |
MinecraftClientData.getDashboardInstance() | 当你打开游戏内 MTR dashboard 时填充。 |
MTR Surveyor 在生成路径点和路线时读取两者并取并集。这是让它在无需服务端配合时也能工作的关键设计 — 一个源缺某个车站时,另一个往往有。
同步流程
MTR 数据变化
└─> MinecraftClientData.sync() (MTR 类)
└─> [TAIL 注入] requestSync() (我们的 mixin)
└─> needsSync = true
└─> 下一个 ClientTickEvent (END)
└─> 节流:每 100 tick (5 秒) 一次
└─> doSync()
└─> XaeroSyncHelper.performSync()
└─> 移除旧的 [MTR] 路径点
└─> 车站模式 或 站台模式
└─> 向 Xaero 当前路径点集合添加新 Waypoint
Xaero 耦合代码刻意放在隔离的内部类(XaeroSyncHelper)里,使外层类加载时不会触发 Xaero 类加载。try/catch(NoClassDefFoundError) 包裹同步逻辑,缺失 Xaero 永远不会崩游戏。
路径点颜色
mod 复用 Xaero 的数字颜色索引:
| 元素 | 颜色索引 | 近似颜色 |
|---|---|---|
| 车站 | 9 | 蓝色 |
| 车厂 | 6 | 金色 |
| 站台 | 3 | 浅蓝色 |
所有 MTR 路径点都带前缀 [MTR] ,因此每次同步都能找到并替换它们 — 这就是过期路径点被清理的方式。
Mixin 一览
| Mixin | 目标 | 用途 |
|---|---|---|
MinecraftClientDataMixin | org.mtr.mod.client.MinecraftClientData | 在 sync() 末尾调用 requestSync()。 |
XaeroWorldMapMixin | xaero.map.gui.GuiMap | 把路线渲染调用注入地图渲染方法,把小部件点击处理注入点击方法。 |
XaeroWorldMapAccessor | xaero.map.gui.GuiMap | @Accessor,向渲染器暴露相机 X/Z 和缩放比例。 |
MTRSimulatorMixin | org.mtr.core.simulation.Simulator | 用空实现覆盖 sync() — 抑制旧的服务端广播行为。 |
MTRAccessorMixin、MainAccessorMixin | org.mtr.mod.Init、org.mtr.core.Main | 原项目遗留的 accessor,当前活动代码路径未使用。 |
安全的依赖加载 — XaeroMixinPlugin
这部分让 mod 在没装 Xaero’s World Map 时也不会崩溃。
XaeroMixinPlugin 实现 SpongePowered 的 IMixinConfigPlugin。加载时它会检查类加载器是否存在 xaero/map/gui/GuiMap.class,并记住结果。之后对每个 mixin,shouldApplyMixin 决定:
- 若 mixin 类名包含
.xaero.且未检测到 Xaero’s World Map → 跳过。 - 否则 → 应用。
因此在只装 Xaero’s Minimap 的情况下,世界地图相关 mixin 永远不会被应用,GuiMap 类永远不被引用,mod 干净加载。路径点同步照常工作;仅路线叠加层不可用。
wrapper 层(遗留)
wrapper/ 包(MTRRoute、MTRRoutePlatform 及其实现)以及 MTRDataSummary 是对 MTR 两种路线类型(Route 与 SimplifiedRoute)的抽象。它们继承自原 AmberFrost 项目,当前活动同步路径并未使用 — 同步代码直接读取 MTR 数据。保留它们以备将来使用,并作为 MTR 路线模型的文档。