跳到主要内容
版本:26.1

Mod 文件

Mod 文件负责确定哪些 Mod 被打包进你的 JAR、在 “Mods” 菜单中显示哪些信息,以及你的 Mod 应当如何被加载到游戏中。

gradle.properties

gradle.properties 文件保存了 Mod 的各种常用属性,例如 mod id 或 Mod 版本。在构建期间,Gradle 会读取这些文件中的值,并将它们内联到多个位置,例如 neoforge.mods.toml 文件。这样,你只需在一处修改值,它们就会自动应用到所有位置。

大多数值也在 MDK 的 gradle.properties 文件 中以注释形式作了说明。

属性描述示例
org.gradle.jvmargs允许你向 Gradle 传递额外的 JVM 参数。最常见的用途是为 Gradle 分配更多或更少的内存。注意这是针对 Gradle 本身,而非 Minecraft。org.gradle.jvmargs=-Xmx3G
org.gradle.daemonGradle 在构建时是否使用守护进程。org.gradle.daemon=false
org.gradle.parallelGradle 是否派生(fork)多个 JVM 以并行执行项目。org.gradle.parallel=false
org.gradle.cachingGradle 是否复用先前构建的任务输出。org.gradle.caching=false
org.gradle.configuration-cacheGradle 是否复用先前构建的构建配置。org.gradle.configuration-cache=false
org.gradle.debugGradle 是否设为调试模式。调试模式主要意味着更多的 Gradle 日志输出。注意这是针对 Gradle 本身,而非 Minecraft。org.gradle.debug=false
minecraft_version你正在开发所针对的 Minecraft 版本。必须与 neo_version 匹配。minecraft_version=1.20.6
minecraft_version_range本 Mod 可使用的 Minecraft 版本范围,采用 Maven 版本范围 形式。注意 快照、预发布版和候选发布版 不保证能正确排序,因为它们不遵循 Maven 版本规则。minecraft_version_range=[1.20.6,1.21)
neo_version你正在开发所针对的 NeoForge 版本。必须与 minecraft_version 匹配。关于 NeoForge 版本机制的更多信息,参见 NeoForge 版本neo_version=20.6.62
mod_id参见 Mod IDmod_id=examplemod
mod_name你的 Mod 的人类可读显示名称。默认情况下,这只能在 Mod 列表中看到;不过,诸如 JEI 这类 Mod 也会在物品提示框中醒目地显示 Mod 名称。mod_name=Example Mod
mod_license你的 Mod 所采用的许可证。建议将其设为你所使用的 SPDX 标识符 和/或指向许可证的链接。你可以访问 https://choosealicense.com/ 来帮助挑选你想使用的许可证。mod_license=MIT
mod_version你的 Mod 的版本,显示在 Mod 列表中。更多信息参见 版本页面mod_version=1.0
mod_group_id参见 Group IDmod_group_id=com.example.examplemod

Mod ID

Mod ID 是你的 Mod 与其他 Mod 相区分的主要方式。它被用于各种各样的地方,包括作为你的 Mod 的注册表命名空间,以及作为你的资源包和数据包命名空间。存在两个 id 相同的 Mod 会导致游戏无法加载。

因此,你的 Mod ID 应当是独特且易记的。通常,它会是你的 Mod 显示名称(但为小写),或其某种变体。Mod ID 只能包含小写字母、数字和下划线,且长度必须在 2 到 64 个字符之间(含两端)。

信息

gradle.properties 文件中修改此属性会自动将变更应用到所有位置,唯独你主 Mod 类中的 @Mod 注解 除外。在那里,你需要手动修改它,使其与 gradle.properties 文件中的值一致。

Group ID

虽然 build.gradle 中的 group 属性只有在你打算把 Mod 发布到 Maven 时才是必需的,但始终正确设置它被视为良好实践。这一步已通过 gradle.propertiesmod_group_id 属性为你完成。

Group ID 应设为你的顶级包(top-level package)。更多信息参见 打包

# In your gradle.properties file
mod_group_id=com.example

你 Java 源码(src/main/java)中的包现在也应符合这一结构,用一个内层包来表示 mod id:

com
- example (top-level package specified in group property)
- mymod (the mod id)
- MyMod.java (renamed ExampleMod.java)

neoforge.mods.toml

neoforge.mods.toml 文件位于 src/main/resources/META-INF/neoforge.mods.toml,是一个采用 TOML 格式的文件,用于定义你的 Mod 的元数据。它还包含关于你的 Mod 应如何被加载到游戏中的附加信息,以及在 “Mods” 菜单中展示的显示信息。MDK 提供的 neoforge.mods.toml 文件 包含了解释每一条目的注释,这里将对它们作更详细的说明。

neoforge.mods.toml 可以分为三部分:与 Mod 文件相关联的非 Mod 专属属性;Mod 属性,每个 Mod 各占一节;以及依赖配置,每个 Mod 的依赖各占一节。与 neoforge.mods.toml 文件相关的部分属性是强制的;强制属性必须指定值,否则将抛出异常。

备注

在默认 MDK 中,Gradle 会用 gradle.properties 文件中指定的值替换此文件里的各种属性。例如,license="${mod_license}" 这一行意味着 license 字段会被 gradle.properties 中的 mod_license 属性替换。像这样被替换的值应当在 gradle.properties 中修改,而不是在这里修改。

非 Mod 专属属性

非 Mod 专属属性是与 JAR 本身相关联的属性,用于指明如何加载这些 Mod 以及任何附加的全局元数据。

属性类型默认值描述示例
modLoaderstringjavafml这些 Mod 使用的语言加载器。可用于支持替代性的语言结构,例如用 Kotlin 对象作为主文件,或用不同的方式确定入口点,例如通过接口或方法。NeoForge 提供了 Java 加载器 "javafml"modLoader="javafml"
loaderVersionstring""语言加载器可接受的版本范围,以 Maven 版本范围 表示。对于 javafml,目前是版本 1。若未指定版本,则任何版本的 Mod 加载器均可使用。loaderVersion="[1,)"
licensestring强制本 JAR 中的 Mod 所采用的许可证。建议将其设为你所使用的 SPDX 标识符 和/或指向许可证的链接。你可以访问 https://choosealicense.com/ 来帮助挑选你想使用的许可证。license="MIT"
showAsResourcePackbooleanfalse当为 true 时,这些 Mod 的资源会在 “Resource Packs” 菜单中作为一个单独的资源包显示,而不是与 “Mod Resources” 包合并。showAsResourcePack=true
showAsDataPackbooleanfalse当为 true 时,这些 Mod 的数据文件会在 “Data Packs” 菜单中作为一个单独的数据包显示,而不是与 “Mod Data” 包合并。showAsDataPack=true
servicesarray[]你的 Mod 所使用的服务数组。它作为 NeoForge 对 Java 平台模块系统实现的一部分,被 Mod 所创建的模块所消费。services=["net.neoforged.neoforgespi.language.IModLanguageProvider"]
propertiestable{}替换属性的表。它被 StringSubstitutor 用来将 ${file.<key>} 替换为其对应的值。properties={"example"="1.2.3"}(随后可通过 ${file.example} 引用)
issueTrackerURLstring一个用于报告和跟踪这些 Mod 问题的地址 URL。"https://github.com/neoforged/NeoForge/issues"
备注

services 属性在功能上等价于指定 模块中的 uses 指令,它允许加载给定类型的服务

或者,也可以在 src/main/resources/META-INF/services 文件夹内的服务文件中定义它,其中文件名是服务的全限定名,文件内容是要加载的服务的名称(另可参见 AtlasViewer Mod 的这个示例)。

Mod 专属属性

Mod 专属属性通过 [[mods]] 标头与指定的 Mod 绑定。这是一个表数组;在下一个标头出现之前,所有键/值属性都会附加到该 Mod。

# Properties for examplemod1
[[mods]]
modId = "examplemod1"

# Properties for examplemod2
[[mods]]
modId = "examplemod2"
属性类型默认值描述示例
modIdstring强制参见 Mod IDmodId="examplemod"
namespacestringmodId 的值Mod 的覆盖命名空间。它同样必须是有效的 mod ID,但可以额外包含点号或短横线。目前未被使用。namespace="example"
versionstring"1"Mod 的版本,最好采用 Maven 版本的某种变体。当设为 ${file.jarVersion} 时,它会被替换为 JAR 清单中 Implementation-Version 属性的值(在开发环境中显示为 0.0NONE)。version="1.20.2-1.0.0"
displayNamestringmodId 的值Mod 的显示名称。用于在界面上表示该 Mod(例如 Mod 列表、Mod 不匹配提示)。displayName="Example Mod"
descriptionstring'''MISSING DESCRIPTION'''在 Mod 列表界面显示的 Mod 描述。建议使用多行字面量字符串。此值也是可翻译的,更多信息参见 翻译 Mod 元数据description='''This is an example.'''
logoFilestring在 Mod 列表界面使用的图片文件的名称和扩展名。该位置必须是从 JAR 或源集根目录开始的绝对路径(例如 main 源集的 src/main/resources)。有效的文件名字符包括小写字母(a-z)、数字(0-9)、斜杠(/)、下划线(_)、点号(.)和短横线(-)。完整字符集为 [a-z0-9_-.]logoFile="test/example_logo.png"
logoBlurbooleantrue渲染 logoFile 时使用 GL_LINEAR*(true)还是 GL_NEAREST*(false)。简单来说,这决定了缩放 logo 时是否将其模糊化。logoBlur=false
updateJSONURLstring一个指向 JSON 的 URL,供更新检查器用来确认你正在游玩的 Mod 是否为最新版本。updateJSONURL="https://example.github.io/update_checker.json"
modUrlstring指向 Mod 下载页的 URL。目前未被使用。modUrl="https://neoforged.net/"
creditsstring在 Mod 列表界面显示的 Mod 鸣谢与致谢。credits="The person over here and there."
authorsstring在 Mod 列表界面显示的 Mod 作者。authors="Example Person"
displayURLstring在 Mod 列表界面显示的、指向 Mod 展示页的 URL。displayURL="https://neoforged.net/"
enumExtensionsstring用于枚举扩展的 JSON 文件路径。enumExtensions="META_INF/enumextensions.json"
featureFlagsstring用于特性标志的 JSON 文件路径。featureFlags="META-INF/feature_flags.json"

特性

特性系统允许 Mod 要求在加载系统时,某些设置、软件或硬件必须可用。当某个特性未被满足时,Mod 加载将失败,并向用户告知该要求。这些配置使用表数组 [[features.<modid>]] 创建,其中 modid 是消费该特性的 Mod 的标识符。目前,NeoForge 提供以下特性:

特性描述示例
javaVersionJava 版本可接受的版本范围,以 Maven 版本范围 表示。这应当是 Minecraft 所使用的受支持版本。javaVersion="[17,)"

Mod 属性

Mod 属性系统是一个由任意键映射到值、并与特定 Mod 相关联的映射表。当一个 Mod 文件定义了多个提供不同元数据的 Mod 时,这会很有用。之后,可以通过 IModInfo#getModProperties 从该映射中获取某个键对应的对象值,从而得到特定的属性值。这些配置使用表数组 [[modproperties.<modid>]] 创建,其中 modid 是消费所定义属性的 Mod 的标识符。

// Assume we have two mods `mod1` and `mod2` with the following property configuration
// [[modproperties.mod1]]
// key="value1"
// [[modproperties.mod2]]
// key="value2"

@Mod("mod1")
public class ModOne {

private final String key;

public ModOne(ModContainer container) {
// Will store 'value1' in key
this.key = (String) container.getModInfo().getModProperties().get("key");
}
}

@Mod("mod2")
public class ModTwo {

private final String key;

public ModTwo(ModContainer container) {
// Will store 'value2' in key
this.key = (String) container.getModInfo().getModProperties().get("key");
}
}

访问转换器专属属性

访问转换器专属属性 通过 [[accessTransformers]] 标头与指定的访问转换器绑定。这是一个表数组;在下一个标头出现之前,所有键/值属性都会附加到该访问转换器。访问转换器标头是可选的;但一旦指定,其所有元素都是强制的。

属性类型默认值描述示例
filestring强制参见 添加 ATfile="at.cfg"

Mixin 配置属性

Mixin 配置属性 通过 [[mixins]] 标头与指定的 mixin 配置绑定。这是一个表数组;在下一个标头出现之前,所有键/值属性都会附加到该 mixin 块。mixin 标头是可选的;但一旦指定,其所有元素都是强制的。

属性类型默认值描述示例
configstring强制mixin 配置文件的位置。config="examplemod.mixins.json"
requiredModsarray[]这些 mixin 得以应用所必须存在的 Mod ID。requiredMods=["sodium"]
behaviorVersionstring要匹配其行为的 fabric mixin 版本。必须介于默认行为版本(每次 neo 离开破坏性变更窗口时固定一次)与运行时所存在的 fabric mixin 版本之间。behaviorVersion="0.17.1"

依赖配置

Mod 可以指定它们的依赖,这些依赖会在加载 Mod 之前由 NeoForge 检查。这些配置使用表数组 [[dependencies.<modid>]] 创建,其中 modid 是消费该依赖的 Mod 的标识符。

属性类型默认值描述示例
modIdstring强制作为依赖添加的 Mod 的标识符。modId="jei"
typestring"required"指定此依赖的性质:"required" 为默认值,若缺少该依赖则阻止 Mod 加载;"optional" 在缺少该依赖时不会阻止 Mod 加载,但仍会验证该依赖是否兼容;"incompatible" 在存在该依赖时阻止 Mod 加载;"discouraged" 在存在该依赖时仍允许 Mod 加载,但会向用户显示警告。type="incompatible"
reasonstring一条可选的、面向用户的消息,用于说明为何需要此依赖,或为何与之不兼容。reason="integration"
versionRangestring""语言加载器可接受的版本范围,以 Maven 版本范围 表示。空字符串匹配任意版本。versionRange="[1, 2)"
orderingstring"NONE"定义本 Mod 必须在此依赖之前("BEFORE")还是之后("AFTER")加载。如果加载顺序无关紧要,返回 "NONE"ordering="AFTER"
sidestring"BOTH"此依赖必须存在的物理端"CLIENT""SERVER""BOTH"side="CLIENT"
referralUrlstring指向该依赖下载页的 URL。目前未被使用。referralUrl="https://library.example.com/"
危险

两个 Mod 的 ordering 可能因循环依赖而导致崩溃,例如 Mod A 必须在 Mod B 之前("BEFORE")加载,而与此同时 Mod B 又必须在 Mod A 之前("BEFORE")加载。

Mod 入口点

现在 neoforge.mods.toml 已经填写完毕,我们需要为 Mod 提供一个入口点。入口点本质上就是执行 Mod 的起始位置。入口点本身由 neoforge.mods.toml 中所使用的语言加载器决定。

javafml@Mod

javafml 是 NeoForge 为 Java 编程语言提供的语言加载器。入口点通过一个带有 @Mod 注解的公有类来定义。@Mod 的值必须包含 neoforge.mods.toml 中指定的某个 mod id。之后,所有初始化逻辑(例如注册事件添加 DeferredRegister)都可以在该类的构造函数中指定。

主 Mod 类只能有一个公有构造函数,否则将抛出 RuntimeException。该构造函数可以按任意顺序拥有以下任意参数;它们都不是明确必需的。但不允许有重复的参数。

参数类型描述
IEventBusMod 专属事件总线(注册、事件等所需)
ModContainer持有本 Mod 元数据的抽象容器
FMLModContainerjavafml 定义的、持有本 Mod 元数据的实际容器;是 ModContainer 的扩展
Dist本 Mod 正在其上加载的物理端
@Mod("examplemod") // Must match a mod id in the neoforge.mods.toml
public class ExampleMod {
// Valid constructor, only uses two of the available argument types
public ExampleMod(IEventBus modBus, ModContainer container) {
// Initialize logic here
}
}

默认情况下,@Mod 注解会在两加载。可以通过指定 dist 参数来改变这一点:

// Must match a mod id in the neoforge.mods.toml
// This mod class will only be loaded on the physical client
@Mod(value = "examplemod", dist = Dist.CLIENT)
public class ExampleModClient {
// Valid constructor
public ExampleModClient(FMLModContainer container, IEventBus modBus, Dist dist) {
// Initialize client-only logic here
}
}
备注

neoforge.mods.toml 中的条目不一定需要对应的 @Mod 注解。同样,neoforge.mods.toml 中的一个条目也可以有多个 @Mod 注解,例如当你想把公共逻辑与纯客户端逻辑分开时。