Physics enhancements

Minecarts no longer glitch on flat rails
Improved acceleration, speed limit, and stopping
master
Tiger Wang 2013-08-29 15:25:12 +01:00
parent 9f59b9a093
commit acaae7a11e
2 changed files with 37 additions and 29 deletions

View File

@ -499,6 +499,7 @@ void cEntity::HandlePhysics(float a_Dt, cChunk & a_Chunk)
int RelBlockX = BlockX - (NextChunk->GetPosX() * cChunkDef::Width); int RelBlockX = BlockX - (NextChunk->GetPosX() * cChunkDef::Width);
int RelBlockZ = BlockZ - (NextChunk->GetPosZ() * cChunkDef::Width); int RelBlockZ = BlockZ - (NextChunk->GetPosZ() * cChunkDef::Width);
BLOCKTYPE BlockIn = NextChunk->GetBlock( RelBlockX, BlockY, RelBlockZ ); BLOCKTYPE BlockIn = NextChunk->GetBlock( RelBlockX, BlockY, RelBlockZ );
BLOCKTYPE BlockBelow = NextChunk->GetBlock( RelBlockX, BlockY - 1, RelBlockZ );
if (!g_BlockIsSolid[BlockIn]) // Making sure we are not inside a solid block if (!g_BlockIsSolid[BlockIn]) // Making sure we are not inside a solid block
{ {
if (m_bOnGround) // check if it's still on the ground if (m_bOnGround) // check if it's still on the ground
@ -539,6 +540,13 @@ void cEntity::HandlePhysics(float a_Dt, cChunk & a_Chunk)
NextSpeed.y += fallspeed; NextSpeed.y += fallspeed;
} }
else else
{
if (
(BlockBelow != E_BLOCK_RAIL) &&
(BlockBelow != E_BLOCK_DETECTOR_RAIL) &&
(BlockBelow != E_BLOCK_POWERED_RAIL) &&
(BlockBelow != E_BLOCK_ACTIVATOR_RAIL)
)
{ {
//Friction //Friction
if (NextSpeed.SqrLength() > 0.0004f) if (NextSpeed.SqrLength() > 0.0004f)
@ -549,6 +557,7 @@ void cEntity::HandlePhysics(float a_Dt, cChunk & a_Chunk)
if ( fabs(NextSpeed.z) < 0.05 ) NextSpeed.z = 0; if ( fabs(NextSpeed.z) < 0.05 ) NextSpeed.z = 0;
} }
} }
}
//Adjust X and Z speed for COBWEB temporary. This speed modification should be handled inside block handlers since we //Adjust X and Z speed for COBWEB temporary. This speed modification should be handled inside block handlers since we
//might have different speed modifiers according to terrain. //might have different speed modifiers according to terrain.

View File

@ -88,20 +88,19 @@ void cMinecart::Tick(float a_Dt, cChunk & a_Chunk)
SpeedY = 0; // Don't move vertically as on ground SpeedY = 0; // Don't move vertically as on ground
// Set Y as current Y rounded up to bypass friction // Set Y as current Y rounded up to bypass friction
// TODO: this causes positioning mismatches on the client, but Entity physics insists on friction! SetPosY(floor(GetPosY()));
SetPosY(ceil(GetPosY()) + 0.05);
if (SpeedZ != 0) // Don't do anything if cart is stationary if (SpeedZ != 0) // Don't do anything if cart is stationary
{ {
if (SpeedZ > 0) if (SpeedZ > 0)
{ {
// Going SOUTH, slow down // Going SOUTH, slow down
SpeedZ = SpeedZ - 0.05; SpeedZ = SpeedZ - 0.1;
} }
else else
{ {
// Going NORTH, slow down // Going NORTH, slow down
SpeedZ = SpeedZ + 0.05; SpeedZ = SpeedZ + 0.1;
} }
} }
break; break;
@ -110,17 +109,17 @@ void cMinecart::Tick(float a_Dt, cChunk & a_Chunk)
case E_RAIL_XM_XP: case E_RAIL_XM_XP:
{ {
SpeedY = 0; SpeedY = 0;
SetPosY(ceil(GetPosY()) + 0.05); SetPosY(floor(GetPosY()));
if (SpeedX != 0) if (SpeedX != 0)
{ {
if (SpeedX > 0) if (SpeedX > 0)
{ {
SpeedX = SpeedX - 0.05; SpeedX = SpeedX - 0.1;
} }
else else
{ {
SpeedX = SpeedX + 0.05; SpeedX = SpeedX + 0.1;
} }
} }
break; break;
@ -131,21 +130,21 @@ void cMinecart::Tick(float a_Dt, cChunk & a_Chunk)
if (SpeedZ >= 0) if (SpeedZ >= 0)
{ {
// SpeedZ POSITIVE, going SOUTH // SpeedZ POSITIVE, going SOUTH
if (SpeedZ <= 6) // Speed limit of 6 SOUTH (m/s??) if (SpeedZ <= 8) // Speed limit of 8 SOUTH (m/s??)
{ {
SpeedZ = SpeedZ + 1; // Speed up SpeedZ = SpeedZ + 0.5; // Speed up
SpeedY = (0 - SpeedZ); // Downward movement is negative (0 minus positive numbers is negative) SpeedY = (0 - SpeedZ); // Downward movement is negative (0 minus positive numbers is negative)
} }
else else
{ {
SpeedZ = 6; // Enforce speed limit SpeedZ = 8; // Enforce speed limit
SpeedY = (0 - SpeedZ); SpeedY = (0 - SpeedZ);
} }
} }
else else
{ {
// SpeedZ NEGATIVE, going NORTH // SpeedZ NEGATIVE, going NORTH
SpeedZ = SpeedZ + 0.1; // Slow down SpeedZ = SpeedZ + 0.6; // Slow down
SpeedY = (0 - SpeedZ); // Upward movement is positive (0 minus negative number is positive number) SpeedY = (0 - SpeedZ); // Upward movement is positive (0 minus negative number is positive number)
} }
break; break;
@ -156,20 +155,20 @@ void cMinecart::Tick(float a_Dt, cChunk & a_Chunk)
if (SpeedX > 0) if (SpeedX > 0)
{ {
// SpeedZ POSITIVE, going SOUTH // SpeedZ POSITIVE, going SOUTH
SpeedZ = SpeedZ - 0.1; // Slow down SpeedZ = SpeedZ - 0.6; // Slow down
SpeedY = SpeedZ; // Upward movement positive SpeedY = SpeedZ; // Upward movement positive
} }
else else
{ {
if (SpeedZ >= -6) // Speed limit of 6 WEST (m/s??) if (SpeedZ >= -8) // Speed limit of 8 WEST (m/s??)
{ {
// SpeedZ NEGATIVE, going NORTH // SpeedZ NEGATIVE, going NORTH
SpeedZ = SpeedZ - 1; // Speed up SpeedZ = SpeedZ - 0.5; // Speed up
SpeedY = SpeedZ; // Downward movement negative SpeedY = SpeedZ; // Downward movement negative
} }
else else
{ {
SpeedZ = 6; // Enforce speed limit SpeedZ = 8; // Enforce speed limit
SpeedY = SpeedZ; SpeedY = SpeedZ;
} }
} }
@ -180,20 +179,20 @@ void cMinecart::Tick(float a_Dt, cChunk & a_Chunk)
{ {
if (SpeedX >= 0) if (SpeedX >= 0)
{ {
if (SpeedX <= 6) if (SpeedX <= 8)
{ {
SpeedX = SpeedX + 1; SpeedX = SpeedX + 0.5;
SpeedY = (0 - SpeedX); SpeedY = (0 - SpeedX);
} }
else else
{ {
SpeedX = 6; SpeedX = 8;
SpeedY = (0 - SpeedX); SpeedY = (0 - SpeedX);
} }
} }
else else
{ {
SpeedX = SpeedX + 0.1; SpeedX = SpeedX + 0.6;
SpeedY = (0 - SpeedX); SpeedY = (0 - SpeedX);
} }
break; break;
@ -203,19 +202,19 @@ void cMinecart::Tick(float a_Dt, cChunk & a_Chunk)
{ {
if (SpeedX > 0) if (SpeedX > 0)
{ {
SpeedX = SpeedX - 0.1; SpeedX = SpeedX - 0.6;
SpeedY = SpeedX; SpeedY = SpeedX;
} }
else else
{ {
if (SpeedX >= -6) if (SpeedX >= -8)
{ {
SpeedX = SpeedX - 1; SpeedX = SpeedX - 0.5;
SpeedY = SpeedX; SpeedY = SpeedX;
} }
else else
{ {
SpeedX = -6; SpeedX = -8;
SpeedY = SpeedX; SpeedY = SpeedX;
} }
} }