import {
    Entity,
    EntityComponentTypes,
    Player,
    StructureRotation,
    system,
    world,
} from "@minecraft/server";
import { ActionFormData, ModalFormData } from "@minecraft/server-ui";
import { Clowns, Entities } from "../entities/Entities";
import { placeCircusTent } from "../utils/utils";

export const playerConfigs = {
    fog_enabled: "fog_enabled",
};

export const worldConfigs = {
    hc_difficulty: "hc_difficulty",
};

export const Difficulty = {
    easy: "easy",
    normal: "normal",
    hard: "hard",
};

world.afterEvents.worldInitialize.subscribe(() => {
    if (world.getDynamicProperty(worldConfigs.hc_difficulty) == undefined) {
        world.setDynamicProperty(worldConfigs.hc_difficulty, Difficulty.medium);
    }
});

world.afterEvents.itemUse.subscribe((event) => {
    const { itemStack, source: player } = event;

    if (itemStack.typeId == "px_hc:configurator") {
        configurations(player);
    }
    if (itemStack.typeId == "minecraft:stick") {
        player.setDynamicProperty("spawn_sequence", 6);
    }
});

/**
 *
 * @param {Player} player
 */
function configurations(player) {
    const UI = new ModalFormData();

    const worldDifficulty = world.getDynamicProperty(worldConfigs.hc_difficulty);

    const difficulty = Object.keys(Difficulty).indexOf(worldDifficulty);

    if (player.getDynamicProperty(playerConfigs.fog_enabled) == undefined) {
        player.setDynamicProperty(playerConfigs.fog_enabled, true);
    }

    const fogEnabled = player.getDynamicProperty(playerConfigs.fog_enabled);

    UI.title("Configurations");
    UI.toggle("Fog", fogEnabled);
    UI.dropdown("Difficulty", Object.values(Difficulty), difficulty);
    UI.submitButton("Confirm");

    UI.show(player).then((response) => {
        const formValues = response.formValues;

        if (response.canceled) return;

        player.setDynamicProperty(playerConfigs.fog_enabled, formValues[0]);

        world.setDynamicProperty(
            worldConfigs.hc_difficulty,
            Object.values(Difficulty)[formValues[1]]
        );
    });
}

world.afterEvents.entitySpawn.subscribe((event) => {
    const { entity } = event;

    if (Object.values(Clowns).includes(entity.typeId)) {
        const worldDifficulty = world.getDynamicProperty(worldConfigs.hc_difficulty);

        if (worldDifficulty != undefined) {
            switch (worldDifficulty) {
                case Difficulty.easy: {
                    entity.triggerEvent("clown:difficulty_easy");
                    getHealth(entity);
                    break;
                }
                case Difficulty.normal: {
                    entity.triggerEvent("clown:difficulty_normal");
                    getHealth(entity);
                    break;
                }
                case Difficulty.hard: {
                    entity.triggerEvent("clown:difficulty_hard");
                    getHealth(entity);
                    break;
                }
            }
        }
    }
    if (entity instanceof Player) {
        if (entity.getDynamicProperty(playerConfigs.fog_enabled) == undefined) {
            entity.setDynamicProperty(playerConfigs.fog_enabled, true);
        }
    }
});

const DIFFICULTY_HANDLER = system.runInterval(() => {
    const entities = world.getAllPlayers()[0]?.dimension.getEntities() ?? [];

    for (let entity of entities) {
        if (Object.values(Clowns).includes(entity.typeId)) {
            const worldDifficulty = world.getDynamicProperty(worldConfigs.hc_difficulty);

            if (worldDifficulty != undefined) {
                switch (worldDifficulty) {
                    case Difficulty.easy: {
                        const clownDifficulty = entity.getProperty("clown:difficulty");

                        const currentHealth = getHealth(entity).currentValue;

                        if (clownDifficulty != worldDifficulty) {
                            entity.triggerEvent("clown:difficulty_easy");
                        }

                        break;
                    }
                    case Difficulty.normal: {
                        const clownDifficulty = entity.getProperty("clown:difficulty");

                        const currentHealth = getHealth(entity).currentValue;

                        if (clownDifficulty != worldDifficulty) {
                            entity.triggerEvent("clown:difficulty_normal");
                        }

                        break;
                    }
                    case Difficulty.hard: {
                        const clownDifficulty = entity.getProperty("clown:difficulty");

                        const currentHealth = getHealth(entity).currentValue;

                        if (clownDifficulty != worldDifficulty) {
                            entity.triggerEvent("clown:difficulty_hard");
                        }

                        break;
                    }
                }
            }
        }
    }
}, 0.5 * 20);

/**
 *
 * @param {Entity} entity
 */
function getHealth(entity) {
    const hp = entity.getComponent(EntityComponentTypes.Health);

    return hp;
}
