package com.meekdev.meenpcs; import net.citizensnpcs.api.CitizensAPI; import net.citizensnpcs.api.event.CitizensEnableEvent; import net.citizensnpcs.api.event.NPCCreateEvent; import net.citizensnpcs.api.event.NPCSpawnEvent; import net.citizensnpcs.api.event.NPCDespawnEvent; import net.citizensnpcs.api.event.NPCRemoveEvent; import net.citizensnpcs.api.npc.NPC; import net.citizensnpcs.api.npc.NPCRegistry; import org.bukkit.event.EventHandler; import org.bukkit.event.EventPriority; import org.bukkit.event.Listener; import org.bukkit.plugin.java.JavaPlugin; import java.util.HashMap; import java.util.Map; import java.util.logging.Level; public class MeenPCs extends JavaPlugin implements Listener { private Map npcs = new HashMap<>(); private NPCInteractionEngine interactionEngine; private boolean citizensEnabled = false; @Override public void onEnable() { if (!getServer().getPluginManager().isPluginEnabled("Citizens")) { getLogger().severe("Citizens 2.0 not found or not enabled"); getServer().getPluginManager().disablePlugin(this); return; } getServer().getPluginManager().registerEvents(this, this); interactionEngine = new NPCInteractionEngine(this); getServer().getPluginManager().registerEvents(interactionEngine, this); getLogger().info("MeenPCs enabled, waiting for Citizens to be ready..."); } @EventHandler(priority = EventPriority.MONITOR) public void onCitizensEnable(CitizensEnableEvent event) { if (citizensEnabled) return; if (!CitizensAPI.hasImplementation()) { getLogger().warning("Citizens implementation not ready yet!"); return; } NPCRegistry registry = CitizensAPI.getNPCRegistry(); if (registry == null) { getLogger().warning("NPCRegistry is null!"); return; } citizensEnabled = true; getLogger().info("Citizens is ready! Initializing NPCs..."); getServer().getScheduler().runTaskTimer(this, () -> { for (InteractiveNPC npc : npcs.values()) { try { npc.update(); } catch (Exception e) { getLogger().log(Level.WARNING, "Error updating NPC " + npc.getName(), e); } } }, 20L, 1L); for (NPC npc : registry.sorted()) { if (npc.isSpawned()) { addInteractiveNPC(npc); } } getLogger().info("Successfully hooked into " + npcs.size() + " existing NPCs"); } @EventHandler(priority = EventPriority.MONITOR) public void onNPCCreate(NPCCreateEvent event) { if (!citizensEnabled) return; getLogger().info("NPC Created: " + event.getNPC().getName()); } @EventHandler(priority = EventPriority.MONITOR, ignoreCancelled = true) public void onNPCSpawn(NPCSpawnEvent event) { if (!citizensEnabled) return; NPC npc = event.getNPC(); if (!npcs.containsKey(npc.getId())) { addInteractiveNPC(npc); getLogger().info("Added interactive behavior to NPC: " + npc.getName()); } } @EventHandler(priority = EventPriority.MONITOR) public void onNPCDespawn(NPCDespawnEvent event) { if (!citizensEnabled) return; InteractiveNPC interactiveNPC = npcs.get(event.getNPC().getId()); if (interactiveNPC != null) { interactiveNPC.cleanup(); } } @EventHandler(priority = EventPriority.MONITOR) public void onNPCRemove(NPCRemoveEvent event) { if (!citizensEnabled) return; InteractiveNPC interactiveNPC = npcs.remove(event.getNPC().getId()); if (interactiveNPC != null) { interactiveNPC.cleanup(); getLogger().info("Removed interactive behavior from NPC: " + event.getNPC().getName()); } } private void addInteractiveNPC(NPC npc) { try { if (!npcs.containsKey(npc.getId())) { InteractiveNPC interactiveNPC = new InteractiveNPC(npc, this); npcs.put(npc.getId(), interactiveNPC); getLogger().info("Successfully added interactive behavior to NPC: " + npc.getName()); } } catch (Exception e) { getLogger().log(Level.SEVERE, "Failed to add interactive behavior to NPC: " + npc.getName(), e); e.printStackTrace(); } } @Override public void onDisable() { // Cleanup for (InteractiveNPC npc : npcs.values()) { npc.cleanup(); } npcs.clear(); citizensEnabled = false; getLogger().info("MeenPCs disabled successfully!"); } public Map getNPCs() { return npcs; } public NPCInteractionEngine getInteractionEngine() { return interactionEngine; } public boolean isCitizensReady() { return citizensEnabled; } }