package xyz.tbvns.rogue_block.Managers;

import lombok.Data;
import net.minecraft.entity.LivingEntity;
import net.minecraft.nbt.NbtCompound;
import net.minecraft.registry.RegistryWrapper;
import net.minecraft.server.MinecraftServer;
import net.minecraft.server.network.ServerPlayerEntity;
import net.minecraft.world.PersistentState;
import net.minecraft.world.PersistentStateManager;
import net.minecraft.world.World;
import xyz.tbvns.rogue_block.Rogue_block;

import java.util.HashMap;
import java.util.UUID;

public class DataManager extends PersistentState {
    //Add thins here if i need global values someday
    //Useful doc: https://fabricmc.net/wiki/tutorial:persistent_states a bit outdated tho

    public HashMap<UUID, playerData> players = new HashMap<>();

    @Data
    public static class playerData {
        private int points = 0;

        public int addPoints(int amount) {
            points += amount;
            return points;
        }
    }

    @Override
    public NbtCompound writeNbt(NbtCompound nbt, RegistryWrapper.WrapperLookup registries) {
        NbtCompound playersNbt = new NbtCompound();
        players.forEach((uuid, playerData) -> {
            NbtCompound playerNbt = new NbtCompound();
            playerNbt.putInt("points", playerData.points);
            playersNbt.put(uuid.toString(), playerNbt);
        });
        nbt.put("players", playersNbt);
        return nbt;
    }

    public static DataManager createFromNbt(NbtCompound tag, RegistryWrapper.WrapperLookup registryLookup) {
        DataManager dataManager = new DataManager();
        NbtCompound playersNbt = tag.getCompound("players");
        playersNbt.getKeys().forEach(key -> {
            playerData playerData = new playerData();
            playerData.points = playersNbt.getCompound(key).getInt("points");
            UUID uuid = UUID.fromString(key);
            dataManager.players.put(uuid, playerData);
        });
        return dataManager;
    }

    public static playerData getPlayerState(LivingEntity player) {
        DataManager serverState = getServerState(player.getWorld().getServer());
        playerData playerState = serverState.players.computeIfAbsent(player.getUuid(), uuid -> new playerData());
        DataManager state = getServerState(player.getServer());
        state.markDirty();
        return playerState;
    }

    private static Type<DataManager> type = new Type<>(
            DataManager::new, // If there's no 'StateSaverAndLoader' yet create one
            DataManager::createFromNbt, // If there is a 'StateSaverAndLoader' NBT, parse it with 'createFromNbt'
            null // Supposed to be an 'DataFixTypes' enum, but we can just pass null
    );

    public static DataManager getServerState(MinecraftServer server) {
        PersistentStateManager persistentStateManager = server.getWorld(World.OVERWORLD).getPersistentStateManager();
        DataManager state = persistentStateManager.getOrCreate(type, Rogue_block.MOD_ID);
        state.markDirty();
        return state;
    }
}
