diff --git a/src/main/java/de/diddiz/LogBlock/listeners/BlockPlaceLogging.java b/src/main/java/de/diddiz/LogBlock/listeners/BlockPlaceLogging.java index e4bbbb9..68ddb3a 100644 --- a/src/main/java/de/diddiz/LogBlock/listeners/BlockPlaceLogging.java +++ b/src/main/java/de/diddiz/LogBlock/listeners/BlockPlaceLogging.java @@ -2,6 +2,8 @@ package de.diddiz.LogBlock.listeners; import static de.diddiz.LogBlock.config.Config.getWorldConfig; import static de.diddiz.LogBlock.config.Config.isLogging; + +import org.bukkit.Location; import org.bukkit.Material; import org.bukkit.block.BlockState; import org.bukkit.event.EventHandler; @@ -11,6 +13,7 @@ import org.bukkit.event.player.PlayerBucketEmptyEvent; import de.diddiz.LogBlock.LogBlock; import de.diddiz.LogBlock.Logging; import de.diddiz.LogBlock.config.WorldConfig; +import de.diddiz.util.BukkitUtils; public class BlockPlaceLogging extends LoggingListener { @@ -26,8 +29,32 @@ public class BlockPlaceLogging extends LoggingListener final BlockState before = event.getBlockReplacedState(); final BlockState after = event.getBlockPlaced().getState(); final String playerName = event.getPlayer().getName(); + + //Handle falling blocks + if (event.getBlock().getType() == Material.SAND || event.getBlock().getType() == Material.GRAVEL) { + Location loc = event.getBlock().getLocation(); + int x = loc.getBlockX(); + int y = loc.getBlockY(); + int z = loc.getBlockZ(); + while (y > 0 && BukkitUtils.canFall(loc.getWorld(), x, (y - 1), z)) { + y--; + } + // If y is 0 then the sand block fell out of the world :( + if (y != 0) { + Location finalLoc = new Location(loc.getWorld(), x, y, z); + if (finalLoc.getBlock().getType() == Material.AIR) { + consumer.queueBlockPlace(playerName, finalLoc, type, event.getBlock().getData()); + } else { + consumer.queueBlockReplace(playerName, finalLoc, finalLoc.getBlock().getTypeId(), finalLoc.getBlock().getData(), type, event.getBlock().getData()); + } + } + return; + } + + //Sign logging is handled elsewhere if (wcfg.isLogging(Logging.SIGNTEXT) && (type == 63 || type == 68)) return; + //Delay queuing by one tick to allow data to be updated LogBlock.getInstance().getServer().getScheduler().scheduleSyncDelayedTask(LogBlock.getInstance(), new Runnable() { diff --git a/src/main/java/de/diddiz/util/BukkitUtils.java b/src/main/java/de/diddiz/util/BukkitUtils.java index a43b124..14a5b8d 100644 --- a/src/main/java/de/diddiz/util/BukkitUtils.java +++ b/src/main/java/de/diddiz/util/BukkitUtils.java @@ -12,6 +12,7 @@ import java.util.Set; import org.bukkit.ChatColor; import org.bukkit.Chunk; import org.bukkit.Location; +import org.bukkit.Material; import org.bukkit.World; import org.bukkit.block.BlockFace; import org.bukkit.block.BlockState; @@ -38,13 +39,13 @@ public class BukkitUtils blockEquivalents.add(new HashSet(Arrays.asList(73, 74))); blockEquivalents.add(new HashSet(Arrays.asList(75, 76))); blockEquivalents.add(new HashSet(Arrays.asList(93, 94))); - + relativeBreakable = new HashSet(2); relativeBreakable.add(63); // Sign relativeBreakable.add(68); // Sign relativeBreakable.add(65); // Ladder relativeBreakable.add(77); // Button - + relativeTopBreakable = new HashSet(19); relativeTopBreakable.add(6); ////Vegetation start//// relativeTopBreakable.add(31); // @@ -66,7 +67,7 @@ public class BukkitUtils relativeTopBreakable.add(93); // Redstone repeater relativeTopBreakable.add(94); // Redstone repeater } - + /** * Returns a list of block locations around the block that are of the type specified by the integer list parameter * @@ -76,15 +77,15 @@ public class BukkitUtils */ public static List getBlocksNearby(org.bukkit.block.Block block, Set type) { ArrayList blocks = new ArrayList(); - if(type.contains(block.getRelative(BlockFace.EAST).getTypeId())) + if (type.contains(block.getRelative(BlockFace.EAST).getTypeId())) blocks.add(block.getRelative(BlockFace.EAST).getLocation()); - if(type.contains(block.getRelative(BlockFace.WEST).getTypeId())) + if (type.contains(block.getRelative(BlockFace.WEST).getTypeId())) blocks.add(block.getRelative(BlockFace.WEST).getLocation()); - if(type.contains(block.getRelative(BlockFace.NORTH).getTypeId())) + if (type.contains(block.getRelative(BlockFace.NORTH).getTypeId())) blocks.add(block.getRelative(BlockFace.NORTH).getLocation()); - if(type.contains(block.getRelative(BlockFace.SOUTH).getTypeId())) + if (type.contains(block.getRelative(BlockFace.SOUTH).getTypeId())) blocks.add(block.getRelative(BlockFace.SOUTH).getLocation()); - if(type.contains(block.getRelative(BlockFace.UP).getTypeId())) + if (type.contains(block.getRelative(BlockFace.UP).getTypeId())) blocks.add(block.getRelative(BlockFace.UP).getLocation()); return blocks; } @@ -183,11 +184,11 @@ public class BukkitUtils public static Set> getBlockEquivalents() { return blockEquivalents; } - + public static Set getRelativeBreakables() { return relativeBreakable; } - + public static Set getRelativeTopBreakabls() { return relativeTopBreakable; } @@ -252,6 +253,20 @@ public class BukkitUtils return 0; } + public static boolean canFall(World world, int x, int y, int z) { + Material mat = world.getBlockAt(x, y, z).getType(); + + // Air + if (mat == Material.AIR) { + return true; + } else if (mat == Material.WATER || mat == Material.STATIONARY_WATER || mat == Material.LAVA || mat == Material.STATIONARY_LAVA) { // Fluids + return true; + } else if (mat == Material.SIGN || mat == Material.FIRE) { // Misc. + return true; + } + return false; + } + public static class ItemStackComparator implements Comparator { @Override