Search in sources :

Example 41 with Biome

use of net.minecraft.world.biome.Biome in project Almura by AlmuraDev.

the class CropBlockImpl method advanceState.

private void advanceState(final World world, final BlockPos pos, final IBlockState state, final boolean fertilizer) {
    final int age = this.getAge(state);
    final CropBlockStateDefinition definition = this.state(age);
    if (fertilizer) {
        world.setBlockState(pos, this.withAge(age + 1), BlockUpdateFlag.UPDATE_NEIGHBORS | BlockUpdateFlag.UPDATE_CLIENTS);
        return;
    }
    final boolean isMaxAge = this.isMaxAge(state);
    final boolean canRollback = definition.canRollback;
    if (isMaxAge) {
        // && !canRollback) { // Remove 3/22/2018 to prevent generated crops from rolling back.
        return;
    }
    boolean rollback = false;
    // Crop soil isn't fertile? Don't grow and rollback if applicable
    if (!this.isFertile(world, pos.down())) {
        rollback = true;
    }
    // Check if its time to perform a growth tick
    @Nullable final Growth growth = definition.growth;
    if (!rollback && growth != null) {
        final Biome biome = world.getBiome(pos);
        // Temperature of biome isn't in required range? Don't grow and rollback if applicable
        // TODO Should fertilizer be blocked from advancing a crop if out of temperature? Or should it be allowed
        // TODO and punish the user afterwards (might be more amusing that way)
        final DoubleRange temperatureRequiredRange = growth.getOrLoadTemperatureRequiredRangeForBiome(biome);
        if (temperatureRequiredRange != null) {
            final float biomeTemperature = biome.getTemperature(pos);
            if (!temperatureRequiredRange.contains(biomeTemperature)) {
                // Range Check
                rollback = true;
            }
            if (biomeTemperature < temperatureRequiredRange.min()) {
                // Check for additional heat source
                if (hasAdditionalSource(world, pos, 1)) {
                    rollback = false;
                }
            }
        }
        // Light of biome isn't in required range? Don't grow and rollback if applicable
        final DoubleRange light = growth.getOrLoadLightRangeForBiome(biome);
        // Skip this section if rollback is true because a Tempoerature fail should never be overridden by light.
        if (!rollback && light != null && world.isAreaLoaded(pos, 1)) {
            final int minLight = (int) light.min();
            final int maxLight = (int) light.max();
            final int lightLevel = world.getLightFromNeighbors(pos);
            if (lightLevel < minLight || lightLevel > maxLight) {
                rollback = !hasAdditionalSource(world, pos, 2);
            }
            if (canRollback && rollback) {
                if (world.canSeeSky(pos)) {
                    final int worldLight = world.getLightFor(EnumSkyBlock.SKY, pos) - world.getSkylightSubtracted();
                    if (worldLight < 6) {
                        // Crops go to sleep on a routine if their lightLevel is predictable
                        // Prevent a crop from rolling back in the middle of the night if it can see sky.
                        rollback = false;
                    }
                }
            }
        }
        if (!rollback && !this.isMaxAge(state)) {
            final DoubleRange change = growth.getOrLoadChanceRangeForBiome(biome);
            if (change == null || change.max() == 0) {
                return;
            }
            // Can we grow? Yes? Awesome!
            if (RANDOM.nextDouble() <= (change.random(RANDOM) / 100) && this.isGrowthEven(world, pos, age)) {
                // If growth will be even, grow
                world.setBlockState(pos, this.withAge(age + 1), BlockUpdateFlag.UPDATE_NEIGHBORS | BlockUpdateFlag.UPDATE_CLIENTS);
                if (ForgeHooks.onCropsGrowPre(world, pos, state, true)) {
                    // If growth will be even, grow
                    world.setBlockState(pos, this.withAge(age + 1), BlockUpdateFlag.UPDATE_NEIGHBORS | BlockUpdateFlag.UPDATE_CLIENTS);
                    if (!world.isRemote) {
                        world.playEvent(2005, pos, 0);
                    }
                    ForgeHooks.onCropsGrowPost(world, pos, state, null);
                }
            }
        }
    }
    if (canRollback && rollback) {
        if (age > 0) {
            world.setBlockState(pos, this.withAge(age - 1), BlockUpdateFlag.UPDATE_NEIGHBORS | BlockUpdateFlag.UPDATE_CLIENTS);
        } else {
            // They let the crop continue to roll back? Tough, they just lost it
            // TODO Dockter, do you want to show a generic "dead crop block"
            world.setBlockState(pos, Blocks.AIR.getDefaultState(), BlockUpdateFlag.UPDATE_NEIGHBORS | BlockUpdateFlag.UPDATE_CLIENTS);
        }
    }
}
Also used : CropBlockStateDefinition(com.almuradev.content.type.block.type.crop.state.CropBlockStateDefinition) DoubleRange(com.almuradev.toolbox.util.math.DoubleRange) Biome(net.minecraft.world.biome.Biome) Growth(com.almuradev.content.type.block.type.crop.processor.growth.Growth) Nullable(javax.annotation.Nullable)

Example 42 with Biome

use of net.minecraft.world.biome.Biome in project Almura by AlmuraDev.

the class Growth method getOrLoadTemperatureRequiredRangeForBiome.

@Nullable
public DoubleRange getOrLoadTemperatureRequiredRangeForBiome(final Biome biome) {
    @Nullable DoubleRange found = this.biomeTemperatureRequiredRanges.get(biome);
    if (found == null) {
        for (final Map.Entry<FunctionPredicate<Biome, ResourceLocation>, DoubleRange> entry : this.biomeTemperatureRequiredPredicates.entrySet()) {
            final FunctionPredicate<Biome, ResourceLocation> predicate = entry.getKey();
            if (predicate.test(biome)) {
                final DoubleRange range = entry.getValue();
                this.biomeTemperatureRequiredRanges.put(biome, range);
                found = range;
                break;
            }
        }
    }
    if (found == null && this.globalTemperatureRequiredRange != null) {
        this.biomeTemperatureRequiredRanges.put(biome, this.globalTemperatureRequiredRange);
        found = this.globalTemperatureRequiredRange;
    }
    return found;
}
Also used : DoubleRange(com.almuradev.toolbox.util.math.DoubleRange) Biome(net.minecraft.world.biome.Biome) ResourceLocation(net.minecraft.util.ResourceLocation) FunctionPredicate(com.almuradev.content.component.predicate.FunctionPredicate) HashMap(java.util.HashMap) Map(java.util.Map) Nullable(javax.annotation.Nullable) Nullable(javax.annotation.Nullable)

Example 43 with Biome

use of net.minecraft.world.biome.Biome in project Almura by AlmuraDev.

the class Growth method getOrLoadChanceRangeForBiome.

@Nullable
public DoubleRange getOrLoadChanceRangeForBiome(final Biome biome) {
    @Nullable DoubleRange found = this.biomeChanceRanges.get(biome);
    if (found == null) {
        for (final Map.Entry<FunctionPredicate<Biome, ResourceLocation>, DoubleRange> entry : this.biomeChancePredicates.entrySet()) {
            final FunctionPredicate<Biome, ResourceLocation> predicate = entry.getKey();
            if (predicate.test(biome)) {
                final DoubleRange range = entry.getValue();
                this.biomeChanceRanges.put(biome, range);
                found = range;
                break;
            }
        }
    }
    if (found == null && this.globalChanceRange != null) {
        this.biomeChanceRanges.put(biome, this.globalChanceRange);
        found = this.globalChanceRange;
    }
    return found;
}
Also used : DoubleRange(com.almuradev.toolbox.util.math.DoubleRange) Biome(net.minecraft.world.biome.Biome) ResourceLocation(net.minecraft.util.ResourceLocation) FunctionPredicate(com.almuradev.content.component.predicate.FunctionPredicate) HashMap(java.util.HashMap) Map(java.util.Map) Nullable(javax.annotation.Nullable) Nullable(javax.annotation.Nullable)

Example 44 with Biome

use of net.minecraft.world.biome.Biome in project Almura by AlmuraDev.

the class MixinBlockTallGrass method getDrops.

/**
 * @author Zidane - Chris Sanders
 * @reason Add in content seeds to drop list for Tall Grass
 */
@Overwrite(remap = false)
public void getDrops(final NonNullList<ItemStack> drops, final IBlockAccess access, final BlockPos pos, final IBlockState state, final int fortune) {
    World world;
    if (access instanceof ChunkCache) {
        world = ((ChunkCache) access).world;
    } else if (access instanceof World) {
        world = (World) access;
    } else {
        return;
    }
    final Random random = world.rand;
    // Roll 1 is Vanilla's 1/8 chance to drop a seed
    final int roll1 = random.nextInt(8);
    if (roll1 == 0) {
        // Forge Start - Lookup seed each time and then do random check. Almura handles its own chance code
        final ItemStack modSeed = net.minecraftforge.common.ForgeHooks.getGrassSeed(random, fortune);
        if (!modSeed.isEmpty()) {
            drops.add(modSeed);
            // Don't double up with Vanilla/mod drops
            return;
        }
        final Biome biome = world.getBiome(pos);
        // Roll 2 is shuffling Almura seeds and picking the first one after shuffling
        registry.getAllOf(ItemType.class).stream().filter(itemType -> itemType instanceof SeedItem && ((SeedItem) itemType).getGrass() != null).collect(Collectors.collectingAndThen(Collectors.toList(), collected -> {
            Collections.shuffle(collected);
            return collected.stream();
        })).findFirst().ifPresent((itemType) -> {
            final SeedItem seed = (SeedItem) itemType;
            final IntRange amountRange = seed.getGrass().getOrLoadAmountRequiredRangeForBiome(biome);
            if (amountRange != null) {
                final int stackSize = amountRange.random(random);
                final DoubleRange chanceRange = seed.getGrass().getOrLoadChanceRangeForBiome(biome);
                if (chanceRange != null) {
                    final double chance = chanceRange.random(random);
                    // Roll 3 is allowing the seed configuration to determine the chance for the drop
                    if (random.nextDouble() <= (chance / 100)) {
                        drops.add((ItemStack) (Object) org.spongepowered.api.item.inventory.ItemStack.of(itemType, stackSize));
                    }
                } else {
                    drops.add((ItemStack) (Object) org.spongepowered.api.item.inventory.ItemStack.of(itemType, stackSize));
                }
            }
        });
    }
// Almura End
}
Also used : ChunkCache(net.minecraft.world.ChunkCache) World(net.minecraft.world.World) BlockPos(net.minecraft.util.math.BlockPos) Random(java.util.Random) Overwrite(org.spongepowered.asm.mixin.Overwrite) SeedItem(com.almuradev.content.type.item.type.seed.SeedItem) BlockTallGrass(net.minecraft.block.BlockTallGrass) Collectors(java.util.stream.Collectors) GameRegistry(org.spongepowered.api.GameRegistry) Inject(javax.inject.Inject) IBlockState(net.minecraft.block.state.IBlockState) ItemStack(net.minecraft.item.ItemStack) Mixin(org.spongepowered.asm.mixin.Mixin) MixinBlock(com.almuradev.content.type.block.mixin.impl.MixinBlock) DoubleRange(com.almuradev.toolbox.util.math.DoubleRange) NonNullList(net.minecraft.util.NonNullList) ItemType(org.spongepowered.api.item.ItemType) Collections(java.util.Collections) IntRange(com.almuradev.toolbox.util.math.IntRange) IBlockAccess(net.minecraft.world.IBlockAccess) Biome(net.minecraft.world.biome.Biome) ChunkCache(net.minecraft.world.ChunkCache) ItemType(org.spongepowered.api.item.ItemType) IntRange(com.almuradev.toolbox.util.math.IntRange) World(net.minecraft.world.World) SeedItem(com.almuradev.content.type.item.type.seed.SeedItem) DoubleRange(com.almuradev.toolbox.util.math.DoubleRange) Biome(net.minecraft.world.biome.Biome) Random(java.util.Random) ItemStack(net.minecraft.item.ItemStack) Overwrite(org.spongepowered.asm.mixin.Overwrite)

Example 45 with Biome

use of net.minecraft.world.biome.Biome in project Almura by AlmuraDev.

the class Grass method getOrLoadChanceRangeForBiome.

@Nullable
public DoubleRange getOrLoadChanceRangeForBiome(final Biome biome) {
    @Nullable DoubleRange found = this.biomeChanceRanges.get(biome);
    if (found == null) {
        for (final Map.Entry<FunctionPredicate<Biome, ResourceLocation>, DoubleRange> entry : this.biomeChancePredicates.entrySet()) {
            final FunctionPredicate<Biome, ResourceLocation> predicate = entry.getKey();
            if (predicate.test(biome)) {
                final DoubleRange range = entry.getValue();
                this.biomeChanceRanges.put(biome, range);
                found = range;
                break;
            }
        }
    }
    if (found == null && this.globalChanceRange != null) {
        this.biomeChanceRanges.put(biome, this.globalChanceRange);
        found = this.globalChanceRange;
    }
    return found;
}
Also used : DoubleRange(com.almuradev.toolbox.util.math.DoubleRange) Biome(net.minecraft.world.biome.Biome) ResourceLocation(net.minecraft.util.ResourceLocation) FunctionPredicate(com.almuradev.content.component.predicate.FunctionPredicate) HashMap(java.util.HashMap) Map(java.util.Map) Nullable(javax.annotation.Nullable) Nullable(javax.annotation.Nullable)

Aggregations

Biome (net.minecraft.world.biome.Biome)110 BlockPos (net.minecraft.util.math.BlockPos)39 IBlockState (net.minecraft.block.state.IBlockState)16 ResourceLocation (net.minecraft.util.ResourceLocation)9 World (net.minecraft.world.World)9 Nullable (javax.annotation.Nullable)8 Random (java.util.Random)7 ChunkPos (net.minecraft.util.math.ChunkPos)7 DoubleRange (com.almuradev.toolbox.util.math.DoubleRange)6 HashMap (java.util.HashMap)6 FunctionPredicate (com.almuradev.content.component.predicate.FunctionPredicate)5 Map (java.util.Map)5 Block (net.minecraft.block.Block)5 WorldServer (net.minecraft.world.WorldServer)5 BiomeChunk (com.almuradev.almura.feature.biome.BiomeChunk)4 Overwrite (org.spongepowered.asm.mixin.Overwrite)4 Entity (net.minecraft.entity.Entity)3 IntRange (com.almuradev.toolbox.util.math.IntRange)2 ArrayList (java.util.ArrayList)2 List (java.util.List)2