修改 Forge Minecraft 中的生物生成率 mod (1.16)

Modify mob spawn rates in a Forge Minecraft mod (1.16)

我是 Minecraft 模组的新手,我想知道如何更改生物生成率。例如,假设我们想要生成很多末影人。

到目前为止,我已经找到似乎在 net.minecraft.world.biome DefaultBiomeFeatures.java:

中设置生成频率的代码
public static void withHostileMobs(MobSpawnInfo.Builder builder) {
   ...
   builder.withSpawner(EntityClassification.MONSTER, new MobSpawnInfo.Spawners(EntityType.ENDERMAN, 10, 1, 4));
   ...
}

意思是末影人在大多数生物群落中生成,尽管很少(10 是重量,苦力怕和蜘蛛有 100)。

我知道 DefaultBiome 然后被 BiomeMaker.java 用于 makeGiantTaigaBiomemakeBirchForestBiome 等。我的结论是我需要更改改变产卵率的生物群系。

我可以使用 BiomeRegistryForgeRegistries.BIOMES 访问生物群系。我在这里看到 2 种方法:

  1. 完全替换生物群系地图。遗憾的是它的register方法是private所以我不能添加新的生物群系来替换现有的。我还读到 here 删除它们显然是不可能的。
  2. 修改现有的生物群系地图。这将使用biome.withMobSpawnSettings(MobSpawnInfo mobSpawnSettings)就地修改生物群系。但是 MobSpawnInfo class 再一次没有任何 public setter,所以我不知道如何修改 MobSpawnInfo 无需手动重新创建整个 MobSpawnInfo 对象。

大多数在线解决方案 (1, 2) 似乎建议以下内容,遗憾的是在当前 1.16.4 中不再有效:

ModLoader.addSpawn(YOURENTITY.class, 25, 1, 3);
EntityRegistry.addSpawn(...)

如有任何帮助,我们将不胜感激。

不要尝试使用 Mixins 修改现有的 Minecraft 包——这被称为 coremodding 并且由于各种原因不受欢迎。 1.16 的正确方法是订阅 BiomeLoadingEvent,然后在所有生物群系加载后对其进行猴子修补:


1.16

@Mod("example")
public class ExampleMod
{
    public ExampleMod() {
        MinecraftForge.EVENT_BUS.register(this);
    }

    @SubscribeEvent(priority = EventPriority.HIGH)
    public void onBiomeLoadingEvent(BiomeLoadingEvent event) {
        List<MobSpawnInfo.Spawners> spawns = 
            event.getSpawns().getSpawner(EntityClassification.MONSTER);

        // Remove existing Enderman spawn information
        spawns.removeIf(e -> e.type == EntityType.ENDERMAN);

        // Make Enderman spawns more frequent and add Blaze spawns in all biomes
        spawns.add(new MobSpawnInfo.Spawners(EntityType.BLAZE, 200, 1, 4));
        spawns.add(new MobSpawnInfo.Spawners(EntityType.ENDERMAN, 200, 1, 4));
    }
}

1.15(也可能适用于 1.14、1.13、1.12,...)

@Mod("example")
public class ExampleMod
{
    public ExampleMod() {
        ForgeRegistries.BIOMES.forEach(biome -> {
            List<Biome.SpawnListEntry> spawns = biome.getSpawns(EntityClassification.MONSTER);
            spawns.removeIf(e -> e.entityType == EntityType.ENDERMAN);
            spawns.add(new Biome.SpawnListEntry(EntityType.BLAZE, 200, 1, 4));
            spawns.add(new Biome.SpawnListEntry(EntityType.ENDERMAN, 200, 1, 4));
        });
    }
}

编辑:请注意,InControl 可用于实现类似的效果,无需编码。