diff --git a/src/main/java/de/craftinc/replicator/BlockPlaceListener.java b/src/main/java/de/craftinc/replicator/BlockPlaceListener.java index ad99301..70aa8d9 100644 --- a/src/main/java/de/craftinc/replicator/BlockPlaceListener.java +++ b/src/main/java/de/craftinc/replicator/BlockPlaceListener.java @@ -23,14 +23,19 @@ import org.bukkit.event.block.BlockPlaceEvent; import java.util.ArrayList; -public class BlockPlaceListener implements Listener { - - public void onBlockPlaced(BlockPlaceEvent event){ +@SuppressWarnings("UnusedDeclaration") +public class BlockPlaceListener implements Listener +{ + public void onBlockPlaced( BlockPlaceEvent event ) + { ArrayList replicators = Replicator.getReplicators(event.getBlockPlaced().getLocation()); - if(!replicators.isEmpty()){ - for(Location loc:replicators){ - Replicator rep = Replicator.getOrCreate(loc,event.getPlayer().getName()); - if(rep!=null){ + if ( !replicators.isEmpty() ) + { + for ( Location loc : replicators ) + { + Replicator rep = Replicator.getOrCreate(loc, event.getPlayer().getName()); + if ( rep != null ) + { event.getPlayer().sendMessage(Messages.newReplicator(rep)); } } diff --git a/src/main/java/de/craftinc/replicator/Commands.java b/src/main/java/de/craftinc/replicator/Commands.java index 3074b3e..f4f97b3 100644 --- a/src/main/java/de/craftinc/replicator/Commands.java +++ b/src/main/java/de/craftinc/replicator/Commands.java @@ -94,7 +94,7 @@ public class Commands implements CommandExecutor ArrayList replicators = new ArrayList(); for ( Location replicatorCenter : replicatorCenters ) { - replicators.add(Replicator.getOrCreate(replicatorCenter)); + replicators.add(Replicator.getOrCreate(replicatorCenter, player.getName())); } sender.sendMessage(Messages.info(replicators)); return true; @@ -102,29 +102,33 @@ public class Commands implements CommandExecutor // replicator specified as argument else if ( args.length == 2 ) { - Replicator rep = Replicator.getByName(args[1], player); - if (rep == null) + Replicator rep = Replicator.getByName(args[1], player.getName()); + if ( rep == null ) { sender.sendMessage(Messages.noReplicatorWithName(args[1])); return true; } - sender.sendMessage(Messages.info(new ArrayList(Arrays.asList(new Replicator[]{rep})))); + sender.sendMessage( + Messages.info(new ArrayList(Arrays.asList(new Replicator[] { rep })))); return true; } } // list - if (args.length == 1 && args[0].equalsIgnoreCase("list")) + if ( args.length == 1 && args[0].equalsIgnoreCase("list") ) { - sender.sendMessage(Messages.list(Replicator.getReplicatorsByOwner(), Replicator.getReplicatorsByUser())); + sender.sendMessage( + Messages.list(Replicator.getReplicatorsByOwner(player.getName()), + Replicator.getReplicatorsByUser(player.getName()))); return true; } - // addowner - if (args.length > 1 && args[0].equalsIgnoreCase("addowner")) + // addowner, delowner, adduser, deluser + if ( args.length > 1 && ( args[0].equalsIgnoreCase("addowner") || args[0].equalsIgnoreCase("delowner") || + args[0].equalsIgnoreCase("adduser") || args[0].equalsIgnoreCase("deluser") ) ) { // looking at replicator - if (args.length == 2) + if ( args.length == 2 ) { // get block where the player is looking at Block potentialReplicatorBlock = player.getTargetBlock(BlockUtil.transparentBlocks, 100); @@ -140,17 +144,67 @@ public class Commands implements CommandExecutor return true; } - ArrayList replicators = new ArrayList(); for ( Location replicatorCenter : replicatorCenters ) { - Replicator replicator = Replicator.getOrCreate(); - replicator.addOwner(args[1]); + Replicator replicator = Replicator.getOrCreate(replicatorCenter, player.getName()); + if ( replicator == null ) + { + sender.sendMessage(Messages.noReplicatorInSight); + continue; + } + if ( args[0].equalsIgnoreCase("addowner") ) + { + replicator.addOwner(args[1]); + } + else if ( args[0].equalsIgnoreCase("delowner") ) + { + replicator.rmOwner(args[1]); + } + else if ( args[0].equalsIgnoreCase("adduser") ) + { + replicator.addUser(args[1]); + } + else if ( args[0].equalsIgnoreCase("deluser") ) + { + replicator.rmUser(args[1]); + } + sender.sendMessage(Messages.addedOwner(args[1], replicator)); } return true; } - } + // replicator name specified as argument + else if ( args.length == 3 ) + { + Replicator replicator = Replicator.getByName(args[2], player.getName()); + if ( replicator == null ) + { + sender.sendMessage(Messages.noReplicatorWithName(args[2])); + return true; + } + + if ( args[0].equalsIgnoreCase("addowner") ) + { + replicator.addOwner(args[1]); + } + else if ( args[0].equalsIgnoreCase("delowner") ) + { + replicator.rmOwner(args[1]); + } + else if ( args[0].equalsIgnoreCase("adduser") ) + { + replicator.addUser(args[1]); + } + else if ( args[0].equalsIgnoreCase("deluser") ) + { + replicator.rmUser(args[1]); + } + + sender.sendMessage(Messages.addedOwner(player.getName(), replicator)); + return true; + } + } } diff --git a/src/main/java/de/craftinc/replicator/LocationSerializer.java b/src/main/java/de/craftinc/replicator/LocationSerializer.java new file mode 100644 index 0000000..1b285f2 --- /dev/null +++ b/src/main/java/de/craftinc/replicator/LocationSerializer.java @@ -0,0 +1,83 @@ +package de.craftinc.replicator; + +import org.bukkit.Location; +import org.bukkit.World; + +import java.util.HashMap; +import java.util.Map; + +public class LocationSerializer +{ + private static String worldKey = "world"; + private static String xKey = "x"; + private static String yKey = "y"; + private static String zKey = "z"; + + + private static World getWorld( String name ) throws Exception + { + World world = Plugin.instance.getServer().getWorld(name); + + if ( world == null ) + { + throw new Exception("World '" + name + "' does not exists anymore! Cannot get instance!"); + } + + return world; + } + + + public static Map serializeLocation( Location l ) + { + if ( l == null ) + { + return null; + } + + Map serializedLocation = new HashMap(); + + serializedLocation.put(worldKey, l.getWorld().getName()); + serializedLocation.put(xKey, l.getX()); + serializedLocation.put(yKey, l.getY()); + serializedLocation.put(zKey, l.getZ()); + + return serializedLocation; + } + + + public static Location deserializeLocation( Map map ) throws Exception + { + if ( map == null ) + { + return null; + } + + World w = getWorld((String) map.get(worldKey)); + + + // verbose loading of coordinates (they might be Double or Integer) + Object objX = map.get(xKey); + Object objY = map.get(yKey); + Object objZ = map.get(zKey); + + double x, y, z; + + if ( objX instanceof Integer ) + x = (double) (Integer) objX; + else + x = (Double) objX; + + if ( objY instanceof Integer ) + y = (double) (Integer) objY; + else + y = (Double) objY; + + if ( objZ instanceof Integer ) + z = (double) (Integer) objZ; + else + z = (Double) objZ; + + + return new Location(w, x, y, z); + } +} diff --git a/src/main/java/de/craftinc/replicator/Messages.java b/src/main/java/de/craftinc/replicator/Messages.java index c6c1ac7..5a5df3b 100644 --- a/src/main/java/de/craftinc/replicator/Messages.java +++ b/src/main/java/de/craftinc/replicator/Messages.java @@ -70,12 +70,19 @@ public class Messages public static String helpGeneral( Player player ) { return ChatColor.GREEN + pluginName + " - Usage:" + NEWLINE + - makeCmd(player, "help", "shows this help", null) + - makeCmd(player, "adduser | deluser", "Add or remove a player's right to use the replicator in front of you or the replicator given by \"id\".", null, "", "[id]") + - makeCmd(player, "addowner | delowner", "Add or remove a player's right to use AND add or remove other users and owners to the replicator in front of you or the replicator given by \"id\".", null, "", "[id]") + - makeCmd(player, "list", "Lists all your replicators.", null) + - makeCmd(player, "info", "Get information about the replicator in front of you or the replicator given by \"id\".", null, "[id]") + - makeCmd(player, "checkversion", "Checks for a newer version.", new String[] { "craftinc.replicator.update" }); + makeCmd(player, "help", "shows this help", null) + + makeCmd(player, "adduser | deluser", + "Add or remove a player's right to use the replicator in front of you or the replicator given by \"id\".", + null, "", "[id]") + + makeCmd(player, "addowner | delowner", + "Add or remove a player's right to use AND add or remove other users and owners to the replicator in front of you or the replicator given by \"id\".", + null, "", "[id]") + + makeCmd(player, "list", "Lists all your replicators.", null) + + makeCmd(player, "info", + "Get information about the replicator in front of you or the replicator given by \"id\".", null, + "[id]") + + makeCmd(player, "checkversion", "Checks for a newer version.", + new String[] { "craftinc.replicator.update" }); } public static String commandIssuedByNonPlayer @@ -88,7 +95,7 @@ public class Messages ChatColor.RED + "Sorry, you don't have permission to check for new versions."; public static String noReplicatorInSight = - ChatColor.RED + "You are not looking at an replicator."; + ChatColor.RED + "You are not looking at an replicator or you do not have permission to do this."; public static String updateMessage( String newVersion, String curVersion ) { @@ -107,16 +114,16 @@ public class Messages { StringBuilder sb = new StringBuilder(); sb.append(ChatColor.YELLOW + "The following replicators have been found:" + NEWLINE); - for (Replicator r: replicators) + for ( Replicator r : replicators ) { - sb.append(ChatColor.GOLD + r.id + " @ " + r.center.getX() + "," + r.center.getZ() + ":" + NEWLINE); + sb.append(ChatColor.GOLD + r.getName() + ":" + NEWLINE); sb.append(ChatColor.GREEN + "Owners:" + NEWLINE); - for (String owner: r.getOwners()) + for ( String owner : r.getOwners() ) { sb.append(ChatColor.WHITE + owner + " "); } sb.append(NEWLINE + ChatColor.GREEN + "Users:" + NEWLINE); - for (String user: r.getUsers()) + for ( String user : r.getUsers() ) { sb.append(ChatColor.WHITE + user + " "); } @@ -125,21 +132,21 @@ public class Messages return sb.toString(); } - public static String list(ArrayList repByOwner, ArrayList repByUser) + public static String list( ArrayList repByOwner, ArrayList repByUser ) { StringBuilder sb = new StringBuilder(); sb.append(ChatColor.YELLOW + "Replicators where you are owner:" + NEWLINE); - for (Replicator r: repByOwner) + for ( Replicator r : repByOwner ) { - sb.append(ChatColor.WHITE + r.id + " @ " + r.center.getX() + "," + r.center.getZ() + NEWLINE); + sb.append(ChatColor.WHITE + r.getName() + NEWLINE); } sb.append(NEWLINE); sb.append(ChatColor.YELLOW + "Replicators where you are user:" + NEWLINE); - for (Replicator r: repByUser) + for ( Replicator r : repByUser ) { - sb.append(ChatColor.WHITE + r.id + " @ " + r.center.getX() + "," + r.center.getZ() + NEWLINE); + sb.append(ChatColor.WHITE + r.getName() + NEWLINE); } return sb.toString(); @@ -147,11 +154,27 @@ public class Messages public static String noReplicatorWithName( String replicatorName ) { - return ChatColor.RED + "No replicator with name: " + replicatorName + " found or you don't have permission for that replicator."; + return ChatColor.RED + "No replicator with name: " + replicatorName + + " found or you don't have permission for that replicator."; } public static String addedOwner( String newOwner, Replicator replicator ) { - return ChatColor.GREEN + "New owner for " + replicator.id + + return ChatColor.GREEN + "Added " + ChatColor.GOLD + newOwner + " as owner for " + ChatColor.GOLD + + replicator.getName(); } + + public static String newReplicator( Replicator replicator ) + { + return ChatColor.GREEN + "Congratulations!" + ChatColor.YELLOW + " You have just built a working replicator with id: " + + ChatColor.GREEN + replicator.getName() + NEWLINE + + " Put item frames with items you want to replicate onto the front side and right click them to replicate." + NEWLINE + + " Use " + ChatColor.GOLD + "/repli adduser|deluser" + ChatColor.YELLOW + " while looking at it to give" + + " give other players permission to use your replicator." + NEWLINE + + " Use " + ChatColor.GOLD + "/repli help" + " to see a full list of commands you can use."; + } + + public static String couldNotSave = ChatColor.RED + "Sorry! Could not save the replicators to disk. After a server " + + "reload or restart the information about this replicator will be lost. You will " + + "still be able to use it. Tell a mod or admin about that problem."; } diff --git a/src/main/java/de/craftinc/replicator/Plugin.java b/src/main/java/de/craftinc/replicator/Plugin.java index bab8642..d3ce17e 100644 --- a/src/main/java/de/craftinc/replicator/Plugin.java +++ b/src/main/java/de/craftinc/replicator/Plugin.java @@ -40,7 +40,11 @@ public class Plugin extends JavaPlugin { Plugin.instance = this; + // load replicators + Replicator.loadReplicators(); + // create listeners + BlockPlaceListener blockPlaceListener = new BlockPlaceListener(); // commands Commands commandExecutor = new Commands(); @@ -48,5 +52,6 @@ public class Plugin extends JavaPlugin // register listeners PluginManager pm = this.getServer().getPluginManager(); + pm.registerEvents(blockPlaceListener, this); } } diff --git a/src/main/java/de/craftinc/replicator/Replicator.java b/src/main/java/de/craftinc/replicator/Replicator.java index e35142d..6d01aad 100644 --- a/src/main/java/de/craftinc/replicator/Replicator.java +++ b/src/main/java/de/craftinc/replicator/Replicator.java @@ -18,68 +18,201 @@ package de.craftinc.replicator; import org.bukkit.Location; -import org.bukkit.block.BlockFace; import org.bukkit.Material; +import org.bukkit.block.BlockFace; +import org.bukkit.configuration.file.FileConfiguration; +import org.bukkit.configuration.file.YamlConfiguration; +import org.bukkit.configuration.serialization.ConfigurationSerializable; +import java.io.File; +import java.io.IOException; import java.util.ArrayList; +import java.util.HashMap; +import java.util.Map; -public class Replicator { +public class Replicator implements ConfigurationSerializable +{ + /** + * Filename where to store the replicators. + */ + private static final String dataFileName = "replicators.yml"; + private static final String keyReplicators = "replicators"; + private static final String keyName = "name"; + private static final String keyCenter = "center"; + private static final String keyOwners = "owners"; + private static final String keyUsers = "users"; + + /** + * List of owners. An owner is able to use the replicator and is able to add other users/owners. + */ private ArrayList owners; + + /** + * List of users. A user is able to use the replicator. + */ private ArrayList users; + /** + * Name of the replicator. It will always be in the format "world,x,y,z". + */ + private String name; + + /** + * Center location of the replicator. + */ private Location center; - public Replicator(String firstOwner, Location spawn, Location center) { + /** + * List of all replicators accessible by center location. + */ + private static HashMap allReplicators; + + private static File replicatorsFile = new File(Plugin.instance.getDataFolder(), dataFileName); + private static FileConfiguration replicatorsFileConf = YamlConfiguration.loadConfiguration(replicatorsFile); + + + public Replicator( String firstOwner, Location center ) + { this.owners = new ArrayList(); this.users = new ArrayList(); this.owners.add(firstOwner); this.center = center; + name = center.getWorld() + "," + center.getBlockX() + "," + center.getBlockY() + "," + center.getBlockZ(); } - public void addUser(String user) { + @SuppressWarnings("unchecked unused") + public Replicator( Map map ) + { + try + { + name = (String) map.get(keyName); + center = LocationSerializer.deserializeLocation((Map) map.get(keyCenter)); + owners = (ArrayList) map.get(keyOwners); + users = (ArrayList) map.get(keyUsers); + + allReplicators.put(center, this); + } + catch ( Exception e ) + { + Plugin.instance.getLogger().severe(e.getMessage()); + } + } + + public ArrayList getOwners() + { + return owners; + } + + public ArrayList getUsers() + { + return users; + } + + public void addUser( String user ) + { this.users.add(user); } - public void addOwner(String owner) { + public void addOwner( String owner ) + { this.users.add(owner); } - public boolean rmUser(String user) { - if(this.users.remove(user)) return true; - else return false; + public boolean rmUser( String user ) + { + if ( this.users.remove(user) ) + return true; + else + return false; } - public boolean rmOwner(String owner) { - if(this.owners.remove(owner)) return true; - else return false; + public boolean rmOwner( String owner ) + { + if ( this.owners.remove(owner) ) + return true; + else + return false; } - public static ArrayList getReplicators(Location currentBlock){ + public boolean isOwner( String player ) + { + for ( String owner : owners ) + { + if ( owner.equals(player) ) + { + return true; + } + } + return false; + } + + public boolean isUser( String player ) + { + for ( String user : users ) + { + if ( user.equals(player) ) + { + return true; + } + } + return false; + } + + public void setName( String newName ) + { + this.name = newName; + //TODO: Save List + } + + public String getName() + { + return name; + } + + public static ArrayList getReplicators( Location currentBlock ) + { ArrayList replicators = new ArrayList(); ArrayList centers = getCenters(currentBlock); - for(Location center:centers){ - if(isValid(center)){ + for ( Location center : centers ) + { + if ( isValid(center) ) + { replicators.add(center); } } return replicators; } - private static Material[][][] getPattern(Location center){ - if(center.getBlock().getRelative(BlockFace.NORTH).getType().equals(Material.AIR)) return Pattern.getNorth(); - if(center.getBlock().getRelative(BlockFace.SOUTH).getType().equals(Material.AIR)) return Pattern.getSouth(); - if(center.getBlock().getRelative(BlockFace.WEST).getType().equals(Material.AIR)) return Pattern.getWest(); - if(center.getBlock().getRelative(BlockFace.EAST).getType().equals(Material.AIR)) return Pattern.getEast(); + private static Material[][][] getPattern( Location center ) + { + if ( center.getBlock().getRelative(BlockFace.NORTH).getType().equals(Material.AIR) ) + return Pattern.getNorth(); + if ( center.getBlock().getRelative(BlockFace.SOUTH).getType().equals(Material.AIR) ) + return Pattern.getSouth(); + if ( center.getBlock().getRelative(BlockFace.WEST).getType().equals(Material.AIR) ) + return Pattern.getWest(); + if ( center.getBlock().getRelative(BlockFace.EAST).getType().equals(Material.AIR) ) + return Pattern.getEast(); return null; } - private static boolean isValid(Location center){ + private static boolean isValid( Location center ) + { Material[][][] pattern = getPattern(center); - for(int x=0;x<=2;x++){ - for(int y=0;y<=2;y++){ - for(int z=0;z<=2;z++){ - if((pattern[x][y][z]!=center.getBlock().getRelative(x-1,y-1,z-1).getType())&&((pattern[x][y][z]!=null))){ + if ( pattern == null ) + { + return false; + } + for ( int x = 0; x <= 2; x++ ) + { + for ( int y = 0; y <= 2; y++ ) + { + for ( int z = 0; z <= 2; z++ ) + { + if ( ( pattern[x][y][z] != center.getBlock().getRelative(x - 1, y - 1, z - 1).getType() ) && + ( ( pattern[x][y][z] != null ) ) ) + { return false; } } @@ -88,18 +221,136 @@ public class Replicator { return true; } - private static ArrayList getCenters(Location currentBlock){ + private static ArrayList getCenters( Location currentBlock ) + { ArrayList centers = new ArrayList(); Location nextBlock; - for(int x=-1;x<=1;x++){ - for(int y=-1;y<=1;y++){ - for(int z=-1;z<=1;z++){ - nextBlock = currentBlock.getBlock().getRelative(x,y,z).getLocation(); - if(nextBlock.getBlock().getType().equals(Pattern.getCenter())) centers.add(nextBlock); + for ( int x = -1; x <= 1; x++ ) + { + for ( int y = -1; y <= 1; y++ ) + { + for ( int z = -1; z <= 1; z++ ) + { + nextBlock = currentBlock.getBlock().getRelative(x, y, z).getLocation(); + if ( nextBlock.getBlock().getType().equals(Pattern.getCenter()) ) + centers.add(nextBlock); } } } return centers; } + /** + * Gets a replicator with the given location. If no replicator exists a new one is created. + * Returns null if player is not owner or user of the replicator. + * + * @param loc center of the replicator + * @param playerName name of the player + * @return Replicator + */ + public static Replicator getOrCreate( Location loc, String playerName ) + { + Replicator rep = allReplicators.get(loc); + + // replicator already exists + if ( rep != null ) + { + if ( rep.isOwner(playerName) || rep.isUser(playerName) ) + { + return rep; + } + else + { + return null; + } + } + // replicator does not exist, create one + else + { + rep = new Replicator(playerName, loc); + allReplicators.put(loc, rep); + try { + Replicator.saveReplicators(); + } + catch ( IOException e ) + { + Plugin.instance.getServer().getPlayer(playerName).sendMessage(Messages.couldNotSave); + Plugin.instance.getLogger().severe("Could not save replicators to file: " + e.getMessage()); + } + return rep; + } + } + + /** + * Get a replicator with the specified name. Returns null if player + * is not owner or user or if replicator does not exist. + * + * @param repName name of the replicator + * @param playerName name of the player + * @return Replicator + */ + public static Replicator getByName( String repName, String playerName ) + { + for ( Replicator rep : allReplicators.values() ) + { + if ( rep.getName().equals(repName) ) + { + if ( rep.isOwner(playerName) || rep.isUser(playerName) ) + { + return rep; + } + } + } + return null; + } + + public static ArrayList getReplicatorsByOwner( String playerName ) + { + ArrayList reps = new ArrayList(); + for ( Replicator rep : allReplicators.values() ) + { + if ( rep.isOwner(playerName) ) + { + reps.add(rep); + } + } + return reps; + } + + public static ArrayList getReplicatorsByUser( String playerName ) + { + ArrayList reps = new ArrayList(); + for ( Replicator rep : allReplicators.values() ) + { + if ( rep.isUser(playerName) ) + { + reps.add(rep); + } + } + return reps; + } + + @SuppressWarnings("unused") + public Map serialize() + { + Map map = new HashMap(); + + map.put(keyName, name); + map.put(keyCenter, LocationSerializer.serializeLocation(center)); + map.put(keyOwners, owners); + map.put(keyUsers, users); + + return map; + } + + public static void loadReplicators() + { + replicatorsFileConf.getList(keyReplicators); + } + + public static void saveReplicators() throws IOException + { + replicatorsFileConf.set(keyReplicators, new ArrayList(allReplicators.values())); + replicatorsFileConf.save(replicatorsFile); + } } diff --git a/src/main/java/de/craftinc/replicator/UpdateHelper.java b/src/main/java/de/craftinc/replicator/UpdateHelper.java index 233f0e0..70d0857 100644 --- a/src/main/java/de/craftinc/replicator/UpdateHelper.java +++ b/src/main/java/de/craftinc/replicator/UpdateHelper.java @@ -1,4 +1,4 @@ -/* Craft Inc. BorderProtection +/* Craft Inc. Replicator Copyright (C) 2013 Paul Schulze This program is free software: you can redistribute it and/or modify @@ -29,7 +29,7 @@ public class UpdateHelper * The URL from which the Plugin tries to get the latest version. */ @SuppressWarnings("FieldCanBeLocal") - private static final String updateUrl = "http://www.craftinc.de/plugins/update/craftinc-borderprotection"; + private static final String updateUrl = "http://www.craftinc.de/plugins/update/craftinc-replicator"; /** * The latest version which was seen on last check.