(svn r10317) -Fix [FS#786]: acceleration not calculated properly when a train goes up a hill between tunnels.
authorrubidium
Mon, 25 Jun 2007 08:24:03 +0000
changeset 7052 80fd9b1cc0cd
parent 7051 bd3f5d602c90
child 7053 6530743d7f29
(svn r10317) -Fix [FS#786]: acceleration not calculated properly when a train goes up a hill between tunnels.
src/train_cmd.cpp
--- a/src/train_cmd.cpp	Mon Jun 25 07:33:40 2007 +0000
+++ b/src/train_cmd.cpp	Mon Jun 25 08:24:03 2007 +0000
@@ -2529,22 +2529,28 @@
 
 static byte AfterSetTrainPos(Vehicle *v, bool new_tile)
 {
-	/* need this hint so it returns the right z coordinate on bridges. */
-	byte new_z = GetSlopeZ(v->x_pos, v->y_pos);
-
 	byte old_z = v->z_pos;
-	v->z_pos = new_z;
+	v->z_pos= GetSlopeZ(v->x_pos, v->y_pos);
 
 	if (new_tile) {
 		CLRBIT(v->u.rail.flags, VRF_GOINGUP);
 		CLRBIT(v->u.rail.flags, VRF_GOINGDOWN);
 
-		if (new_z != old_z) {
-			TileIndex tile = TileVirtXY(v->x_pos, v->y_pos);
-
-			/* XXX workaround, whole UP/DOWN detection needs overhaul */
-			if (!IsTunnelTile(tile)) {
-				SETBIT(v->u.rail.flags, (new_z > old_z) ? VRF_GOINGUP : VRF_GOINGDOWN);
+		if ((v->u.rail.track == TRACK_X || v->u.rail.track == TRACK_Y)) {
+			/* Any track that isn't TRACK_X or TRACK_Y cannot be sloped.
+			 * To check whether the current tile is sloped, and in which
+			 * direction it is sloped, we get the 'z' at the center of
+			 * the tile (middle_z) and the edge of the tile (old_z),
+			 * which we then can compare. */
+			static const int HALF_TILE_SIZE = TILE_SIZE / 2;
+			static const int INV_TILE_SIZE_MASK = ~(TILE_SIZE - 1);
+
+			byte middle_z = GetSlopeZ((v->x_pos & INV_TILE_SIZE_MASK) | HALF_TILE_SIZE, (v->y_pos & INV_TILE_SIZE_MASK) | HALF_TILE_SIZE);
+
+			/* For some reason tunnel tiles are always given as sloped :(
+			 * But they are not sloped... */
+			if (middle_z != old_z && !IsTunnelTile(TileVirtXY(v->x_pos, v->y_pos))) {
+				SETBIT(v->u.rail.flags, (middle_z > old_z) ? VRF_GOINGUP : VRF_GOINGDOWN);
 			}
 		}
 	}