// src/main/java/com/example/pVOPlugin/commands/AdminCommand.java
package com.example.pVOPlugin.commands;

import com.example.pVOPlugin.PVOPlugin;
import com.example.pVOPlugin.gui.TechnologyGUI;
import org.bukkit.command.Command;
import org.bukkit.command.CommandExecutor;
import org.bukkit.command.CommandSender;
import org.bukkit.command.TabCompleter;
import org.bukkit.entity.Player;

import java.util.Arrays;
import java.util.Collections;
import java.util.List;

public class AdminCommand implements CommandExecutor, TabCompleter {

    private final PVOPlugin plugin;

    public AdminCommand(PVOPlugin plugin) {
        this.plugin = plugin;
    }

    @Override
    public boolean onCommand(CommandSender sender, Command command, String label, String[] args) {

        if (!(sender instanceof Player)) {
            sender.sendMessage("§cЭта команда может быть использована только игроками.");
            return true;
        }

        Player player = (Player) sender;

        if (!player.hasPermission("pvoplugin.admin")) {
            player.sendMessage("§cУ вас нет прав для использования этой команды.");
            return true;
        }

        if (args.length < 1) {
            player.sendMessage("§cИспользование: /pvoadmin <opentechgui>");
            return true;
        }

        String subCommand = args[0].toLowerCase();

        if (subCommand.equals("opentechgui")) {
            switchTechnologyGUI(player);
            return true;
        }

        player.sendMessage("§cНеизвестная подкоманда.");
        return true;
    }

    private void switchTechnologyGUI(Player player) {
        TechnologyGUI techGUI = new TechnologyGUI(plugin, player, plugin.getTechnologyManager());
        techGUI.open();
    }

    @Override
    public List<String> onTabComplete(CommandSender sender, Command command, String alias, String[] args) {
        if (command.getName().equalsIgnoreCase("pvoadmin")) {
            if (args.length == 1) {
                return Arrays.asList("opentechgui");
            }
        }
        return Collections.emptyList();
    }
}
// src/main/java/com/example/pVOPlugin/commands/PVOCommand.java
package com.example.pVOPlugin.commands;

import com.example.pVOPlugin.PVOPlugin;
import com.example.pVOPlugin.managers.TechnologyManager;
import com.example.pVOPlugin.models.PVO;
import org.bukkit.Bukkit;
import org.bukkit.ChatColor;
import org.bukkit.Material;
import org.bukkit.command.*;
import org.bukkit.entity.Player;
import org.bukkit.inventory.ItemStack;
import org.bukkit.inventory.meta.ItemMeta;

import java.util.*;

public class PVOCommand implements CommandExecutor, TabCompleter {

    private final PVOPlugin plugin;

    public PVOCommand(PVOPlugin plugin) {
        this.plugin = plugin;
    }

    @Override
    public boolean onCommand(CommandSender sender, Command command, String label, String[] args) {

        if (command.getName().equalsIgnoreCase("givepvo")) {
            return handleGivePVO(sender, args);
        }

        if (command.getName().equalsIgnoreCase("pvo")) {
            return handlePVO(sender, args);
        }

        return false;
    }

    private boolean handleGivePVO(CommandSender sender, String[] args) {
        if (!(sender instanceof Player)) {
            sender.sendMessage("§cЭта команда может быть использована только игроками.");
            return true;
        }

        Player player = (Player) sender;

        if (args.length != 1) {
            player.sendMessage("§cИспользование: /givepvo <тип>");
            return true;
        }

        String type = args[0].toLowerCase();

        Material pvoMaterial;
        String displayName;

        switch (type) {
            case "km-1":
                pvoMaterial = Material.REDSTONE_BLOCK;
                displayName = ChatColor.AQUA + "PVO KM-1";
                break;
            case "km-2":
                pvoMaterial = Material.EMERALD_BLOCK;
                displayName = ChatColor.AQUA + "PVO KM-2";
                break;
            case "rtio-100":
                pvoMaterial = Material.DIAMOND_BLOCK;
                displayName = ChatColor.AQUA + "PVO RTIO-100";
                break;
            case "rtio-200":
                pvoMaterial = Material.GOLD_BLOCK;
                displayName = ChatColor.AQUA + "PVO RTIO-200";
                break;
            case "rtio-300":
                pvoMaterial = Material.IRON_BLOCK;
                displayName = ChatColor.AQUA + "PVO RTIO-300";
                break;
            default:
                player.sendMessage("§cНеизвестный тип PVO.");
                return true;
        }

        ItemStack pvoItem = new ItemStack(pvoMaterial);
        ItemMeta meta = pvoItem.getItemMeta();
        if (meta != null) {
            meta.setDisplayName(displayName);
            List<String> lore = new ArrayList<>();
            lore.add("§7Тип: " + type.toUpperCase());
            lore.add("§7Энергия: " + plugin.getConfigManager().getConfig().getInt("pvo.initial_energy", 1000));
            meta.setLore(lore);
            pvoItem.setItemMeta(meta);
        }

        player.getInventory().addItem(pvoItem);
        player.sendMessage("§aВы получили " + displayName + ".");
        return true;
    }

    private boolean handlePVO(CommandSender sender, String[] args) {
        if (!(sender instanceof Player)) {
            sender.sendMessage("§cЭта команда может быть использована только игроками.");
            return true;
        }

        Player player = (Player) sender;

        if (!player.hasPermission("pvoplugin.admin")) {
            player.sendMessage("§cУ вас нет прав для использования этой команды.");
            return true;
        }

        if (args.length < 1) {
            player.sendMessage("§cИспользование: /pvo <on|off|addenergy|exclude|research>");
            return true;
        }

        String subCommand = args[0].toLowerCase();

        TechnologyManager technologyManager = plugin.getTechnologyManager();

        switch (subCommand) {
            case "on":
                activatePVO(player, true);
                break;
            case "off":
                activatePVO(player, false);
                break;
            case "addenergy":
                if (args.length != 2) {
                    player.sendMessage("§cИспользование: /pvo addenergy <количество>");
                    return true;
                }
                try {
                    int amount = Integer.parseInt(args[1]);
                    promptEnergyInput(player, amount);
                } catch (NumberFormatException e) {
                    player.sendMessage("§cВведите корректное число.");
                }
                break;
            case "exclude":
                if (args.length != 2) {
                    player.sendMessage("§cИспользование: /pvo exclude <ник>");
                    return true;
                }
                String targetPlayer = args[1].toLowerCase();
                addExclusion(player, targetPlayer);
                break;
            case "research":
                if (args.length != 2) {
                    player.sendMessage("§cИспользование: /pvo research <технология>");
                    return true;
                }
                String techKey = args[1].toLowerCase();
                if (technologyManager.getTechnologies().containsKey(techKey)) {
                    promptResearchInput(player, techKey);
                } else {
                    player.sendMessage("§cТехнология не найдена.");
                }
                break;
            default:
                player.sendMessage("§cНеизвестная подкоманда.");
                break;
        }

        return true;
    }

    private void activatePVO(Player player, boolean activate) {
        // Активируем или деактивируем все PVO блоки
        for (PVO pvo : plugin.getPVOManager().getAllPVOs()) {
            pvo.setEnabled(activate);
        }
        plugin.getPVOManager().savePVOs();
        player.sendMessage("§aВсе PVO " + (activate ? "включены." : "выключены."));
    }

    private void promptEnergyInput(Player player, int amount) {
        // Запрос ввода через чат
        plugin.getTechnologyManager().promptAction(player, TechnologyManager.ActionType.ADD_ENERGY);
        // В данном примере добавляем количество как часть сообщения
        player.sendMessage(ChatColor.YELLOW + "Введите количество энергии для добавления через чат:");
    }

    private void addExclusion(Player player, String targetPlayer) {
        // Добавляем игрока в исключения всех PVO блоков
        for (PVO pvo : plugin.getPVOManager().getAllPVOs()) {
            pvo.addExclusion(targetPlayer);
        }
        plugin.getPVOManager().savePVOs();
        player.sendMessage("§aИгрок " + targetPlayer + " добавлен в исключения всех PVO.");
    }

    private void promptResearchInput(Player player, String techKey) {
        // Запрос ввода технологии для исследования через чат
        plugin.getTechnologyManager().promptAction(player, TechnologyManager.ActionType.RESEARCH_TECHNOLOGY);
        player.sendMessage(ChatColor.YELLOW + "Введите название технологии для исследования через чат:");
    }

    @Override
    public List<String> onTabComplete(CommandSender sender, Command command, String alias, String[] args) {
        if (command.getName().equalsIgnoreCase("givepvo")) {
            if (args.length == 1) {
                return Arrays.asList("km-1", "km-2", "rtio-100", "rtio-200", "rtio-300");
            }
        }

        if (command.getName().equalsIgnoreCase("pvo")) {
            if (args.length == 1) {
                return Arrays.asList("on", "off", "addenergy", "exclude", "research");
            }
            if (args.length == 2) {
                if (args[0].equalsIgnoreCase("exclude")) {
                    // Возвращаем список онлайн игроков
                    List<String> players = new ArrayList<>();
                    for (Player p : Bukkit.getOnlinePlayers()) {
                        players.add(p.getName());
                    }
                    return players;
                }
                if (args[0].equalsIgnoreCase("research")) {
                    // Возвращаем список доступных технологий
                    return new ArrayList<>(plugin.getTechnologyManager().getTechnologies().keySet());
                }
            }
        }

        return Collections.emptyList();
    }
}
// src/main/java/com/example/pVOPlugin/gui/PVOGUI.java
package com.example.pVOPlugin.gui;

import com.example.pVOPlugin.PVOPlugin;
import com.example.pVOPlugin.managers.TechnologyManager;
import com.example.pVOPlugin.models.PVO;
import org.bukkit.Bukkit;
import org.bukkit.ChatColor;
import org.bukkit.Material;
import org.bukkit.entity.Player;
import org.bukkit.event.inventory.InventoryClickEvent;
import org.bukkit.inventory.*;
import org.bukkit.inventory.meta.ItemMeta;

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

public class PVOGUI {

    private final PVOPlugin plugin;
    private final Player player;
    private final PVO pvo;
    private final Inventory inventory;

    public PVOGUI(PVOPlugin plugin, Player player, PVO pvo) {
        this.plugin = plugin;
        this.player = player;
        this.pvo = pvo;
        this.inventory = Bukkit.createInventory(null, 27, ChatColor.RED + "Настройки PVO");
        initializeGUI();
    }

    private void initializeGUI() {
        // Заполняем все слоты серыми стеклами
        ItemStack filler = createItem(Material.GRAY_STAINED_GLASS_PANE, " ");
        for (int i = 0; i < inventory.getSize(); i++) {
            inventory.setItem(i, filler);
        }

        // Кнопка включения/выключения
        ItemStack toggleItem = new ItemStack(pvo.isEnabled() ? Material.LIME_WOOL : Material.RED_WOOL);
        ItemMeta toggleMeta = toggleItem.getItemMeta();
        if (toggleMeta != null) {
            toggleMeta.setDisplayName(ChatColor.GREEN + (pvo.isEnabled() ? "Выключить PVO" : "Включить PVO"));
            toggleItem.setItemMeta(toggleMeta);
            inventory.setItem(11, toggleItem);
        }

        // Кнопка добавления энергии
        ItemStack energyItem = new ItemStack(Material.GLOWSTONE_DUST);
        ItemMeta energyMeta = energyItem.getItemMeta();
        if (energyMeta != null) {
            energyMeta.setDisplayName(ChatColor.YELLOW + "Добавить энергию");
            List<String> lore = new ArrayList<>();
            lore.add(ChatColor.GRAY + "Текущая энергия: " + pvo.getEnergy());
            energyMeta.setLore(lore);
            energyItem.setItemMeta(energyMeta);
            inventory.setItem(13, energyItem);
        }

        // Кнопка управления исключениями
        ItemStack excludeItem = new ItemStack(Material.PLAYER_HEAD);
        ItemMeta excludeMeta = excludeItem.getItemMeta();
        if (excludeMeta != null) {
            excludeMeta.setDisplayName(ChatColor.BLUE + "Управление исключениями");
            List<String> lore = new ArrayList<>();
            lore.add(ChatColor.GRAY + "Исключено игроков: " + pvo.getExclusions().size());
            excludeMeta.setLore(lore);
            excludeItem.setItemMeta(excludeMeta);
            inventory.setItem(15, excludeItem);
        }

        // Кнопка открытия технологического прогресса
        ItemStack techItem = new ItemStack(Material.BOOK);
        ItemMeta techMeta = techItem.getItemMeta();
        if (techMeta != null) {
            techMeta.setDisplayName(ChatColor.GOLD + "Технологический Прогресс");
            techMeta.setLore(List.of(ChatColor.GRAY + "Управляйте исследованиями и улучшениями."));
            techItem.setItemMeta(techMeta);
            inventory.setItem(22, techItem);
        }

        // Кнопка закрытия GUI
        ItemStack closeButton = new ItemStack(Material.BARRIER);
        ItemMeta closeMeta = closeButton.getItemMeta();
        if (closeMeta != null) {
            closeMeta.setDisplayName(ChatColor.RED + "Закрыть");
            closeButton.setItemMeta(closeMeta);
            inventory.setItem(26, closeButton);
        }
    }

    private ItemStack createItem(Material material, String name) {
        ItemStack item = new ItemStack(material);
        ItemMeta meta = item.getItemMeta();
        if (meta != null) {
            meta.setDisplayName(name);
            item.setItemMeta(meta);
        }
        return item;
    }

    public Inventory getInventory() {
        return inventory;
    }

    public void open() {
        player.openInventory(inventory);
    }

    public void handleClick(InventoryClickEvent event) {
        if (!event.getInventory().equals(inventory)) return;

        event.setCancelled(true);
        ItemStack clicked = event.getCurrentItem();

        if (clicked == null || clicked.getType() == Material.AIR) return;

        switch (clicked.getType()) {
            case LIME_WOOL:
            case RED_WOOL:
                togglePVO();
                break;
            case GLOWSTONE_DUST:
                promptEnergyInput();
                break;
            case PLAYER_HEAD:
                manageExclusions();
                break;
            case BOOK:
                openTechnologyGUI();
                break;
            case BARRIER:
                player.closeInventory();
                break;
            default:
                break;
        }
    }

    private void togglePVO() {
        pvo.setEnabled(!pvo.isEnabled());
        plugin.getPVOManager().addPVO(pvo.getLocation(), pvo);
        plugin.getPVOManager().savePVOs();

        player.sendMessage(ChatColor.GREEN + "PVO " + (pvo.isEnabled() ? "включено." : "выключено."));
        // Обновляем GUI
        initializeGUI();
        player.openInventory(inventory);
    }

    private void promptEnergyInput() {
        // Запрос ввода через чат
        plugin.getTechnologyManager().promptAction(player, TechnologyManager.ActionType.ADD_ENERGY);
        // В данном примере добавляем количество как часть сообщения
        player.sendMessage(ChatColor.YELLOW + "Введите количество энергии для добавления через чат:");
    }

    private void manageExclusions() {
        player.sendMessage(ChatColor.BLUE + "Введите ник игрока через команду /pvo exclude <ник>");
    }

    private void openTechnologyGUI() {
        // Открываем технологический GUI
        plugin.getTechnologyManager().openTechnologyGUI(player);
    }

    public void update() {
        initializeGUI();
        player.openInventory(inventory);
    }
}
// src/main/java/com/example/pVOPlugin/gui/TechnologyGUI.java
package com.example.pVOPlugin.gui;

import com.example.pVOPlugin.PVOPlugin;
import com.example.pVOPlugin.managers.TechnologyManager;
import com.example.pVOPlugin.managers.TechnologyManager.Technology;
import org.bukkit.Bukkit;
import org.bukkit.ChatColor;
import org.bukkit.Material;
import org.bukkit.entity.Player;
import org.bukkit.event.inventory.InventoryClickEvent;
import org.bukkit.inventory.Inventory;
import org.bukkit.inventory.ItemStack;
import org.bukkit.inventory.meta.ItemMeta;

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

public class TechnologyGUI {

    private final PVOPlugin plugin;
    private final Player player;
    private final TechnologyManager technologyManager;
    private final Inventory inventory;

    public TechnologyGUI(PVOPlugin plugin, Player player, TechnologyManager technologyManager) {
        this.plugin = plugin;
        this.player = player;
        this.technologyManager = technologyManager;
        this.inventory = Bukkit.createInventory(null, 54, ChatColor.GOLD + "Технологический Прогресс");
        initializeGUI();
    }

    private void initializeGUI() {
        // Заполняем все слоты серыми стеклами
        ItemStack filler = createItem(Material.BLACK_STAINED_GLASS_PANE, " ");
        for (int i = 0; i < inventory.getSize(); i++) {
            inventory.setItem(i, filler);
        }

        // Получаем доступные технологии
        Map<String, Technology> technologies = technologyManager.getTechnologies();

        int slot = 10; // Начальный слот для технологий

        for (Technology tech : technologies.values()) {
            ItemStack techItem = new ItemStack(Material.ENCHANTED_BOOK);
            ItemMeta techMeta = techItem.getItemMeta();
            if (techMeta != null) {
                techMeta.setDisplayName(ChatColor.GOLD + tech.getName());
                List<String> lore = new ArrayList<>();
                lore.add(ChatColor.GRAY + tech.getDescription());
                lore.add("");
                lore.add(ChatColor.GREEN + "Стоимость: " + tech.getCost() + " энергии");
                lore.add(ChatColor.YELLOW + "Вероятность успеха: " + tech.getSuccessRate() + "%");
                techMeta.setLore(lore);
                techItem.setItemMeta(techMeta);
            }
            inventory.setItem(slot, techItem);
            slot += 2; // Размещаем через слот для эстетики
        }

        // Кнопка закрытия GUI
        ItemStack closeButton = new ItemStack(Material.BARRIER);
        ItemMeta closeMeta = closeButton.getItemMeta();
        if (closeMeta != null) {
            closeMeta.setDisplayName(ChatColor.RED + "Закрыть");
            closeButton.setItemMeta(closeMeta);
            inventory.setItem(53, closeButton);
        }
    }

    private ItemStack createItem(Material material, String name) {
        ItemStack item = new ItemStack(material);
        ItemMeta meta = item.getItemMeta();
        if (meta != null) {
            meta.setDisplayName(name);
            item.setItemMeta(meta);
        }
        return item;
    }

    public Inventory getInventory() {
        return inventory;
    }

    public void open() {
        player.openInventory(inventory);
    }

    public void handleClick(InventoryClickEvent event) {
        if (!event.getInventory().equals(inventory)) return;

        event.setCancelled(true);
        ItemStack clicked = event.getCurrentItem();

        if (clicked == null || clicked.getType() == Material.AIR) return;

        switch (clicked.getType()) {
            case ENCHANTED_BOOK:
                researchTechnology(clicked);
                break;
            case BARRIER:
                player.closeInventory();
                break;
            default:
                break;
        }
    }

    private void researchTechnology(ItemStack item) {
        String techName = ChatColor.stripColor(item.getItemMeta().getDisplayName()).toLowerCase();
        technologyManager.promptAction(player, TechnologyManager.ActionType.RESEARCH_TECHNOLOGY);
        player.sendMessage(ChatColor.YELLOW + "Введите название технологии для исследования через чат:");
    }
}
// src/main/java/com/example/pVOPlugin/listeners/BlockPlaceListener.java
package com.example.pVOPlugin.listeners;

import com.example.pVOPlugin.PVOPlugin;
import com.example.pVOPlugin.models.PVO;
import org.bukkit.ChatColor;
import org.bukkit.Material;
import org.bukkit.block.Block;
import org.bukkit.entity.Player;
import org.bukkit.event.EventHandler;
import org.bukkit.event.Listener;
import org.bukkit.event.block.BlockPlaceEvent;
import org.bukkit.configuration.file.FileConfiguration;

import java.util.HashSet;

public class BlockPlaceListener implements Listener {

    private final PVOPlugin plugin;

    public BlockPlaceListener(PVOPlugin plugin) {
        this.plugin = plugin;
    }

    @EventHandler
    public void onBlockPlace(BlockPlaceEvent event) {
        Player player = event.getPlayer();
        Block block = event.getBlockPlaced();

        // Проверяем, является ли размещённый блок PVO
        if (isPVOBlock(block.getType())) {
            FileConfiguration config = plugin.getConfigManager().getConfig();
            int initialEnergy = config.getInt("pvo.initial_energy", 1000);
            String type = getPVOType(block.getType());

            PVO pvo = new PVO(block.getLocation(), true, initialEnergy, new HashSet<>(), type, 1);
            plugin.getPVOManager().addPVO(block.getLocation(), pvo);
            plugin.getPVOManager().savePVOs();
            player.sendMessage(ChatColor.GREEN + "PVO размещено и сохранено.");
        }
    }

    private boolean isPVOBlock(Material type) {
        return type == Material.REDSTONE_BLOCK ||
                type == Material.EMERALD_BLOCK ||
                type == Material.DIAMOND_BLOCK ||
                type == Material.GOLD_BLOCK ||
                type == Material.IRON_BLOCK;
    }

    private String getPVOType(Material type) {
        switch (type) {
            case REDSTONE_BLOCK:
                return "km-1";
            case EMERALD_BLOCK:
                return "km-2";
            case DIAMOND_BLOCK:
                return "rtio-100";
            case GOLD_BLOCK:
                return "rtio-200";
            case IRON_BLOCK:
                return "rtio-300";
            default:
                return "unknown";
        }
    }
}
// src/main/java/com/example/pVOPlugin/listeners/ChatListener.java
package com.example.pVOPlugin.listeners;

import com.example.pVOPlugin.PVOPlugin;
import org.bukkit.event.EventHandler;
import org.bukkit.event.Listener;
import org.bukkit.event.player.AsyncPlayerChatEvent;

public class ChatListener implements Listener {

    private final PVOPlugin plugin;

    public ChatListener(PVOPlugin plugin) {
        this.plugin = plugin;
    }

    @EventHandler
    public void onPlayerChat(AsyncPlayerChatEvent event) {
        // Передаём событие в TechnologyManager для обработки
        plugin.getTechnologyManager().handleChatInput(event);
    }
}
// src/main/java/com/example/pVOPlugin/listeners/EnergyInputListener.java
package com.example.pVOPlugin.listeners;

import com.example.pVOPlugin.PVOPlugin;
import org.bukkit.event.EventHandler;
import org.bukkit.event.Listener;
import org.bukkit.event.player.AsyncPlayerChatEvent;

public class EnergyInputListener implements Listener {

    private final PVOPlugin plugin;

    public EnergyInputListener(PVOPlugin plugin) {
        this.plugin = plugin;
    }

    @EventHandler
    public void onPlayerChat(AsyncPlayerChatEvent event) {
        // Обработка вводов пользователей происходит в TechnologyManager через главный класс
        // Этот класс может быть оставлен пустым или использоваться для дополнительных проверок
    }
}
// src/main/java/com/example/pVOPlugin/listeners/ExclusionInputListener.java
package com.example.pVOPlugin.listeners;

import com.example.pVOPlugin.PVOPlugin;
import org.bukkit.event.EventHandler;
import org.bukkit.event.Listener;
import org.bukkit.event.player.AsyncPlayerChatEvent;

public class ExclusionInputListener implements Listener {

    private final PVOPlugin plugin;

    public ExclusionInputListener(PVOPlugin plugin) {
        this.plugin = plugin;
    }

    @EventHandler
    public void onPlayerChat(AsyncPlayerChatEvent event) {
        // Обработка вводов пользователей происходит в TechnologyManager через главный класс
        // Этот класс может быть оставлен пустым или использоваться для дополнительных проверок
    }
}
// src/main/java/com/example/pVOPlugin/listeners/GUIListener.java
package com.example.pVOPlugin.listeners;

import com.example.pVOPlugin.gui.*;
import com.example.pVOPlugin.PVOPlugin;
import com.example.pVOPlugin.models.PVO;
import org.bukkit.ChatColor;
import org.bukkit.event.EventHandler;
import org.bukkit.event.Listener;
import org.bukkit.event.inventory.InventoryClickEvent;

public class GUIListener implements Listener {

    private final PVOPlugin plugin;

    public GUIListener(PVOPlugin plugin) {
        this.plugin = plugin;
    }

    @EventHandler
    public void onInventoryClick(InventoryClickEvent event) {
        String title = event.getView().getTitle();
        if (title.equals(ChatColor.RED + "Настройки PVO")) {
            if (event.getWhoClicked() instanceof org.bukkit.entity.Player) {
                org.bukkit.entity.Player player = (org.bukkit.entity.Player) event.getWhoClicked();
                // Находим PVO, связанный с этим GUI
                for (PVO pvo : plugin.getPVOManager().getAllPVOs()) {
                    PVOGUI gui = plugin.getPVOManager().getPVO(pvo.getLocation()) != null ? new PVOGUI(plugin, player, pvo) : null;
                    if (gui != null && event.getInventory().equals(gui.getInventory())) {
                        gui.handleClick(event);
                        break;
                    }
                }
            }
        }

        if (title.equals(ChatColor.GOLD + "Технологический Прогресс")) {
            if (event.getWhoClicked() instanceof org.bukkit.entity.Player) {
                org.bukkit.entity.Player player = (org.bukkit.entity.Player) event.getWhoClicked();
                // Здесь можно добавить логику обработки кликов в технологическом GUI
                // Например, исследование технологий при клике на соответствующий предмет
                event.setCancelled(true);
                // Реализуйте дальнейшую логику по необходимости
            }
        }
    }
}
// src/main/java/com/example/pVOPlugin/listeners/PlayerInteractListener.java
package com.example.pVOPlugin.listeners;

import com.example.pVOPlugin.PVOPlugin;
import com.example.pVOPlugin.gui.PVOGUI;
import com.example.pVOPlugin.models.PVO;
import org.bukkit.Material;
import org.bukkit.block.Block;
import org.bukkit.entity.Player;
import org.bukkit.event.EventHandler;
import org.bukkit.event.Listener;
import org.bukkit.event.player.PlayerInteractEvent;
import org.bukkit.inventory.EquipmentSlot;

public class PlayerInteractListener implements Listener {

    private final PVOPlugin plugin;

    public PlayerInteractListener(PVOPlugin plugin) {
        this.plugin = plugin;
    }

    @EventHandler
    public void onPlayerInteract(PlayerInteractEvent event) {
        // Проверяем, что игрок нажал правой кнопкой мыши на блок
        if (!event.hasBlock() || !isRightClick(event.getAction())) return;

        // Проверяем, что используется главная рука
        if (event.getHand() != EquipmentSlot.HAND) return;

        Player player = event.getPlayer();
        Block block = event.getClickedBlock();

        if (block == null) return;

        // Проверяем, является ли блок PVO
        if (isPVOBlock(block.getType())) {
            // Проверяем, что игрок приседает
            if (player.isSneaking()) {
                PVO pvo = plugin.getPVOManager().getPVO(block.getLocation());
                if (pvo != null) {
                    PVOGUI gui = new PVOGUI(plugin, player, pvo);
                    gui.open();
                    event.setCancelled(true);
                }
            }
        }
    }

    private boolean isRightClick(org.bukkit.event.block.Action action) {
        return action == org.bukkit.event.block.Action.RIGHT_CLICK_BLOCK || action == org.bukkit.event.block.Action.RIGHT_CLICK_AIR;
    }

    private boolean isPVOBlock(Material type) {
        return type == Material.REDSTONE_BLOCK ||
                type == Material.EMERALD_BLOCK ||
                type == Material.DIAMOND_BLOCK ||
                type == Material.GOLD_BLOCK ||
                type == Material.IRON_BLOCK;
    }
}
// src/main/java/com/example/pVOPlugin/listeners/PlayerMoveListener.java
package com.example.pVOPlugin.listeners;

import com.example.pVOPlugin.PVOPlugin;
import com.example.pVOPlugin.models.PVO;
import org.bukkit.Bukkit;
import org.bukkit.Location;
import org.bukkit.Particle;
import org.bukkit.entity.Player;
import org.bukkit.event.Listener;
import org.bukkit.potion.PotionEffect;
import org.bukkit.potion.PotionEffectType;
import org.bukkit.scheduler.BukkitRunnable;

import java.util.Collection;

public class PlayerMoveListener implements Listener {

    private final PVOPlugin plugin;

    public PlayerMoveListener(PVOPlugin plugin) {
        this.plugin = plugin;
        startEffectTask();
    }

    private void startEffectTask() {
        new BukkitRunnable() {
            @Override
            public void run() {
                Collection<PVO> pvos = plugin.getPVOManager().getAllPVOs();
                for (PVO pvo : pvos) {
                    if (!pvo.isEnabled()) continue;

                    Location loc = pvo.getLocation();
                    double radius = plugin.getConfigManager().getConfig().getDouble("pvo.radius", 10.0) + (pvo.getLevel() * 2); // Радиус увеличивается с уровнем

                    for (Player player : Bukkit.getOnlinePlayers()) {
                        if (!player.getWorld().equals(loc.getWorld())) continue;

                        double distance = player.getLocation().distance(loc);
                        if (distance <= radius) {
                            if (!pvo.getExclusions().contains(player.getName().toLowerCase())) {
                                if (pvo.getEnergy() >= plugin.getConfigManager().getConfig().getInt("pvo.energy_cost", 10)) {
                                    player.addPotionEffect(new PotionEffect(PotionEffectType.WITHER, 60, 1), true);
                                    pvo.removeEnergy(plugin.getConfigManager().getConfig().getInt("pvo.energy_cost", 10));
                                    showEffect(loc);
                                    plugin.getPVOManager().addPVO(loc, pvo);
                                }
                            }
                        }
                    }
                }
                plugin.getPVOManager().savePVOs();
            }
        }.runTaskTimer(plugin, 0L, 20L); // Запуск каждую секунду
    }

    private void showEffect(Location loc) {
        loc.getWorld().spawnParticle(Particle.SMOKE_NORMAL, loc, 10, 1, 1, 1, 0.1);
    }
}
// src/main/java/com/example/pVOPlugin/listeners/TechnologyGUIListener.java
package com.example.pVOPlugin.listeners;

import com.example.pVOPlugin.PVOPlugin;
import com.example.pVOPlugin.managers.TechnologyManager;
import org.bukkit.ChatColor;
import org.bukkit.Material;
import org.bukkit.event.EventHandler;
import org.bukkit.event.Listener;
import org.bukkit.event.inventory.InventoryClickEvent;
import org.bukkit.inventory.ItemStack;

public class TechnologyGUIListener implements Listener {

    private final PVOPlugin plugin;

    public TechnologyGUIListener(PVOPlugin plugin) {
        this.plugin = plugin;
    }

    @EventHandler
    public void onTechnologyGUIClick(InventoryClickEvent event) {
        String title = event.getView().getTitle();
        if (title.equals(ChatColor.GOLD + "Технологический Прогресс")) {
            if (!(event.getWhoClicked() instanceof org.bukkit.entity.Player)) return;

            org.bukkit.entity.Player player = (org.bukkit.entity.Player) event.getWhoClicked();
            ItemStack clicked = event.getCurrentItem();

            if (clicked == null || clicked.getType() == Material.AIR) return;

            if (clicked.getType() == Material.ENCHANTED_BOOK) {
                // Получаем название технологии
                String techName = ChatColor.stripColor(clicked.getItemMeta().getDisplayName()).toLowerCase();
                // Запрашиваем подтверждение исследования
                plugin.getTechnologyManager().promptAction(player, TechnologyManager.ActionType.RESEARCH_TECHNOLOGY);
                player.sendMessage(ChatColor.YELLOW + "Введите название технологии для исследования через чат:");
                event.setCancelled(true);
            }

            if (clicked.getType() == Material.BARRIER) {
                player.closeInventory();
            }
        }
    }
}
// src/main/java/com/example/pVOPlugin/managers/ConfigManager.java
package com.example.pVOPlugin.managers;

import com.example.pVOPlugin.PVOPlugin;
import org.bukkit.configuration.file.FileConfiguration;
import org.bukkit.configuration.file.YamlConfiguration;

import java.io.File;
import java.io.IOException;

public class ConfigManager {
    private final PVOPlugin plugin;
    private File configFile;
    private FileConfiguration config;

    public ConfigManager(PVOPlugin plugin) {
        this.plugin = plugin;
    }

    public void setup() {
        if (!plugin.getDataFolder().exists()) {
            plugin.getDataFolder().mkdirs();
        }

        configFile = new File(plugin.getDataFolder(), "config.yml");
        if (!configFile.exists()) {
            plugin.saveResource("config.yml", false);
        }

        config = YamlConfiguration.loadConfiguration(configFile);
    }

    public FileConfiguration getConfig() {
        return config;
    }

    public void saveConfigFile() {
        try {
            config.save(configFile);
        } catch (IOException e) {
            plugin.getLogger().severe("Не удалось сохранить config.yml!");
            e.printStackTrace();
        }
    }

    public void reloadConfigFile() {
        config = YamlConfiguration.loadConfiguration(configFile);
    }
}
// src/main/java/com/example/pVOPlugin/managers/PVOManager.java
package com.example.pVOPlugin.managers;

import com.example.pVOPlugin.models.PVO;
import com.example.pVOPlugin.PVOPlugin;
import org.bukkit.Bukkit;
import org.bukkit.Location;
import org.bukkit.configuration.ConfigurationSection;
import org.bukkit.configuration.file.FileConfiguration;

import java.util.*;

public class PVOManager {

    private final PVOPlugin plugin;
    private final Map<Location, PVO> pvoMap;

    public PVOManager(PVOPlugin plugin) {
        this.plugin = plugin;
        this.pvoMap = new HashMap<>();
    }

    public void loadPVOs() {
        FileConfiguration config = plugin.getConfigManager().getConfig();
        ConfigurationSection section = config.getConfigurationSection("pvos");
        if (section != null) {
            for (String key : section.getKeys(false)) {
                ConfigurationSection pvoSection = section.getConfigurationSection(key);
                if (pvoSection != null) {
                    double x = pvoSection.getDouble("location.x");
                    double y = pvoSection.getDouble("location.y");
                    double z = pvoSection.getDouble("location.z");
                    String worldName = pvoSection.getString("location.world");
                    boolean enabled = pvoSection.getBoolean("enabled");
                    int energy = pvoSection.getInt("energy");
                    List<String> exclusions = pvoSection.getStringList("exclusions");
                    String type = pvoSection.getString("type");
                    int level = pvoSection.getInt("level", 1);

                    Location loc = new Location(Bukkit.getWorld(worldName), x, y, z);
                    PVO pvo = new PVO(loc, enabled, energy, new HashSet<>(exclusions), type, level);
                    pvoMap.put(loc, pvo);
                }
            }
        }
        plugin.getLogger().info("Загружено " + pvoMap.size() + " PVO блоков.");
    }

    public void savePVOs() {
        FileConfiguration config = plugin.getConfigManager().getConfig();
        config.set("pvos", null); // Очистка секции перед сохранением

        int count = 0;
        for (Map.Entry<Location, PVO> entry : pvoMap.entrySet()) {
            Location loc = entry.getKey();
            PVO pvo = entry.getValue();
            String key = "pvo_" + count++;
            config.set("pvos." + key + ".location.x", loc.getX());
            config.set("pvos." + key + ".location.y", loc.getY());
            config.set("pvos." + key + ".location.z", loc.getZ());
            config.set("pvos." + key + ".location.world", loc.getWorld().getName());
            config.set("pvos." + key + ".enabled", pvo.isEnabled());
            config.set("pvos." + key + ".energy", pvo.getEnergy());
            config.set("pvos." + key + ".exclusions", new ArrayList<>(pvo.getExclusions()));
            config.set("pvos." + key + ".type", pvo.getType());
            config.set("pvos." + key + ".level", pvo.getLevel());
        }

        plugin.getConfigManager().saveConfigFile();
    }

    public void addPVO(Location loc, PVO pvo) {
        pvoMap.put(loc, pvo);
    }

    public void removePVO(Location loc) {
        pvoMap.remove(loc);
    }

    public PVO getPVO(Location loc) {
        return pvoMap.get(loc);
    }

    public Collection<PVO> getAllPVOs() {
        return pvoMap.values();
    }

    public Set<PVO> getPVOsInRadius(Location loc, double radius) {
        Set<PVO> result = new HashSet<>();
        for (PVO pvo : pvoMap.values()) {
            if (pvo.getLocation().getWorld().equals(loc.getWorld()) &&
                    pvo.getLocation().distance(loc) <= radius) {
                result.add(pvo);
            }
        }
        return result;
    }
}
// src/main/java/com/example/pVOPlugin/managers/RecipeManager.java
package com.example.pVOPlugin.managers;

import com.example.pVOPlugin.PVOPlugin;
import org.bukkit.Material;
import org.bukkit.NamespacedKey;
import org.bukkit.inventory.ItemStack;
import org.bukkit.inventory.ShapedRecipe;
import org.bukkit.inventory.meta.ItemMeta;

public class RecipeManager {

    private final PVOPlugin plugin;

    public RecipeManager(PVOPlugin plugin) {
        this.plugin = plugin;
    }

    public void registerRecipes() {
        // Рецепты для каждого типа PVO с большим количеством ресурсов и вероятностью успеха
        registerPVORecipe("km1", Material.REDSTONE_BLOCK, "PVO KM-1",
                new String[]{" R ", " E ", " R "},
                'R', Material.REDSTONE, 'E', Material.EMERALD,
                100, 80.0); // Стоимость, вероятность успеха

        registerPVORecipe("km2", Material.EMERALD_BLOCK, "PVO KM-2",
                new String[]{" E ", " D ", " E "},
                'E', Material.EMERALD, 'D', Material.DIAMOND,
                200, 75.0);

        registerPVORecipe("rtio100", Material.DIAMOND_BLOCK, "PVO RTIO-100",
                new String[]{" G ", " C ", " G "},
                'G', Material.GOLD_INGOT, 'C', Material.CAULDRON,
                300, 70.0);

        registerPVORecipe("rtio200", Material.GOLD_BLOCK, "PVO RTIO-200",
                new String[]{" S ", " L ", " S "},
                'S', Material.STICK, 'L', Material.LAVA_BUCKET,
                400, 65.0);

        registerPVORecipe("rtio300", Material.IRON_BLOCK, "PVO RTIO-300",
                new String[]{" I ", " N ", " I "},
                'I', Material.IRON_INGOT, 'N', Material.NETHER_STAR,
                500, 60.0);
    }

    private void registerPVORecipe(String key, Material resultMaterial, String displayName,
                                   String[] shape, char ingredient1, Material material1,
                                   char ingredient2, Material material2,
                                   int cost, double successRate) {
        ItemStack item = new ItemStack(resultMaterial);
        ItemMeta meta = item.getItemMeta();
        if (meta != null) {
            meta.setDisplayName("§b" + displayName);
            // Добавляем информацию о стоимости и вероятности успеха
            meta.setLore(java.util.Arrays.asList(
                    "§7Стоимость крафта: " + cost + " энергии",
                    "§7Вероятность успеха: " + successRate + "%"
            ));
            item.setItemMeta(meta);
        }

        ShapedRecipe recipe = new ShapedRecipe(NamespacedKey.minecraft("pvo_" + key), item);
        recipe.shape(shape);
        recipe.setIngredient(ingredient1, material1);
        recipe.setIngredient(ingredient2, material2);
        plugin.getServer().addRecipe(recipe);
    }
}
// src/main/java/com/example/pVOPlugin/managers/TechnologyManager.java
package com.example.pVOPlugin.managers;

import com.example.pVOPlugin.PVOPlugin;
import com.example.pVOPlugin.gui.TechnologyGUI;
import com.example.pVOPlugin.models.PVO;
import org.bukkit.ChatColor;
import org.bukkit.configuration.ConfigurationSection;
import org.bukkit.configuration.file.FileConfiguration;
import org.bukkit.entity.Player;
import org.bukkit.event.player.AsyncPlayerChatEvent;

import java.util.*;

public class TechnologyManager {

    private final PVOPlugin plugin;
    private final Map<UUID, PendingAction> pendingActions; // Ассоциация игроков с ожидающими действиями
    private final Map<String, Technology> technologies; // Доступные технологии

    public TechnologyManager(PVOPlugin plugin) {
        this.plugin = plugin;
        this.pendingActions = new HashMap<>();
        this.technologies = new HashMap<>();
    }

    public void loadTechnologies() {
        FileConfiguration config = plugin.getConfigManager().getConfig();
        ConfigurationSection section = config.getConfigurationSection("technologies");
        if (section != null) {
            for (String key : section.getKeys(false)) {
                ConfigurationSection techSection = section.getConfigurationSection(key);
                if (techSection != null) {
                    String name = techSection.getString("name");
                    String description = techSection.getString("description");
                    int cost = techSection.getInt("cost");
                    double successRate = techSection.getDouble("success_rate", 100.0);
                    technologies.put(key.toLowerCase(), new Technology(key.toLowerCase(), name, description, cost, successRate));
                }
            }
        } else {
            // Если секция отсутствует, инициализируем стандартные технологии
            initializeDefaultTechnologies();
            saveTechnologies();
        }
        plugin.getLogger().info("Загружено " + technologies.size() + " технологий.");
    }

    private void initializeDefaultTechnologies() {
        technologies.put("upgrade_energy", new Technology("upgrade_energy", "Увеличение Энергии", "Повышает максимальную энергию PVO.", 500, 90.0));
        technologies.put("synthesis_speed", new Technology("synthesis_speed", "Скорость Синтеза", "Увеличивает скорость синтеза PVO.", 300, 85.0));
        technologies.put("enhanced_scope", new Technology("enhanced_scope", "Увеличенный Обхват", "Расширяет радиус действия PVO.", 400, 80.0));
        technologies.put("adaptive_shield", new Technology("adaptive_shield", "Адаптивный Щит", "Увеличивает защиту от атак.", 600, 75.0));
        technologies.put("energy_regeneration", new Technology("energy_regeneration", "Регенерация Энергии", "Увеличивает скорость регенерации энергии PVO.", 450, 80.0));
        // Добавьте дополнительные технологии по необходимости
    }

    public void saveTechnologies() {
        FileConfiguration config = plugin.getConfigManager().getConfig();
        config.set("technologies", null); // Очистка секции перед сохранением

        for (Map.Entry<String, Technology> entry : technologies.entrySet()) {
            String key = entry.getKey();
            Technology tech = entry.getValue();
            config.set("technologies." + key + ".name", tech.getName());
            config.set("technologies." + key + ".description", tech.getDescription());
            config.set("technologies." + key + ".cost", tech.getCost());
            config.set("technologies." + key + ".success_rate", tech.getSuccessRate());
        }

        plugin.getConfigManager().saveConfigFile();
    }

    public Map<String, Technology> getTechnologies() {
        return technologies;
    }

    public void handleChatInput(AsyncPlayerChatEvent event) {
        Player player = event.getPlayer();
        UUID uuid = player.getUniqueId();

        if (pendingActions.containsKey(uuid)) {
            PendingAction action = pendingActions.get(uuid);
            String message = event.getMessage();
            event.setCancelled(true);

            switch (action.getType()) {
                case ADD_ENERGY:
                    handleAddEnergy(player, action, message);
                    break;
                case RESEARCH_TECHNOLOGY:
                    handleResearchTechnology(player, action, message);
                    break;
                default:
                    player.sendMessage(ChatColor.RED + "Неизвестное действие.");
                    break;
            }

            pendingActions.remove(uuid);
        }
    }

    private void handleAddEnergy(Player player, PendingAction action, String message) {
        try {
            int amount = Integer.parseInt(message);
            if (amount <= 0) {
                player.sendMessage(ChatColor.RED + "Количество энергии должно быть положительным числом.");
                return;
            }

            // Добавляем энергию определённому PVO (можно расширить для выбора конкретного PVO)
            for (PVO pvo : plugin.getPVOManager().getAllPVOs()) {
                pvo.addEnergy(amount);
            }
            plugin.getPVOManager().savePVOs();
            player.sendMessage(ChatColor.GREEN + "Добавлено энергии: " + amount);
        } catch (NumberFormatException e) {
            player.sendMessage(ChatColor.RED + "Введите корректное число.");
        }
    }

    private void handleResearchTechnology(Player player, PendingAction action, String message) {
        String techKey = message.toLowerCase();
        Technology tech = technologies.get(techKey);
        if (tech == null) {
            player.sendMessage(ChatColor.RED + "Технология не найдена.");
            return;
        }

        // Рассчитываем вероятность успеха
        double chance = tech.getSuccessRate();
        double roll = Math.random() * 100;
        if (roll <= chance) {
            // Успех исследования
            // Применяем эффект исследования (например, улучшаем все PVO)
            for (PVO pvo : plugin.getPVOManager().getAllPVOs()) {
                applyTechnology(pvo, tech);
            }
            plugin.getPVOManager().savePVOs();
            player.sendMessage(ChatColor.GREEN + "Вы успешно исследовали технологию: " + tech.getName());
            plugin.getLogger().info(player.getName() + " успешно исследовал технологию " + tech.getName());
        } else {
            // Провал исследования
            player.sendMessage(ChatColor.RED + "Исследование технологии " + tech.getName() + " провалилось.");
            plugin.getLogger().info(player.getName() + " провалил исследование технологии " + tech.getName());
        }
    }

    private void applyTechnology(PVO pvo, Technology tech) {
        switch (tech.getKey()) {
            case "upgrade_energy":
                // Увеличиваем максимальную энергию в зависимости от уровня
                int additionalEnergy = 500 * pvo.getLevel();
                pvo.addEnergy(additionalEnergy);
                break;
            case "synthesis_speed":
                // Увеличиваем скорость синтеза
                // Реализуйте соответствующую логику
                break;
            case "enhanced_scope":
                // Увеличиваем радиус действия
                // Реализуйте соответствующую логику
                break;
            case "adaptive_shield":
                // Увеличиваем защиту PVO
                // Реализуйте соответствующую логику
                break;
            case "energy_regeneration":
                // Увеличиваем скорость регенерации энергии
                // Реализуйте соответствующую логику
                break;
            // Добавьте дополнительные технологии по необходимости
            default:
                break;
        }
    }

    public void promptAction(Player player, ActionType actionType) {
        pendingActions.put(player.getUniqueId(), new PendingAction(actionType));
        switch (actionType) {
            case ADD_ENERGY:
                player.sendMessage(ChatColor.YELLOW + "Введите количество энергии через чат:");
                break;
            case RESEARCH_TECHNOLOGY:
                player.sendMessage(ChatColor.YELLOW + "Введите название технологии для исследования через чат:");
                break;
            default:
                break;
        }
    }

    public void openTechnologyGUI(Player player) {
        TechnologyGUI techGUI = new TechnologyGUI(plugin, player, this);
        techGUI.open();
    }

    // Внутренний класс для представления технологии
    public static class Technology {
        private final String key;
        private final String name;
        private final String description;
        private final int cost;
        private final double successRate;

        public Technology(String key, String name, String description, int cost, double successRate) {
            this.key = key;
            this.name = name;
            this.description = description;
            this.cost = cost;
            this.successRate = successRate;
        }

        public String getKey() {
            return key;
        }

        public String getName() {
            return name;
        }

        public String getDescription() {
            return description;
        }

        public int getCost() {
            return cost;
        }

        public double getSuccessRate() {
            return successRate;
        }
    }

    // Внутренний класс для представления ожидающего действия
    private static class PendingAction {
        private final ActionType type;

        public PendingAction(ActionType type) {
            this.type = type;
        }

        public ActionType getType() {
            return type;
        }
    }

    // Перечисление типов действий
    public enum ActionType {
        ADD_ENERGY,
        RESEARCH_TECHNOLOGY
    }
}
// src/main/java/com/example/pVOPlugin/models/PVO.java
package com.example.pVOPlugin.models;

import org.bukkit.Location;

import java.util.Set;

public class PVO {
    private final Location location;
    private boolean enabled;
    private int energy;
    private final Set<String> exclusions;
    private final String type;
    private int level; // Уровень PVO для индивидуальных характеристик

    public PVO(Location location, boolean enabled, int energy, Set<String> exclusions, String type, int level) {
        this.location = location;
        this.enabled = enabled;
        this.energy = energy;
        this.exclusions = exclusions;
        this.type = type;
        this.level = level;
    }

    public Location getLocation() {
        return location;
    }

    public boolean isEnabled() {
        return enabled;
    }

    public void setEnabled(boolean enabled) {
        this.enabled = enabled;
    }

    public int getEnergy() {
        return energy;
    }

    public void addEnergy(int amount) {
        this.energy += amount;
    }

    public void removeEnergy(int amount) {
        this.energy = Math.max(this.energy - amount, 0);
    }

    public Set<String> getExclusions() {
        return exclusions;
    }

    public void addExclusion(String playerName) {
        this.exclusions.add(playerName.toLowerCase());
    }

    public void removeExclusion(String playerName) {
        this.exclusions.remove(playerName.toLowerCase());
    }

    public String getType() {
        return type;
    }

    public int getLevel() {
        return level;
    }

    public void upgradeLevel() {
        this.level += 1;
    }

    public void setLevel(int level) {
        this.level = level;
    }
}
// src/main/java/com/example/pVOPlugin/PVOPlugin.java
package com.example.pVOPlugin;

import com.example.pVOPlugin.commands.AdminCommand;
import com.example.pVOPlugin.commands.PVOCommand;
import com.example.pVOPlugin.listeners.*;
import com.example.pVOPlugin.managers.ConfigManager;
import com.example.pVOPlugin.managers.PVOManager;
import com.example.pVOPlugin.managers.TechnologyManager;
import com.example.pVOPlugin.managers.RecipeManager;
import org.bukkit.event.Listener;
import org.bukkit.plugin.java.JavaPlugin;

public class PVOPlugin extends JavaPlugin implements Listener {

    private static PVOPlugin instance;
    private ConfigManager configManager;
    private PVOManager pvoManager;
    private TechnologyManager technologyManager;
    private RecipeManager recipeManager;

    @Override
    public void onEnable() {
        instance = this;

        // Инициализация менеджеров
        configManager = new ConfigManager(this);
        configManager.setup();

        pvoManager = new PVOManager(this);
        pvoManager.loadPVOs();

        technologyManager = new TechnologyManager(this);
        technologyManager.loadTechnologies();

        recipeManager = new RecipeManager(this);
        recipeManager.registerRecipes();

        // Регистрация команд
        PVOCommand pvoCommand = new PVOCommand(this);
        getCommand("givepvo").setExecutor(pvoCommand);
        getCommand("pvo").setExecutor(pvoCommand);
        getCommand("pvo").setTabCompleter(pvoCommand);

        AdminCommand adminCommand = new AdminCommand(this);
        getCommand("pvoadmin").setExecutor(adminCommand);
        getCommand("pvoadmin").setTabCompleter(adminCommand);

        // Регистрация слушателей событий
        getServer().getPluginManager().registerEvents(new BlockPlaceListener(this), this);
        getServer().getPluginManager().registerEvents(new PlayerInteractListener(this), this);
        getServer().getPluginManager().registerEvents(new PlayerMoveListener(this), this);
        getServer().getPluginManager().registerEvents(new GUIListener(this), this);

        // Регистрация слушателя чата для обработки специальных команд
        getServer().getPluginManager().registerEvents(new ChatListener(this), this);

        getLogger().info("PVOPlugin успешно включён!");
    }

    @Override
    public void onDisable() {
        pvoManager.savePVOs();
        technologyManager.saveTechnologies();
        getLogger().info("PVOPlugin успешно выключен.");
    }

    public static PVOPlugin getInstance() {
        return instance;
    }

    public ConfigManager getConfigManager() {
        return configManager;
    }

    public PVOManager getPVOManager() {
        return pvoManager;
    }

    public TechnologyManager getTechnologyManager() {
        return technologyManager;
    }

    public RecipeManager getRecipeManager() {
        return recipeManager;
    }
}
# src/main/resources/config.yml
pvo:
  initial_energy: 1000
  max_energy: 5000
  radius: 10.0
  energy_cost: 10
  regeneration_rate: 5

technologies:
  upgrade_energy:
    name: Увеличение Энергии
    description: Повышает максимальную энергию PVO.
    cost: 500
    success_rate: 90.0
  synthesis_speed:
    name: Скорость Синтеза
    description: Увеличивает скорость синтеза PVO.
    cost: 300
    success_rate: 85.0
  enhanced_scope:
    name: Увеличенный Обхват
    description: Расширяет радиус действия PVO.
    cost: 400
    success_rate: 80.0
  adaptive_shield:
    name: Адаптивный Щит
    description: Увеличивает защиту от атак.
    cost: 600
    success_rate: 75.0
  energy_regeneration:
    name: Регенерация Энергии
    description: Увеличивает скорость регенерации энергии PVO.
    cost: 450
    success_rate: 80.0
  advanced_processing:
    name: Продвинутая Обработка
    description: Увеличивает эффективность синтеза PVO.
    cost: 700
    success_rate: 70.0
  # Добавьте дополнительные технологии по необходимости
# src/main/resources/plugin.yml
name: PVOPlugin
main: com.example.pVOPlugin.PVOPlugin
version: 2.0
api-version: 1.20
description: Расширенный плагин PVO с технологическим прогрессом и индивидуальными настройками.
commands:
  givepvo:
    description: Выдача PVO.
    usage: /givepvo <тип>
    permission: pvoplugin.givepvo
  pvo:
    description: Управление PVO.
    usage: /pvo <подкоманда>
    permission: pvoplugin.admin
  pvoadmin:
    description: Административные команды для технологического прогресса.
    usage: /pvoadmin <opentechgui>
    permission: pvoplugin.admin
permissions:
  pvoplugin.givepvo:
    description: Разрешение на выдачу PVO.
    default: op
  pvoplugin.admin:
    description: Административные права PVO.
    default: op

Улучши плагин, исправь gui (ведь сейчас оно не работает), а также команды (чтобы они работали)