diff --git a/src/main/java/epicsquid/roots/block/BlockElementalSoil.java b/src/main/java/epicsquid/roots/block/BlockElementalSoil.java index 26596a37d..06b3f8f97 100644 --- a/src/main/java/epicsquid/roots/block/BlockElementalSoil.java +++ b/src/main/java/epicsquid/roots/block/BlockElementalSoil.java @@ -46,277 +46,277 @@ import java.util.Random; public class BlockElementalSoil extends BlockBase { - public static final PropertyInteger WATER_SPEED = PropertyInteger.create("water", 0, 4); - public static final PropertyInteger AIR_SPEED = PropertyInteger.create("air", 0, 4); - public static final PropertyInteger EARTH_FERTILITY = PropertyInteger.create("earth", 0, 4); - public static final PropertyInteger FIRE_MULTIPLIER = PropertyInteger.create("fire", 0, 4); - - private final @Nonnull - Item itemBlock; - private EnumElementalSoilType soilType; - - public static EnumElementalSoilType SOIL_INIT = EnumElementalSoilType.BASE; - - public BlockElementalSoil(@Nonnull Material mat, @Nonnull SoundType type, @Nonnull String name, @Nonnull EnumElementalSoilType soilType) { - super(mat, type, 0.8f, name); - this.soilType = soilType; - this.itemBlock = new ItemBlockElementalSoil(this).setRegistryName(LibRegistry.getActiveModid(), name); - this.setHarvestReqs("shovel", 0); - this.setTickRandomly(true); - - if (this.soilType != EnumElementalSoilType.BASE) { - PropertyInteger property = this.soilType == EnumElementalSoilType.WATER ? - WATER_SPEED : - this.soilType == EnumElementalSoilType.EARTH ? EARTH_FERTILITY : this.soilType == EnumElementalSoilType.AIR ? AIR_SPEED : FIRE_MULTIPLIER; - - this.setDefaultState(this.blockState.getBaseState().withProperty(property, 1)); - } - } - - public void doHarvest(BlockEvent.CropGrowEvent.Post cropGrowEvent) { - BlockPos pos = cropGrowEvent.getPos(); - IBlockState soil = cropGrowEvent.getWorld().getBlockState(pos.down()); - IBlockState plant = cropGrowEvent.getWorld().getBlockState(pos); - World world = cropGrowEvent.getWorld(); - doHarvest(world, pos, soil, plant); - world.scheduleUpdate(pos, this, 30); - } - - private boolean shouldHarvest(World world, BlockPos pos) { - // Assume pos is the location of the crop - return world.getBlockState(pos.down().down()).getBlock() != Blocks.GRAVEL; - } - - private void doHarvest(World world, BlockPos pos, IBlockState soil, IBlockState plant) { - if (soil.getBlock() != ModBlocks.elemental_soil_water) return; - - if (shouldHarvest(world, pos) && plant.getBlock() instanceof IPlantable && Harvest.isGrown(plant) && soil.getBlock().canSustainPlant(soil, world, pos.down(), EnumFacing.UP, (IPlantable) plant.getBlock())) { - if (soil.getBlock() == ModBlocks.elemental_soil_water) { - int speed = soil.getValue(BlockElementalSoil.WATER_SPEED); - if (speed > 0) { - List drops = Harvest.harvestReturnDrops(plant, pos, world, null); - handleDrops(world, pos, drops); - } - } - } - } - - private void handleDrops(World world, BlockPos pos, List drops) { - List dropsList = Lists.newArrayList(drops); - BlockPos under = pos.down().down(); - TileEntity te = world.getTileEntity(under); - if (te != null) { - IItemHandler cap = te.getCapability(CapabilityItemHandler.ITEM_HANDLER_CAPABILITY, null); - if (cap != null) { - List remainder = new ArrayList<>(); - for (ItemStack next : dropsList) { - if (next.isEmpty()) continue; - - ItemStack remains = ItemHandlerHelper.insertItemStacked(cap, next, false); - if (!remains.isEmpty()) { - remainder.add(remains); - } - } - dropsList.clear(); - if (!remainder.isEmpty()) { - dropsList.addAll(remainder); - } - } - } - if (!dropsList.isEmpty()) { - for (ItemStack stack : dropsList) { - ItemUtil.spawnItem(world, pos, stack); - } - } - } - - @SuppressWarnings("deprecation") - @Override - @Nonnull - public IBlockState getStateFromMeta(int meta) { - if (soilType == null) { - soilType = SOIL_INIT; - } - switch (soilType) { - case AIR: - return getDefaultState().withProperty(AIR_SPEED, meta + 1); - case FIRE: - return getDefaultState().withProperty(FIRE_MULTIPLIER, meta + 1); - case EARTH: - return getDefaultState().withProperty(EARTH_FERTILITY, meta + 1); - case WATER: - return getDefaultState().withProperty(WATER_SPEED, meta + 1); - case BASE: - default: - return getDefaultState(); - } - } - - @Nonnull - @Override - protected BlockStateContainer createBlockState() { - if (soilType == null) { - soilType = SOIL_INIT; - } - switch (soilType) { - case AIR: - return new BlockStateContainer(this, AIR_SPEED); - case FIRE: - return new BlockStateContainer(this, FIRE_MULTIPLIER); - case EARTH: - return new BlockStateContainer(this, EARTH_FERTILITY); - case WATER: - return new BlockStateContainer(this, WATER_SPEED); - case BASE: - default: - return new BlockStateContainer(this); - } - } - - @Override - public int getMetaFromState(IBlockState state) { - PropertyInteger property = this.soilType == EnumElementalSoilType.WATER ? - WATER_SPEED : - this.soilType == EnumElementalSoilType.EARTH ? EARTH_FERTILITY : this.soilType == EnumElementalSoilType.AIR ? AIR_SPEED : - this.soilType == EnumElementalSoilType.BASE ? null : FIRE_MULTIPLIER; - - if (property == null) return 0; - - return state.getValue(property) - 1 > 0 ? state.getValue(property) - 1 : 0; - } - - @Override - public boolean canSustainPlant(@Nonnull IBlockState state, @Nonnull IBlockAccess world, BlockPos pos, @Nonnull EnumFacing direction, IPlantable plantable) { - if (soilType == EnumElementalSoilType.WATER && plantable == Blocks.REEDS) { - return true; - } else if (plantable == Blocks.CACTUS) { - return soilType == EnumElementalSoilType.EARTH; - } - - EnumPlantType plant = plantable.getPlantType(world, pos.offset(direction)); - switch (plant) { - case Nether: - case Cave: - case Crop: - case Desert: - case Plains: - return true; - } - return plant == CustomPlantType.ELEMENT_FIRE - || plant == CustomPlantType.ELEMENT_AIR - || plant == CustomPlantType.ELEMENT_EARTH - || plant == CustomPlantType.ELEMENT_WATER; - } - - @Override - public void updateTick(World world, BlockPos pos, IBlockState state, Random rand) { - super.updateTick(world, pos, state, rand); - - if (world.isAirBlock(pos.up())) { - return; - } - - IBlockState upState = world.getBlockState(pos.up()); - Block upBlock = upState.getBlock(); - doHarvest(world, pos.up(), world.getBlockState(pos), upState); - - if (!(upBlock instanceof IGrowable)) - return; - - // TODO: Who knows if this value is any good - if (rand.nextInt(5) == 0) { - upBlock.randomTick(world, pos.up(), upState, rand); - } - } - - @SideOnly(Side.CLIENT) - @Override - public void randomDisplayTick(IBlockState stateIn, World worldIn, BlockPos pos, Random rand) { - if (GeneralConfig.DisableParticles) { - return; - } - - if (soilType == EnumElementalSoilType.FIRE && rand.nextInt(5) == 0) { - double d8 = pos.getX() + (double) rand.nextFloat(); - double d4 = pos.getY() + stateIn.getBoundingBox(worldIn, pos).maxY - 0.2f; - double d6 = pos.getZ() + (double) rand.nextFloat(); - worldIn.spawnParticle(EnumParticleTypes.LAVA, d8, d4, d6, 0.0D, 0.0D, 0.0D); - } - - if (soilType == EnumElementalSoilType.WATER) { - for (int i = 0; i < 2; i++) { - double x_offset = Math.min(Math.max(0.05, rand.nextDouble()), 0.95); - double y_offset = Math.min(Math.max(0.05, rand.nextDouble()), 0.95); - - double d0 = (double) pos.getX() + x_offset; - double d1 = (double) pos.getY() + 1D; - double d2 = (double) pos.getZ() + y_offset; - worldIn.spawnParticle(EnumParticleTypes.WATER_SPLASH, d0, d1, d2, 0, 1.5D, 0); - } - } - - if (soilType == EnumElementalSoilType.AIR && rand.nextInt(13) == 0) { - for (int i = 0; i < 2; i++) { - double x_offset = Math.min(Math.max(0.05, rand.nextDouble()), 0.95); - double y_offset = Math.min(Math.max(0.05, rand.nextDouble()), 0.95); - - double d0 = (double) pos.getX() + x_offset; - double d1 = (double) pos.getY() + 0.5D; - double d2 = (double) pos.getZ() + y_offset; - - worldIn.spawnParticle(EnumParticleTypes.CLOUD, d0, d1, d2, 0.0D, 0.05D, 0.0D); - } - } - - if (soilType == EnumElementalSoilType.EARTH && rand.nextInt(6) == 0) { - for (int i = 0; i < 2 + rand.nextInt(3); i++) { - double x_offset = Math.min(Math.max(0.05, rand.nextDouble()), 0.95); - double y_offset = Math.min(Math.max(0.05, rand.nextDouble()), 0.95); - - double d0 = (double) pos.getX() + x_offset; - double d1 = (double) pos.getY() + 1D; - double d2 = (double) pos.getZ() + y_offset; - worldIn.spawnParticle(EnumParticleTypes.BLOCK_CRACK, d0, d1, d2, 0, 1D, 0, Block.getStateId(stateIn)); - } - } - } - - @Override - public Item getItemBlock() { - return itemBlock; - } - - @Override - public boolean isFertile(@Nonnull World world, @Nonnull BlockPos pos) { - return true; - } - - @Override - @SideOnly(Side.CLIENT) - public void addInformation(ItemStack stack, @Nullable World worldIn, List tooltip, ITooltipFlag flagIn) { - if (stack.getItem() instanceof ItemBlock) { - Block type = ((ItemBlock) stack.getItem()).getBlock(); - if (type == ModBlocks.elemental_soil_fire) { - tooltip.add(""); - tooltip.add(TextFormatting.RED + "" + TextFormatting.BOLD + I18n.format("tile.magmatic_soil.effect")); - } else if (type == ModBlocks.elemental_soil_air) { - tooltip.add(""); - tooltip.add(TextFormatting.AQUA + "" + TextFormatting.BOLD + I18n.format("tile.caelic_soil.effect")); - } else if (type == ModBlocks.elemental_soil_earth) { - tooltip.add(""); - tooltip.add(TextFormatting.YELLOW + "" + TextFormatting.BOLD + I18n.format("tile.terran_soil.effect")); - } else if (type == ModBlocks.elemental_soil_water) { - tooltip.add(""); - tooltip.add(TextFormatting.BLUE + "" + TextFormatting.BOLD + I18n.format("tile.aqueous_soil.effect")); - } - } - } - - @Override - @SuppressWarnings("deprecation") - public void neighborChanged(IBlockState state, World worldIn, BlockPos pos, Block blockIn, BlockPos fromPos) { - worldIn.scheduleUpdate(pos, this, this.tickRate(worldIn)); - super.neighborChanged(state, worldIn, pos, blockIn, fromPos); - } + public static final PropertyInteger WATER_SPEED = PropertyInteger.create("water", 0, 4); + public static final PropertyInteger AIR_SPEED = PropertyInteger.create("air", 0, 4); + public static final PropertyInteger EARTH_FERTILITY = PropertyInteger.create("earth", 0, 4); + public static final PropertyInteger FIRE_MULTIPLIER = PropertyInteger.create("fire", 0, 4); + + private final @Nonnull + Item itemBlock; + private EnumElementalSoilType soilType; + + public static EnumElementalSoilType SOIL_INIT = EnumElementalSoilType.BASE; + + public BlockElementalSoil(@Nonnull Material mat, @Nonnull SoundType type, @Nonnull String name, @Nonnull EnumElementalSoilType soilType) { + super(mat, type, 0.8f, name); + this.soilType = soilType; + this.itemBlock = new ItemBlockElementalSoil(this).setRegistryName(LibRegistry.getActiveModid(), name); + this.setHarvestReqs("shovel", 0); + this.setTickRandomly(true); + + if (this.soilType != EnumElementalSoilType.BASE) { + PropertyInteger property = this.soilType == EnumElementalSoilType.WATER ? + WATER_SPEED : + this.soilType == EnumElementalSoilType.EARTH ? EARTH_FERTILITY : this.soilType == EnumElementalSoilType.AIR ? AIR_SPEED : FIRE_MULTIPLIER; + + this.setDefaultState(this.blockState.getBaseState().withProperty(property, 1)); + } + } + + public void doHarvest(BlockEvent.CropGrowEvent.Post cropGrowEvent) { + BlockPos pos = cropGrowEvent.getPos(); + IBlockState soil = cropGrowEvent.getWorld().getBlockState(pos.down()); + IBlockState plant = cropGrowEvent.getWorld().getBlockState(pos); + World world = cropGrowEvent.getWorld(); + doHarvest(world, pos, soil, plant); + world.scheduleUpdate(pos, this, 30); + } + + private boolean shouldHarvest(World world, BlockPos pos) { + // Assume pos is the location of the crop + return world.getBlockState(pos.down().down()).getBlock() != Blocks.GRAVEL; + } + + private void doHarvest(World world, BlockPos pos, IBlockState soil, IBlockState plant) { + if (soil.getBlock() != ModBlocks.elemental_soil_water) return; + + if (shouldHarvest(world, pos) && plant.getBlock() instanceof IPlantable && Harvest.isGrown(plant) && soil.getBlock().canSustainPlant(soil, world, pos.down(), EnumFacing.UP, (IPlantable) plant.getBlock())) { + if (soil.getBlock() == ModBlocks.elemental_soil_water) { + int speed = soil.getValue(BlockElementalSoil.WATER_SPEED); + if (speed > 0) { + List drops = Harvest.harvestReturnDrops(plant, pos, world, null); + handleDrops(world, pos, drops); + } + } + } + } + + private void handleDrops(World world, BlockPos pos, List drops) { + List dropsList = Lists.newArrayList(drops); + BlockPos under = pos.down().down(); + TileEntity te = world.getTileEntity(under); + if (te != null) { + IItemHandler cap = te.getCapability(CapabilityItemHandler.ITEM_HANDLER_CAPABILITY, null); + if (cap != null) { + List remainder = new ArrayList<>(); + for (ItemStack next : dropsList) { + if (next.isEmpty()) continue; + + ItemStack remains = ItemHandlerHelper.insertItemStacked(cap, next, false); + if (!remains.isEmpty()) { + remainder.add(remains); + } + } + dropsList.clear(); + if (!remainder.isEmpty()) { + dropsList.addAll(remainder); + } + } + } + if (!dropsList.isEmpty()) { + for (ItemStack stack : dropsList) { + ItemUtil.spawnItem(world, pos, stack); + } + } + } + + @SuppressWarnings("deprecation") + @Override + @Nonnull + public IBlockState getStateFromMeta(int meta) { + if (soilType == null) { + soilType = SOIL_INIT; + } + switch (soilType) { + case AIR: + return getDefaultState().withProperty(AIR_SPEED, meta + 1); + case FIRE: + return getDefaultState().withProperty(FIRE_MULTIPLIER, meta + 1); + case EARTH: + return getDefaultState().withProperty(EARTH_FERTILITY, meta + 1); + case WATER: + return getDefaultState().withProperty(WATER_SPEED, meta + 1); + case BASE: + default: + return getDefaultState(); + } + } + + @Nonnull + @Override + protected BlockStateContainer createBlockState() { + if (soilType == null) { + soilType = SOIL_INIT; + } + switch (soilType) { + case AIR: + return new BlockStateContainer(this, AIR_SPEED); + case FIRE: + return new BlockStateContainer(this, FIRE_MULTIPLIER); + case EARTH: + return new BlockStateContainer(this, EARTH_FERTILITY); + case WATER: + return new BlockStateContainer(this, WATER_SPEED); + case BASE: + default: + return new BlockStateContainer(this); + } + } + + @Override + public int getMetaFromState(IBlockState state) { + PropertyInteger property = this.soilType == EnumElementalSoilType.WATER ? + WATER_SPEED : + this.soilType == EnumElementalSoilType.EARTH ? EARTH_FERTILITY : this.soilType == EnumElementalSoilType.AIR ? AIR_SPEED : + this.soilType == EnumElementalSoilType.BASE ? null : FIRE_MULTIPLIER; + + if (property == null) return 0; + + return Math.max(state.getValue(property) - 1, 0); + } + + @Override + public boolean canSustainPlant(@Nonnull IBlockState state, @Nonnull IBlockAccess world, BlockPos pos, @Nonnull EnumFacing direction, IPlantable plantable) { + if (soilType == EnumElementalSoilType.WATER && plantable == Blocks.REEDS) { + return true; + } else if (plantable == Blocks.CACTUS) { + return soilType == EnumElementalSoilType.EARTH; + } + + EnumPlantType plant = plantable.getPlantType(world, pos.offset(direction)); + switch (plant) { + case Nether: + case Cave: + case Crop: + case Desert: + case Plains: + return true; + } + return plant == CustomPlantType.ELEMENT_FIRE + || plant == CustomPlantType.ELEMENT_AIR + || plant == CustomPlantType.ELEMENT_EARTH + || plant == CustomPlantType.ELEMENT_WATER; + } + + @Override + public void updateTick(World world, BlockPos pos, IBlockState state, Random rand) { + super.updateTick(world, pos, state, rand); + + if (world.isAirBlock(pos.up())) { + return; + } + + IBlockState upState = world.getBlockState(pos.up()); + Block upBlock = upState.getBlock(); + doHarvest(world, pos.up(), world.getBlockState(pos), upState); + + if (!(upBlock instanceof IGrowable)) + return; + + // TODO: Who knows if this value is any good + if (rand.nextInt(5) == 0) { + upBlock.randomTick(world, pos.up(), upState, rand); + } + } + + @SideOnly(Side.CLIENT) + @Override + public void randomDisplayTick(IBlockState stateIn, World worldIn, BlockPos pos, Random rand) { + if (GeneralConfig.DisableParticles) { + return; + } + + if (soilType == EnumElementalSoilType.FIRE && rand.nextInt(5) == 0) { + double d8 = pos.getX() + (double) rand.nextFloat(); + double d4 = pos.getY() + stateIn.getBoundingBox(worldIn, pos).maxY - 0.2f; + double d6 = pos.getZ() + (double) rand.nextFloat(); + worldIn.spawnParticle(EnumParticleTypes.LAVA, d8, d4, d6, 0.0D, 0.0D, 0.0D); + } + + if (soilType == EnumElementalSoilType.WATER) { + for (int i = 0; i < 2; i++) { + double x_offset = Math.min(Math.max(0.05, rand.nextDouble()), 0.95); + double y_offset = Math.min(Math.max(0.05, rand.nextDouble()), 0.95); + + double d0 = (double) pos.getX() + x_offset; + double d1 = (double) pos.getY() + 1D; + double d2 = (double) pos.getZ() + y_offset; + worldIn.spawnParticle(EnumParticleTypes.WATER_SPLASH, d0, d1, d2, 0, 1.5D, 0); + } + } + + if (soilType == EnumElementalSoilType.AIR && rand.nextInt(13) == 0) { + for (int i = 0; i < 2; i++) { + double x_offset = Math.min(Math.max(0.05, rand.nextDouble()), 0.95); + double y_offset = Math.min(Math.max(0.05, rand.nextDouble()), 0.95); + + double d0 = (double) pos.getX() + x_offset; + double d1 = (double) pos.getY() + 0.5D; + double d2 = (double) pos.getZ() + y_offset; + + worldIn.spawnParticle(EnumParticleTypes.CLOUD, d0, d1, d2, 0.0D, 0.05D, 0.0D); + } + } + + if (soilType == EnumElementalSoilType.EARTH && rand.nextInt(6) == 0) { + for (int i = 0; i < 2 + rand.nextInt(3); i++) { + double x_offset = Math.min(Math.max(0.05, rand.nextDouble()), 0.95); + double y_offset = Math.min(Math.max(0.05, rand.nextDouble()), 0.95); + + double d0 = (double) pos.getX() + x_offset; + double d1 = (double) pos.getY() + 1D; + double d2 = (double) pos.getZ() + y_offset; + worldIn.spawnParticle(EnumParticleTypes.BLOCK_CRACK, d0, d1, d2, 0, 1D, 0, Block.getStateId(stateIn)); + } + } + } + + @Override + public Item getItemBlock() { + return itemBlock; + } + + @Override + public boolean isFertile(@Nonnull World world, @Nonnull BlockPos pos) { + return true; + } + + @Override + @SideOnly(Side.CLIENT) + public void addInformation(ItemStack stack, @Nullable World worldIn, List tooltip, ITooltipFlag flagIn) { + if (stack.getItem() instanceof ItemBlock) { + Block type = ((ItemBlock) stack.getItem()).getBlock(); + if (type == ModBlocks.elemental_soil_fire) { + tooltip.add(""); + tooltip.add(TextFormatting.RED + "" + TextFormatting.BOLD + I18n.format("tile.magmatic_soil.effect")); + } else if (type == ModBlocks.elemental_soil_air) { + tooltip.add(""); + tooltip.add(TextFormatting.AQUA + "" + TextFormatting.BOLD + I18n.format("tile.caelic_soil.effect")); + } else if (type == ModBlocks.elemental_soil_earth) { + tooltip.add(""); + tooltip.add(TextFormatting.YELLOW + "" + TextFormatting.BOLD + I18n.format("tile.terran_soil.effect")); + } else if (type == ModBlocks.elemental_soil_water) { + tooltip.add(""); + tooltip.add(TextFormatting.BLUE + "" + TextFormatting.BOLD + I18n.format("tile.aqueous_soil.effect")); + } + } + } + + @Override + @SuppressWarnings("deprecation") + public void neighborChanged(IBlockState state, World worldIn, BlockPos pos, Block blockIn, BlockPos fromPos) { + worldIn.scheduleUpdate(pos, this, this.tickRate(worldIn)); + super.neighborChanged(state, worldIn, pos, blockIn, fromPos); + } } diff --git a/src/main/java/epicsquid/roots/world/tree/WorldGenBigWildwoodTree.java b/src/main/java/epicsquid/roots/world/tree/WorldGenBigWildwoodTree.java index 518342373..3d917ee1c 100644 --- a/src/main/java/epicsquid/roots/world/tree/WorldGenBigWildwoodTree.java +++ b/src/main/java/epicsquid/roots/world/tree/WorldGenBigWildwoodTree.java @@ -15,276 +15,276 @@ import java.util.Random; public class WorldGenBigWildwoodTree extends WorldGenAbstractTree { - private Random rand; - private World world; - private BlockPos basePos = BlockPos.ORIGIN; - private int heightLimit = 12; - private int height; - private double heightAttenuation = 0.618D; - private double branchSlope = 0.381D; - private double scaleWidth = 1.0D; - private double leafDensity = 1.0D; - public List affectedBlocks; - /** - * Sets the distance limit for how far away the generator will populate leaves from the base leaf node. - */ - int leafDistanceLimit = 4; - List foliageCoords; - - public WorldGenBigWildwoodTree(boolean notify) { - super(notify); - } - - /** - * Generates a list of leaf nodes for the tree, to be populated by generateLeaves. - */ - private void generateLeafNodeList() { - this.height = (int) ((double) this.heightLimit * this.heightAttenuation); - - if (this.height >= this.heightLimit) { - this.height = this.heightLimit - 1; - } - - int i = (int) (1.382D + Math.pow(this.leafDensity * (double) this.heightLimit / 13.0D, 2.0D)); - - if (i < 1) { - i = 1; - } - - int j = this.basePos.getY() + this.height; - int k = this.heightLimit - this.leafDistanceLimit; - this.foliageCoords = new ArrayList<>(); - this.foliageCoords.add(new FoliageCoordinates(this.basePos.up(k), j)); - - for (; k >= 0; --k) { - float f = this.layerSize(k); - - if (f >= 0.0F) { - for (int l = 0; l < i; ++l) { - double d0 = this.scaleWidth * (double) f * ((double) this.rand.nextFloat() + 0.328D); - double d1 = (double) (this.rand.nextFloat() * 2.0F) * Math.PI; - double d2 = d0 * Math.sin(d1) + 0.5D; - double d3 = d0 * Math.cos(d1) + 0.5D; - BlockPos blockpos = this.basePos.add(d2, (double) (k - 1), d3); - BlockPos blockpos1 = blockpos.up(this.leafDistanceLimit); - - if (this.checkBlockLine(blockpos, blockpos1) == -1) { - int i1 = this.basePos.getX() - blockpos.getX(); - int j1 = this.basePos.getZ() - blockpos.getZ(); - double d4 = (double) blockpos.getY() - Math.sqrt((double) (i1 * i1 + j1 * j1)) * this.branchSlope; - int k1 = d4 > (double) j ? j : (int) d4; - BlockPos blockpos2 = new BlockPos(this.basePos.getX(), k1, this.basePos.getZ()); - - if (this.checkBlockLine(blockpos2, blockpos) == -1) { - this.foliageCoords.add(new FoliageCoordinates(blockpos, blockpos2.getY())); - } - } - } - } - } - } - - private void crosSection(BlockPos pos, float p_181631_2_, IBlockState p_181631_3_) { - int i = (int) ((double) p_181631_2_ + 0.618D); - - for (int j = -i; j <= i; ++j) { - for (int k = -i; k <= i; ++k) { - if (Math.pow((double) Math.abs(j) + 0.5D, 2.0D) + Math.pow((double) Math.abs(k) + 0.5D, 2.0D) <= (double) (p_181631_2_ * p_181631_2_)) { - BlockPos blockpos = pos.add(j, 0, k); - IBlockState state = this.world.getBlockState(blockpos); - - if (state.getBlock().isAir(state, world, blockpos) || state.getBlock().isLeaves(state, world, blockpos)) { - this.setBlockAndNotifyAdequately(this.world, blockpos, p_181631_3_); - affectedBlocks.add(blockpos); - } - } - } - } - } - - /** - * Gets the rough size of a layer of the tree. - */ - private float layerSize(int y) { - if ((float) y < (float) this.heightLimit * 0.3F) { - return -1.0F; - } else { - float f = (float) this.heightLimit / 2.0F; - float f1 = f - (float) y; - float f2 = MathHelper.sqrt(f * f - f1 * f1); - - if (f1 == 0.0F) { - f2 = f; - } else if (Math.abs(f1) >= f) { - return 0.0F; - } - - return f2 * 0.5F; - } - } - - private float leafSize(int y) { - if (y >= 0 && y < this.leafDistanceLimit) { - return y != 0 && y != this.leafDistanceLimit - 1 ? 3.0F : 2.0F; - } else { - return -1.0F; - } - } - - /** - * Generates the leaves surrounding an individual entry in the leafNodes list. - */ - private void generateLeafNode(BlockPos pos) { - for (int i = 0; i < this.leafDistanceLimit; ++i) { - this.crosSection(pos.up(i), this.leafSize(i), ModBlocks.wildwood_leaves.getDefaultState().withProperty(BlockLeaves.CHECK_DECAY, false)); - } - } - - private void limb(BlockPos p_175937_1_, BlockPos p_175937_2_, Block p_175937_3_) { - BlockPos blockpos = p_175937_2_.add(-p_175937_1_.getX(), -p_175937_1_.getY(), -p_175937_1_.getZ()); - int i = this.getGreatestDistance(blockpos); - float f = (float) blockpos.getX() / (float) i; - float f1 = (float) blockpos.getY() / (float) i; - float f2 = (float) blockpos.getZ() / (float) i; - - for (int j = 0; j <= i; ++j) { - BlockPos blockpos1 = p_175937_1_.add((double) (0.5F + (float) j * f), (double) (0.5F + (float) j * f1), (double) (0.5F + (float) j * f2)); - BlockLog.EnumAxis blocklog$enumaxis = this.getLogAxis(p_175937_1_, blockpos1); - this.setBlockAndNotifyAdequately(this.world, blockpos1, p_175937_3_.getDefaultState().withProperty(BlockLog.LOG_AXIS, blocklog$enumaxis)); - affectedBlocks.add(blockpos1); - } - } - - /** - * Returns the absolute greatest distance in the BlockPos object. - */ - private int getGreatestDistance(BlockPos posIn) { - int i = MathHelper.abs(posIn.getX()); - int j = MathHelper.abs(posIn.getY()); - int k = MathHelper.abs(posIn.getZ()); - - if (k > i && k > j) { - return k; - } else { - return j > i ? j : i; - } - } - - private BlockLog.EnumAxis getLogAxis(BlockPos p_175938_1_, BlockPos p_175938_2_) { - BlockLog.EnumAxis blocklog$enumaxis = BlockLog.EnumAxis.Y; - int i = Math.abs(p_175938_2_.getX() - p_175938_1_.getX()); - int j = Math.abs(p_175938_2_.getZ() - p_175938_1_.getZ()); - int k = Math.max(i, j); - - if (k > 0) { - if (i == k) { - blocklog$enumaxis = BlockLog.EnumAxis.X; - } else if (j == k) { - blocklog$enumaxis = BlockLog.EnumAxis.Z; - } - } - - return blocklog$enumaxis; - } - - /** - * Generates the leaf portion of the tree as specified by the leafNodes list. - */ - private void generateLeaves() { - for (FoliageCoordinates worldgenbigtree$foliagecoordinates : this.foliageCoords) { - this.generateLeafNode(worldgenbigtree$foliagecoordinates); - } - } - - /** - * Indicates whether or not a leaf node requires additional wood to be added to preserve integrity. - */ - private boolean leafNodeNeedsBase(int p_76493_1_) { - return (double) p_76493_1_ >= (double) this.heightLimit * 0.2D; - } - - /** - * Places the trunk for the big tree that is being generated. Able to generate double-sized trunks by changing a - * field that is always 1 to 2. - */ - private void generateTrunk() { - BlockPos blockpos = this.basePos; - BlockPos blockpos1 = this.basePos.up(this.height); - Block block = ModBlocks.wildwood_log; - this.limb(blockpos, blockpos1, block); - } - - /** - * Generates additional wood blocks to fill out the bases of different leaf nodes that would otherwise degrade. - */ - private void generateLeafNodeBases() { - for (FoliageCoordinates worldgenbigtree$foliagecoordinates : this.foliageCoords) { - int i = worldgenbigtree$foliagecoordinates.getBranchBase(); - BlockPos blockpos = new BlockPos(this.basePos.getX(), i, this.basePos.getZ()); - - if (!blockpos.equals(worldgenbigtree$foliagecoordinates) && this.leafNodeNeedsBase(i - this.basePos.getY())) { - this.limb(blockpos, worldgenbigtree$foliagecoordinates, ModBlocks.wildwood_log); - } - } - } - - /** - * Checks a line of blocks in the world from the first coordinate to triplet to the second, returning the distance - * (in blocks) before a non-air, non-leaf block is encountered and/or the end is encountered. - */ - private int checkBlockLine(BlockPos posOne, BlockPos posTwo) { - BlockPos blockpos = posTwo.add(-posOne.getX(), -posOne.getY(), -posOne.getZ()); - int i = this.getGreatestDistance(blockpos); - float f = (float) blockpos.getX() / (float) i; - float f1 = (float) blockpos.getY() / (float) i; - float f2 = (float) blockpos.getZ() / (float) i; - - if (i == 0) { - return -1; - } else { - for (int j = 0; j <= i; ++j) { - BlockPos blockpos1 = posOne.add((double) (0.5F + (float) j * f), (double) (0.5F + (float) j * f1), (double) (0.5F + (float) j * f2)); - - if (!this.isReplaceable(world, blockpos1)) { - return j; - } - } - - return -1; - } - } - - @Override - public void setDecorationDefaults() { - this.leafDistanceLimit = 5; - } - - @Override - public boolean generate(World worldIn, Random rand, BlockPos position) { - this.world = worldIn; - this.basePos = position; - this.rand = new Random(rand.nextLong()); - this.affectedBlocks = new ArrayList<>(); - - this.generateLeafNodeList(); - this.generateLeaves(); - this.generateTrunk(); - this.generateLeafNodeBases(); - this.world = null; //Fix vanilla Mem leak, holds latest world - return true; - } - - public static class FoliageCoordinates extends BlockPos { - private final int branchBase; - - public FoliageCoordinates(BlockPos pos, int p_i45635_2_) { - super(pos.getX(), pos.getY(), pos.getZ()); - this.branchBase = p_i45635_2_; - } - - public int getBranchBase() { - return this.branchBase; - } - } + private Random rand; + private World world; + private BlockPos basePos = BlockPos.ORIGIN; + private int heightLimit = 12; + private int height; + private double heightAttenuation = 0.618D; + private double branchSlope = 0.381D; + private double scaleWidth = 1.0D; + private double leafDensity = 1.0D; + public List affectedBlocks; + /** + * Sets the distance limit for how far away the generator will populate leaves from the base leaf node. + */ + int leafDistanceLimit = 4; + List foliageCoords; + + public WorldGenBigWildwoodTree(boolean notify) { + super(notify); + } + + /** + * Generates a list of leaf nodes for the tree, to be populated by generateLeaves. + */ + private void generateLeafNodeList() { + this.height = (int) ((double) this.heightLimit * this.heightAttenuation); + + if (this.height >= this.heightLimit) { + this.height = this.heightLimit - 1; + } + + int i = (int) (1.382D + Math.pow(this.leafDensity * (double) this.heightLimit / 13.0D, 2.0D)); + + if (i < 1) { + i = 1; + } + + int j = this.basePos.getY() + this.height; + int k = this.heightLimit - this.leafDistanceLimit; + this.foliageCoords = new ArrayList<>(); + this.foliageCoords.add(new FoliageCoordinates(this.basePos.up(k), j)); + + for (; k >= 0; --k) { + float f = this.layerSize(k); + + if (f >= 0.0F) { + for (int l = 0; l < i; ++l) { + double d0 = this.scaleWidth * (double) f * ((double) this.rand.nextFloat() + 0.328D); + double d1 = (double) (this.rand.nextFloat() * 2.0F) * Math.PI; + double d2 = d0 * Math.sin(d1) + 0.5D; + double d3 = d0 * Math.cos(d1) + 0.5D; + BlockPos blockpos = this.basePos.add(d2, (double) (k - 1), d3); + BlockPos blockpos1 = blockpos.up(this.leafDistanceLimit); + + if (this.checkBlockLine(blockpos, blockpos1) == -1) { + int i1 = this.basePos.getX() - blockpos.getX(); + int j1 = this.basePos.getZ() - blockpos.getZ(); + double d4 = (double) blockpos.getY() - Math.sqrt((double) (i1 * i1 + j1 * j1)) * this.branchSlope; + int k1 = d4 > (double) j ? j : (int) d4; + BlockPos blockpos2 = new BlockPos(this.basePos.getX(), k1, this.basePos.getZ()); + + if (this.checkBlockLine(blockpos2, blockpos) == -1) { + this.foliageCoords.add(new FoliageCoordinates(blockpos, blockpos2.getY())); + } + } + } + } + } + } + + private void crosSection(BlockPos pos, float p_181631_2_, IBlockState p_181631_3_) { + int i = (int) ((double) p_181631_2_ + 0.618D); + + for (int j = -i; j <= i; ++j) { + for (int k = -i; k <= i; ++k) { + if (Math.pow((double) Math.abs(j) + 0.5D, 2.0D) + Math.pow((double) Math.abs(k) + 0.5D, 2.0D) <= (double) (p_181631_2_ * p_181631_2_)) { + BlockPos blockpos = pos.add(j, 0, k); + IBlockState state = this.world.getBlockState(blockpos); + + if (state.getBlock().isAir(state, world, blockpos) || state.getBlock().isLeaves(state, world, blockpos)) { + this.setBlockAndNotifyAdequately(this.world, blockpos, p_181631_3_); + affectedBlocks.add(blockpos); + } + } + } + } + } + + /** + * Gets the rough size of a layer of the tree. + */ + private float layerSize(int y) { + if ((float) y < (float) this.heightLimit * 0.3F) { + return -1.0F; + } else { + float f = (float) this.heightLimit / 2.0F; + float f1 = f - (float) y; + float f2 = MathHelper.sqrt(f * f - f1 * f1); + + if (f1 == 0.0F) { + f2 = f; + } else if (Math.abs(f1) >= f) { + return 0.0F; + } + + return f2 * 0.5F; + } + } + + private float leafSize(int y) { + if (y >= 0 && y < this.leafDistanceLimit) { + return y != 0 && y != this.leafDistanceLimit - 1 ? 3.0F : 2.0F; + } else { + return -1.0F; + } + } + + /** + * Generates the leaves surrounding an individual entry in the leafNodes list. + */ + private void generateLeafNode(BlockPos pos) { + for (int i = 0; i < this.leafDistanceLimit; ++i) { + this.crosSection(pos.up(i), this.leafSize(i), ModBlocks.wildwood_leaves.getDefaultState().withProperty(BlockLeaves.CHECK_DECAY, false)); + } + } + + private void limb(BlockPos p_175937_1_, BlockPos p_175937_2_, Block p_175937_3_) { + BlockPos blockpos = p_175937_2_.add(-p_175937_1_.getX(), -p_175937_1_.getY(), -p_175937_1_.getZ()); + int i = this.getGreatestDistance(blockpos); + float f = (float) blockpos.getX() / (float) i; + float f1 = (float) blockpos.getY() / (float) i; + float f2 = (float) blockpos.getZ() / (float) i; + + for (int j = 0; j <= i; ++j) { + BlockPos blockpos1 = p_175937_1_.add((double) (0.5F + (float) j * f), (double) (0.5F + (float) j * f1), (double) (0.5F + (float) j * f2)); + BlockLog.EnumAxis blocklog$enumaxis = this.getLogAxis(p_175937_1_, blockpos1); + this.setBlockAndNotifyAdequately(this.world, blockpos1, p_175937_3_.getDefaultState().withProperty(BlockLog.LOG_AXIS, blocklog$enumaxis)); + affectedBlocks.add(blockpos1); + } + } + + /** + * Returns the absolute greatest distance in the BlockPos object. + */ + private int getGreatestDistance(BlockPos posIn) { + int i = MathHelper.abs(posIn.getX()); + int j = MathHelper.abs(posIn.getY()); + int k = MathHelper.abs(posIn.getZ()); + + if (k > i && k > j) { + return k; + } else { + return Math.max(j, i); + } + } + + private BlockLog.EnumAxis getLogAxis(BlockPos p_175938_1_, BlockPos p_175938_2_) { + BlockLog.EnumAxis blocklog$enumaxis = BlockLog.EnumAxis.Y; + int i = Math.abs(p_175938_2_.getX() - p_175938_1_.getX()); + int j = Math.abs(p_175938_2_.getZ() - p_175938_1_.getZ()); + int k = Math.max(i, j); + + if (k > 0) { + if (i == k) { + blocklog$enumaxis = BlockLog.EnumAxis.X; + } else if (j == k) { + blocklog$enumaxis = BlockLog.EnumAxis.Z; + } + } + + return blocklog$enumaxis; + } + + /** + * Generates the leaf portion of the tree as specified by the leafNodes list. + */ + private void generateLeaves() { + for (FoliageCoordinates worldgenbigtree$foliagecoordinates : this.foliageCoords) { + this.generateLeafNode(worldgenbigtree$foliagecoordinates); + } + } + + /** + * Indicates whether or not a leaf node requires additional wood to be added to preserve integrity. + */ + private boolean leafNodeNeedsBase(int p_76493_1_) { + return (double) p_76493_1_ >= (double) this.heightLimit * 0.2D; + } + + /** + * Places the trunk for the big tree that is being generated. Able to generate double-sized trunks by changing a + * field that is always 1 to 2. + */ + private void generateTrunk() { + BlockPos blockpos = this.basePos; + BlockPos blockpos1 = this.basePos.up(this.height); + Block block = ModBlocks.wildwood_log; + this.limb(blockpos, blockpos1, block); + } + + /** + * Generates additional wood blocks to fill out the bases of different leaf nodes that would otherwise degrade. + */ + private void generateLeafNodeBases() { + for (FoliageCoordinates worldgenbigtree$foliagecoordinates : this.foliageCoords) { + int i = worldgenbigtree$foliagecoordinates.getBranchBase(); + BlockPos blockpos = new BlockPos(this.basePos.getX(), i, this.basePos.getZ()); + + if (!blockpos.equals(worldgenbigtree$foliagecoordinates) && this.leafNodeNeedsBase(i - this.basePos.getY())) { + this.limb(blockpos, worldgenbigtree$foliagecoordinates, ModBlocks.wildwood_log); + } + } + } + + /** + * Checks a line of blocks in the world from the first coordinate to triplet to the second, returning the distance + * (in blocks) before a non-air, non-leaf block is encountered and/or the end is encountered. + */ + private int checkBlockLine(BlockPos posOne, BlockPos posTwo) { + BlockPos blockpos = posTwo.add(-posOne.getX(), -posOne.getY(), -posOne.getZ()); + int i = this.getGreatestDistance(blockpos); + float f = (float) blockpos.getX() / (float) i; + float f1 = (float) blockpos.getY() / (float) i; + float f2 = (float) blockpos.getZ() / (float) i; + + if (i == 0) { + return -1; + } else { + for (int j = 0; j <= i; ++j) { + BlockPos blockpos1 = posOne.add((double) (0.5F + (float) j * f), (double) (0.5F + (float) j * f1), (double) (0.5F + (float) j * f2)); + + if (!this.isReplaceable(world, blockpos1)) { + return j; + } + } + + return -1; + } + } + + @Override + public void setDecorationDefaults() { + this.leafDistanceLimit = 5; + } + + @Override + public boolean generate(World worldIn, Random rand, BlockPos position) { + this.world = worldIn; + this.basePos = position; + this.rand = new Random(rand.nextLong()); + this.affectedBlocks = new ArrayList<>(); + + this.generateLeafNodeList(); + this.generateLeaves(); + this.generateTrunk(); + this.generateLeafNodeBases(); + this.world = null; //Fix vanilla Mem leak, holds latest world + return true; + } + + public static class FoliageCoordinates extends BlockPos { + private final int branchBase; + + public FoliageCoordinates(BlockPos pos, int p_i45635_2_) { + super(pos.getX(), pos.getY(), pos.getZ()); + this.branchBase = p_i45635_2_; + } + + public int getBranchBase() { + return this.branchBase; + } + } }