import { EquipmentSlot, EntityEquippableComponent, GameMode, system, ItemStack } from '@minecraft/server';
import { musicDiscs } from '../musicDisc/musicDiscs';
import { randomNum, randomWholeNum } from '../math/randomNumbers';
const states = [
    "moremusicdiscs:vanilla_disc_1",
    "moremusicdiscs:vanilla_disc_2",
    "moremusicdiscs:custom_disc_1"
];
export class jukeboxManager {
    static interactWithJukebox(block, player) {
        const dimension = block.dimension;
        const disc = this.getPlayingDisc(block.permutation);
        const center = block.center();
        if (!disc) {
            const mainhand = player.getComponent(EntityEquippableComponent.componentId).getEquipmentSlot(EquipmentSlot.Mainhand);
            if (!mainhand) return;
            const item = mainhand.getItem();
            if (!item) return;
            const discdata = musicDiscs[item.typeId];
            if (!discdata) return;
            if (player.getGameMode() != GameMode.creative) mainhand.setItem();
            dimension.playSound(discdata.sound.id, center, {
                volume: discdata.sound.volume
            });
            this.setDisc(block, item.typeId);
            this.getPlayersInRadius(center, dimension, 20).forEach((player)=>{
                player.onScreenDisplay.setActionBar(`§dNow Playing: ${discdata.musicName} - ${discdata.artist}`);
            });
            this.playNotes(block.location, dimension, item.typeId);
        } else {
            const players = this.getPlayersInRadius(center, block.dimension, 100);
            for (const player1 of players){
                if (player1.isValid()) player1.runCommand(`stopsound @s  ${disc.data.sound.id}`);
            }
            const item1 = new ItemStack(disc.id, 1);
            const itemEntity = this.spawnItemAnywhere(item1, {
                x: center.x,
                y: center.y + 0.5,
                z: center.z
            }, block.dimension);
            itemEntity.applyImpulse({
                x: randomNum(-0.2, 0.2),
                y: 0.2,
                z: randomNum(-0.2, 0.2)
            });
            this.clearDisc(block);
        }
    }
    static breakJukebox(data) {
        const { block , dimension , player , destroyedBlockPermutation  } = data;
        const playingDisc = this.getPlayingDisc(data.destroyedBlockPermutation);
        if (!playingDisc) return;
        const item = new ItemStack(playingDisc.id, 1);
        const center = block.center();
        const itemEntity = this.spawnItemAnywhere(item, {
            x: center.x,
            y: center.y,
            z: center.z
        }, block.dimension);
        itemEntity.applyImpulse({
            x: randomNum(-0.2, 0.2),
            y: 0.2,
            z: randomNum(-0.2, 0.2)
        });
        const players = this.getPlayersInRadius(center, block.dimension, 100);
        for (const player1 of players){
            if (player1.isValid()) player1.runCommand(`stopsound @s  ${playingDisc.data.sound.id}`);
        }
    }
    static getPlayingDisc(permutation) {
        let disc = undefined;
        for (const state of states){
            const data = permutation.getState(state);
            if (data != "none") {
                disc = {
                    id: data,
                    data: musicDiscs[data]
                };
                break;
            }
        }
        return disc;
    }
    static getPlayersInRadius(location, dimension, radius) {
        let players = [];
        players = dimension.getEntities({
            location: location,
            maxDistance: radius,
            type: "minecraft:player"
        });
        return players;
    }
    static spawnItemAnywhere(item, location, dimension) {
        const itemEntity = dimension.spawnItem(item, {
            x: location.x,
            y: 100,
            z: location.z
        });
        itemEntity.teleport(location);
        return itemEntity;
    }
    static clearDisc(block) {
        block.setPermutation(block.permutation.withState("moremusicdiscs:playing_disc", false));
        for (const state of states){
            block.setPermutation(block.permutation.withState(state, "none"));
        }
    }
    static setDisc(block, id) {
        for (const state of states){
            block.setPermutation(block.permutation.withState("moremusicdiscs:playing_disc", true));
            block.setPermutation(block.permutation.withState(state, id));
        }
    }
    static playNotes(location, dimension, playingID) {
        function tick() {
            const players = jukeboxManager.getPlayersInRadius(location, dimension, 30);
            if (players[0] != undefined) {
                let block = undefined;
                try {
                    block = dimension.getBlock(location);
                } catch  {}
                if (block == undefined) return;
                if (block.typeId != 'moremusicdiscs:jukebox') return;
                const playingDisc = jukeboxManager.getPlayingDisc(block.permutation);
                if (!playingDisc) return;
                if (playingDisc.id != playingID) return;
                const center = block.center();
                try {
                    dimension.spawnParticle("minecraft:note_particle", {
                        x: center.x,
                        y: center.y + 0.6,
                        z: center.z
                    });
                } catch  {}
            }
            let randomtick = randomWholeNum(10, 20);
            system.runTimeout(()=>{
                tick();
            }, randomtick);
        }
        tick();
    }
}
