some more commands

This commit is contained in:
aPunch 2012-01-25 14:07:49 -06:00
parent 653e37ad24
commit ed38ef822e
6 changed files with 122 additions and 52 deletions

View File

@ -19,6 +19,7 @@ import net.citizensnpcs.api.npc.trait.InstanceFactory;
import net.citizensnpcs.api.npc.trait.Trait;
import net.citizensnpcs.api.npc.trait.trait.SpawnLocation;
import net.citizensnpcs.command.CommandManager;
import net.citizensnpcs.command.Injector;
import net.citizensnpcs.command.command.NPCCommands;
import net.citizensnpcs.command.exception.CommandUsageException;
import net.citizensnpcs.command.exception.MissingNestedCommandException;
@ -167,6 +168,14 @@ public class Citizens extends JavaPlugin {
return saves;
}
public CitizensNPCManager getNPCManager() {
return npcManager;
}
public InstanceFactory<Character> getCharacterManager() {
return characterManager;
}
private void saveNPCs() {
for (NPC npc : npcManager.getAllNPCs())
((CitizensNPC) npc).save();
@ -213,6 +222,7 @@ public class Citizens extends JavaPlugin {
private void registerPermissions() {
Map<String, Boolean> children = new HashMap<String, Boolean>();
children.put("citizens.npc.create", true);
children.put("citizens.npc.spawn", true);
children.put("citizens.npc.despawn", true);
children.put("citizens.npc.select", true);
@ -222,6 +232,8 @@ public class Citizens extends JavaPlugin {
}
private void registerCommands() {
cmdManager.setInjector(new Injector(this));
cmdManager.register(NPCCommands.class);
}

View File

@ -58,23 +58,23 @@ public class CommandManager {
* their respective {@link Method}. The child map has the key of the command
* name (one for each alias) with the method.
*/
private Map<Method, Map<CommandIdentifier, Method>> commands = new HashMap<Method, Map<CommandIdentifier, Method>>();
private final Map<Method, Map<CommandIdentifier, Method>> commands = new HashMap<Method, Map<CommandIdentifier, Method>>();
// Used to store the instances associated with a method.
private Map<Method, Object> instances = new HashMap<Method, Object>();
private final Map<Method, Object> instances = new HashMap<Method, Object>();
/*
* Mapping of commands (not including aliases) with a description. This is
* only for top level commands.
*/
private Map<CommandIdentifier, String> descs = new HashMap<CommandIdentifier, String>();
private final Map<CommandIdentifier, String> descs = new HashMap<CommandIdentifier, String>();
// Stores the injector used to getInstance.
private Injector injector;
private Map<Method, Requirements> requirements = new HashMap<Method, Requirements>();
private final Map<Method, Requirements> requirements = new HashMap<Method, Requirements>();
private Map<Method, ServerCommand> serverCommands = new HashMap<Method, ServerCommand>();
private final Map<Method, ServerCommand> serverCommands = new HashMap<Method, ServerCommand>();
/*
* Register an class that contains commands (denoted by {@link Command}. If
@ -82,33 +82,21 @@ public class CommandManager {
* be registered to be called statically. Otherwise, new instances will be
* created of the command classes and methods will not be called statically.
*/
public void register(Class<?> cls) {
registerMethods(cls, null);
public void register(Class<?> clazz) {
registerMethods(clazz, null);
}
/*
* Register the methods of a class. This will automatically construct
* instances as necessary.
*/
private void registerMethods(Class<?> cls, Method parent) {
try {
if (getInjector() == null)
registerMethods(cls, parent, null);
else {
Object obj = getInjector().getInstance(cls);
registerMethods(cls, parent, obj);
}
} catch (InvocationTargetException e) {
logger.log(Level.SEVERE, "Failed to register commands", e);
} catch (IllegalAccessException e) {
logger.log(Level.SEVERE, "Failed to register commands", e);
} catch (InstantiationException e) {
logger.log(Level.SEVERE, "Failed to register commands", e);
}
private void registerMethods(Class<?> clazz, Method parent) {
Object obj = injector.getInstance(clazz);
registerMethods(clazz, parent, obj);
}
// Register the methods of a class.
private void registerMethods(Class<?> cls, Method parent, Object obj) {
private void registerMethods(Class<?> clazz, Method parent, Object obj) {
Map<CommandIdentifier, Method> map;
// Make a new hash map to cache the commands for this class
@ -120,7 +108,7 @@ public class CommandManager {
commands.put(parent, map);
}
for (Method method : cls.getMethods()) {
for (Method method : clazz.getMethods()) {
if (!method.isAnnotationPresent(Command.class))
continue;
boolean isStatic = Modifier.isStatic(method.getModifiers());
@ -157,7 +145,6 @@ public class CommandManager {
continue;
instances.put(method, obj);
Messaging.log("Put instance.");
}
// Build a list of commands and their usage details, at least for
@ -379,19 +366,6 @@ public class CommandManager {
return false;
}
/*
* Get the injector used to create new instances. This can be null, in which
* case only classes will be registered statically.
*/
public Injector getInjector() {
return injector;
}
// Set the injector for creating new instances.
public void setInjector(Injector injector) {
this.injector = injector;
}
// Returns whether a player has permission.
private boolean hasPermission(Player player, String perm) {
return ((Player) player).hasPermission("citizens." + perm);
@ -408,4 +382,8 @@ public class CommandManager {
}
return cmds.toArray(new String[cmds.size()]);
}
public void setInjector(Injector injector) {
this.injector = injector;
}
}

View File

@ -6,10 +6,46 @@
package net.citizensnpcs.command;
import java.lang.reflect.Constructor;
import java.lang.reflect.InvocationTargetException;
import java.util.logging.Level;
public interface Injector {
import net.citizensnpcs.util.Messaging;
public Object getInstance(Class<?> cls) throws InvocationTargetException, IllegalAccessException,
InstantiationException;
public class Injector {
private Object[] args;
private Class<?>[] argClasses;
public Injector(Object... args) {
this.args = args;
argClasses = new Class[args.length];
for (int i = 0; i < args.length; ++i) {
argClasses[i] = args[i].getClass();
}
}
public Object getInstance(Class<?> clazz) {
try {
Constructor<?> ctr = clazz.getConstructor(argClasses);
ctr.setAccessible(true);
return ctr.newInstance(args);
} catch (NoSuchMethodException e) {
Messaging.log(Level.SEVERE, "Error initializing commands class " + clazz + ": ");
e.printStackTrace();
return null;
} catch (InvocationTargetException e) {
Messaging.log(Level.SEVERE, "Error initializing commands class " + clazz + ": ");
e.printStackTrace();
return null;
} catch (InstantiationException e) {
Messaging.log(Level.SEVERE, "Error initializing commands class " + clazz + ": ");
e.printStackTrace();
return null;
} catch (IllegalAccessException e) {
Messaging.log(Level.SEVERE, "Error initializing commands class " + clazz + ": ");
e.printStackTrace();
return null;
}
}
}

View File

@ -1,30 +1,66 @@
package net.citizensnpcs.command.command;
import org.bukkit.ChatColor;
import org.bukkit.entity.Player;
import net.citizensnpcs.api.CitizensAPI;
import net.citizensnpcs.Citizens;
import net.citizensnpcs.api.npc.NPC;
import net.citizensnpcs.command.CommandContext;
import net.citizensnpcs.command.annotation.Command;
import net.citizensnpcs.command.annotation.Permission;
import net.citizensnpcs.npc.CitizensNPC;
import net.citizensnpcs.npc.CitizensNPCManager;
import net.citizensnpcs.util.Messaging;
import net.citizensnpcs.util.StringHelper;
// TODO add requirements
public class NPCCommands {
private final Citizens plugin;
public NPCCommands(Citizens plugin) {
this.plugin = plugin;
}
@Command(
aliases = { "npc" },
usage = "spawn [name]",
desc = "Spawn an NPC",
modifiers = { "spawn", "create" },
usage = "create [name] (character)",
desc = "Create a new NPC",
modifiers = { "create" },
min = 2,
max = 3)
@Permission("npc.create")
public void createNPC(CommandContext args, Player player, NPC npc) {
CitizensNPC create = (CitizensNPC) plugin.getNPCManager().createNPC(args.getString(1));
String msg = ChatColor.GREEN + "You created " + StringHelper.wrap(create.getName());
if (args.argsLength() == 3 && plugin.getCharacterManager().getInstance(args.getString(2)) != null) {
create.setCharacter(plugin.getCharacterManager().getInstance(args.getString(2)));
msg += " with the character " + StringHelper.wrap(args.getString(2));
}
msg += " at your location.";
create.spawn(player.getLocation());
plugin.getNPCManager().selectNPC(player, create);
Messaging.send(player, msg);
}
@Command(
aliases = { "npc" },
usage = "spawn [id]",
desc = "Spawn an existing NPC",
modifiers = { "spawn" },
min = 2,
max = 2)
@Permission("npc.spawn")
public static void spawnNPC(CommandContext args, Player player, NPC npc) {
CitizensNPC create = (CitizensNPC) CitizensAPI.getNPCManager().createNPC(args.getString(1));
create.spawn(player.getLocation());
create.save();
public void spawnNPC(CommandContext args, Player player, NPC npc) {
CitizensNPC respawn = (CitizensNPC) plugin.getNPCManager().getNPC(args.getInteger(1));
if (respawn == null) {
Messaging.sendError(player, "No NPC with the ID '" + args.getInteger(1) + "' exists.");
return;
}
respawn.spawn(player.getLocation());
plugin.getNPCManager().selectNPC(player, respawn);
Messaging.send(player, ChatColor.GREEN + "You respawned " + StringHelper.wrap(respawn.getName())
+ " at your location.");
}
@Command(
@ -35,8 +71,10 @@ public class NPCCommands {
min = 1,
max = 1)
@Permission("npc.despawn")
public static void despawnNPC(CommandContext args, Player player, NPC npc) {
CitizensNPC despawn = (CitizensNPC) ((CitizensNPCManager) CitizensAPI.getNPCManager()).getSelectedNPC(player);
public void despawnNPC(CommandContext args, Player player, NPC npc) {
CitizensNPC despawn = (CitizensNPC) plugin.getNPCManager().getSelectedNPC(player);
despawn.despawn();
plugin.getNPCManager().deselectNPC(player);
Messaging.send(player, ChatColor.GREEN + "You despawned " + StringHelper.wrap(despawn.getName()) + ".");
}
}

View File

@ -41,6 +41,7 @@ public class CitizensNPC extends AbstractNPC {
getHandle().die();
spawned = false;
save();
}
@Override
@ -90,6 +91,7 @@ public class CitizensNPC extends AbstractNPC {
addTrait(new SpawnLocation(loc));
spawned = true;
save();
}
@Override

View File

@ -144,6 +144,10 @@ public class CitizensNPCManager implements NPCManager {
selected.put(player.getName(), npc.getId());
}
public void deselectNPC(Player player) {
selected.remove(player.getName());
}
public boolean npcIsSelectedByPlayer(Player player, NPC npc) {
if (!selected.containsKey(player.getName()))
return false;