From 149e0319f17b126f3330775c477c3e03d27d40d4 Mon Sep 17 00:00:00 2001 From: SenseiKiwi Date: Fri, 24 Jan 2014 07:16:32 -0400 Subject: [PATCH] Removed Exit Platforms for Safe Cases Updated our code to stop Fabric of Reality platforms from generating under exits all the time. Now they generate only when the supporting blocks are replaceable (in which case they're replaced by FoR) or when they're not opaque solids or have tile entities (then FoR generates on top). The exit search algorithm treats replaceable non-liquid blocks as air, so an attempt is made to build against the ground and not on top of replaceable blocks. The area around the door is cleared of blocks to avoid killing the player with lingering replaceable blocks that might be harmful, like poison ivy. --- .../mod_pocketDim/core/DDTeleporter.java | 24 ++++++++++- .../mod_pocketDim/helpers/yCoordHelper.java | 40 +++++++++++-------- 2 files changed, 46 insertions(+), 18 deletions(-) diff --git a/src/main/java/StevenDimDoors/mod_pocketDim/core/DDTeleporter.java b/src/main/java/StevenDimDoors/mod_pocketDim/core/DDTeleporter.java index fda57f6d..f2c75222 100644 --- a/src/main/java/StevenDimDoors/mod_pocketDim/core/DDTeleporter.java +++ b/src/main/java/StevenDimDoors/mod_pocketDim/core/DDTeleporter.java @@ -692,6 +692,8 @@ public class DDTeleporter if (destination != null) { // Set up a 3x3 platform at the destination + // Only place fabric of reality if the block is replaceable or air + // Don't cause block updates int x = destination.getX(); int y = destination.getY(); int z = destination.getZ(); @@ -699,7 +701,27 @@ public class DDTeleporter { for (int dz = -1; dz <= 1; dz++) { - world.setBlock(x + dx, y, z + dz, properties.FabricBlockID); + // Checking if the block is not an opaque solid is equivalent + // checking for a replaceable block, because we only allow + // exits intersecting blocks on those two surfaces. + if (!world.isBlockNormalCube(x + dx, y, z + dz)) + { + world.setBlock(x + dx, y, z + dz, properties.FabricBlockID, 0, 2); + } + } + } + + // Clear out any blocks in the space above the platform layer + // This removes any potential threats like replaceable Poison Ivy from BoP + // Remember to avoid block updates to keep gravel from collapsing + for (int dy = 1; dy <= 2; dy++) + { + for (int dx = -1; dx <= 1; dx++) + { + for (int dz = -1; dz <= 1; dz++) + { + world.setBlock(x + dx, y + dy, z + dz, 0, 0, 2); + } } } diff --git a/src/main/java/StevenDimDoors/mod_pocketDim/helpers/yCoordHelper.java b/src/main/java/StevenDimDoors/mod_pocketDim/helpers/yCoordHelper.java index 355a3284..3810c8b9 100644 --- a/src/main/java/StevenDimDoors/mod_pocketDim/helpers/yCoordHelper.java +++ b/src/main/java/StevenDimDoors/mod_pocketDim/helpers/yCoordHelper.java @@ -73,8 +73,9 @@ public class yCoordHelper public static Point3D findSafeCubeUp(World world, int x, int startY, int z) { - // Search for a 3x3x3 cube of air with blocks underneath - // We can also match against a 3x2x3 box with replaceable blocks underneath + // Search for a 3x2x3 box with solid opaque blocks (without tile entities) + // or replaceable blocks underneath. The box must contain either air and + // non-liquid replaceable blocks only. // We shift the search area into the bounds of a chunk for the sake of simplicity, // so that we don't need to worry about working across chunks. @@ -88,7 +89,7 @@ public class yCoordHelper Chunk chunk = initializeChunkArea(world, x >> 4, z >> 4); int height = world.getActualHeight(); - int y, dx, dz, blockID; + int y, dx, dz, blockID, metadata; boolean isSafe; Block block; @@ -98,8 +99,9 @@ public class yCoordHelper int layers = -1000000; // Check if a 3x3 layer of blocks is empty - // If we find a layer that contains replaceable blocks, it can - // serve as the base where we'll place the player and door. + // Treat non-liquid replaceable blocks like air + // If we find a layer that contains replaceable blocks or solid opaque blocks without + // tile entities, then it can serve as the base where we'll place the player and door. for (y = Math.max(startY - 1, 0); y < height; y++) { isSafe = true; @@ -108,10 +110,11 @@ public class yCoordHelper for (dz = -1; dz <= 1 && isSafe; dz++) { blockID = chunk.getBlockID(localX + dx, y, localZ + dz); - if (blockID != 0) + metadata = chunk.getBlockMetadata(localX + dx, y, localZ + dz); + block = Block.blocksList[blockID]; + if (blockID != 0 && (!block.blockMaterial.isReplaceable() || block.blockMaterial.isLiquid())) { - block = Block.blocksList[blockID]; - if (!block.blockMaterial.isReplaceable()) + if (!block.blockMaterial.isReplaceable() && (!block.isOpaqueCube() || block.hasTileEntity(metadata))) { isSafe = false; } @@ -133,8 +136,9 @@ public class yCoordHelper public static Point3D findSafeCubeDown(World world, int x, int startY, int z) { - // Search for a 3x3x3 cube of air with blocks underneath - // We can also match against a 3x2x3 box with + // Search for a 3x2x3 box with solid opaque blocks (without tile entities) + // or replaceable blocks underneath. The box must contain either air and + // non-liquid replaceable blocks only. // We shift the search area into the bounds of a chunk for the sake of simplicity, // so that we don't need to worry about working across chunks. @@ -148,15 +152,16 @@ public class yCoordHelper Chunk chunk = initializeChunkArea(world, x >> 4, z >> 4); int height = world.getActualHeight(); - int y, dx, dz, blockID; + int y, dx, dz, blockID, metadata; boolean isSafe; boolean hasBlocks; Block block; int layers = 0; // Check if a 3x3 layer of blocks is empty - // If we find a layer that contains replaceable blocks, it can - // serve as the base where we'll place the player and door. + // Treat non-liquid replaceable blocks like air + // If we find a layer that contains replaceable blocks or solid opaque blocks without + // tile entities, then it can serve as the base where we'll place the player and door. for (y = Math.min(startY + 2, height - 1); y >= 0; y--) { isSafe = true; @@ -166,10 +171,11 @@ public class yCoordHelper for (dz = -1; dz <= 1 && isSafe; dz++) { blockID = chunk.getBlockID(localX + dx, y, localZ + dz); - if (blockID != 0) - { - block = Block.blocksList[blockID]; - if (!block.blockMaterial.isReplaceable()) + metadata = chunk.getBlockMetadata(localX + dx, y, localZ + dz); + block = Block.blocksList[blockID]; + if (blockID != 0 && (!block.blockMaterial.isReplaceable() || block.blockMaterial.isLiquid())) + { + if (!block.blockMaterial.isReplaceable() && (!block.isOpaqueCube() || block.hasTileEntity(metadata))) { if (layers >= 3) {