@EventHandler public void onBlockPlaceEvent(BlockPlaceEvent event) { if (!isEnabled()) return; if (event.isCancelled()) return; try { BlockType type = BlockType.Unknown; Player player = event.getPlayer(); Block block = event.getBlock(); if (event.getBlock().getTypeId() == 0) { ForgePermittor.log("tile: " + getValidator().CheckItem(event.getItemInHand()), true); if (getValidator().CheckItem(event.getItemInHand()) == ItemType.Container) type = BlockType.Container; } else { ForgePermittor.log("tile: " + getValidator().CheckBlock(event.getBlock()), true); type = getValidator().CheckBlock(event.getBlock()); } if (type == BlockType.Container) { if (CheckBlockPlaceforContainer(player, block.getRelative(BlockFace.NORTH)) || CheckBlockPlaceforContainer(player, block.getRelative(BlockFace.SOUTH)) || CheckBlockPlaceforContainer(player, block.getRelative(BlockFace.WEST)) || CheckBlockPlaceforContainer(player, block.getRelative(BlockFace.EAST))) { event.setCancelled(true); } } } catch (Exception e) { ForgePermittor.log(e.toString(), true); } }
/** Check the four sides of the base block to see if there's room for a large chest */ public static Block findLarge(Block base) { // Check all 4 sides for air. Block block; block = base.getRelative(BlockFace.NORTH); if (canBeReplaced(block.getState()) && (!Config.getInstance().getNoInterfere() || !checkChest(block, Material.CHEST))) { return block; } block = base.getRelative(BlockFace.EAST); if (canBeReplaced(block.getState()) && (!Config.getInstance().getNoInterfere() || !checkChest(block, Material.CHEST))) { return block; } block = base.getRelative(BlockFace.SOUTH); if (canBeReplaced(block.getState()) && (!Config.getInstance().getNoInterfere() || !checkChest(block, Material.CHEST))) { return block; } block = base.getRelative(BlockFace.WEST); if (canBeReplaced(block.getState()) && (!Config.getInstance().getNoInterfere() || !checkChest(block, Material.CHEST))) { return block; } return null; }
public boolean isDoubleChest() { final Block b = loc.getBlock(); return (isChest(b.getRelative(BlockFace.NORTH)) || isChest(b.getRelative(BlockFace.SOUTH)) || isChest(b.getRelative(BlockFace.EAST)) || isChest(b.getRelative(BlockFace.WEST))); }
@EventHandler(priority = EventPriority.HIGHEST, ignoreCancelled = true) public void BlockBreakEvent(BlockBreakEvent e) { if (e.getBlock().hasMetadata("ce.Ice")) e.setCancelled(true); CEventHandler.handleEvent(e.getPlayer(), e, blockBroken); if (e.getBlock().hasMetadata("ce.mine")) { Block b = e.getBlock(); b.removeMetadata("ce.mine", Main.plugin); Block[] blocks = { b.getRelative(0, 1, 0), b.getRelative(1, 0, 0), b.getRelative(-1, 0, 0), b.getRelative(0, 0, 1), b.getRelative(0, 0, -1) }; for (Block block : blocks) { if (block.hasMetadata("ce.mine.secondary")) { String[] s = block.getMetadata("ce.mine.secondary").get(0).asString().split(" "); Location loc = new Location( e.getPlayer().getWorld(), Integer.parseInt(s[0]), Integer.parseInt(s[1]), Integer.parseInt(s[2])); Location blockLoc = b.getLocation(); if (loc.getBlockX() == blockLoc.getBlockX() && loc.getBlockY() == blockLoc.getBlockY() && loc.getBlockZ() == blockLoc.getBlockZ()) block.removeMetadata("ce.mine.secondary", Main.plugin); } } } }
protected int getDiagonalNeighborCount( Block block, MaterialAndData liveMaterial, boolean includeCommands) { int liveCount = 0; for (BlockFace face : DIAGONAL_FACES) { if (liveMaterial.is(block.getRelative(face))) { liveCount++; } } if (yRadius > 0) { Block upBlock = block.getRelative(BlockFace.UP); for (BlockFace face : NEIGHBOR_FACES) { if (liveMaterial.is(upBlock.getRelative(face))) { liveCount++; } } Block downBlock = block.getRelative(BlockFace.DOWN); for (BlockFace face : NEIGHBOR_FACES) { if (liveMaterial.is(downBlock.getRelative(face))) { liveCount++; } } } return liveCount; }
// RŽcupŽration du Relative et ajout du SignManager dans le Set public static boolean registerSign(Location locsign) { try { locsign.getBlock(); } catch (Exception e) { return false; } // VŽrifie sur la locsign est un block if (!(locsign.getBlock().getState() instanceof org.bukkit.block.Sign)) return false; Block bs = locsign.getBlock(); org.bukkit.material.Sign signmat = (org.bukkit.material.Sign) bs.getState().getData(); Location relative = null; if (!signmat.isWallSign()) relative = bs.getRelative(BlockFace.DOWN).getLocation(); else if (signmat.getAttachedFace() == BlockFace.EAST) relative = bs.getRelative(BlockFace.EAST).getLocation(); else if (signmat.getAttachedFace() == BlockFace.WEST) relative = bs.getRelative(BlockFace.WEST).getLocation(); else if (signmat.getAttachedFace() == BlockFace.NORTH) relative = bs.getRelative(BlockFace.NORTH).getLocation(); else if (signmat.getAttachedFace() == BlockFace.SOUTH) relative = bs.getRelative(BlockFace.SOUTH).getLocation(); SignManager sm = new SignManager(locsign, relative); sm.RefreshSign(); return true; }
private void destroyAbove(final Block b) { if (b.getTypeId() != PitfallSettings.redstonePitItem) return; b.setTypeId(0); plugin .getServer() .getScheduler() .scheduleSyncDelayedTask( plugin, new Runnable() { public void run() { try { b.setTypeId(PitfallSettings.redstonePitItem); } catch (Exception e) { } } }, PitfallSettings.returnDelay); if (PitfallSettings.redstoneTriggerCorner) { destroyAbove(b.getRelative(BlockFace.NORTH_EAST)); destroyAbove(b.getRelative(BlockFace.NORTH_WEST)); destroyAbove(b.getRelative(BlockFace.SOUTH_EAST)); destroyAbove(b.getRelative(BlockFace.SOUTH_WEST)); } destroyAbove(b.getRelative(BlockFace.NORTH)); destroyAbove(b.getRelative(BlockFace.EAST)); destroyAbove(b.getRelative(BlockFace.WEST)); destroyAbove(b.getRelative(BlockFace.SOUTH)); }
private boolean isCloseDoor(Location actual) { BlockFace[] blockFaces = {BlockFace.EAST, BlockFace.NORTH, BlockFace.WEST, BlockFace.SOUTH}; actual.setY(actual.getY()); Block base = actual.getBlock(); for (BlockFace bf : blockFaces) { Block bu = base.getRelative(bf); if ((bu.getType() == Material.WOODEN_DOOR)) { byte openData = 0x4; byte doorData = (byte) (bu.getData()); if ((doorData & 0x4) == 0x4) { doorData = (byte) (doorData & 0x3); } else { doorData = (byte) (doorData | 0x7); } bu.setData(doorData); if ((bu.getRelative(BlockFace.UP).getType() == Material.WOODEN_DOOR)) { doorData = (byte) (bu.getRelative(BlockFace.UP).getData()); if ((doorData & 0x1) == 1) { doorData = 0x9; } else { doorData = 0x8; } bu.getRelative(BlockFace.UP).setData(doorData); } return true; } } return false; }
// return true if block can be broken private boolean checkBlockBroken(Block broken) { return canBreakBlock(broken.getRelative(BlockFace.UP), broken) && canBreakBlock(broken.getRelative(BlockFace.NORTH), broken) && canBreakBlock(broken.getRelative(BlockFace.EAST), broken) && canBreakBlock(broken.getRelative(BlockFace.SOUTH), broken) && canBreakBlock(broken.getRelative(BlockFace.WEST), broken); }
public static boolean poweringDoor(Block block) { return block.getRelative(BlockFace.NORTH).getState().getData() instanceof Openable || block.getRelative(BlockFace.SOUTH).getState().getData() instanceof Openable || block.getRelative(BlockFace.EAST).getState().getData() instanceof Openable || block.getRelative(BlockFace.WEST).getState().getData() instanceof Openable || block.getRelative(BlockFace.DOWN).getState().getData() instanceof Openable || block.getRelative(BlockFace.UP).getState().getData() instanceof Openable; }
private static Location getAdjacentTrack(final Block center, final BlockFace dir) { if (MinecartUtils.isTrack(center.getRelative(dir))) return center.getRelative(dir).getLocation(); if ((center.getRelative(dir).getTypeId() == Material.CHEST.getId()) && MinecartUtils.isTrack(center.getRelative(dir).getRelative(dir))) return center.getRelative(dir).getRelative(dir).getLocation(); return null; }
private boolean isReversed(BlockFace primary) { BlockFace secondary = primary.getOppositeFace(); if (isSolid(top.getRelative(secondary)) || isSolid(bottom.getRelative(secondary))) { return false; } else { return isSolid(top.getRelative(primary)) || isSolid(bottom.getRelative(primary)); } }
/** * Returns a list of block locations around the block that are of the type specified by the * integer list parameter * * @param block * @param type * @return List of block locations around the block that are of the type specified by the integer * list parameter */ public static List<Location> getBlocksNearby(org.bukkit.block.Block block, Set<Material> type) { ArrayList<Location> blocks = new ArrayList<Location>(); for (BlockFace blockFace : relativeBlockFaces) { if (type.contains(block.getRelative(blockFace).getType())) { blocks.add(block.getRelative(blockFace).getLocation()); } } return blocks; }
/** * This method checks a block for shop protection for other chests near or that chest * * @param block Block to chest, intended to be a chest * @param player Player to cross-check for permissions * @param plugin currently active PhysicalShop to consider * @return true if the player should be blocked */ public static boolean isProtectedChestsAround( final Block block, final Player player, final PhysicalShop plugin) { for (final BlockFace blockFace : CARDINAL_DIRECTIONS) { final Block checkBlock = block.getRelative(blockFace); if (checkBlock.getType() == CHEST && !hasAccess(player, checkBlock.getRelative(UP), plugin)) return true; } return false; }
@Override public void toPlayer(Player player, Location value) { Block block = value.getBlock(); Block above = block.getRelative(0, 1, 0); while (!block.isEmpty() || !above.isEmpty()) { block = above; above = block.getRelative(0, 1, 0); } player.teleport(block.getLocation()); }
private static boolean checkBlockIsOnBorderOfSlice(Block block, ArrayList<Block> slice) { BlockFace[] faces = {BlockFace.NORTH, BlockFace.EAST, BlockFace.SOUTH, BlockFace.WEST}; if (slice.contains(block.getRelative(faces[0])) && slice.contains(block.getRelative(faces[1])) && slice.contains(block.getRelative(faces[2])) && slice.contains(block.getRelative(faces[3]))) { return false; } return true; }
@SuppressWarnings("deprecation") private boolean signFinder( Player player, Block block, BlockFace[] testBlocks, BlockFace[] testFaces, final Block lever) { Block newBlock; BlockFace testFace; for (int c = 0; c < 5; c++) { if (c == 2) { newBlock = block.getRelative(testBlocks[c], 2); testFace = testFaces[1]; } else { newBlock = block.getRelative(testBlocks[c]); testFace = testFaces[0]; } if (!(newBlock.getState() instanceof Sign)) continue; if (((org.bukkit.material.Sign) newBlock.getState().getData()).getFacing() != testFace) continue; int s = signConverter(player, newBlock); if (s > 0) { boolean n = s == 1; if (n || !enableBL) return n; if (lever.getType() != Material.LEVER) return n; Lever l = (Lever) lever.getState().getData(); // if (l.isPowered()) // return n; l.setPowered(false); l.setPowered(true); lever.setData(l.getData()); lever.getWorld().playEffect(lever.getLocation(), Effect.SMOKE, 4); Bukkit.getScheduler() .scheduleSyncDelayedTask( PLUGIN, new Runnable() { @Override public void run() { if (lever.getType() != Material.LEVER) return; Lever l = (Lever) lever.getState().getData(); if (!l.isPowered()) return; l.setPowered(false); lever.setData(l.getData()); lever.getWorld().playEffect(lever.getLocation(), Effect.SMOKE, 4); } }, 20L); } } return false; }
private static void buildTreeLayer2(ArrayList<Block> blocks) { ArrayList<Block> branches = new ArrayList<Block>(); for (Block b : blocks) { BlockFace dir = getBuildDirection(b); Block handle = b.getRelative(dir); handle.setTypeIdAndData(17, (byte) 1, false); branches.add(handle); switch (dir) { case NORTH: branches.add(handle.getRelative(-1, 0, 1)); branches.add(handle.getRelative(-1, 0, -1)); break; case EAST: branches.add(handle.getRelative(-1, 0, -1)); branches.add(handle.getRelative(1, 0, -1)); break; case SOUTH: branches.add(handle.getRelative(1, 0, 1)); branches.add(handle.getRelative(1, 0, -1)); break; case WEST: branches.add(handle.getRelative(-1, 0, 1)); branches.add(handle.getRelative(1, 0, 1)); break; } } if (!branches.isEmpty()) { for (Block branch : branches) { branch.setTypeIdAndData(17, (byte) 1, false); populateTreeBranch(branch, 2); } } }
@EventHandler public void onVehicleImpact(CartBlockImpactEvent event) { // validate if (!event.getBlocks().matches(getMaterial())) return; if (!event.getBlocks().hasSign()) return; if (event.isMinor()) return; if (!(event.getBlocks().matches("cartlift up") || event.getBlocks().matches("cartlift down"))) return; Minecart cart = (Minecart) event.getVehicle(); // go boolean up = event.getBlocks().matches("cartlift up"); Block destination = event.getBlocks().sign; BlockFace face; if (up) face = BlockFace.UP; else face = BlockFace.DOWN; while (true) { if (destination.getLocation().getBlockY() <= 0 && !up) return; if (destination.getLocation().getBlockY() >= destination.getWorld().getMaxHeight() - 1 && up) return; destination = destination.getRelative(face); if (SignUtil.isSign(destination) && event.getBlocks().base.getTypeId() == destination.getRelative(BlockFace.UP, 1).getTypeId()) { ChangedSign state = BukkitUtil.toChangedSign(destination); String testLine = state.getLine(1); if (testLine.equalsIgnoreCase("[CartLift Up]") || testLine.equalsIgnoreCase("[CartLift Down]") || testLine.equalsIgnoreCase("[CartLift]")) { destination = destination.getRelative(BlockFace.UP, 2); break; } } } CartUtils.teleport( cart, new Location( destination.getWorld(), destination.getX(), destination.getY(), destination.getZ(), cart.getLocation().getYaw(), cart.getLocation().getPitch())); }
public void update() { for (int k = 0; k < y; k++) { for (int i = 0; i < x; i++) { for (int j = 0; j < z; j++) { startBlock.getRelative(i, k, j).setTypeId(field[k][i][j]); if (data != null) { startBlock.getRelative(i, k, j).setData((byte) data[k][i][j]); } } } } }
// finds a block the player can probably see. this is how visualizations "cling" to the ground or // ceiling private static Location getVisibleLocation(World world, int x, int y, int z) { Block block = world.getBlockAt(x, y, z); BlockFace direction = (isTransparent(block)) ? BlockFace.DOWN : BlockFace.UP; while (block.getY() >= 1 && block.getY() < world.getMaxHeight() - 1 && (!isTransparent(block.getRelative(BlockFace.UP)) || isTransparent(block))) { block = block.getRelative(direction); } return block.getLocation(); }
@EventHandler(ignoreCancelled = true) public void onBlockPistonRetract(BlockPistonRetractEvent event) { Block piston = event.getBlock(); Block extension = piston.getRelative(event.getDirection()); Block block = extension.getRelative(event.getDirection()); Deadbolted db = Deadbolt.get(block); if (db.isProtected()) { // TODO why cant we just cancel event.setCancelled(true); piston.setData((byte) (piston.getData() ^ 0x8)); extension.setType(Material.AIR); } }
@SuppressWarnings("deprecation") @EventHandler(priority = EventPriority.LOW) public void onBlockPistonExtend(BlockPistonExtendEvent event) { Map map = Rixor.getRotation().getSlot().getMap(); for (Block block : event.getBlocks()) { BlockState newState = block.getRelative(event.getDirection()).getState(); newState.setData(new MaterialData(block.getType(), block.getData())); BlockChangeEvent change = new BlockChangeEvent( event, map, null, block.getRelative(event.getDirection()).getState(), newState); Rixor.callEvent(change); } }
public void onBlockRedstoneChange(BlockRedstoneEvent event) { if (PitfallSettings.redstonePitEnabled) { Block b = event.getBlock(); if (event.getOldCurrent() == 0 && event.getNewCurrent() > 0) { if (b.getRelative(BlockFace.UP).getTypeId() == PitfallSettings.redstonePitItem) { destroyAbove(b.getRelative(BlockFace.UP)); } if (b.getRelative(BlockFace.DOWN).getTypeId() == PitfallSettings.redstonePitItem) { destroyBelow(b.getRelative(BlockFace.DOWN), b); } } } }
@Override public void animate(Fight fight, Character attacking, Character defending, ItemStack weapon) { if (attacking.getPlayer().isOnline()) { Player player = attacking.getPlayer().getPlayer(); BlockIterator iterator = new BlockIterator(player, 8); long delay = 0L; int i = 0; while (iterator.hasNext()) { Block block = iterator.next(); setShard(block.getRelative(BlockFace.UP, 2).getRelative(BlockFace.DOWN, i), delay); float yaw = player.getLocation().getYaw(); yaw = (yaw + 90) % 360; int left = (int) Math.floor((yaw - 90) / 90); int right = (int) Math.floor((yaw + 90) / 90); BlockFace leftBlockFace = BlockFace.UP; switch (left) { case 0: leftBlockFace = BlockFace.NORTH; break; case 1: leftBlockFace = BlockFace.WEST; break; case 2: leftBlockFace = BlockFace.SOUTH; break; case 3: leftBlockFace = BlockFace.EAST; break; } BlockFace rightBlockFace = BlockFace.UP; switch (right) { case 0: rightBlockFace = BlockFace.NORTH; break; case 1: rightBlockFace = BlockFace.WEST; break; case 2: rightBlockFace = BlockFace.SOUTH; break; case 3: rightBlockFace = BlockFace.EAST; break; } setShard(block.getRelative(leftBlockFace, 2).getRelative(BlockFace.DOWN, i), delay); setShard(block.getRelative(rightBlockFace, 2).getRelative(BlockFace.DOWN, i), delay); delay += 5L; i++; } } }
/** * Places Blocks of a predetermined type just above the highest Block at each corner of the given * Chunk * * @param chunk The given Chunk */ public static void markCorners(Chunk chunk) { // Get the highest Block (should be empty) at the South-West corner Block block = chunk.getBlock(0, 127, 0); // Move down until a non-empty Block is found while (block.getTypeId() == 0) block = block.getRelative(BlockFace.DOWN); // Change the empty Block just above the Block found block.getRelative(BlockFace.UP).setTypeId(cornerID); // Get the highest Block (should be empty) at the South-East corner block = chunk.getBlock(0, 127, 15); // Move down until a non-empty Block is found while (block.getTypeId() == 0) block = block.getRelative(BlockFace.DOWN); // Change the empty Block just above the Block found block.getRelative(BlockFace.UP).setTypeId(cornerID); // Get the highest Block (should be empty) at the North-West corner block = chunk.getBlock(15, 127, 0); // Move down until a non-empty Block is found while (block.getTypeId() == 0) block = block.getRelative(BlockFace.DOWN); // Change the empty Block just above the Block found block.getRelative(BlockFace.UP).setTypeId(cornerID); // Get the highest Block (should be empty) at the North-East corner block = chunk.getBlock(15, 127, 15); // Move down until a non-empty Block is found while (block.getTypeId() == 0) block = block.getRelative(BlockFace.DOWN); // Change the empty Block just above the Block found block.getRelative(BlockFace.UP).setTypeId(cornerID); }
public static Block findOtherHalfofChest(Block b) { // didn't find one, so find the other half of the chest and check it's faces Block[] adjBlocks = new Block[] { b.getRelative(BlockFace.NORTH), b.getRelative(BlockFace.EAST), b.getRelative(BlockFace.SOUTH), b.getRelative(BlockFace.WEST) }; for (int i = 0; i < adjBlocks.length; i++) if (adjBlocks[i].getType() == Material.CHEST) return adjBlocks[i]; return null; }
@Override public CastResult cast(SpellContext context) { Player player = context.<Player>getPlayer(); Block target = context.<Block>getTarget().get(); BlockFace direction = getClickedFace(player); Block phased = null; switch (direction) { case NORTH: phased = target.getRelative(0, 0, -1); break; case SOUTH: phased = target.getRelative(0, 0, 1); break; case EAST: phased = target.getRelative(1, 0, 0); break; case WEST: phased = target.getRelative(-1, 0, 0); break; case UP: phased = target.getRelative(0, +3, 0); break; case DOWN: phased = target.getRelative(0, -2, 0); break; default: phased = target; break; } if (!BukkitTargetUtils.getTransparent().contains(phased.getType())) { player.sendMessage(ChatColor.RED + "You cannot phase through that block"); return CastResult.FAILURE; } else if (BukkitTargetUtils.getTransparent() .contains(phased.getRelative(0, -1, 0).getType())) { Location loc = phased.getRelative(0, -1, 0).getLocation(); loc.add(0.5, 0, 0.5); loc.setPitch(player.getLocation().getPitch()); loc.setYaw(player.getLocation().getYaw()); player.teleport(loc); return CastResult.SUCCESS; } else if (BukkitTargetUtils.getTransparent().contains(phased.getRelative(0, 1, 0).getType())) { Location loc = phased.getLocation(); loc.add(0.5, 0, 0.5); loc.setPitch(player.getLocation().getPitch()); loc.setYaw(player.getLocation().getYaw()); player.teleport(loc); return CastResult.SUCCESS; } else { player.sendMessage(ChatColor.RED + "You cannot phase through that block"); return CastResult.FAILURE; } }
public String getNotchPortalDestination(Player p, Location l) throws MoreThanOneSignFoundException, NoMultiverseSignFoundException { // Determine corner, should be 1 of 4 Block block = l.getBlock(); Location portalStart; Location portalEnd; List<Sign> foundSigns = null; if (block.getType() == Material.PORTAL) { // We found the bottom 2: ## if (block.getRelative(1, 0, 0).getType() == Material.PORTAL) { portalEnd = block.getRelative(1, 0, 0).getLocation(); portalStart = block.getRelative(0, 2, 0).getLocation(); foundSigns = this.checkBlocksOutside( l.getWorld().getBlockAt(portalStart), l.getWorld().getBlockAt(portalEnd), Axis.X); this.plugin.log(Level.FINER, "Found normal X"); } else if (block.getRelative(-1, 0, 0).getType() == Material.PORTAL) { portalEnd = block.getLocation(); portalStart = block.getRelative(-1, 2, 0).getLocation(); foundSigns = this.checkBlocksOutside( l.getWorld().getBlockAt(portalStart), l.getWorld().getBlockAt(portalEnd), Axis.X); this.plugin.log(Level.FINER, "Found inverse X"); } else if (block.getRelative(0, 0, 1).getType() == Material.PORTAL) { portalEnd = block.getRelative(0, 0, 1).getLocation(); portalStart = block.getRelative(0, 2, 0).getLocation(); foundSigns = this.checkBlocksOutside( l.getWorld().getBlockAt(portalStart), l.getWorld().getBlockAt(portalEnd), Axis.Z); this.plugin.log(Level.FINER, "Found normal Z"); } else if (block.getRelative(0, 0, -1).getType() == Material.PORTAL) { portalEnd = block.getLocation(); portalStart = block.getRelative(0, 2, -1).getLocation(); foundSigns = this.checkBlocksOutside( l.getWorld().getBlockAt(portalStart), l.getWorld().getBlockAt(portalEnd), Axis.Z); this.plugin.log(Level.FINER, "Found inverse Z"); } } if (foundSigns != null) { this.plugin.log(Level.FINE, "Woo! Notch Portal!"); return processSigns(foundSigns, p); } else { this.plugin.log(Level.FINE, ":( No Notch Portal Here..."); } return null; }
public static void smartLogFallables(Consumer consumer, String playerName, Block origin) { WorldConfig wcfg = getWorldConfig(origin.getWorld()); if (wcfg == null) return; // Handle falling blocks Block checkBlock = origin.getRelative(BlockFace.UP); int up = 0; final int highestBlock = checkBlock.getWorld().getHighestBlockYAt(checkBlock.getLocation()); while (BukkitUtils.getRelativeTopFallables().contains(checkBlock.getType())) { // Record this block as falling consumer.queueBlockBreak(playerName, checkBlock.getState()); // Guess where the block is going (This could be thrown of by explosions, but it is better // than nothing) Location loc = origin.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); // Run this check to avoid false positives if (!BukkitUtils.getFallingEntityKillers().contains(finalLoc.getBlock().getType())) { finalLoc.add(0, up, 0); // Add this here after checking for block breakers if (finalLoc.getBlock().getType() == Material.AIR || BukkitUtils.getRelativeTopFallables().contains(finalLoc.getBlock().getType())) { consumer.queueBlockPlace( playerName, finalLoc, checkBlock.getTypeId(), checkBlock.getData()); } else { consumer.queueBlockReplace( playerName, finalLoc, finalLoc.getBlock().getTypeId(), finalLoc.getBlock().getData(), checkBlock.getTypeId(), checkBlock.getData()); } up++; } } if (checkBlock.getY() >= highestBlock) break; checkBlock = checkBlock.getRelative(BlockFace.UP); } }