package net.knarcraft.blacksmith.util;

import net.knarcraft.blacksmith.config.SettingValueType;
import org.bukkit.Material;
import org.bukkit.enchantments.Enchantment;
import org.bukkit.enchantments.EnchantmentTarget;
import org.bukkit.inventory.ItemStack;
import org.bukkit.inventory.meta.Damageable;

import java.util.ArrayList;
import java.util.List;

/**
 * A helper class for getting valid values for tab-completion
 */
public final class TabCompleteValuesHelper {

    private TabCompleteValuesHelper() {

    }

    /**
     * Gets tab-completion values for the given value type
     *
     * @param valueType <p>The value type to get possible values for</p>
     * @return <p>The values to show the user</p>
     */
    public static List<String> getTabCompletions(SettingValueType valueType) {
        return switch (valueType) {
            case POSITIVE_INTEGER -> getPositiveIntegers();
            case BOOLEAN -> getBooleans();
            case POSITIVE_DOUBLE -> getPositiveDoubles();
            case STRING -> getStrings();
            case PERCENTAGE -> getPercentages();
            case STRING_LIST -> getReforgeAbleMaterials();
            case MATERIAL -> getAllReforgeAbleMaterials();
            case ENCHANTMENT -> getAllEnchantments();
        };
    }

    /**
     * Gets a complete list of all reforge-able materials
     *
     * @return <p>A complete list of reforge-able materials</p>
     */
    private static List<String> getAllReforgeAbleMaterials() {
        List<String> reforgeAbleMaterials = new ArrayList<>();
        for (Material material : Material.values()) {
            ItemStack item = new ItemStack(material);
            if (item.getItemMeta() instanceof Damageable && EnchantmentTarget.BREAKABLE.includes(item)) {
                reforgeAbleMaterials.add(material.name());
            }
        }
        return reforgeAbleMaterials;
    }

    /**
     * Gets a complete list of enchantments
     *
     * @return <p>A complete list of enchantments</p>
     */
    private static List<String> getAllEnchantments() {
        List<String> enchantments = new ArrayList<>();
        for (Enchantment enchantment : Enchantment.values()) {
            enchantments.add(enchantment.toString());
        }
        return enchantments;
    }

    /**
     * Gets some example possible values for reforge-able materials
     *
     * @return <p>Some example possible values for reforge-able materials</p>
     */
    private static List<String> getReforgeAbleMaterials() {
        List<String> stringLists = new ArrayList<>();
        stringLists.add("preset:sword-smith");
        stringLists.add("preset:weapon-smith");
        stringLists.add("preset:armor-smith");
        stringLists.add("preset:tool-smith");
        stringLists.add("preset:ranged-smith");
        stringLists.add("bow,crossbow,elytra");
        return stringLists;
    }

    /**
     * Gets some example string values
     *
     * @return <p>Some example string values</p>
     */
    private static List<String> getStrings() {
        List<String> strings = new ArrayList<>(1);
        strings.add("&aExample message. Use & for color tags.");
        return strings;
    }

    /**
     * Gets some example percentage values
     *
     * @return <p>Some example percentage values</p>
     */
    private static List<String> getPercentages() {
        List<String> percentages = new ArrayList<>(6);
        percentages.add("0");
        percentages.add("10");
        percentages.add("25");
        percentages.add("45");
        percentages.add("75");
        percentages.add("100");
        return percentages;
    }

    /**
     * Gets some possible positive doubles
     *
     * @return <p>Some possible positive doubles</p>
     */
    private static List<String> getPositiveDoubles() {
        List<String> positiveDoubles = new ArrayList<>(4);
        positiveDoubles.add("0.0");
        positiveDoubles.add("0.0001");
        positiveDoubles.add("5.0");
        positiveDoubles.add("7.34");
        positiveDoubles.add("5674.34534");
        return positiveDoubles;
    }

    /**
     * Gets some example positive integers
     *
     * @return <p>Some example positive integers</p>
     */
    private static List<String> getPositiveIntegers() {
        List<String> positiveIntegers = new ArrayList<>(6);
        positiveIntegers.add("0");
        positiveIntegers.add("5");
        positiveIntegers.add("10");
        positiveIntegers.add("25");
        positiveIntegers.add("50");
        positiveIntegers.add("100");
        positiveIntegers.add("4565");
        return positiveIntegers;
    }

    /**
     * Gets the possible boolean values
     *
     * @return <p>The possible boolean values</p>
     */
    private static List<String> getBooleans() {
        List<String> booleans = new ArrayList<>(2);
        booleans.add("True");
        booleans.add("False");
        return booleans;
    }

}
