diff options
-rw-r--r-- | src/Blocks/BlockBigFlower.h | 7 | ||||
-rw-r--r-- | src/Blocks/BlockCactus.h | 36 | ||||
-rw-r--r-- | src/Blocks/BlockCarpet.h | 3 | ||||
-rw-r--r-- | src/Blocks/BlockCocoaPod.h | 5 | ||||
-rw-r--r-- | src/Blocks/BlockComparator.h | 5 | ||||
-rw-r--r-- | src/Blocks/BlockCrops.h | 9 | ||||
-rw-r--r-- | src/Blocks/BlockDeadBush.h | 5 | ||||
-rw-r--r-- | src/Blocks/BlockDoor.h | 20 | ||||
-rw-r--r-- | src/Blocks/BlockFlower.h | 4 | ||||
-rw-r--r-- | src/Blocks/BlockMushroom.h | 5 | ||||
-rw-r--r-- | src/Blocks/BlockNetherWart.h | 3 | ||||
-rw-r--r-- | src/Blocks/BlockPortal.h | 4 | ||||
-rw-r--r-- | src/Blocks/BlockPressurePlate.h | 5 | ||||
-rw-r--r-- | src/Blocks/BlockRail.h | 10 | ||||
-rw-r--r-- | src/Blocks/BlockRedstoneRepeater.h | 5 | ||||
-rw-r--r-- | src/Blocks/BlockRedstoneWire.h | 5 | ||||
-rw-r--r-- | src/Blocks/BlockSapling.h | 3 | ||||
-rw-r--r-- | src/Blocks/BlockSignPost.h | 5 | ||||
-rw-r--r-- | src/Blocks/BlockSnow.h | 4 | ||||
-rw-r--r-- | src/Blocks/BlockStandingBanner.h | 5 | ||||
-rw-r--r-- | src/Blocks/BlockStems.h | 3 | ||||
-rw-r--r-- | src/Blocks/BlockSugarCane.h | 44 | ||||
-rw-r--r-- | src/Blocks/BlockTallGrass.h | 10 | ||||
-rw-r--r-- | src/Blocks/BlockVines.h | 7 |
24 files changed, 130 insertions, 82 deletions
diff --git a/src/Blocks/BlockBigFlower.h b/src/Blocks/BlockBigFlower.h index 1b2c0d735..37c172747 100644 --- a/src/Blocks/BlockBigFlower.h +++ b/src/Blocks/BlockBigFlower.h @@ -25,9 +25,10 @@ private: if (IsMetaTopPart(a_Meta)) { BLOCKTYPE BottomType; + auto RootPosition = a_Position.addedY(-1); if ( - (a_Position.y < 1) || - !a_World.GetBlockTypeMeta(a_Position - Vector3i(0, 1, 0), BottomType, a_Meta) || + !cChunkDef::IsValidHeight(RootPosition) || + !a_World.GetBlockTypeMeta(RootPosition, BottomType, a_Meta) || (BottomType != E_BLOCK_BIG_FLOWER) ) { @@ -104,7 +105,7 @@ private: // Both parts can only that they're rooted in grass. const auto RootPosition = a_Position.addedY(IsMetaTopPart(a_Meta) ? -2 : -1); - return (RootPosition.y >= 0) && IsBlockTypeOfDirt(a_Chunk.GetBlock(RootPosition)); + return cChunkDef::IsValidHeight(RootPosition) && IsBlockTypeOfDirt(a_Chunk.GetBlock(RootPosition)); } diff --git a/src/Blocks/BlockCactus.h b/src/Blocks/BlockCactus.h index 23c4d3421..9b1461cb8 100644 --- a/src/Blocks/BlockCactus.h +++ b/src/Blocks/BlockCactus.h @@ -20,11 +20,12 @@ private: virtual bool CanBeAt(const cChunk & a_Chunk, const Vector3i a_Position, const NIBBLETYPE a_Meta) const override { - if (a_Position.y <= 0) + const auto SurfacePosition = a_Position.addedY(-1); + if (!cChunkDef::IsValidHeight(SurfacePosition)) { return false; } - BLOCKTYPE Surface = a_Chunk.GetBlock(a_Position.addedY(-1)); + BLOCKTYPE Surface = a_Chunk.GetBlock(SurfacePosition); if ((Surface != E_BLOCK_SAND) && (Surface != E_BLOCK_CACTUS)) { // Cactus can only be placed on sand and itself @@ -75,25 +76,25 @@ private: virtual int Grow(cChunk & a_Chunk, Vector3i a_RelPos, int a_NumStages = 1) const override { // Check the total height of the cacti blocks here: - int top = a_RelPos.y + 1; + auto Top = a_RelPos.addedY(1); while ( - (top < cChunkDef::Height) && - (a_Chunk.GetBlock({a_RelPos.x, top, a_RelPos.z}) == E_BLOCK_CACTUS) + cChunkDef::IsValidHeight(Top) && + (a_Chunk.GetBlock(Top) == E_BLOCK_CACTUS) ) { - ++top; + Top.y++; } - int bottom = a_RelPos.y - 1; + auto Bottom = a_RelPos.addedY(-1); while ( - (bottom > 0) && - (a_Chunk.GetBlock({a_RelPos.x, bottom, a_RelPos.z}) == E_BLOCK_CACTUS) + cChunkDef::IsValidHeight(Bottom) && + (a_Chunk.GetBlock(Bottom) == E_BLOCK_CACTUS) ) { - --bottom; + --Bottom.y; } // Refuse if already too high: - auto numToGrow = std::min(a_NumStages, a_Chunk.GetWorld()->GetMaxCactusHeight() + 1 - (top - bottom)); + auto numToGrow = std::min(a_NumStages, a_Chunk.GetWorld()->GetMaxCactusHeight() + 1 - (Top.y - Bottom.y)); if (numToGrow <= 0) { return 0; @@ -102,14 +103,14 @@ private: BLOCKTYPE blockType; for (int i = 0; i < numToGrow; ++i) { - Vector3i pos(a_RelPos.x, top + i, a_RelPos.z); - if (!a_Chunk.UnboundedRelGetBlockType(pos, blockType) || (blockType != E_BLOCK_AIR)) + auto NewTop = Top.addedY(i); + if (!a_Chunk.UnboundedRelGetBlockType(NewTop, blockType) || (blockType != E_BLOCK_AIR)) { // Cannot grow there return i; } - a_Chunk.UnboundedRelFastSetBlock(pos, E_BLOCK_CACTUS, 0); + a_Chunk.UnboundedRelFastSetBlock(NewTop, E_BLOCK_CACTUS, 0); // Check surroundings. Cacti may ONLY be surrounded by non-solid blocks; if they aren't, drop as pickup and bail out the growing static const Vector3i neighborOffsets[] = @@ -122,7 +123,7 @@ private: for (const auto & ofs: neighborOffsets) { if ( - a_Chunk.UnboundedRelGetBlockType(pos + ofs, blockType) && + a_Chunk.UnboundedRelGetBlockType(NewTop + ofs, blockType) && ( cBlockInfo::IsSolid(blockType) || (blockType == E_BLOCK_LAVA) || @@ -131,7 +132,7 @@ private: ) { // Remove the cactus - auto absPos = a_Chunk.RelativeToAbsolute(pos); + auto absPos = a_Chunk.RelativeToAbsolute(NewTop); a_Chunk.GetWorld()->DropBlockAsPickups(absPos); return i + 1; } @@ -143,7 +144,8 @@ private: virtual PlantAction CanGrow(cChunk & a_Chunk, Vector3i a_RelPos) const override { // Only allow growing if there's an air block above: - if (((a_RelPos.y + 1) < cChunkDef::Height) && (a_Chunk.GetBlock(a_RelPos.addedY(1)) == E_BLOCK_AIR)) + const auto RelPosAbove = a_RelPos.addedY(1); + if (cChunkDef::IsValidHeight(RelPosAbove) && (a_Chunk.GetBlock(RelPosAbove) == E_BLOCK_AIR)) { return Super::CanGrow(a_Chunk, a_RelPos); } diff --git a/src/Blocks/BlockCarpet.h b/src/Blocks/BlockCarpet.h index 841e94b11..2477ee344 100644 --- a/src/Blocks/BlockCarpet.h +++ b/src/Blocks/BlockCarpet.h @@ -27,7 +27,8 @@ private: virtual bool CanBeAt(const cChunk & a_Chunk, const Vector3i a_Position, const NIBBLETYPE a_Meta) const override { - return (a_Position.y > 0) && (a_Chunk.GetBlock(a_Position.addedY(-1)) != E_BLOCK_AIR); + const auto PosBelow = a_Position.addedY(-1); + return cChunkDef::IsValidHeight(PosBelow) && (a_Chunk.GetBlock(PosBelow) != E_BLOCK_AIR); } diff --git a/src/Blocks/BlockCocoaPod.h b/src/Blocks/BlockCocoaPod.h index e018388c5..85dc42fbf 100644 --- a/src/Blocks/BlockCocoaPod.h +++ b/src/Blocks/BlockCocoaPod.h @@ -43,7 +43,10 @@ private: auto LogPos = AddFaceDirection(a_Position, BlockFace, true); BLOCKTYPE BlockType; NIBBLETYPE BlockMeta; - a_Chunk.UnboundedRelGetBlock(LogPos, BlockType, BlockMeta); + if (!a_Chunk.UnboundedRelGetBlock(LogPos, BlockType, BlockMeta)) + { + return true; + } return ((BlockType == E_BLOCK_LOG) && ((BlockMeta & 0x03) == E_META_LOG_JUNGLE)); } diff --git a/src/Blocks/BlockComparator.h b/src/Blocks/BlockComparator.h index 18aa2a8b9..815bbe6a1 100644 --- a/src/Blocks/BlockComparator.h +++ b/src/Blocks/BlockComparator.h @@ -154,14 +154,15 @@ private: virtual bool CanBeAt(const cChunk & a_Chunk, const Vector3i a_Position, const NIBBLETYPE a_Meta) const override { - if (a_Position.y <= 0) + const auto BelowPos = a_Position.addedY(-1); + if (!cChunkDef::IsValidHeight(BelowPos)) { return false; } BLOCKTYPE BelowBlock; NIBBLETYPE BelowBlockMeta; - a_Chunk.GetBlockTypeMeta(a_Position.addedY(-1), BelowBlock, BelowBlockMeta); + a_Chunk.GetBlockTypeMeta(BelowPos, BelowBlock, BelowBlockMeta); if (cBlockInfo::FullyOccupiesVoxel(BelowBlock)) { diff --git a/src/Blocks/BlockCrops.h b/src/Blocks/BlockCrops.h index b323ace10..59413ba08 100644 --- a/src/Blocks/BlockCrops.h +++ b/src/Blocks/BlockCrops.h @@ -118,7 +118,14 @@ private: virtual bool CanBeAt(const cChunk & a_Chunk, const Vector3i a_Position, const NIBBLETYPE a_Meta) const override { - return (a_Position.y > 0) && (a_Chunk.GetBlock(a_Position.addedY(-1)) == E_BLOCK_FARMLAND); + const auto BlockBelow = a_Position.addedY(-1); + + if (!cChunkDef::IsValidHeight(BlockBelow)) + { + return false; + } + + return a_Chunk.GetBlock(BlockBelow) == E_BLOCK_FARMLAND; } diff --git a/src/Blocks/BlockDeadBush.h b/src/Blocks/BlockDeadBush.h index 080dd150c..884b6f686 100644 --- a/src/Blocks/BlockDeadBush.h +++ b/src/Blocks/BlockDeadBush.h @@ -29,12 +29,13 @@ private: virtual bool CanBeAt(const cChunk & a_Chunk, const Vector3i a_Position, const NIBBLETYPE a_Meta) const override { - if (a_Position.y <= 0) + const auto PosBelow = a_Position.addedY(-1); + if (!cChunkDef::IsValidHeight(PosBelow)) { return false; } - BLOCKTYPE BelowBlock = a_Chunk.GetBlock(a_Position.addedY(-1)); + BLOCKTYPE BelowBlock = a_Chunk.GetBlock(PosBelow); switch (BelowBlock) { case E_BLOCK_CLAY: diff --git a/src/Blocks/BlockDoor.h b/src/Blocks/BlockDoor.h index 1b5c33d46..45102fd01 100644 --- a/src/Blocks/BlockDoor.h +++ b/src/Blocks/BlockDoor.h @@ -191,14 +191,18 @@ private: virtual bool CanBeAt(const cChunk & a_Chunk, const Vector3i a_Position, const NIBBLETYPE a_Meta) const override { // CanBeAt is also called on placement, so the top part can't check for the bottom part. - // Both parts can only that their base is a valid block. + // Both parts can only that the base of the door (i.e. -2 for a door top) is a valid block. + const auto BasePosition = a_Position.addedY(((a_Meta & 0x8) == 0x8) ? -2 : -1); + if (!cChunkDef::IsValidHeight(BasePosition)) + { + return false; + } BLOCKTYPE BlockType; NIBBLETYPE BlockMeta; - const auto BasePosition = a_Position.addedY(((a_Meta & 0x8) == 0x8) ? -2 : -1); a_Chunk.GetBlockTypeMeta(BasePosition, BlockType, BlockMeta); - return (BasePosition.y >= 0) && CanBeOn(BlockType, BlockMeta); + return CanBeOn(BlockType, BlockMeta); } @@ -216,9 +220,10 @@ private: if ((Meta & 0x08) != 0) { // The coords are pointing at the top part of the door - if (a_BlockPos.y > 0) + const auto BottomPos = a_BlockPos.addedY(-1); + if (cChunkDef::IsValidHeight(BottomPos)) { - NIBBLETYPE DownMeta = a_ChunkInterface.GetBlockMeta(a_BlockPos.addedY(-1)); + NIBBLETYPE DownMeta = a_ChunkInterface.GetBlockMeta(BottomPos); return static_cast<NIBBLETYPE>((DownMeta & 0x07) | 0x08 | (Meta << 4)); } // This is the top part of the door at the bottommost layer of the world, there's no bottom: @@ -227,9 +232,10 @@ private: else { // The coords are pointing at the bottom part of the door - if (a_BlockPos.y < cChunkDef::Height - 1) + const auto TopPos = a_BlockPos.addedY(1); + if (cChunkDef::IsValidHeight(TopPos)) { - NIBBLETYPE UpMeta = a_ChunkInterface.GetBlockMeta(a_BlockPos.addedY(1)); + NIBBLETYPE UpMeta = a_ChunkInterface.GetBlockMeta(TopPos); return static_cast<NIBBLETYPE>(Meta | (UpMeta << 4)); } // This is the bottom part of the door at the topmost layer of the world, there's no top: diff --git a/src/Blocks/BlockFlower.h b/src/Blocks/BlockFlower.h index 023ba4a37..ef140e9b2 100644 --- a/src/Blocks/BlockFlower.h +++ b/src/Blocks/BlockFlower.h @@ -30,7 +30,9 @@ private: virtual bool CanBeAt(const cChunk & a_Chunk, const Vector3i a_Position, const NIBBLETYPE a_Meta) const override { - return (a_Position.y > 0) && IsBlockTypeOfDirt(a_Chunk.GetBlock(a_Position.addedY(-1))); + const auto BottomPos = a_Position.addedY(-1); + + return cChunkDef::IsValidHeight(BottomPos) && IsBlockTypeOfDirt(a_Chunk.GetBlock(BottomPos)); } diff --git a/src/Blocks/BlockMushroom.h b/src/Blocks/BlockMushroom.h index bed16c557..9e4378d4e 100644 --- a/src/Blocks/BlockMushroom.h +++ b/src/Blocks/BlockMushroom.h @@ -23,14 +23,15 @@ private: virtual bool CanBeAt(const cChunk & a_Chunk, const Vector3i a_Position, const NIBBLETYPE a_Meta) const override { - if (a_Position.y <= 0) + const auto BasePos = a_Position.addedY(-1); + if (!cChunkDef::IsValidHeight(BasePos)) { return false; } // TODO: Cannot be at too much daylight - switch (a_Chunk.GetBlock(a_Position.addedY(-1))) + switch (a_Chunk.GetBlock(BasePos)) { case E_BLOCK_GLASS: case E_BLOCK_CACTUS: diff --git a/src/Blocks/BlockNetherWart.h b/src/Blocks/BlockNetherWart.h index 43081d511..c0686afc6 100644 --- a/src/Blocks/BlockNetherWart.h +++ b/src/Blocks/BlockNetherWart.h @@ -60,7 +60,8 @@ private: virtual bool CanBeAt(const cChunk & a_Chunk, const Vector3i a_Position, const NIBBLETYPE a_Meta) const override { // Needs to be placed on top of a Soulsand block: - return (a_Position.y > 0) && (a_Chunk.GetBlock(a_Position.addedY(-1)) == E_BLOCK_SOULSAND); + const auto BasePos = a_Position.addedY(-1); + return cChunkDef::IsValidHeight(BasePos) && (a_Chunk.GetBlock(BasePos) == E_BLOCK_SOULSAND); } diff --git a/src/Blocks/BlockPortal.h b/src/Blocks/BlockPortal.h index 05daa9337..f4b5a50bd 100644 --- a/src/Blocks/BlockPortal.h +++ b/src/Blocks/BlockPortal.h @@ -51,9 +51,9 @@ private: virtual bool CanBeAt(const cChunk & a_Chunk, const Vector3i a_Position, const NIBBLETYPE a_Meta) const override { - if ((a_Position.y <= 0) || (a_Position.y >= cChunkDef::Height - 1)) + if (!cChunkDef::IsValidHeight(a_Position.addedY(-1)) || !cChunkDef::IsValidHeight(a_Position.addedY(1))) { - return false; // In case someone places a portal with meta 1 or 2 at boundaries, and server tries to get invalid coords at Y - 1 or Y + 1. + return false; // Must be 1 away from the boundary, there will always be another portal or an obsidian between the portal block and the boundary. } switch (a_Meta) diff --git a/src/Blocks/BlockPressurePlate.h b/src/Blocks/BlockPressurePlate.h index 6d852bfc0..d69234cee 100644 --- a/src/Blocks/BlockPressurePlate.h +++ b/src/Blocks/BlockPressurePlate.h @@ -22,14 +22,15 @@ private: virtual bool CanBeAt(const cChunk & a_Chunk, const Vector3i a_Position, const NIBBLETYPE a_Meta) const override { - if (a_Position.y <= 0) + const auto PosBelow = a_Position.addedY(-1); + if (!cChunkDef::IsValidHeight(PosBelow)) { return false; } BLOCKTYPE Block; NIBBLETYPE BlockMeta; - a_Chunk.GetBlockTypeMeta(a_Position.addedY(-1), Block, BlockMeta); + a_Chunk.GetBlockTypeMeta(PosBelow, Block, BlockMeta); // upside down slabs if (cBlockSlabHandler::IsAnySlabType(Block)) diff --git a/src/Blocks/BlockRail.h b/src/Blocks/BlockRail.h index 4e2e6211f..48f20a86b 100644 --- a/src/Blocks/BlockRail.h +++ b/src/Blocks/BlockRail.h @@ -177,11 +177,17 @@ private: virtual bool CanBeAt(const cChunk & a_Chunk, const Vector3i a_Position, NIBBLETYPE a_Meta) const override { + const auto BelowPos = a_Position.addedY(-1); + if (!cChunkDef::IsValidHeight(BelowPos)) + { + return false; + } + BLOCKTYPE BelowBlock; NIBBLETYPE BelowBlockMeta; - a_Chunk.GetBlockTypeMeta(a_Position.addedY(-1), BelowBlock, BelowBlockMeta); + a_Chunk.GetBlockTypeMeta(BelowPos, BelowBlock, BelowBlockMeta); - if ((a_Position.y <= 0) || !CanBeSupportedBy(BelowBlock, BelowBlockMeta)) + if (!CanBeSupportedBy(BelowBlock, BelowBlockMeta)) { return false; } diff --git a/src/Blocks/BlockRedstoneRepeater.h b/src/Blocks/BlockRedstoneRepeater.h index 893691d7b..5476df8eb 100644 --- a/src/Blocks/BlockRedstoneRepeater.h +++ b/src/Blocks/BlockRedstoneRepeater.h @@ -109,14 +109,15 @@ private: virtual bool CanBeAt(const cChunk & a_Chunk, const Vector3i a_Position, const NIBBLETYPE a_Meta) const override { - if (a_Position.y <= 0) + const auto BelowPos = a_Position.addedY(-1); + if (!cChunkDef::IsValidHeight(BelowPos)) { return false; } BLOCKTYPE BelowBlock; NIBBLETYPE BelowBlockMeta; - a_Chunk.GetBlockTypeMeta(a_Position.addedY(-1), BelowBlock, BelowBlockMeta); + a_Chunk.GetBlockTypeMeta(BelowPos, BelowBlock, BelowBlockMeta); if (cBlockInfo::FullyOccupiesVoxel(BelowBlock)) { diff --git a/src/Blocks/BlockRedstoneWire.h b/src/Blocks/BlockRedstoneWire.h index de8e59a40..f0f3baecc 100644 --- a/src/Blocks/BlockRedstoneWire.h +++ b/src/Blocks/BlockRedstoneWire.h @@ -22,14 +22,15 @@ private: virtual bool CanBeAt(const cChunk & a_Chunk, const Vector3i a_Position, const NIBBLETYPE a_Meta) const override { - if (a_Position.y <= 0) + const auto BelowPos = a_Position.addedY(-1); + if (!cChunkDef::IsValidHeight(BelowPos)) { return false; } BLOCKTYPE BelowBlock; NIBBLETYPE BelowBlockMeta; - a_Chunk.GetBlockTypeMeta(a_Position.addedY(-1), BelowBlock, BelowBlockMeta); + a_Chunk.GetBlockTypeMeta(BelowPos, BelowBlock, BelowBlockMeta); if (cBlockInfo::FullyOccupiesVoxel(BelowBlock)) { diff --git a/src/Blocks/BlockSapling.h b/src/Blocks/BlockSapling.h index d32b9b449..ae8a190a3 100644 --- a/src/Blocks/BlockSapling.h +++ b/src/Blocks/BlockSapling.h @@ -31,7 +31,8 @@ private: virtual bool CanBeAt(const cChunk & a_Chunk, const Vector3i a_Position, const NIBBLETYPE a_Meta) const override { - return (a_Position.y > 0) && IsBlockTypeOfDirt(a_Chunk.GetBlock(a_Position.addedY(-1))); + const auto BelowPos = a_Position.addedY(-1); + return cChunkDef::IsValidHeight(BelowPos) && IsBlockTypeOfDirt(a_Chunk.GetBlock(BelowPos)); } diff --git a/src/Blocks/BlockSignPost.h b/src/Blocks/BlockSignPost.h index b96498cbd..89da77fbb 100644 --- a/src/Blocks/BlockSignPost.h +++ b/src/Blocks/BlockSignPost.h @@ -30,12 +30,13 @@ private: virtual bool CanBeAt(const cChunk & a_Chunk, const Vector3i a_Position, const NIBBLETYPE a_Meta) const override { - if (a_Position.y <= 0) + const auto BelowPos = a_Position.addedY(-1); + if (!cChunkDef::IsValidHeight(BelowPos)) { return false; } - BLOCKTYPE Type = a_Chunk.GetBlock(a_Position.addedY(-1)); + BLOCKTYPE Type = a_Chunk.GetBlock(BelowPos); return (Type == E_BLOCK_SIGN_POST) || (Type == E_BLOCK_WALLSIGN) || cBlockInfo::IsSolid(Type); } diff --git a/src/Blocks/BlockSnow.h b/src/Blocks/BlockSnow.h index f3fa87a1b..51361ce17 100644 --- a/src/Blocks/BlockSnow.h +++ b/src/Blocks/BlockSnow.h @@ -69,11 +69,11 @@ private: virtual bool CanBeAt(const cChunk & a_Chunk, const Vector3i a_Position, const NIBBLETYPE a_Meta) const override { - if (a_Position.y <= 0) + const auto BelowPos = a_Position.addedY(-1); + if (!cChunkDef::IsValidHeight(BelowPos)) { return false; } - auto BelowPos = a_Position.addedY(-1); auto BlockBelow = a_Chunk.GetBlock(BelowPos); auto MetaBelow = a_Chunk.GetMeta(BelowPos); return CanBeOn(BlockBelow, MetaBelow); diff --git a/src/Blocks/BlockStandingBanner.h b/src/Blocks/BlockStandingBanner.h index 391b7fde7..177e9a68c 100644 --- a/src/Blocks/BlockStandingBanner.h +++ b/src/Blocks/BlockStandingBanner.h @@ -31,12 +31,13 @@ public: virtual bool CanBeAt(const cChunk & a_Chunk, const Vector3i a_Position, const NIBBLETYPE a_Meta) const override { - if (a_Position.y < 1) + const auto BelowPos = a_Position.addedY(-1); + if (!cChunkDef::IsValidHeight(BelowPos)) { return false; } - return cBlockInfo::IsSolid(a_Chunk.GetBlock(a_Position.addedY(-1))); + return cBlockInfo::IsSolid(a_Chunk.GetBlock(BelowPos)); } diff --git a/src/Blocks/BlockStems.h b/src/Blocks/BlockStems.h index 11cd83967..9d598003d 100644 --- a/src/Blocks/BlockStems.h +++ b/src/Blocks/BlockStems.h @@ -58,7 +58,8 @@ private: virtual bool CanBeAt(const cChunk & a_Chunk, const Vector3i a_Position, const NIBBLETYPE a_Meta) const override { - return (a_Position.y > 0) && (a_Chunk.GetBlock(a_Position.addedY(-1)) == E_BLOCK_FARMLAND); + const auto BelowPos = a_Position.addedY(-1); + return cChunkDef::IsValidHeight(BelowPos) && (a_Chunk.GetBlock(BelowPos) == E_BLOCK_FARMLAND); } diff --git a/src/Blocks/BlockSugarCane.h b/src/Blocks/BlockSugarCane.h index cffe667e5..1f6c8a8fa 100644 --- a/src/Blocks/BlockSugarCane.h +++ b/src/Blocks/BlockSugarCane.h @@ -29,12 +29,13 @@ private: virtual bool CanBeAt(const cChunk & a_Chunk, const Vector3i a_Position, const NIBBLETYPE a_Meta) const override { - if (a_Position.y <= 0) + const auto BelowPos = a_Position.addedY(-1); + if (!cChunkDef::IsValidHeight(BelowPos)) { return false; } - switch (a_Chunk.GetBlock(a_Position.addedY(-1))) + switch (a_Chunk.GetBlock(BelowPos)) { case E_BLOCK_DIRT: case E_BLOCK_GRASS: @@ -43,16 +44,16 @@ private: { static const Vector3i Coords[] = { - {-1, -1, 0}, - { 1, -1, 0}, - { 0, -1, -1}, - { 0, -1, 1}, + {-1, 0, 0}, + { 1, 0, 0}, + { 0, 0, -1}, + { 0, 0, 1}, } ; for (size_t i = 0; i < ARRAYCOUNT(Coords); i++) { BLOCKTYPE BlockType; NIBBLETYPE BlockMeta; - if (!a_Chunk.UnboundedRelGetBlock(a_Position + Coords[i], BlockType, BlockMeta)) + if (!a_Chunk.UnboundedRelGetBlock(BelowPos + Coords[i], BlockType, BlockMeta)) { // Too close to the edge, cannot simulate return true; @@ -90,31 +91,36 @@ private: virtual int Grow(cChunk & a_Chunk, Vector3i a_RelPos, int a_NumStages = 1) const override { // Check the total height of the sugarcane blocks here: - int top = a_RelPos.y + 1; + auto top = a_RelPos.addedY(1); while ( - (top < cChunkDef::Height) && - (a_Chunk.GetBlock({a_RelPos.x, top, a_RelPos.z}) == E_BLOCK_SUGARCANE) + cChunkDef::IsValidHeight(top) && + (a_Chunk.GetBlock(top) == E_BLOCK_SUGARCANE) ) { - ++top; + ++top.y; } - int bottom = a_RelPos.y - 1; + auto bottom = a_RelPos.addedY(-1); while ( - (bottom > 0) && - (a_Chunk.GetBlock({a_RelPos.x, bottom, a_RelPos.z}) == E_BLOCK_SUGARCANE) + cChunkDef::IsValidHeight(bottom) && + (a_Chunk.GetBlock(bottom) == E_BLOCK_SUGARCANE) ) { - --bottom; + --bottom.y; } // Grow by at most a_NumStages, but no more than max height: - auto toGrow = std::min(a_NumStages, a_Chunk.GetWorld()->GetMaxSugarcaneHeight() + 1 - (top - bottom)); - Vector3i topPos(a_RelPos.x, top, a_RelPos.z); + auto toGrow = std::min(a_NumStages, a_Chunk.GetWorld()->GetMaxSugarcaneHeight() + 1 - (top.y - bottom.y)); for (int i = 0; i < toGrow; i++) { - if (a_Chunk.GetBlock(topPos.addedY(i)) == E_BLOCK_AIR) + const auto NewTop = top.addedY(i); + if (!cChunkDef::IsValidHeight(NewTop)) { - a_Chunk.SetBlock(topPos.addedY(i), E_BLOCK_SUGARCANE, 0); + return i; + } + + if (a_Chunk.GetBlock(NewTop) == E_BLOCK_AIR) + { + a_Chunk.SetBlock(NewTop, E_BLOCK_SUGARCANE, 0); } else { diff --git a/src/Blocks/BlockTallGrass.h b/src/Blocks/BlockTallGrass.h index ea638c878..a30c7ce05 100644 --- a/src/Blocks/BlockTallGrass.h +++ b/src/Blocks/BlockTallGrass.h @@ -54,12 +54,13 @@ private: virtual bool CanBeAt(const cChunk & a_Chunk, const Vector3i a_Position, const NIBBLETYPE a_Meta) const override { - if (a_Position.y <= 0) + const auto BelowPos = a_Position.addedY(-1); + if (!cChunkDef::IsValidHeight(BelowPos)) { return false; } - BLOCKTYPE BelowBlock = a_Chunk.GetBlock(a_Position.addedY(-1)); + BLOCKTYPE BelowBlock = a_Chunk.GetBlock(BelowPos); return IsBlockTypeOfDirt(BelowBlock); } @@ -70,7 +71,8 @@ private: /** Growing a tall grass produces a big flower (2-block high fern or double-tall grass). */ virtual int Grow(cChunk & a_Chunk, Vector3i a_RelPos, int a_NumStages = 1) const override { - if (a_RelPos.y > (cChunkDef::Height - 2)) + const auto TopPos = a_RelPos.addedY(1); + if (!cChunkDef::IsValidHeight(TopPos)) { return 0; } @@ -83,7 +85,7 @@ private: default: return 0; } a_Chunk.SetBlock(a_RelPos, E_BLOCK_BIG_FLOWER, largeFlowerMeta); - a_Chunk.SetBlock(a_RelPos.addedY(1), E_BLOCK_BIG_FLOWER, E_META_BIG_FLOWER_TOP); + a_Chunk.SetBlock(TopPos, E_BLOCK_BIG_FLOWER, E_META_BIG_FLOWER_TOP); return 1; } diff --git a/src/Blocks/BlockVines.h b/src/Blocks/BlockVines.h index a23ba1489..edbd30f36 100644 --- a/src/Blocks/BlockVines.h +++ b/src/Blocks/BlockVines.h @@ -119,15 +119,16 @@ private: } // Check if vine above us, add its meta to MaxMeta: - if ((a_Position.y < cChunkDef::Height - 1) && (a_Chunk.GetBlock(a_Position.addedY(1)) == E_BLOCK_VINES)) + const auto AbovePos = a_Position.addedY(1); + if (cChunkDef::IsValidHeight(AbovePos) && (a_Chunk.GetBlock(AbovePos) == E_BLOCK_VINES)) { - MaxMeta |= a_Chunk.GetMeta(a_Position.addedY(1)); + MaxMeta |= a_Chunk.GetMeta(AbovePos); } NIBBLETYPE Common = a_CurrentMeta & MaxMeta; // Neighbors that we have and are legal. if (Common != a_CurrentMeta) { - bool HasTop = (a_Position.y < (cChunkDef::Height - 1)) && IsBlockAttachable(a_Chunk.GetBlock(a_Position.addedY(1))); + bool HasTop = cChunkDef::IsValidHeight(AbovePos) && IsBlockAttachable(a_Chunk.GetBlock(AbovePos)); if ((Common == 0) && !HasTop) // Meta equals 0 also means top. Make a last-ditch attempt to save the vine. { return VINE_LOST_SUPPORT; |