diff --git a/build.xml b/build.xml index fc3fdb825..e87795e76 100644 --- a/build.xml +++ b/build.xml @@ -17,8 +17,8 @@ - + diff --git a/lib/CitizensAPI.jar b/lib/CitizensAPI.jar index 36e99a431..2f6480c37 100644 Binary files a/lib/CitizensAPI.jar and b/lib/CitizensAPI.jar differ diff --git a/lib/bukkit-1.2.3-R0.2-SNAPSHOT.jar b/lib/bukkit-1.2.3-R0.2-SNAPSHOT.jar index b918b7532..5a2b7f08d 100644 Binary files a/lib/bukkit-1.2.3-R0.2-SNAPSHOT.jar and b/lib/bukkit-1.2.3-R0.2-SNAPSHOT.jar differ diff --git a/lib/craftbukkit-1.2.3-R0.2-SNAPSHOT.jar b/lib/craftbukkit-1.2.3-R0.2-SNAPSHOT.jar index bee4712df..04c546a3b 100644 Binary files a/lib/craftbukkit-1.2.3-R0.2-SNAPSHOT.jar and b/lib/craftbukkit-1.2.3-R0.2-SNAPSHOT.jar differ diff --git a/src/main/java/net/citizensnpcs/Citizens.java b/src/main/java/net/citizensnpcs/Citizens.java index f9e26a824..640b45054 100644 --- a/src/main/java/net/citizensnpcs/Citizens.java +++ b/src/main/java/net/citizensnpcs/Citizens.java @@ -12,7 +12,6 @@ import net.citizensnpcs.api.event.CitizensReloadEvent; import net.citizensnpcs.api.exception.NPCException; import net.citizensnpcs.api.exception.NPCLoadException; import net.citizensnpcs.api.npc.NPC; -import net.citizensnpcs.api.npc.character.CharacterManager; import net.citizensnpcs.api.util.DataKey; import net.citizensnpcs.api.util.DatabaseStorage; import net.citizensnpcs.api.util.Storage; @@ -60,10 +59,6 @@ public class Citizens extends JavaPlugin { private Storage saves; // TODO: refactor this into an NPCStore (remove // dependency on Storage). - public CharacterManager getCharacterManager() { - return characterManager; - } - public CommandManager getCommandManager() { return commands; } @@ -255,8 +250,8 @@ public class Citizens extends JavaPlugin { if (!key.keyExists("name")) throw new NPCLoadException("Could not find a name for the NPC with ID '" + id + "'."); - NPC npc = npcManager.createNPC(EntityType.valueOf(key.getString("traits.type").toUpperCase()), id, - key.getString("name"), null); + NPC npc = npcManager.createNPC(EntityType.valueOf(key.getString("traits.type").toUpperCase()), id, key + .getString("name"), null); try { ((CitizensNPC) npc).load(key); } catch (NPCException ex) { diff --git a/src/main/java/net/citizensnpcs/command/CommandManager.java b/src/main/java/net/citizensnpcs/command/CommandManager.java index 76e83748a..f91df3775 100644 --- a/src/main/java/net/citizensnpcs/command/CommandManager.java +++ b/src/main/java/net/citizensnpcs/command/CommandManager.java @@ -28,6 +28,8 @@ import org.bukkit.command.ConsoleCommandSender; import org.bukkit.entity.EntityType; import org.bukkit.entity.Player; +import com.google.common.collect.Sets; + public class CommandManager { /* @@ -95,17 +97,23 @@ public class CommandManager { if (cmdRequirements != null) { NPC npc = (NPC) methodArgs[2]; + // Requirements if (cmdRequirements.selected() && npc == null) throw new RequirementMissingException("You must have an NPC selected to execute that command."); + if (cmdRequirements.ownership() && npc != null && !npc.getTrait(Owner.class).getOwner().equals(player.getName()) && !player.hasPermission("citizens.admin")) throw new RequirementMissingException("You must be the owner of this NPC to execute that command."); - if (cmdRequirements.type() != EntityType.UNKNOWN - && !cmdRequirements.type().name().equals(npc.getTrait(MobType.class).getType())) - throw new RequirementMissingException("The NPC must be of the type '" - + cmdRequirements.type().name().toLowerCase().replace('_', '-') - + "' in order for you to use that command."); + + Set types = Sets.newHashSet(cmdRequirements.types()); + if (!types.contains(EntityType.UNKNOWN)) { + EntityType type = EntityType.valueOf(npc.getTrait(MobType.class).getType()); + if (!types.contains(type)) { + throw new RequirementMissingException("The NPC cannot be the mob type '" + + type.name().toLowerCase().replace('_', '-') + "' to use that command."); + } + } } } diff --git a/src/main/java/net/citizensnpcs/command/Requirements.java b/src/main/java/net/citizensnpcs/command/Requirements.java index c817c2b3d..d73c3b425 100644 --- a/src/main/java/net/citizensnpcs/command/Requirements.java +++ b/src/main/java/net/citizensnpcs/command/Requirements.java @@ -12,5 +12,5 @@ public @interface Requirements { boolean selected() default false; - EntityType type() default EntityType.UNKNOWN; + EntityType[] types() default { EntityType.UNKNOWN }; } \ No newline at end of file diff --git a/src/main/java/net/citizensnpcs/command/command/EditorCommands.java b/src/main/java/net/citizensnpcs/command/command/EditorCommands.java index e3e27a151..d3d71d7a4 100644 --- a/src/main/java/net/citizensnpcs/command/command/EditorCommands.java +++ b/src/main/java/net/citizensnpcs/command/command/EditorCommands.java @@ -16,38 +16,39 @@ import org.bukkit.entity.Player; public class EditorCommands { @Command( - aliases = { "npc" }, - usage = "equip", - desc = "Toggle the equipment editor", - modifiers = { "equip" }, - min = 1, - max = 1, - permission = "npc.edit.equip") - @Requirements(selected = true, ownership = true, type = EntityType.PLAYER) + aliases = { "npc" }, + usage = "equip", + desc = "Toggle the equipment editor", + modifiers = { "equip" }, + min = 1, + max = 1, + permission = "npc.edit.equip") + @Requirements(selected = true, ownership = true, types = { EntityType.ENDERMAN, EntityType.PLAYER, EntityType.PIG, + EntityType.SHEEP }) public void equip(CommandContext args, Player player, NPC npc) { Editor.enterOrLeave(player, new EquipmentEditor(player, npc)); } @Command( - aliases = { "npc" }, - usage = "path", - desc = "Toggle the waypoint editor", - modifiers = { "path" }, - min = 1, - max = 1, - permission = "npc.edit.path") + aliases = { "npc" }, + usage = "path", + desc = "Toggle the waypoint editor", + modifiers = { "path" }, + min = 1, + max = 1, + permission = "npc.edit.path") public void path(CommandContext args, Player player, NPC npc) { Editor.enterOrLeave(player, npc.getTrait(Waypoints.class).getEditor(player)); } @Command( - aliases = { "npc" }, - usage = "text", - desc = "Toggle the text editor", - modifiers = { "text" }, - min = 1, - max = 1, - permission = "npc.edit.text") + aliases = { "npc" }, + usage = "text", + desc = "Toggle the text editor", + modifiers = { "text" }, + min = 1, + max = 1, + permission = "npc.edit.text") public void text(CommandContext args, Player player, NPC npc) { Editor.enterOrLeave(player, npc.getTrait(Text.class).getEditor(player)); } diff --git a/src/main/java/net/citizensnpcs/editor/Equipable.java b/src/main/java/net/citizensnpcs/editor/Equipable.java new file mode 100644 index 000000000..aece7ba46 --- /dev/null +++ b/src/main/java/net/citizensnpcs/editor/Equipable.java @@ -0,0 +1,8 @@ +package net.citizensnpcs.editor; + +import org.bukkit.entity.Player; + +public interface Equipable { + + public void equip(Player equipper); +} \ No newline at end of file diff --git a/src/main/java/net/citizensnpcs/editor/EquipmentEditor.java b/src/main/java/net/citizensnpcs/editor/EquipmentEditor.java index 07236116a..9faac4a9e 100644 --- a/src/main/java/net/citizensnpcs/editor/EquipmentEditor.java +++ b/src/main/java/net/citizensnpcs/editor/EquipmentEditor.java @@ -2,17 +2,15 @@ package net.citizensnpcs.editor; import net.citizensnpcs.api.CitizensAPI; import net.citizensnpcs.api.npc.NPC; -import net.citizensnpcs.api.trait.trait.Equipment; +import net.citizensnpcs.npc.CitizensNPC; import net.citizensnpcs.util.Messaging; -import org.bukkit.Material; import org.bukkit.entity.Player; import org.bukkit.event.Event.Result; import org.bukkit.event.EventHandler; import org.bukkit.event.block.Action; import org.bukkit.event.player.PlayerInteractEntityEvent; import org.bukkit.event.player.PlayerInteractEvent; -import org.bukkit.inventory.ItemStack; public class EquipmentEditor extends Editor { private final NPC npc; @@ -26,9 +24,10 @@ public class EquipmentEditor extends Editor { @Override public void begin() { Messaging.send(player, "Entered the equipment editor!"); - Messaging.send(player, "Right click to equip armor and items."); - Messaging.send(player, "Right click while crouching to equip armor in the NPC's hand."); - Messaging.send(player, "Right click with an empty hand to remove all armor and items."); + Messaging.send(player, "Right click to equip the NPC!"); + Messaging.send(player, "Right click with an empty hand to reset all items."); + Messaging.send(player, + "If the NPC is human, right click while crouching to equip armor its hand."); } @Override @@ -49,67 +48,10 @@ public class EquipmentEditor extends Editor { || !event.getPlayer().equals(player)) return; - ItemStack hand = player.getItemInHand(); - Equipment trait = npc.getTrait(Equipment.class); - int slot = 0; - // First, determine the slot to edit - switch (hand.getType()) { - case PUMPKIN: - case JACK_O_LANTERN: - case LEATHER_HELMET: - case CHAINMAIL_HELMET: - case GOLD_HELMET: - case IRON_HELMET: - case DIAMOND_HELMET: - if (!player.isSneaking()) - slot = 1; - break; - case LEATHER_CHESTPLATE: - case CHAINMAIL_CHESTPLATE: - case GOLD_CHESTPLATE: - case IRON_CHESTPLATE: - case DIAMOND_CHESTPLATE: - if (!player.isSneaking()) - slot = 2; - break; - case LEATHER_LEGGINGS: - case CHAINMAIL_LEGGINGS: - case GOLD_LEGGINGS: - case IRON_LEGGINGS: - case DIAMOND_LEGGINGS: - if (!player.isSneaking()) - slot = 3; - break; - case LEATHER_BOOTS: - case CHAINMAIL_BOOTS: - case GOLD_BOOTS: - case IRON_BOOTS: - case DIAMOND_BOOTS: - if (!player.isSneaking()) - slot = 4; - break; - case AIR: - for (int i = 0; i < 5; i++) { - if (trait.get(i) != null && trait.get(i).getType() != Material.AIR) { - player.getWorld().dropItemNaturally(npc.getBukkitEntity().getLocation(), trait.get(i)); - trait.set(i, null); - } - } - Messaging.send(player, "" + npc.getName() + " had all of its items removed."); - } - // Now edit the equipment based on the slot - if (trait.get(slot) != null && trait.get(slot).getType() != Material.AIR) - player.getWorld().dropItemNaturally(npc.getBukkitEntity().getLocation(), trait.get(slot)); + CitizensNPC handle = (CitizensNPC) npc; + if (!(handle instanceof Equipable)) + return; - ItemStack set = hand; - if (set != null && set.getType() != Material.AIR) { - if (hand.getAmount() > 1) - hand.setAmount(hand.getAmount() - 1); - else - hand = null; - player.setItemInHand(hand); - set.setAmount(1); - } - trait.set(slot, set); + ((Equipable) handle).equip(event.getPlayer()); } } \ No newline at end of file diff --git a/src/main/java/net/citizensnpcs/npc/entity/CitizensEndermanNPC.java b/src/main/java/net/citizensnpcs/npc/entity/CitizensEndermanNPC.java index 6be9e8e45..fcc5d11a9 100644 --- a/src/main/java/net/citizensnpcs/npc/entity/CitizensEndermanNPC.java +++ b/src/main/java/net/citizensnpcs/npc/entity/CitizensEndermanNPC.java @@ -1,15 +1,22 @@ package net.citizensnpcs.npc.entity; +import net.citizensnpcs.api.trait.trait.Equipment; +import net.citizensnpcs.editor.Equipable; import net.citizensnpcs.npc.CitizensMobNPC; import net.citizensnpcs.npc.CitizensNPCManager; +import net.citizensnpcs.util.Messaging; import net.minecraft.server.EntityEnderman; import net.minecraft.server.PathfinderGoalSelector; import net.minecraft.server.World; +import org.bukkit.Material; import org.bukkit.entity.Enderman; +import org.bukkit.entity.Player; +import org.bukkit.inventory.ItemStack; +import org.bukkit.material.MaterialData; -public class CitizensEndermanNPC extends CitizensMobNPC { +public class CitizensEndermanNPC extends CitizensMobNPC implements Equipable { public CitizensEndermanNPC(CitizensNPCManager manager, int id, String name) { super(manager, id, name, EntityEndermanNPC.class); @@ -20,6 +27,37 @@ public class CitizensEndermanNPC extends CitizensMobNPC { return (Enderman) getHandle().getBukkitEntity(); } + @Override + public void equip(Player equipper) { + ItemStack hand = equipper.getItemInHand(); + if (!hand.getType().isBlock()) { + Messaging.sendError(equipper, "Invalid block!"); + return; + } + + MaterialData carried = getBukkitEntity().getCarriedMaterial(); + if (carried.getItemType() == Material.AIR) { + if (hand.getType() == Material.AIR) { + Messaging.sendError(equipper, "Invalid block!"); + return; + } + } else { + equipper.getWorld().dropItemNaturally(getBukkitEntity().getLocation(), carried.toItemStack(1)); + getBukkitEntity().setCarriedMaterial(hand.getData()); + } + + ItemStack set = hand; + if (set.getType() != Material.AIR) { + if (hand.getAmount() > 1) + hand.setAmount(hand.getAmount() - 1); + else + hand = null; + equipper.setItemInHand(hand); + set.setAmount(1); + } + getTrait(Equipment.class).set(0, set); + } + public static class EntityEndermanNPC extends EntityEnderman { public EntityEndermanNPC(World world) { diff --git a/src/main/java/net/citizensnpcs/npc/entity/CitizensHumanNPC.java b/src/main/java/net/citizensnpcs/npc/entity/CitizensHumanNPC.java index 74d3ad987..d53e0481d 100644 --- a/src/main/java/net/citizensnpcs/npc/entity/CitizensHumanNPC.java +++ b/src/main/java/net/citizensnpcs/npc/entity/CitizensHumanNPC.java @@ -1,19 +1,24 @@ package net.citizensnpcs.npc.entity; import net.citizensnpcs.api.exception.NPCLoadException; +import net.citizensnpcs.api.trait.trait.Equipment; import net.citizensnpcs.api.util.DataKey; +import net.citizensnpcs.editor.Equipable; import net.citizensnpcs.npc.CitizensNPC; import net.citizensnpcs.npc.CitizensNPCManager; +import net.citizensnpcs.util.Messaging; import net.citizensnpcs.util.StringHelper; import net.minecraft.server.EntityLiving; import net.minecraft.server.ItemInWorldManager; import net.minecraft.server.WorldServer; import org.bukkit.Location; +import org.bukkit.Material; import org.bukkit.craftbukkit.CraftWorld; import org.bukkit.entity.Player; +import org.bukkit.inventory.ItemStack; -public class CitizensHumanNPC extends CitizensNPC { +public class CitizensHumanNPC extends CitizensNPC implements Equipable { public CitizensHumanNPC(CitizensNPCManager manager, int id, String name) { super(manager, id, name); @@ -22,8 +27,8 @@ public class CitizensHumanNPC extends CitizensNPC { @Override protected EntityLiving createHandle(Location loc) { WorldServer ws = ((CraftWorld) loc.getWorld()).getHandle(); - EntityHumanNPC handle = new EntityHumanNPC(ws.getServer().getServer(), ws, - StringHelper.parseColors(getFullName()), new ItemInWorldManager(ws)); + EntityHumanNPC handle = new EntityHumanNPC(ws.getServer().getServer(), ws, StringHelper + .parseColors(getFullName()), new ItemInWorldManager(ws)); handle.removeFromPlayerMap(getFullName()); handle.setPositionRotation(loc.getX(), loc.getY(), loc.getZ(), loc.getYaw(), loc.getPitch()); return handle; @@ -59,4 +64,70 @@ public class CitizensHumanNPC extends CitizensNPC { mcEntity.move(0, -0.1, 0); } } + + @Override + public void equip(Player equipper) { + ItemStack hand = equipper.getItemInHand(); + Equipment trait = getTrait(Equipment.class); + int slot = 0; + // First, determine the slot to edit + switch (hand.getType()) { + case PUMPKIN: + case JACK_O_LANTERN: + case LEATHER_HELMET: + case CHAINMAIL_HELMET: + case GOLD_HELMET: + case IRON_HELMET: + case DIAMOND_HELMET: + if (!equipper.isSneaking()) + slot = 1; + break; + case LEATHER_CHESTPLATE: + case CHAINMAIL_CHESTPLATE: + case GOLD_CHESTPLATE: + case IRON_CHESTPLATE: + case DIAMOND_CHESTPLATE: + if (!equipper.isSneaking()) + slot = 2; + break; + case LEATHER_LEGGINGS: + case CHAINMAIL_LEGGINGS: + case GOLD_LEGGINGS: + case IRON_LEGGINGS: + case DIAMOND_LEGGINGS: + if (!equipper.isSneaking()) + slot = 3; + break; + case LEATHER_BOOTS: + case CHAINMAIL_BOOTS: + case GOLD_BOOTS: + case IRON_BOOTS: + case DIAMOND_BOOTS: + if (!equipper.isSneaking()) + slot = 4; + break; + case AIR: + for (int i = 0; i < 5; i++) { + if (trait.get(i) != null && trait.get(i).getType() != Material.AIR) { + equipper.getWorld().dropItemNaturally(getBukkitEntity().getLocation(), trait.get(i)); + trait.set(i, null); + } + } + Messaging.send(equipper, "" + getName() + " had all of its items removed."); + } + // Now edit the equipment based on the slot + if (trait.get(slot) != null && trait.get(slot).getType() != Material.AIR) + equipper.getWorld().dropItemNaturally(getBukkitEntity().getLocation(), trait.get(slot)); + + ItemStack set = hand; + if (set != null && set.getType() != Material.AIR) { + if (hand.getAmount() > 1) + hand.setAmount(hand.getAmount() - 1); + else + hand = null; + equipper.setItemInHand(hand); + set.setAmount(1); + } + trait.set(slot, set); + } } \ No newline at end of file