import { BlockPermutation, ItemStack } from "@minecraft/server";
import { dimensionToHeight, doorManager, spawnItemAnywhere } from "./manager";
import { BlockPoweredEvent } from "../../Block Events/redstone";

const redstoneDoorEvent = new BlockPoweredEvent("gs_cb:powered", {
    onPower({ block }) {
        if (block.permutation.getState("gs_cb:open_bit") == true)
            return;
        doorManager.interactWithDoor(block);
    },
    onUnpowered({ block }) {
        const topHalf = block.permutation.getState("gs_cb:upper_block_bit");
        let doorPart = undefined;
        if (topHalf == false) {
            //gets the block above
            try {
                doorPart = block.above(1);
            }
            catch { }
        }
        else
            try {
                doorPart = block.below(1);
            }
            catch { } //gets the block below
        if (block.permutation.getState("gs_cb:open_bit") == false)
            return;
        if (doorPart && doorPart.hasTag(doorManager.doorTag) && doorPart.permutation.getState('gs_cb:powered') == true)
            return;
        doorManager.interactWithDoor(block);
    }
});
export class BlockComponentDoor {
    onTick = (data) => {
        redstoneDoorEvent.tick(data.block, data.dimension);
        const block = data.block;
        const doordata = doorManager.doors.find((f) => f.id == block.typeId);
        const topHalf = block.permutation.getState("gs_cb:upper_block_bit");
        let doorPart = undefined;
        if (topHalf == false) {
            //gets the block above
            try {
                doorPart = block.above(1);
            }
            catch { }
        }
        else
            try {
                doorPart = block.below(1);
            }
            catch { } //gets the block below
        if (doorPart == undefined) {
            if (topHalf == true) {
                block.setPermutation(BlockPermutation.resolve("minecraft:air"));
            }
            else {
                if (doordata) {
                    const item = new ItemStack(doordata.itemID, 1);
                    spawnItemAnywhere(item, block.location, block.dimension);
                }
                block.setPermutation(BlockPermutation.resolve("minecraft:air"));
            }
        }
        else if (!doorPart.hasTag(doorManager.doorTag)) {
            if (topHalf == true) {
                block.setPermutation(BlockPermutation.resolve("minecraft:air"));
            }
            else {
                if (doordata) {
                    const item = new ItemStack(doordata.itemID, 1);
                    spawnItemAnywhere(item, block.location, block.dimension);
                }
                block.setPermutation(BlockPermutation.resolve("minecraft:air"));
            }
        }
        else
            try {
                if (topHalf == true)
                    return;
                let below = undefined;
                below = block.below(1);
                if (below?.isAir || below?.isLiquid)
                    doorManager.breakDoor(block.typeId, block, false);
            }
            catch { }
    };
    //on interact with door
    onPlayerInteract = (data) => {
        //interact with the door

        const isMetalDoor = data.block.getTags().includes('gs_cb:metal_door');
        if(isMetalDoor){return;}

        doorManager.interactWithDoor(data.block);
    };
    //on place door
    beforeOnPlayerPlace = (data) => {
        const { block, player, dimension, permutationToPlace } = data;
        const loc = block.location;
        //if the aboveBlock location is higher than the max height of the dimension, cancel the placement
        if (loc.y + 1 >= dimensionToHeight(dimension.id)) {
            data.cancel = true;
            return;
        }
        let blockAbove = undefined;
        let blockBelow = undefined;
        try {
            blockBelow = dimension.getBlock({ x: loc.x, y: loc.y - 1, z: loc.z });
        }
        catch { }
        //if the below block is undefined, cancel the placement
        if (blockBelow == undefined) {
            data.cancel = true;
            return;
        }
        //if the belowBlock is air or liquid, cancel the placement
        if (blockBelow.isAir || blockBelow.isLiquid) {
            data.cancel = true;
            return;
        }
        try {
            blockAbove = dimension.getBlock({ x: loc.x, y: loc.y + 1, z: loc.z });
        }
        catch { }
        //if the above block is undefined, cancel the placement
        if (blockAbove == undefined) {
            data.cancel = true;
            return;
        }
        if ((blockAbove.isAir || blockAbove.isLiquid)) {
            doorManager.placeDoor(block, blockAbove, data.permutationToPlace);
        }
        else {
            //if the aboveBlock isn't air or liquid, cancel the placement
            data.cancel = true;
            return;
        }
    };
    constructor(doors) {
        for (const door of doors) {
            doorManager.doors.push(door);
        }
    }
}
