package net.minecraft.world.level.block; import com.mojang.serialization.MapCodec; import net.minecraft.core.BlockPos; import net.minecraft.core.particles.ParticleTypes; import net.minecraft.server.level.ServerLevel; import net.minecraft.sounds.SoundEvents; import net.minecraft.sounds.SoundSource; import net.minecraft.util.RandomSource; import net.minecraft.world.level.Level; import net.minecraft.world.level.LevelReader; import net.minecraft.world.level.block.state.BlockBehaviour; import net.minecraft.world.level.block.state.BlockState; import net.minecraft.world.level.levelgen.Heightmap; public class FireflyBushBlock extends VegetationBlock implements BonemealableBlock { private static final double FIREFLY_CHANCE_PER_TICK = 0.7; private static final double FIREFLY_HORIZONTAL_RANGE = 10.0; private static final double FIREFLY_VERTICAL_RANGE = 5.0; private static final int FIREFLY_SPAWN_MAX_BRIGHTNESS_LEVEL = 13; private static final int FIREFLY_AMBIENT_SOUND_CHANCE_ONE_IN = 30; public static final MapCodec CODEC = simpleCodec(FireflyBushBlock::new); public FireflyBushBlock(BlockBehaviour.Properties properties) { super(properties); } @Override protected MapCodec codec() { return CODEC; } @Override public void animateTick(BlockState state, Level level, BlockPos pos, RandomSource random) { if (random.nextInt(30) == 0 && level.isMoonVisible() && level.getHeight(Heightmap.Types.MOTION_BLOCKING_NO_LEAVES, pos) <= pos.getY()) { level.playLocalSound(pos, SoundEvents.FIREFLY_BUSH_IDLE, SoundSource.AMBIENT, 1.0F, 1.0F, false); } if (level.getMaxLocalRawBrightness(pos) <= 13 && random.nextDouble() <= 0.7) { double d = pos.getX() + random.nextDouble() * 10.0 - 5.0; double e = pos.getY() + random.nextDouble() * 5.0; double f = pos.getZ() + random.nextDouble() * 10.0 - 5.0; level.addParticle(ParticleTypes.FIREFLY, d, e, f, 0.0, 0.0, 0.0); } } @Override public boolean isValidBonemealTarget(LevelReader level, BlockPos pos, BlockState state) { return BonemealableBlock.hasSpreadableNeighbourPos(level, pos, state); } @Override public boolean isBonemealSuccess(Level level, RandomSource random, BlockPos pos, BlockState state) { return true; } @Override public void performBonemeal(ServerLevel level, RandomSource random, BlockPos pos, BlockState state) { BonemealableBlock.findSpreadableNeighbourPos(level, pos, state).ifPresent(blockPos -> level.setBlockAndUpdate(blockPos, this.defaultBlockState())); } }