package com.pam.harvestcraft.worldgen; import com.pam.harvestcraft.HarvestCraft; import com.pam.harvestcraft.blocks.BlockRegistry; import net.minecraft.block.Block; import net.minecraft.init.Blocks; import net.minecraft.util.math.BlockPos; import net.minecraft.world.World; import net.minecraft.world.biome.Biome; import net.minecraft.world.chunk.IChunkGenerator; import net.minecraft.world.chunk.IChunkProvider; import net.minecraftforge.common.BiomeDictionary; import net.minecraftforge.fml.common.IWorldGenerator; import java.util.Random; public class BeehiveWorldGen implements IWorldGenerator { @Override public void generate(Random random, int chunkX, int chunkZ, World world, IChunkGenerator chunkGenerator, IChunkProvider chunkProvider) { if (!HarvestCraft.config.enableBeehiveGeneration) return; final Biome biome = world.getBiomeForCoordsBody(new BlockPos(chunkX, 0, chunkZ)); if (BiomeDictionary.hasType(biome, BiomeDictionary.Type.END) || BiomeDictionary.hasType(biome, BiomeDictionary.Type.NETHER)) { return; } tryGenerateBeehives(world, random, chunkX * 16, chunkZ * 16); } private static void tryGenerateBeehives(World world, Random random, int chunkX, int chunkZ) { final BlockPos.MutableBlockPos variableBlockPos = new BlockPos.MutableBlockPos(); for (int i = 0; i < HarvestCraft.config.beehiveRarity; ++i) { int x = chunkX + random.nextInt(16); int y = random.nextInt(128) - 1; int z = chunkZ + random.nextInt(16); variableBlockPos.setPos(x, y, z); if (!isBlockLeaves(world, variableBlockPos)) continue; int newY = getHeightBelowLeaves(world, x, y, z); if (newY < 0) continue; variableBlockPos.setY(newY); world.setBlockState(variableBlockPos, BlockRegistry.beehive.getDefaultState()); } } private static boolean isBlockLeaves(World world, BlockPos blockPos) { final Block block = world.getBlockState(blockPos).getBlock(); return block == Blocks.LEAVES || block == Blocks.LEAVES2; } private static int getHeightBelowLeaves(World world, int posX, int posY, int posZ) { final BlockPos.MutableBlockPos variableBlockPos = new BlockPos.MutableBlockPos(); variableBlockPos.setPos(posX, posY, posZ); // Starting from a known leaves block, descend until air block is reached. // If another block is reached (non-leaves, non-air), abort and return -1. for (int y = posY, sealevel = world.getSeaLevel(); y >= sealevel; --y) { variableBlockPos.setY(y); final Block block = world.getBlockState(variableBlockPos).getBlock(); if (block == Blocks.LEAVES || block == Blocks.LEAVES2) continue; if (world.isAirBlock(variableBlockPos)) return y; return -1; } return -1; } }