package com.shanebeestudios.skbee.api.nbt;

import de.tr7zw.changeme.nbtapi.NBTCompound;
import de.tr7zw.changeme.nbtapi.NBTContainer;
import de.tr7zw.changeme.nbtapi.NBTItem;
import org.bukkit.inventory.ItemStack;
import org.jetbrains.annotations.Contract;
import org.jetbrains.annotations.NotNull;

/**
 * Wrapper class for {@link NBTItem} using a Bukkit {@link ItemStack}
 * <p>This is used due to a deprecation in NBTItem, as well as a protected constructor,
 * as well as funny changes in NBT-API due to MC 1.20.5</p>
 */
@SuppressWarnings("deprecation")
public class NBTCustomItemStack extends NBTContainer implements NBTCustom {

    private final ItemStack originalItemStack;
    private final boolean isFull;

    public NBTCustomItemStack(ItemStack itemStack, boolean isVanilla, boolean isFull) {
        super(getInitialContainer(itemStack, isVanilla, isFull).getCompound());
        this.originalItemStack = itemStack;
        this.isFull = isFull;
    }

    private static NBTCompound getInitialContainer(ItemStack itemStack, boolean isVanilla, boolean isFull) {
        NBTCompound nbtContainer;
        if (isVanilla) {
            nbtContainer = NBTReflection.getVanillaNBT(itemStack);
        } else {
            nbtContainer = NBTItem.convertItemtoNBT(itemStack);
        }
        if (nbtContainer == null) nbtContainer = new NBTContainer();
        // Create a clone (Minecraft seems to freak out without doing this)
        NBTCompound clone = new NBTContainer();
        clone.mergeCompound(getContainer(nbtContainer, isFull));
        return clone;
    }

    private static NBTCompound getContainer(NBTCompound itemContainer, boolean isFull) {
        if (isFull) {
            return itemContainer;
        }
        return itemContainer.getOrCreateCompound("components");
    }

    @Override
    protected void saveCompound() {
        super.saveCompound();
        if (this.isFull) return;
        NBTContainer originalItemContainer = NBTItem.convertItemtoNBT(this.originalItemStack.clone());
        NBTCompound components = getContainer(originalItemContainer, false);
        components.clearNBT();
        components.mergeCompound(this);
        ItemStack itemStack = NBTItem.convertNBTtoItem(originalItemContainer);
        if (itemStack == null) return;
        this.originalItemStack.setItemMeta(itemStack.getItemMeta());
    }

    public ItemStack getItem() {
        return this.originalItemStack.clone();
    }

    @Override
    public void deleteCustomNBT() {
        // Unused
    }

    @Override
    public @NotNull NBTCompound getCopy() {
        NBTContainer nbtContainer = new NBTContainer();
        nbtContainer.mergeCompound(this);
        return nbtContainer;
    }

    @Override
    @Contract("true -> !null")
    public NBTCompound getCustomNBT(boolean createTagIfMissing) {
        if (createTagIfMissing)
            return this.getOrCreateCompound("minecraft:custom_data");
        return this.getCompound("minecraft:custom_data");
    }

}
