package net.minecraft.world.entity.ai.goal;

import net.minecraft.world.level.chunk.ChunkAccess;
import net.minecraft.world.level.chunk.ChunkStatus;
import javax.annotation.Nullable;
import net.minecraft.world.phys.Vec3;
import java.util.Random;
import net.minecraft.core.particles.SimpleParticleType;
import net.minecraft.core.particles.ItemParticleOption;
import net.minecraft.world.level.ItemLike;
import net.minecraft.world.item.ItemStack;
import net.minecraft.world.item.Items;
import net.minecraft.core.particles.ParticleTypes;
import net.minecraft.server.level.ServerLevel;
import net.minecraft.world.level.BlockGetter;
import net.minecraft.world.entity.Entity;
import net.minecraft.world.level.Level;
import net.minecraft.core.BlockPos;
import net.minecraft.world.level.LevelAccessor;
import net.minecraft.world.level.LevelReader;
import net.minecraft.world.level.GameRules;
import net.minecraft.world.entity.PathfinderMob;
import net.minecraft.world.entity.Mob;
import net.minecraft.world.level.block.Block;

public class RemoveBlockGoal extends MoveToBlockGoal {
    private final Block blockToRemove;
    private final Mob removerMob;
    private int ticksSinceReachedGoal;
    
    public RemoveBlockGoal(final Block bph, final PathfinderMob alg, final double double3, final int integer) {
        super(alg, double3, 24, integer);
        this.blockToRemove = bph;
        this.removerMob = alg;
    }
    
    @Override
    public boolean canUse() {
        if (!this.removerMob.level.getGameRules().getBoolean(GameRules.RULE_MOBGRIEFING)) {
            return false;
        }
        if (this.nextStartTick > 0) {
            --this.nextStartTick;
            return false;
        }
        if (this.tryFindBlock()) {
            this.nextStartTick = 20;
            return true;
        }
        this.nextStartTick = this.nextStartTick(this.mob);
        return false;
    }
    
    private boolean tryFindBlock() {
        return (this.blockPos != null && this.isValidTarget(this.mob.level, this.blockPos)) || this.findNearestBlock();
    }
    
    @Override
    public void stop() {
        super.stop();
        this.removerMob.fallDistance = 1.0f;
    }
    
    @Override
    public void start() {
        super.start();
        this.ticksSinceReachedGoal = 0;
    }
    
    public void playDestroyProgressSound(final LevelAccessor bjx, final BlockPos fk) {
    }
    
    public void playBreakSound(final Level bjw, final BlockPos fk) {
    }
    
    @Override
    public void tick() {
        super.tick();
        final Level bjw2 = this.removerMob.level;
        final BlockPos fk3 = new BlockPos(this.removerMob);
        final BlockPos fk4 = this.getPosWithBlock(fk3, bjw2);
        final Random random5 = this.removerMob.getRandom();
        if (this.isReachedTarget() && fk4 != null) {
            if (this.ticksSinceReachedGoal > 0) {
                final Vec3 cvl6 = this.removerMob.getDeltaMovement();
                this.removerMob.setDeltaMovement(cvl6.x, 0.3, cvl6.z);
                if (!bjw2.isClientSide) {
                    final double double7 = 0.08;
                    ((ServerLevel)bjw2).<ItemParticleOption>sendParticles(new ItemParticleOption(ParticleTypes.ITEM, new ItemStack(Items.EGG)), fk4.getX() + 0.5, fk4.getY() + 0.7, fk4.getZ() + 0.5, 3, (random5.nextFloat() - 0.5) * 0.08, (random5.nextFloat() - 0.5) * 0.08, (random5.nextFloat() - 0.5) * 0.08, 0.15000000596046448);
                }
            }
            if (this.ticksSinceReachedGoal % 2 == 0) {
                final Vec3 cvl6 = this.removerMob.getDeltaMovement();
                this.removerMob.setDeltaMovement(cvl6.x, -0.3, cvl6.z);
                if (this.ticksSinceReachedGoal % 6 == 0) {
                    this.playDestroyProgressSound(bjw2, this.blockPos);
                }
            }
            if (this.ticksSinceReachedGoal > 60) {
                bjw2.removeBlock(fk4, false);
                if (!bjw2.isClientSide) {
                    for (int integer6 = 0; integer6 < 20; ++integer6) {
                        final double double7 = random5.nextGaussian() * 0.02;
                        final double double8 = random5.nextGaussian() * 0.02;
                        final double double9 = random5.nextGaussian() * 0.02;
                        ((ServerLevel)bjw2).<SimpleParticleType>sendParticles(ParticleTypes.POOF, fk4.getX() + 0.5, fk4.getY(), fk4.getZ() + 0.5, 1, double7, double8, double9, 0.15000000596046448);
                    }
                    this.playBreakSound(bjw2, fk4);
                }
            }
            ++this.ticksSinceReachedGoal;
        }
    }
    
    @Nullable
    private BlockPos getPosWithBlock(final BlockPos fk, final BlockGetter bjg) {
        if (bjg.getBlockState(fk).getBlock() == this.blockToRemove) {
            return fk;
        }
        final BlockPos[] array;
        final BlockPos[] arr4 = array = new BlockPos[] { fk.below(), fk.west(), fk.east(), fk.north(), fk.south(), fk.below().below() };
        for (final BlockPos fk2 : array) {
            if (bjg.getBlockState(fk2).getBlock() == this.blockToRemove) {
                return fk2;
            }
        }
        return null;
    }
    
    @Override
    protected boolean isValidTarget(final LevelReader bjz, final BlockPos fk) {
        final ChunkAccess bzy4 = bjz.getChunk(fk.getX() >> 4, fk.getZ() >> 4, ChunkStatus.FULL, false);
        return bzy4 != null && bzy4.getBlockState(fk).getBlock() == this.blockToRemove && bzy4.getBlockState(fk.above()).isAir() && bzy4.getBlockState(fk.above(2)).isAir();
    }
}
