import { world, system, BlockPermutation } from "@minecraft/server";

const PORTAL_BLOCK = "pa:portal_al_limbo";
const PORTAL_PARTICLE = "pa:rayos_al_limbo";

const SOUND_ENTER = "portal.travel";
const SOUND_LAMENT = "entity.ghast.scream";

const PARTICLE_INTERVAL = 40;
const TELEPORT_COOLDOWN = 80;

const cooldown = new Map();

function randomRange(min, max) {
  return Math.floor(Math.random() * (max - min + 1)) + min;
}

function pantallaNegra(player) {
  player.runCommandAsync("camera @p fade out 0.3 0.7 color 0 0 0");
  player.runCommandAsync("camera @p fade in 0.3 0.7");
}

function encontrarAlturaSegura(dim, x, z) {
  for (let y = 200; y > 10; y--) {
    const suelo = dim.getBlock({ x, y, z });
    const aire = dim.getBlock({ x, y: y + 1, z });

    if (!suelo || !aire) continue;

    if (suelo.typeId !== "minecraft:air" && aire.typeId === "minecraft:air") {
      return y + 1;
    }
  }
  return 90;
}

// Cooldown tick
system.runInterval(() => {
  for (const [id, time] of cooldown) {
    time <= 1 ? cooldown.delete(id) : cooldown.set(id, time - 1);
  }
}, 1);

// DETECCIÓN PORTAL
system.runInterval(() => {
  for (const player of world.getAllPlayers()) {
    if (cooldown.has(player.id)) continue;

    const dim = player.dimension;

    const px = Math.floor(player.location.x);
    const py = Math.floor(player.location.y);
    const pz = Math.floor(player.location.z);

    const block = dim.getBlock({ x: px, y: py, z: pz });
    if (!block || block.typeId !== PORTAL_BLOCK) continue;

    cooldown.set(player.id, TELEPORT_COOLDOWN);

    player.runCommandAsync(`playsound ${SOUND_ENTER} @p ~ ~ ~ 1 1`);
    pantallaNegra(player);

    system.runTimeout(() => {

      // OVERWORLD → LIMBO (END)
      if (dim.id === "minecraft:overworld") {
        const end = world.getDimension("minecraft:the_end");

        const x = randomRange(20000, 30000);
        const z = randomRange(20000, 30000);
        const y = encontrarAlturaSegura(end, x, z);

        end.getBlock({ x, y: y - 1, z })?.setPermutation(
          BlockPermutation.resolve("pa:hilwolr")
        );

        player.teleport(
          { x: x + 0.5, y, z: z + 0.5 },
          { dimension: end }
        );

        player.runCommandAsync(`playsound ${SOUND_LAMENT} @p ~ ~ ~ 1 0.8`);
      }

      // LIMBO → SPAWN
      else if (dim.id === "minecraft:the_end") {
        const spawn = player.getSpawnPoint();
        if (!spawn) return;

        player.teleport(
          { x: spawn.x + 0.5, y: spawn.y, z: spawn.z + 0.5 },
          { dimension: world.getDimension(spawn.dimension) }
        );

        player.runCommandAsync(`playsound ${SOUND_ENTER} @p ~ ~ ~ 0.8 0.9`);
      }

    }, 20);
  }
}, 1);

// PARTÍCULAS
system.runInterval(() => {
  for (const dim of world.getDimensions()) {
    for (const player of dim.getPlayers()) {
      const pos = {
        x: Math.floor(player.location.x),
        y: Math.floor(player.location.y),
        z: Math.floor(player.location.z)
      };

      const block = dim.getBlock(pos);
      if (block?.typeId === PORTAL_BLOCK) {
        dim.spawnParticle(PORTAL_PARTICLE, {
          x: block.location.x + 0.5,
          y: block.location.y + 0.5,
          z: block.location.z + 0.5
        });
      }
    }
  }
}, PARTICLE_INTERVAL);