Merge pull request #2306 from cuberite/FixNeighborChangedLoop
Added neighbor specification in the OnNeighborChanged() block callback.
This commit is contained in:
commit
11cf88b872
@ -65,13 +65,22 @@ public:
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
virtual void OnNeighborChanged(cChunkInterface & a_ChunkInterface, int a_BlockX, int a_BlockY, int a_BlockZ) override
|
|
||||||
|
virtual void OnNeighborChanged(cChunkInterface & a_ChunkInterface, int a_BlockX, int a_BlockY, int a_BlockZ, eBlockFace a_WhichNeighbor) override
|
||||||
{
|
{
|
||||||
|
// Don't care about any neighbor but the one above us (fix recursion loop in #2213):
|
||||||
|
if (a_WhichNeighbor != BLOCK_FACE_YP)
|
||||||
|
{
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
|
// Don't care about anything if we're at the top of the world:
|
||||||
if (a_BlockY >= cChunkDef::Height)
|
if (a_BlockY >= cChunkDef::Height)
|
||||||
{
|
{
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// Check whether we should revert to dirt:
|
||||||
BLOCKTYPE UpperBlock = a_ChunkInterface.GetBlock(a_BlockX, a_BlockY + 1, a_BlockZ);
|
BLOCKTYPE UpperBlock = a_ChunkInterface.GetBlock(a_BlockX, a_BlockY + 1, a_BlockZ);
|
||||||
if (cBlockInfo::FullyOccupiesVoxel(UpperBlock))
|
if (cBlockInfo::FullyOccupiesVoxel(UpperBlock))
|
||||||
{
|
{
|
||||||
@ -79,11 +88,13 @@ public:
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
virtual void ConvertToPickups(cItems & a_Pickups, NIBBLETYPE a_BlockMeta) override
|
virtual void ConvertToPickups(cItems & a_Pickups, NIBBLETYPE a_BlockMeta) override
|
||||||
{
|
{
|
||||||
a_Pickups.Add(E_BLOCK_DIRT, 1, 0); // Reset meta
|
a_Pickups.Add(E_BLOCK_DIRT, 1, 0); // Reset meta
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
bool IsWaterInNear(cChunk & a_Chunk, int a_RelX, int a_RelY, int a_RelZ)
|
bool IsWaterInNear(cChunk & a_Chunk, int a_RelX, int a_RelY, int a_RelZ)
|
||||||
{
|
{
|
||||||
if (a_Chunk.GetWorld()->IsWeatherWetAt(a_RelX, a_RelZ))
|
if (a_Chunk.GetWorld()->IsWeatherWetAt(a_RelX, a_RelZ))
|
||||||
|
@ -389,12 +389,12 @@ void cBlockHandler::OnDestroyedByPlayer(cChunkInterface & a_ChunkInterface, cWor
|
|||||||
void cBlockHandler::OnPlaced(cChunkInterface & a_ChunkInterface, cWorldInterface & a_WorldInterface, int a_BlockX, int a_BlockY, int a_BlockZ, BLOCKTYPE a_BlockType, NIBBLETYPE a_BlockMeta)
|
void cBlockHandler::OnPlaced(cChunkInterface & a_ChunkInterface, cWorldInterface & a_WorldInterface, int a_BlockX, int a_BlockY, int a_BlockZ, BLOCKTYPE a_BlockType, NIBBLETYPE a_BlockMeta)
|
||||||
{
|
{
|
||||||
// Notify the neighbors
|
// Notify the neighbors
|
||||||
NeighborChanged(a_ChunkInterface, a_BlockX - 1, a_BlockY, a_BlockZ);
|
NeighborChanged(a_ChunkInterface, a_BlockX - 1, a_BlockY, a_BlockZ, BLOCK_FACE_XP);
|
||||||
NeighborChanged(a_ChunkInterface, a_BlockX + 1, a_BlockY, a_BlockZ);
|
NeighborChanged(a_ChunkInterface, a_BlockX + 1, a_BlockY, a_BlockZ, BLOCK_FACE_XM);
|
||||||
NeighborChanged(a_ChunkInterface, a_BlockX, a_BlockY - 1, a_BlockZ);
|
NeighborChanged(a_ChunkInterface, a_BlockX, a_BlockY - 1, a_BlockZ, BLOCK_FACE_YP);
|
||||||
NeighborChanged(a_ChunkInterface, a_BlockX, a_BlockY + 1, a_BlockZ);
|
NeighborChanged(a_ChunkInterface, a_BlockX, a_BlockY + 1, a_BlockZ, BLOCK_FACE_YM);
|
||||||
NeighborChanged(a_ChunkInterface, a_BlockX, a_BlockY, a_BlockZ - 1);
|
NeighborChanged(a_ChunkInterface, a_BlockX, a_BlockY, a_BlockZ - 1, BLOCK_FACE_ZP);
|
||||||
NeighborChanged(a_ChunkInterface, a_BlockX, a_BlockY, a_BlockZ + 1);
|
NeighborChanged(a_ChunkInterface, a_BlockX, a_BlockY, a_BlockZ + 1, BLOCK_FACE_ZM);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
@ -404,23 +404,23 @@ void cBlockHandler::OnPlaced(cChunkInterface & a_ChunkInterface, cWorldInterface
|
|||||||
void cBlockHandler::OnDestroyed(cChunkInterface & a_ChunkInterface, cWorldInterface & a_WorldInterface, int a_BlockX, int a_BlockY, int a_BlockZ)
|
void cBlockHandler::OnDestroyed(cChunkInterface & a_ChunkInterface, cWorldInterface & a_WorldInterface, int a_BlockX, int a_BlockY, int a_BlockZ)
|
||||||
{
|
{
|
||||||
// Notify the neighbors
|
// Notify the neighbors
|
||||||
NeighborChanged(a_ChunkInterface, a_BlockX - 1, a_BlockY, a_BlockZ);
|
NeighborChanged(a_ChunkInterface, a_BlockX - 1, a_BlockY, a_BlockZ, BLOCK_FACE_XP);
|
||||||
NeighborChanged(a_ChunkInterface, a_BlockX + 1, a_BlockY, a_BlockZ);
|
NeighborChanged(a_ChunkInterface, a_BlockX + 1, a_BlockY, a_BlockZ, BLOCK_FACE_XM);
|
||||||
NeighborChanged(a_ChunkInterface, a_BlockX, a_BlockY - 1, a_BlockZ);
|
NeighborChanged(a_ChunkInterface, a_BlockX, a_BlockY - 1, a_BlockZ, BLOCK_FACE_YP);
|
||||||
NeighborChanged(a_ChunkInterface, a_BlockX, a_BlockY + 1, a_BlockZ);
|
NeighborChanged(a_ChunkInterface, a_BlockX, a_BlockY + 1, a_BlockZ, BLOCK_FACE_YM);
|
||||||
NeighborChanged(a_ChunkInterface, a_BlockX, a_BlockY, a_BlockZ - 1);
|
NeighborChanged(a_ChunkInterface, a_BlockX, a_BlockY, a_BlockZ - 1, BLOCK_FACE_ZP);
|
||||||
NeighborChanged(a_ChunkInterface, a_BlockX, a_BlockY, a_BlockZ + 1);
|
NeighborChanged(a_ChunkInterface, a_BlockX, a_BlockY, a_BlockZ + 1, BLOCK_FACE_ZM);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
void cBlockHandler::NeighborChanged(cChunkInterface & a_ChunkInterface, int a_BlockX, int a_BlockY, int a_BlockZ)
|
void cBlockHandler::NeighborChanged(cChunkInterface & a_ChunkInterface, int a_NeighborX, int a_NeighborY, int a_NeighborZ, eBlockFace a_WhichNeighbor)
|
||||||
{
|
{
|
||||||
if ((a_BlockY >= 0) && (a_BlockY < cChunkDef::Height))
|
if ((a_NeighborY >= 0) && (a_NeighborY < cChunkDef::Height))
|
||||||
{
|
{
|
||||||
cBlockInfo::GetHandler(a_ChunkInterface.GetBlock(a_BlockX, a_BlockY, a_BlockZ))->OnNeighborChanged(a_ChunkInterface, a_BlockX, a_BlockY, a_BlockZ);
|
cBlockInfo::GetHandler(a_ChunkInterface.GetBlock(a_NeighborX, a_NeighborY, a_NeighborZ))->OnNeighborChanged(a_ChunkInterface, a_NeighborX, a_NeighborY, a_NeighborZ, a_WhichNeighbor);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -56,13 +56,19 @@ public:
|
|||||||
/// Called before a block gets destroyed / replaced with air
|
/// Called before a block gets destroyed / replaced with air
|
||||||
virtual void OnDestroyed(cChunkInterface & a_ChunkInterface, cWorldInterface & a_WorldInterface, int a_BlockX, int a_BlockY, int a_BlockZ);
|
virtual void OnDestroyed(cChunkInterface & a_ChunkInterface, cWorldInterface & a_WorldInterface, int a_BlockX, int a_BlockY, int a_BlockZ);
|
||||||
|
|
||||||
/// Called when a direct neighbor of this block has been changed (The position is the own position, not the neighbor position)
|
/** Called when a direct neighbor of this block has been changed (The position is the block's own position, not the changing neighbor's position)
|
||||||
virtual void OnNeighborChanged(cChunkInterface & a_ChunkInterface, int a_BlockX, int a_BlockY, int a_BlockZ) {}
|
a_WhichNeighbor indicates which neighbor has changed. For example, BLOCK_FACE_YP meant the neighbor above has changed.
|
||||||
|
BLOCK_FACE_NONE means that it is a neighbor not directly adjacent (diagonal, etc.) */
|
||||||
|
virtual void OnNeighborChanged(cChunkInterface & a_ChunkInterface, int a_BlockX, int a_BlockY, int a_BlockZ, eBlockFace a_WhichNeighbor) {}
|
||||||
|
|
||||||
/// Notifies all neighbors of the given block about a change
|
/** Notifies the specified neighbor that the current block has changed.
|
||||||
static void NeighborChanged(cChunkInterface & a_ChunkInterface, int a_BlockX, int a_BlockY, int a_BlockZ);
|
a_NeighborXYZ coords are the coords of the neighbor
|
||||||
|
a_WhichNeighbor specifies which neighbor (relative to a_NeighborXYZ) has changed.
|
||||||
|
For example BLOCK_FACE_YP means that the block at {a_NeighborX, a_NeighborY + 1, a_NeighborZ} has changed.
|
||||||
|
BLOCK_FACE_NONE means that it is a neighbor not directly adjacent (diagonal, etc.) */
|
||||||
|
static void NeighborChanged(cChunkInterface & a_ChunkInterface, int a_NeighborX, int a_NeighborY, int a_NeighborZ, eBlockFace a_WhichNeighbor);
|
||||||
|
|
||||||
/// Called while the player diggs the block.
|
/** Called when the player starts digging the block. */
|
||||||
virtual void OnDigging(cChunkInterface & cChunkInterface, cWorldInterface & a_WorldInterface, cPlayer * a_Player, int a_BlockX, int a_BlockY, int a_BlockZ) {}
|
virtual void OnDigging(cChunkInterface & cChunkInterface, cWorldInterface & a_WorldInterface, cPlayer * a_Player, int a_BlockX, int a_BlockY, int a_BlockZ) {}
|
||||||
|
|
||||||
/// Called if the user right clicks the block and the block is useable
|
/// Called if the user right clicks the block and the block is useable
|
||||||
|
@ -75,10 +75,14 @@ public:
|
|||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
virtual void OnNeighborChanged(cChunkInterface & a_ChunkInterface, int a_BlockX, int a_BlockY, int a_BlockZ) override
|
virtual void OnNeighborChanged(cChunkInterface & a_ChunkInterface, int a_BlockX, int a_BlockY, int a_BlockZ, eBlockFace a_WhichNeighbor) override
|
||||||
{
|
{
|
||||||
|
// Unset 0x8 bit so this block gets checked for decay:
|
||||||
NIBBLETYPE Meta = a_ChunkInterface.GetBlockMeta(a_BlockX, a_BlockY, a_BlockZ);
|
NIBBLETYPE Meta = a_ChunkInterface.GetBlockMeta(a_BlockX, a_BlockY, a_BlockZ);
|
||||||
a_ChunkInterface.SetBlockMeta(a_BlockX, a_BlockY, a_BlockZ, Meta & 0x7); // Unset 0x8 bit so it gets checked for decay
|
if ((Meta & 0x08) != 0)
|
||||||
|
{
|
||||||
|
a_ChunkInterface.SetBlockMeta(a_BlockX, a_BlockY, a_BlockZ, Meta & 0x7);
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
|
@ -47,15 +47,14 @@ public:
|
|||||||
super::OnPlaced(a_ChunkInterface, a_WorldInterface, a_BlockX, a_BlockY, a_BlockZ, a_BlockType, a_BlockMeta);
|
super::OnPlaced(a_ChunkInterface, a_WorldInterface, a_BlockX, a_BlockY, a_BlockZ, a_BlockType, a_BlockMeta);
|
||||||
|
|
||||||
// Alert diagonal rails
|
// Alert diagonal rails
|
||||||
OnNeighborChanged(a_ChunkInterface, a_BlockX + 1, a_BlockY + 1, a_BlockZ);
|
OnNeighborChanged(a_ChunkInterface, a_BlockX + 1, a_BlockY + 1, a_BlockZ, BLOCK_FACE_NONE);
|
||||||
OnNeighborChanged(a_ChunkInterface, a_BlockX - 1, a_BlockY + 1, a_BlockZ);
|
OnNeighborChanged(a_ChunkInterface, a_BlockX - 1, a_BlockY + 1, a_BlockZ, BLOCK_FACE_NONE);
|
||||||
OnNeighborChanged(a_ChunkInterface, a_BlockX, a_BlockY + 1, a_BlockZ + 1);
|
OnNeighborChanged(a_ChunkInterface, a_BlockX, a_BlockY + 1, a_BlockZ + 1, BLOCK_FACE_NONE);
|
||||||
OnNeighborChanged(a_ChunkInterface, a_BlockX, a_BlockY + 1, a_BlockZ - 1);
|
OnNeighborChanged(a_ChunkInterface, a_BlockX, a_BlockY + 1, a_BlockZ - 1, BLOCK_FACE_NONE);
|
||||||
|
OnNeighborChanged(a_ChunkInterface, a_BlockX + 1, a_BlockY - 1, a_BlockZ, BLOCK_FACE_NONE);
|
||||||
OnNeighborChanged(a_ChunkInterface, a_BlockX + 1, a_BlockY - 1, a_BlockZ);
|
OnNeighborChanged(a_ChunkInterface, a_BlockX - 1, a_BlockY - 1, a_BlockZ, BLOCK_FACE_NONE);
|
||||||
OnNeighborChanged(a_ChunkInterface, a_BlockX - 1, a_BlockY - 1, a_BlockZ);
|
OnNeighborChanged(a_ChunkInterface, a_BlockX, a_BlockY - 1, a_BlockZ + 1, BLOCK_FACE_NONE);
|
||||||
OnNeighborChanged(a_ChunkInterface, a_BlockX, a_BlockY - 1, a_BlockZ + 1);
|
OnNeighborChanged(a_ChunkInterface, a_BlockX, a_BlockY - 1, a_BlockZ - 1, BLOCK_FACE_NONE);
|
||||||
OnNeighborChanged(a_ChunkInterface, a_BlockX, a_BlockY - 1, a_BlockZ - 1);
|
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
@ -64,19 +63,18 @@ public:
|
|||||||
super::OnDestroyed(a_ChunkInterface, a_WorldInterface, a_BlockX, a_BlockY, a_BlockZ);
|
super::OnDestroyed(a_ChunkInterface, a_WorldInterface, a_BlockX, a_BlockY, a_BlockZ);
|
||||||
|
|
||||||
// Alert diagonal rails
|
// Alert diagonal rails
|
||||||
OnNeighborChanged(a_ChunkInterface, a_BlockX + 1, a_BlockY + 1, a_BlockZ);
|
OnNeighborChanged(a_ChunkInterface, a_BlockX + 1, a_BlockY + 1, a_BlockZ, BLOCK_FACE_NONE);
|
||||||
OnNeighborChanged(a_ChunkInterface, a_BlockX - 1, a_BlockY + 1, a_BlockZ);
|
OnNeighborChanged(a_ChunkInterface, a_BlockX - 1, a_BlockY + 1, a_BlockZ, BLOCK_FACE_NONE);
|
||||||
OnNeighborChanged(a_ChunkInterface, a_BlockX, a_BlockY + 1, a_BlockZ + 1);
|
OnNeighborChanged(a_ChunkInterface, a_BlockX, a_BlockY + 1, a_BlockZ + 1, BLOCK_FACE_NONE);
|
||||||
OnNeighborChanged(a_ChunkInterface, a_BlockX, a_BlockY + 1, a_BlockZ - 1);
|
OnNeighborChanged(a_ChunkInterface, a_BlockX, a_BlockY + 1, a_BlockZ - 1, BLOCK_FACE_NONE);
|
||||||
|
OnNeighborChanged(a_ChunkInterface, a_BlockX + 1, a_BlockY - 1, a_BlockZ, BLOCK_FACE_NONE);
|
||||||
OnNeighborChanged(a_ChunkInterface, a_BlockX + 1, a_BlockY - 1, a_BlockZ);
|
OnNeighborChanged(a_ChunkInterface, a_BlockX - 1, a_BlockY - 1, a_BlockZ, BLOCK_FACE_NONE);
|
||||||
OnNeighborChanged(a_ChunkInterface, a_BlockX - 1, a_BlockY - 1, a_BlockZ);
|
OnNeighborChanged(a_ChunkInterface, a_BlockX, a_BlockY - 1, a_BlockZ + 1, BLOCK_FACE_NONE);
|
||||||
OnNeighborChanged(a_ChunkInterface, a_BlockX, a_BlockY - 1, a_BlockZ + 1);
|
OnNeighborChanged(a_ChunkInterface, a_BlockX, a_BlockY - 1, a_BlockZ - 1, BLOCK_FACE_NONE);
|
||||||
OnNeighborChanged(a_ChunkInterface, a_BlockX, a_BlockY - 1, a_BlockZ - 1);
|
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
virtual void OnNeighborChanged(cChunkInterface & a_ChunkInterface, int a_BlockX, int a_BlockY, int a_BlockZ) override
|
virtual void OnNeighborChanged(cChunkInterface & a_ChunkInterface, int a_BlockX, int a_BlockY, int a_BlockZ, eBlockFace a_WhichNeighbor) override
|
||||||
{
|
{
|
||||||
NIBBLETYPE Meta = a_ChunkInterface.GetBlockMeta(a_BlockX, a_BlockY, a_BlockZ);
|
NIBBLETYPE Meta = a_ChunkInterface.GetBlockMeta(a_BlockX, a_BlockY, a_BlockZ);
|
||||||
if (IsUnstable(a_ChunkInterface, a_BlockX, a_BlockY, a_BlockZ) && (Meta != FindMeta(a_ChunkInterface, a_BlockX, a_BlockY, a_BlockZ)))
|
if (IsUnstable(a_ChunkInterface, a_BlockX, a_BlockY, a_BlockZ) && (Meta != FindMeta(a_ChunkInterface, a_BlockX, a_BlockY, a_BlockZ)))
|
||||||
|
@ -1037,7 +1037,7 @@ void cChunk::GrowMelonPumpkin(int a_RelX, int a_RelY, int a_RelZ, BLOCKTYPE a_Bl
|
|||||||
VERIFY(UnboundedRelFastSetBlock(a_RelX + x, a_RelY, a_RelZ + z, ProduceType, Meta));
|
VERIFY(UnboundedRelFastSetBlock(a_RelX + x, a_RelY, a_RelZ + z, ProduceType, Meta));
|
||||||
auto Absolute = RelativeToAbsolute(Vector3i{a_RelX + x, a_RelY, a_RelZ + z}, m_PosX, m_PosZ);
|
auto Absolute = RelativeToAbsolute(Vector3i{a_RelX + x, a_RelY, a_RelZ + z}, m_PosX, m_PosZ);
|
||||||
cChunkInterface ChunkInterface(this->GetWorld()->GetChunkMap());
|
cChunkInterface ChunkInterface(this->GetWorld()->GetChunkMap());
|
||||||
cBlockHandler::NeighborChanged(ChunkInterface, Absolute.x, Absolute.y, Absolute.z);
|
cBlockHandler::NeighborChanged(ChunkInterface, Absolute.x, Absolute.y - 1, Absolute.z, BLOCK_FACE_YP);
|
||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@ -160,7 +160,7 @@ void cBlockHandler::OnDestroyed(cChunkInterface & a_ChunkInterface, cWorldInterf
|
|||||||
|
|
||||||
|
|
||||||
|
|
||||||
void cBlockHandler::NeighborChanged(cChunkInterface & a_ChunkInterface, int a_BlockX, int a_BlockY, int a_BlockZ)
|
void cBlockHandler::NeighborChanged(cChunkInterface & a_ChunkInterface, int a_BlockX, int a_BlockY, int a_BlockZ, eBlockFace a_WhichNeighbor)
|
||||||
{
|
{
|
||||||
}
|
}
|
||||||
|
|
||||||
|
Loading…
Reference in New Issue
Block a user