配置与注解 API
基本信息
| 属性 | 值 |
|---|---|
| 包 | me.eigenraven.lwjgl3ify.api |
| 声明位置 | gradle.properties 的 apiPackage = api |
| 本条目覆盖的类型 | 3(ConfigUtils、Lwjgl3Aware、MakeEnumExtensible) |
api 包顶层类型总数 |
9(不含 InputEvents 内 4 个嵌套类型) |
这 3 个类型构成 LWJGL3ify 对其他 mod 开放的两类能力:读取/扩展它的配置,以及在字节码层面豁免或启用它的转换器。
功能
ConfigUtils —— 反射式配置访问器
ConfigUtils.java:17。它不直接引用 me.eigenraven.lwjgl3ify.core.Config,而是用反射 + MethodHandle 在运行时定位(ConfigUtils.java:31-42),因此其他 mod 可以 compileOnly 依赖它而在 lwjgl3ify 缺席时仍能运行。
构造器 ConfigUtils(Logger logger)(:29):
Class.forName("me.eigenraven.lwjgl3ify.core.Config")(:31)。- 读静态字段
LWJGL3IFY_VERSION(:32-33)。 - 用
MethodHandles.publicLookup().in(configClass)定位 3 个静态方法(:35-42):getExtensibleEnums→Set、addExtensibleEnum(String)→void、isConfigLoaded→boolean。 - 任一步失败走
catch (ReflectiveOperationException e):把configClass置null,若logger != null打 warn"Could not find lwjgl3ify in the classpath"(:43-48)。
公共方法:
| 方法 | 位置 | lwjgl3ify 缺席时的返回值 |
|---|---|---|
isLwjgl3ifyLoaded() |
:54 |
false(configClass == null) |
getExtensibleEnums() |
:61 |
Collections.emptySet()(:66) |
addExtensibleEnum(String className) |
:79 |
静默无操作(:82 的 if 不成立) |
isConfigLoaded() |
:92 |
false(:97) |
addExtensibleEnum 的 Javadoc 明确其前提条件:“it can’t already have been loaded”——枚举类若已被加载,扩展就不会生效(:74-77)。
Lwjgl3Aware —— 跳过重定向的注解
Lwjgl3Aware.java:13,一个无成员的标记注解。类注释为"Mark a class to not be transformed for lwjgl3 compatibility"(:9)。
消费方是 LwjglRedirectTransformer:命中时抛 Lwjgl3AwareException,被 :104-105 捕获后 return false。与之并列的还有 jar 级开关——manifest 属性 Lwjgl3ify-Aware(LwjglRedirectTransformer.java:31-32)。
MakeEnumExtensible —— 请求可扩展枚举的注解
MakeEnumExtensible.java:13,同样是无成员标记注解,类注释"Mark an enum for an automatic IExtensibleEnum implementation"(:9)。
消费方是 ExtensibleEnumTransformer,其 MARKER_ANNOTATION 字段指向它(ExtensibleEnumTransformer.java:37);同一转换器还检查 IExtensibleEnum 接口(MARKER_IFACE,:36),即注解与接口两条路都认。生成的动态方法名为 dynamicCreate(:49)。
对应的运行时支撑类是 me.eigenraven.lwjgl3ify.IExtensibleEnum 与 me.eigenraven.lwjgl3ify.EnumHelper(不在 api 包内,属内部实现)。
数值
| 数值 | 值 |
|---|---|
api 包顶层类型总数 |
9(不含 InputEvents 内 4 个嵌套类型) |
| 本条目覆盖 | 3 |
| 输入与显示事件 API 覆盖 | 7 |
ConfigUtils 定位的 MethodHandle 数 |
3 |
ConfigUtils 公共方法数 |
4 |
| 标记注解数 | 2(Lwjgl3Aware、MakeEnumExtensible,均 0 成员) |
lwjgl3ify 缺席时 addExtensibleEnum 的行为 |
静默无操作 |
已知静默失败点
ConfigUtils的三个调用方法各包一层catch (Throwable t),但处理方式是Throwables.propagate(t)重抛(:68-70、:84-86、:99-101),不是吞掉。这与DisplayEvents.fire的策略相反,属于正确做法。- 真正需要注意的静默点是构造器:lwjgl3ify 缺席时只打一条 WARN 日志(
:46),isLwjgl3ifyLoaded()返回false,addExtensibleEnum变成无操作。若调用方不检查isLwjgl3ifyLoaded(),请求会无声丢失。这是 API 的设计选择(便于可选依赖),但需要调用方主动校验。 - 上述"缺席"分支仅在
catch (ReflectiveOperationException)时触发(:43)。若 lwjgl3ify 在 classpath 上但某个MethodHandle定位失败,同样走该分支并把configClass置空——即"存在但不可用"与"不存在"被折叠为同一状态。
交互
| 触发 | 行为 |
|---|---|
调用方 new ConfigUtils(logger) |
尝试反射定位 core.Config;成功则 3 个 handle 就绪 |
| lwjgl3ify 不在 classpath | 打 WARN,isLwjgl3ifyLoaded() 恒为 false,getExtensibleEnums() 返回空集 |
addExtensibleEnum("...EnumType") 且类未加载 |
追加进 EarlyConfig.EXTENSIBLE_ENUMS,下个 ExtensibleEnumTransformer 见到时生成 dynamicCreate |
addExtensibleEnum 传入已加载的枚举 |
Javadoc 声明无效;实际表现无法核实(转换器侧行为未逐行核验) |
目标类标注 @Lwjgl3Aware |
LwjglRedirectTransformer 跳过该类 |
目标 jar manifest 含 Lwjgl3ify-Aware: true |
整个 jar 跳过 redirect 转换 |
目标枚举标注 @MakeEnumExtensible |
生成 dynamicCreate 扩展方法 |
相关条目
- 输入与显示事件 API -
api包的另外 7 个类型 - RFB 字节码转换器 - 两个标记注解的消费方
- 早期配置 JSON -
getExtensibleEnums的真实存储 - 第三方兼容钩子 - ModularUI2 使用
InputEvents的实例