package asm.mixins;

import dev.crucifixbeta.CrucifixBeta;
import dev.crucifixbeta.api.events.impl.FireworkShooterRotationEvent;
import dev.crucifixbeta.api.events.impl.RemoveFireworkEvent;
import dev.crucifixbeta.api.utils.Wrapper;
import net.fabricmc.api.EnvType;
import net.fabricmc.api.Environment;
import net.minecraft.entity.LivingEntity;
import net.minecraft.entity.projectile.FireworkRocketEntity;
import net.minecraft.particle.ParticleTypes;
import net.minecraft.sound.SoundCategory;
import net.minecraft.sound.SoundEvents;
import net.minecraft.util.math.Vec3d;
import org.spongepowered.asm.mixin.Mixin;
import org.spongepowered.asm.mixin.Shadow;
import org.spongepowered.asm.mixin.injection.At;
import org.spongepowered.asm.mixin.injection.Inject;
import org.spongepowered.asm.mixin.injection.Redirect;
import org.spongepowered.asm.mixin.injection.At.Shift;
import org.spongepowered.asm.mixin.injection.callback.CallbackInfo;

@Environment(EnvType.CLIENT)
@Mixin({FireworkRocketEntity.class})
public class MixinFireworkRocketEntity implements Wrapper {
   @Shadow
   private int life;

   @Inject(
      method = {"tick"},
      at = {@At(
         value = "INVOKE",
         target = "Lnet/minecraft/entity/projectile/FireworkRocketEntity;updateRotation()V",
         shift = Shift.AFTER
      )},
      cancellable = true
   )
   private void hookTickPre(CallbackInfo ci) {
      FireworkRocketEntity var2 = FireworkRocketEntity.class.cast(this);
      RemoveFireworkEvent var3 = RemoveFireworkEvent.get(var2);
      CrucifixBeta.EVENT_BUS.post(var3);
      if (var3.isCancelled()) {
         ci.cancel();
         if (this.life == 0 && !var2.isSilent()) {
            mc.world.playSound(null, var2.getX(), var2.getY(), var2.getZ(), SoundEvents.ENTITY_FIREWORK_ROCKET_LAUNCH, SoundCategory.AMBIENT, 3.0F, 1.0F);
         }

         this.life++;
         if (mc.world.isClient) {
            mc.world
               .addParticle(
                  ParticleTypes.FIREWORK,
                  var2.getX(),
                  var2.getY(),
                  var2.getZ(),
                  mc.world.random.nextGaussian() * 0.05,
                  -var2.getVelocity().y * 0.5,
                  mc.world.random.nextGaussian() * 0.05
               );
         }
      }
   }

   @Redirect(
      method = {"tick"},
      at = @At(
         value = "INVOKE",
         target = "Lnet/minecraft/entity/LivingEntity;getRotationVector()Lnet/minecraft/util/math/Vec3d;"
      ),
      require = 0
   )
   public Vec3d hook(LivingEntity instance) {
      FireworkShooterRotationEvent var2 = FireworkShooterRotationEvent.get(instance, instance.getYaw(), instance.getPitch());
      CrucifixBeta.EVENT_BUS.post(var2);
      return var2.isCancelled() ? var2.getRotationVector() : instance.getRotationVector();
   }
}
