package dev.crucifixbeta.api.utils.path;

import com.google.common.collect.Lists;
import dev.crucifixbeta.api.utils.Wrapper;
import java.util.ArrayList;
import java.util.List;
import net.fabricmc.api.EnvType;
import net.fabricmc.api.Environment;
import net.minecraft.network.packet.c2s.play.PlayerMoveC2SPacket.OnGroundOnly;
import net.minecraft.network.packet.c2s.play.PlayerMoveC2SPacket.PositionAndOnGround;
import net.minecraft.util.math.Vec3d;

@Environment(EnvType.CLIENT)
public class TPUtils implements Wrapper {
   public static void teleportWithBack(Vec3d newPos, TPUtils.TeleportType type, Runnable runnable) {
      switch (type) {
         case Legacy:
            legacyTeleportWithBack(newPos, runnable);
            break;
         case New:
            newTeleportWithBack(newPos, runnable);
      }
   }

   public static void legacyTeleportWithBack(Vec3d newPos, Runnable runnable) {
      ArrayList<Vec3> var2 = PathUtils.computePath(newPos);
      var2.removeFirst();
      var2.forEach(vec3 -> mc.player.networkHandler.sendPacket(new PositionAndOnGround(vec3.x(), vec3.y(), vec3.z(), false)));
      runnable.run();
      List<Vec3> var3 = Lists.reverse(var2);
      var3.removeFirst();
      var3.forEach(vec3 -> mc.player.networkHandler.sendPacket(new PositionAndOnGround(vec3.x(), vec3.y(), vec3.z(), false)));
      mc.player.networkHandler.sendPacket(new PositionAndOnGround(mc.player.getX(), mc.player.getY(), mc.player.getZ(), false));
   }

   public static void newTeleportWithBack(Vec3d newPos, Runnable runnable) {
      int var2 = (int)Math.ceil(mc.player.getPos().distanceTo(newPos) / 10.0) - 1;

      for (int var3 = 0; var3 < var2; var3++) {
         mc.player.networkHandler.sendPacket(new OnGroundOnly(true));
      }

      mc.player.networkHandler.sendPacket(new PositionAndOnGround(newPos.x, newPos.y, newPos.z, true));
      runnable.run();

      for (int var4 = 0; var4 < var2; var4++) {
         mc.player.networkHandler.sendPacket(new OnGroundOnly(true));
      }

      mc.player.networkHandler.sendPacket(new PositionAndOnGround(mc.player.getX(), mc.player.getY(), mc.player.getZ(), false));
   }

   public static void newTeleport(Vec3d newPos) {
      int var1 = (int)Math.ceil(mc.player.getPos().distanceTo(newPos) / 10.0) - 1;

      for (int var2 = 0; var2 < var1; var2++) {
         mc.player.networkHandler.sendPacket(new OnGroundOnly(true));
      }

      mc.player.networkHandler.sendPacket(new PositionAndOnGround(newPos.x, newPos.y, newPos.z, true));
   }

   @Environment(EnvType.CLIENT)
   public static enum TeleportType {
      Legacy,
      New;

}
}
