From 33e3f4916173b4129cbbe60f94dae659a70edb83 Mon Sep 17 00:00:00 2001 From: Peter Nelson Date: Thu, 31 Jan 2019 20:54:15 +0000 Subject: [PATCH] Fix #7119: When rotating a ship, apply an additional offset to avoid movement glitch. --- src/saveload/vehicle_sl.cpp | 11 +++++++++++ src/ship.h | 2 ++ src/ship_cmd.cpp | 15 +++++++++++++++ 3 files changed, 28 insertions(+) diff --git a/src/saveload/vehicle_sl.cpp b/src/saveload/vehicle_sl.cpp index 11935fa403..540416586c 100644 --- a/src/saveload/vehicle_sl.cpp +++ b/src/saveload/vehicle_sl.cpp @@ -375,6 +375,17 @@ void AfterLoadVehicles(bool part_of_load) FOR_ALL_SHIPS(s) { s->rotation = s->direction; } + } else { + Ship *s; + FOR_ALL_SHIPS(s) { + if (s->rotation == s->direction) continue; + /* In case we are rotating on gameload, set the rotation position to + * the current position, otherwise the applied workaround offset would + * be with respect to 0,0. + */ + s->rotation_x_pos = s->x_pos; + s->rotation_y_pos = s->y_pos; + } } } diff --git a/src/ship.h b/src/ship.h index adbc322282..60d4466d68 100644 --- a/src/ship.h +++ b/src/ship.h @@ -29,6 +29,8 @@ struct Ship FINAL : public SpecializedVehicle { TrackBitsByte state; ///< The "track" the ship is following. ShipPathCache path; ///< Cached path. DirectionByte rotation; ///< Visible direction. + int16 rotation_x_pos; ///< NOSAVE: X Position before rotation. + int16 rotation_y_pos; ///< NOSAVE: Y Position before rotation. /** We don't want GCC to zero our struct! It already is zeroed and has an index! */ Ship() : SpecializedVehicleBase() {} diff --git a/src/ship_cmd.cpp b/src/ship_cmd.cpp index b357fa64c2..5d3a28b1b4 100644 --- a/src/ship_cmd.cpp +++ b/src/ship_cmd.cpp @@ -319,6 +319,15 @@ void Ship::UpdateDeltaXY() this->x_extent = bb[1]; this->y_extent = bb[0]; this->z_extent = 6; + + if (this->direction != this->rotation) { + /* If we are rotating, then it is possible the ship was moved to its next position. In that + * case, because we are still showing the old direction, the ship will appear to glitch sideways + * slightly. We can work around this by applying an additional offset to make the ship appear + * where it was before it moved. */ + this->x_offs -= this->x_pos - this->rotation_x_pos; + this->y_offs -= this->y_pos - this->rotation_y_pos; + } } /** @@ -678,6 +687,9 @@ static void ShipController(Ship *v) /* Stop for rotation */ v->cur_speed = 0; v->direction = new_direction; + /* Remember our current location to avoid movement glitch */ + v->rotation_x_pos = v->x_pos; + v->rotation_y_pos = v->y_pos; break; } } @@ -704,6 +716,9 @@ getout: reverse_direction: v->direction = ReverseDir(v->direction); + /* Remember our current location to avoid movement glitch */ + v->rotation_x_pos = v->x_pos; + v->rotation_y_pos = v->y_pos; v->cur_speed = 0; v->path.clear(); goto getout;