Roguelike Dungeons
[!INFO] Git Commit:
9ed3801| Updated: 2026-10-03
Roguelike Dungeons(地牢生成器)是 Greymerk 编写、现由 GTNH 维护的 1.7.10 Forge 模组,作用是在世界生成时随机播撒多层地牢。它是一个纯世界生成 mod:不注册任何方块、物品、实体、TileEntity、附魔、配方或维度,全部结构在生成时直接写入原版方块。src/main/resources 下只有 mcmod.info 一个文件——没有语言文件、没有纹理、没有 assets/<domain>/。
它注册的内容极少但体系庞大:1 个 IWorldGenerator、1 条指令、1 个 Forge 事件监听器,以及 34 种主题、37 种房间、34 种房间段、8 种塔、16 类战利品、7 套内置地牢设置、14 个配置键。战斗内容通过 6 个战利品分类 provider 与 28 件彩蛋物品实现。
注意两处内部矛盾(均可复现,详见对应条目):Potion.getPotionID 的 9 个条目与本 mod 自己的 PotionEffect.getEffectID 逐项冲突;SpawnCriteria 的 dimensionBL 因一行自我 addAll 而被静默忽略。
身份字符串
以下字符串互不相同,是本 mod 记录在案的全部身份标识:
| 身份 | 值 | 来源 |
|---|---|---|
| modid | Roguelike(首字母大写) |
Roguelike.java:18 @Mod(modid = "Roguelike", …);gradle.properties:10 modId = Roguelike |
| @Mod 显示名 | Roguelike Dungeons |
Roguelike.java:18 name =;gradle.properties:6 modName = Roguelike Dungeons |
| 分类名 / 目录名 | roguelike-dungeons |
本 wiki 分类名(relation.md 行「驼峰转小写」是对目录名的变换,不是对 modid 的描述) |
| 源码根包 | greymerk.roguelike |
gradle.properties:14 modGroup = greymerk.roguelike |
| FML 容器 modid(coremod) | 无。gradle.properties:105 coreModClass =(空),无 IFMLLoadingPlugin 实现 |
同左 |
| 资源域 | 不存在。src/main/resources 仅 mcmod.info |
find src/main/resources -type f |
| 注册域 | 不适用。全树无 registerBlock / registerItem / registerTileEntity,唯一的注册是 registerWorldGenerator(worldGen, 0)(Roguelike.java:34),不带域 |
同左 |
| jar 名 | roguelike(不是 Roguelike-Dungeons) |
gradle.properties:173 customArchiveBaseName = roguelike |
| 版本令牌类 | greymerk.roguelike.RLDTags(构建期生成,仓库中不存在该 .java) |
gradle.properties:53 generateGradleTokenClass;:56 gradleTokenVersion = VERSION |
| 配置目录 | config/roguelike_dungeons |
config/RogueConfig.java:28 |
| 指令名 | roguelike(权限 2) |
util/CommandSpawnDungeon.java:27-29,34-36 |
| Mixins | 无 | gradle.properties:86 usesMixins = false;resources 下无 mixins.*.json |
| API 包 | 无 | gradle.properties:78 apiPackage =(空) |
⚠️ jar 名与 modid 与分类名三者全不相同:roguelike / Roguelike / roguelike-dungeons。装包时按目录名找 jar 会找不到。
⚠️ 两个同名类:greymerk.roguelike.DungeonGenerator(21 行,实现 IWorldGenerator,唯一被注册)与 greymerk.roguelike.dungeon.DungeonGenerator(66 行,内部编排器)。二者无继承关系,引用必须带包名。
@Mod 类数量 = 1:greymerk.roguelike.Roguelike(Roguelike.java:18-20)。grep -rn '@Mod(' src --include='*.java' 命中 1 处;不加括号的 grep -rn '@Mod\b' 同样只命中 1 处 —— 本树不存在 MixinExtras 注入器注解造成的误计问题。@Mod 另带 acceptableRemoteVersions = "*"(:18),没有 acceptedMinecraftVersions。
版本门(Version Gate)
门禁形态:Form B 变体 —— 真实 Gradle 构建、非反编译源码、单一 git 标签。
| 门禁形式 | 结果 |
|---|---|
gradle.properties 的 modVersion |
不存在。该文件 203 行内无 modVersion 键(grep -rn 'modVersion' --include='*.gradle' --include='*.properties' 命中 0) |
build.gradle 的 version |
不存在。build.gradle 仅 8 行,只有 //version: 1707058017 注释与 id 'com.gtnewhorizons.gtnhconvention' 插件声明 |
@Mod(version = …) |
有值:version = Roguelike.version(Roguelike.java:18),而 Roguelike.version = RLDTags.VERSION(:25)。RLDTags 由 GTNH 构建插件在编译期生成,仓库中无此文件 |
mcmod.info |
"version": "${modVersion}"、"mcversion": "${minecraftVersion}"(mcmod.info:6,9),均为占位符 |
版本值来源:modVersion 由 com.gtnewhorizons.gtnhconvention 插件从 git 标签推导。本仓库只有 1 个标签 —— 附注标签 1.6.6-GTNH(git tag -l --format='%(refname:short) %(objecttype)' → 1.6.6-GTNH tag),且它正好指向 HEAD(git rev-list -n1 1.6.6-GTNH → 9ed3801…)。
本仓不含构建产物(无 build/、无 RLDTags.class、无 ~/.gradle 缓存),因此无法核实插件最终注入 RLDTags.VERSION 与 mcmod.info 的确切字符串。此处报告标签名 1.6.6-GTNH 作为版本证据,不伪造注入后的版本号。
Minecraft / Forge 版本(这两个是字面量,可直接引用):minecraftVersion = 1.7.10(gradle.properties:24)、forgeVersion = 10.13.4.1614(:27),经 mcmod.info:9 注入。
引用的提交:9ed3801fab3af2d39929b03d242ea08660c8b53d(2025-06-19,Update dev username (#8))。已用 git cat-file -t 9ed3801… → commit 验证对象存在。
为什么不用 git describe 当版本门:本项目已因此误判 11 次。git describe --tags 在本仓恰好返回 1.6.6-GTNH(因唯一标签就在 HEAD),但这是巧合而非可靠依据 —— 它既不反映 modVersion 的实际注入逻辑,也无法区分 Form A(无构建)情形。此处只用它做标签存在性佐证,版本结论改由「@Mod 令牌链 + 唯一标签」两条独立证据得出。
反编译溯源:无。grep -rln '\$FF: synthetic\|/\* synthetic \*/' src 命中 0,且源码有完整 Javadoc 与规范格式。enableGenericInjection = true / enableModernJavaSyntax = true(gradle.properties)只表示构建期会注入泛型与 Jabel 降级,不改变源码来源。
依赖
本 mod 零依赖。 无硬依赖、无软依赖、无仅参考依赖。
| 层级 | 模组 | 证据 |
|---|---|---|
| Gradle 编译依赖 | 无 | dependencies.gradle 的 dependencies { } 块完全为空 |
mcmod.info 依赖声明 |
无 | grep -c 'dependencies' src/main/resources/mcmod.info → 0;文件仅有 modid/name/description/version/url/authorList/mcversion 7 个键 |
@Mod(dependencies = …) |
无 | Roguelike.java:18 只有 modid/name/version/acceptableRemoteVersions |
| 跨模组耦合代码 | 无 | grep -rn 'Loader\.|isModLoaded|Mods\.|IItemProvider' src/main/java 命中 0 |
全部代码只 import net.minecraft.*(原版)、net.minecraftforge.*(Forge)、cpw.mods.fml.*(FML)与 Gson/Guava。本 mod 不与任何其他模组交互,跨模组内容一律不适用(ROADMAP §0.11 的跨版本/跨模组隔离要求在本分类天然满足:仓内只有单一版本、单一 loader)。
实际注册的内容
全部为运行时存活内容(每个工厂方法的 switch 都与其枚举常量 1:1 对应,且调用点已追溯到实际注册处):
| 类型 | 数量 | 注册 / 工厂位置 | 存活依据 |
|---|---|---|---|
@Mod 类 |
1 | Roguelike.java:18 |
— |
IWorldGenerator |
1 | Roguelike.java:34(权重 0) |
类被 Roguelike.java:30 实例化为静态字段 |
| 服务端指令 | 1 | Roguelike.java:47 |
FMLServerStartingEvent 内注册 |
| Forge 事件监听器 | 1 | Roguelike.java:39 |
已注册,但触发条件不可满足(见下) |
主题 Theme |
34 | theme/Theme.java:42 |
34 常量 ↔ 34 case ↔ 34 new;CityGrounds.java:69 随机可达 |
房间 DungeonRoom |
37 | dungeon/base/DungeonRoom.java:81 |
37 ↔ 37 ↔ 37;6 处调用点 |
房间段 Segment |
34 | dungeon/segment/Segment.java:75 |
34 ↔ 34 ↔ 34;8 处调用点 |
塔 Tower |
8 | dungeon/towers/Tower.java:18 |
8 常量全有 case;2 处调用点 |
战利品分类 Loot |
16 | treasure/loot/LootSettings.java:37-51 |
15 个绑定 provider,STARTER 单独注入 |
彩蛋物品 ItemNovelty |
28 | treasure/loot/provider/ItemNovelty.java:18 |
28 常量 ↔ 28 names.put;指令与战利品均调用 |
药剂 PotionMixture |
6 | treasure/loot/PotionMixture.java:12 |
6 常量全有 case |
| 内置地牢设置 | 7 | dungeon/settings/SettingsResolver.java:63-69 |
逐个 add 进 builtin 列表 |
| 配置键 | 14 | config/RogueConfig.java:12-26 |
枚举 15 常量,MOBDROPS 为死常量 |
| 方块 / 物品 / 实体 / TileEntity / 附魔 / 配方 / 维度 | 各 0 | — | grep -rn 'registerBlock|registerItem|registerTileEntity|registerEnchantment|registerPotion|addRecipe' 命中 0 |
语言构成:296 个 .java,.scala 0,.kt 0,src 下无其他文件类型(另 resources 下 1 个 mcmod.info)。
两处「注册了但不可达」(均已 grep 取证,不计入上表的存活内容):
Loot.addEquipment(treasure/loot/Loot.java:109)唯一调用点在EntityJoinWorld.java:31,而该监听器要求实体带药水效果 ID 4 且等级 ≥ II(:28-30)。全树addPotionEffect调用点 0,本 mod 亦不注册任何实体 —— 触发条件无内部来源。RogueConfig.MOBDROPS(config/RogueConfig.java:18)全树仅此 1 处命中,既无getName()分支也无setDefaults()赋值,从不进入配置文件。
覆盖维度与条目
本 mod 不涉及方块、物品、实体、附魔、药水效果、封包、集成与 API,因此不创建这些维度目录(避免空目录)。实际覆盖 5 个维度、13 个条目:
| 维度 | 条目数 | 覆盖内容 |
|---|---|---|
structure/ |
4 | 34 主题 / 37 房间 / 34 房间段 / 8 塔 |
setting/ |
2 | 14 个配置键 + JSON 地牢设置包(7 内置 + 8 分区) |
command/ |
1 | /roguelike 指令的 6 个子指令 |
worldgen/ |
2 | 区块网格生成算法 + 生成条件判定 |
treasure/ |
4 | 16 战利品分类 / 28 彩蛋物品 / 药水药剂 / 怪物装备 |
粒度选择:本 mod 是结构型 mod,同族变体共享「1 个枚举 + 1 个 switch 工厂 + 1 个基类」,故按族合并为单页 + 表格(34 主题 1 页、37 房间 1 页、34 段 1 页、8 塔 1 页),沿用 hardcore-ender-expansion 49 方块 4 页的既定惯例;战利品与彩蛋物品同理各 1 页。跨族的独立子系统(配置、指令、生成流程、生成条件、药水、怪物装备)各占 1 页。
结构列表
- 主题(Theme) - 34 种地牢材质主题,含权重墙表与楼梯类型
- 地牢房间(Room) - 37 种房间及其
getSize()占地(4–12)与代码规模 - 房间段(Segment) - 34 种拱门/壁龛/陷阱连接件
- 塔(Tower) - 8 种塔,7 种被内置设置选中
设置列表
- 配置项(roguelike.cfg) - 14 个生效键 + 死常量
MOBDROPS - JSON 地牢设置包 -
config/roguelike_dungeons/settings/的继承加载与 8 个分区
指令列表
/roguelike指令 - 1 条指令 6 个子指令;用法文本只列出其中 3 个
世界生成列表
- 世界生成流程 -
IWorldGenerator注册、区块网格算法、Y 分层难度 - 生成条件(SpawnCriteria) - 维度/生物群系判定;
dimensionBL被静默忽略的缺陷
战利品列表
- 战利品表(Loot) - 16 个分类与 15 个默认 provider
- 彩蛋物品(ItemNovelty) - 28 件原版物品彩蛋,含
/roguelike give名字表 - 药水与药剂 - 自建
Potion/PotionEffect影子类;两套 ID 表互相矛盾 - 怪物装备(Mob Equipment) -
EntityJoinWorld监听器已注册但触发条件不可达
已知问题汇总
| 位置 | 现象 | 证据 |
|---|---|---|
treasure/loot/Potion.java:71-94 |
getPotionID 的 9/9 条目与本 mod 自己的 PotionEffect.getEffectID(:33-85)逐项冲突 |
两表同仓对撞,无需外部资料 |
dungeon/settings/SpawnCriteria.java:96 |
this.dimensionBlackList.addAll(this.dimensionBlackList) 自我相加,JSON 的 dimensionBL 永不生效,且每次判定使列表长度翻倍 |
对照紧邻的白名单正确写法 :105-107 |
EntityJoinWorld.java:28-31 |
触发条件(药水 ID 4、II 级)无内部来源,Loot.addEquipment 不可达 |
全树 addPotionEffect 命中 0 |
config/RogueConfig.java:18 |
MOBDROPS 死常量,无 getName/getDefault/setDefaults 条目 |
全树命中 1(仅声明行) |
util/CommandSpawnDungeon.java:49,313 |
用法文本只列 3 个子指令,代码实际处理 6 个 | 缺少 dim/settings/citadel |
util/CommandSpawnDungeon.java:188-199 |
dungeon nearby <次数> 忽略每次生成结果,统一回报成功 |
循环内无返回值检查 |
以上均为逐字核对源码后记录的事实。仓库只有 1 个 commit(git rev-list --count HEAD = 1),无提交历史可判断作者意图;源码中除 SpawnCriteria 处有正确写法可作对照外,相关位置均无 TODO 或说明注释。故此处只陈述现象,不主张「缺陷」或「未完成」。