diff --git a/src/openrct2-ui/windows/TopToolbar.cpp b/src/openrct2-ui/windows/TopToolbar.cpp index 0604afaf3a..550c7b4cab 100644 --- a/src/openrct2-ui/windows/TopToolbar.cpp +++ b/src/openrct2-ui/windows/TopToolbar.cpp @@ -2832,14 +2832,13 @@ static void top_toolbar_tool_update_scenery(int16_t x, int16_t y) for (rct_large_scenery_tile* tile = scenery->large_scenery.tiles; tile->x_offset != (int16_t)(uint16_t)0xFFFF; tile++) { - LocationXY16 tileLocation = { tile->x_offset, tile->y_offset }; + CoordsXY tileLocation = { tile->x_offset, tile->y_offset }; + auto rotatedTileCoords = tileLocation.Rotate((parameter1 >> 8) & 0xFF); - rotate_map_coordinates(&tileLocation.x, &tileLocation.y, (parameter1 >> 8) & 0xFF); + rotatedTileCoords.x += mapTile.x; + rotatedTileCoords.y += mapTile.y; - tileLocation.x += mapTile.x; - tileLocation.y += mapTile.y; - - gMapSelectionTiles.push_back({ tileLocation.x, tileLocation.y }); + gMapSelectionTiles.push_back(rotatedTileCoords); } gMapSelectFlags |= MAP_SELECT_FLAG_ENABLE_CONSTRUCT; diff --git a/src/openrct2-ui/windows/TrackDesignPlace.cpp b/src/openrct2-ui/windows/TrackDesignPlace.cpp index 5c62835ee6..ec699e56f3 100644 --- a/src/openrct2-ui/windows/TrackDesignPlace.cpp +++ b/src/openrct2-ui/windows/TrackDesignPlace.cpp @@ -125,9 +125,9 @@ static void window_track_place_attempt_placement( static void window_track_place_clear_mini_preview(); static void window_track_place_draw_mini_preview(TrackDesign* td6); static void window_track_place_draw_mini_preview_track( - TrackDesign* td6, int32_t pass, LocationXY16 origin, LocationXY16* min, LocationXY16* max); + TrackDesign* td6, int32_t pass, CoordsXY origin, CoordsXY& min, CoordsXY& max); static void window_track_place_draw_mini_preview_maze( - TrackDesign* td6, int32_t pass, LocationXY16 origin, LocationXY16* min, LocationXY16* max); + TrackDesign* td6, int32_t pass, CoordsXY origin, CoordsXY& min, CoordsXY& max); static LocationXY16 draw_mini_preview_get_pixel_position(int16_t x, int16_t y); static bool draw_mini_preview_is_pixel_in_bounds(LocationXY16 pixel); static uint8_t* draw_mini_preview_get_pixel_ptr(LocationXY16 pixel); @@ -502,11 +502,11 @@ static void window_track_place_draw_mini_preview(TrackDesign* td6) window_track_place_clear_mini_preview(); // First pass is used to determine the width and height of the image so it can centre it - LocationXY16 min = { 0, 0 }; - LocationXY16 max = { 0, 0 }; + CoordsXY min = { 0, 0 }; + CoordsXY max = { 0, 0 }; for (int32_t pass = 0; pass < 2; pass++) { - LocationXY16 origin = { 0, 0 }; + CoordsXY origin = { 0, 0 }; if (pass == 1) { origin.x -= ((max.x + min.x) >> 6) * 32; @@ -515,17 +515,17 @@ static void window_track_place_draw_mini_preview(TrackDesign* td6) if (td6->type == RIDE_TYPE_MAZE) { - window_track_place_draw_mini_preview_maze(td6, pass, origin, &min, &max); + window_track_place_draw_mini_preview_maze(td6, pass, origin, min, max); } else { - window_track_place_draw_mini_preview_track(td6, pass, origin, &min, &max); + window_track_place_draw_mini_preview_track(td6, pass, origin, min, max); } } } static void window_track_place_draw_mini_preview_track( - TrackDesign* td6, int32_t pass, LocationXY16 origin, LocationXY16* min, LocationXY16* max) + TrackDesign* td6, int32_t pass, CoordsXY origin, CoordsXY& min, CoordsXY& max) { uint8_t rotation = (_currentTrackPieceDirection + get_current_rotation()) & 3; @@ -543,20 +543,19 @@ static void window_track_place_draw_mini_preview_track( const rct_preview_track* trackBlock = trackBlockArray[trackType]; while (trackBlock->index != 255) { - int16_t x = origin.x; - int16_t y = origin.y; - map_offset_with_rotation(&x, &y, trackBlock->x, trackBlock->y, rotation); + auto rotatedAndOffsetTrackBlock = origin + CoordsXY{ trackBlock->x, trackBlock->y }.Rotate(rotation); if (pass == 0) { - min->x = std::min(min->x, x); - max->x = std::max(max->x, x); - min->y = std::min(min->y, y); - max->y = std::max(max->y, y); + min.x = std::min(min.x, rotatedAndOffsetTrackBlock.x); + max.x = std::max(max.x, rotatedAndOffsetTrackBlock.x); + min.y = std::min(min.y, rotatedAndOffsetTrackBlock.y); + max.y = std::max(max.y, rotatedAndOffsetTrackBlock.y); } else { - LocationXY16 pixelPosition = draw_mini_preview_get_pixel_position(x, y); + LocationXY16 pixelPosition = draw_mini_preview_get_pixel_position( + rotatedAndOffsetTrackBlock.x, rotatedAndOffsetTrackBlock.y); if (draw_mini_preview_is_pixel_in_bounds(pixelPosition)) { uint8_t* pixel = draw_mini_preview_get_pixel_ptr(pixelPosition); @@ -589,7 +588,7 @@ static void window_track_place_draw_mini_preview_track( const rct_track_coordinates* track_coordinate = &TrackCoordinates[trackType]; trackType *= 10; - map_offset_with_rotation(&origin.x, &origin.y, track_coordinate->x, track_coordinate->y, rotation); + auto rotatedAndOfffsetTrack = origin + CoordsXY{ track_coordinate->x, track_coordinate->y }.Rotate(rotation); rotation += track_coordinate->rotation_end - track_coordinate->rotation_begin; rotation &= 3; if (track_coordinate->rotation_end & 4) @@ -598,28 +597,26 @@ static void window_track_place_draw_mini_preview_track( } if (!(rotation & 4)) { - origin.x += CoordsDirectionDelta[rotation].x; - origin.y += CoordsDirectionDelta[rotation].y; + origin = rotatedAndOfffsetTrack + CoordsDirectionDelta[rotation]; } } // Draw entrance and exit preview. for (const auto& entrance : td6->entrance_elements) { - int16_t x = origin.x; - int16_t y = origin.y; - map_offset_with_rotation(&x, &y, entrance.x, entrance.y, rotation); + auto rotatedAndOffsetEntrance = origin + CoordsXY{ entrance.x, entrance.y }.Rotate(rotation); if (pass == 0) { - min->x = std::min(min->x, x); - max->x = std::max(max->x, x); - min->y = std::min(min->y, y); - max->y = std::max(max->y, y); + min.x = std::min(min.x, rotatedAndOffsetEntrance.x); + max.x = std::max(max.x, rotatedAndOffsetEntrance.x); + min.y = std::min(min.y, rotatedAndOffsetEntrance.y); + max.y = std::max(max.y, rotatedAndOffsetEntrance.y); } else { - LocationXY16 pixelPosition = draw_mini_preview_get_pixel_position(x, y); + LocationXY16 pixelPosition = draw_mini_preview_get_pixel_position( + rotatedAndOffsetEntrance.x, rotatedAndOffsetEntrance.y); if (draw_mini_preview_is_pixel_in_bounds(pixelPosition)) { uint8_t* pixel = draw_mini_preview_get_pixel_ptr(pixelPosition); @@ -637,28 +634,23 @@ static void window_track_place_draw_mini_preview_track( } static void window_track_place_draw_mini_preview_maze( - TrackDesign* td6, int32_t pass, LocationXY16 origin, LocationXY16* min, LocationXY16* max) + TrackDesign* td6, int32_t pass, CoordsXY origin, CoordsXY& min, CoordsXY& max) { uint8_t rotation = (_currentTrackPieceDirection + get_current_rotation()) & 3; for (const auto& mazeElement : td6->maze_elements) { - int16_t x = mazeElement.x * 32; - int16_t y = mazeElement.y * 32; - rotate_map_coordinates(&x, &y, rotation); - - x += origin.x; - y += origin.y; + auto rotatedMazeCoords = origin + CoordsXY{ mazeElement.x * 32, mazeElement.y * 32 }.Rotate(rotation); if (pass == 0) { - min->x = std::min(min->x, x); - max->x = std::max(max->x, x); - min->y = std::min(min->y, y); - max->y = std::max(max->y, y); + min.x = std::min(min.x, rotatedMazeCoords.x); + max.x = std::max(max.x, rotatedMazeCoords.x); + min.y = std::min(min.y, rotatedMazeCoords.y); + max.y = std::max(max.y, rotatedMazeCoords.y); } else { - LocationXY16 pixelPosition = draw_mini_preview_get_pixel_position(x, y); + LocationXY16 pixelPosition = draw_mini_preview_get_pixel_position(rotatedMazeCoords.x, rotatedMazeCoords.y); if (draw_mini_preview_is_pixel_in_bounds(pixelPosition)) { uint8_t* pixel = draw_mini_preview_get_pixel_ptr(pixelPosition); diff --git a/src/openrct2/ride/Ride.cpp b/src/openrct2/ride/Ride.cpp index cac818ec8e..b1432a9506 100644 --- a/src/openrct2/ride/Ride.cpp +++ b/src/openrct2/ride/Ride.cpp @@ -6914,11 +6914,9 @@ void sub_6CB945(Ride* ride) if (ride->stations[stationId].Start.xy == RCT_XY8_UNDEFINED) continue; - LocationXYZ16 location = { - (int16_t)(ride->stations[stationId].Start.x * 32), - (int16_t)(ride->stations[stationId].Start.y * 32), - (ride->stations[stationId].Height), - }; + CoordsXYZ location = { ride->stations[stationId].Start.x * 32, ride->stations[stationId].Start.y * 32, + ride->stations[stationId].Height * 8 }; + auto tileHeight = TileCoordsXYZ(location).z; uint8_t direction = 0xFF; bool specialTrack = false; @@ -6938,7 +6936,7 @@ void sub_6CB945(Ride* ride) bool trackFound = false; do { - if (tileElement->base_height != location.z) + if (tileElement->base_height != tileHeight) continue; if (tileElement->GetType() != TILE_ELEMENT_TYPE_TRACK) continue; @@ -6976,8 +6974,8 @@ void sub_6CB945(Ride* ride) const rct_preview_track* trackBlock = get_track_def_from_ride(ride, tileElement->AsTrack()->GetTrackType()); while ((++trackBlock)->index != 0xFF) { - LocationXYZ16 blockLocation = location; - map_offset_with_rotation(&blockLocation.x, &blockLocation.y, trackBlock->x, trackBlock->y, direction); + CoordsXYZ blockLocation = location + CoordsXYZ{ CoordsXY{ trackBlock->x, trackBlock->y }.Rotate(direction), 0 }; + auto blockTileHeight = TileCoordsXYZ(blockLocation).z; bool trackFound = false; tileElement = map_get_first_element_at(blockLocation.x >> 5, blockLocation.y >> 5); @@ -6985,7 +6983,7 @@ void sub_6CB945(Ride* ride) break; do { - if (blockLocation.z != tileElement->base_height) + if (blockTileHeight != tileElement->base_height) continue; if (tileElement->GetType() != TILE_ELEMENT_TYPE_TRACK) continue; diff --git a/src/openrct2/ride/TrackDesign.cpp b/src/openrct2/ride/TrackDesign.cpp index fd0ce84c87..9eaf214787 100644 --- a/src/openrct2/ride/TrackDesign.cpp +++ b/src/openrct2/ride/TrackDesign.cpp @@ -1467,8 +1467,7 @@ static bool track_design_place_ride(TrackDesign* td6, int16_t x, int16_t y, int1 case PTD_OPERATION_DRAW_OUTLINES: for (const rct_preview_track* trackBlock = trackBlockArray[trackType]; trackBlock->index != 0xFF; trackBlock++) { - LocationXY16 tile = { x, y }; - map_offset_with_rotation(&tile.x, &tile.y, trackBlock->x, trackBlock->y, rotation); + auto tile = CoordsXY{ x, y } + CoordsXY{ trackBlock->x, trackBlock->y }.Rotate(rotation); track_design_update_max_min_coordinates(tile.x, tile.y, z); track_design_add_selection_tile(tile.x, tile.y); } @@ -1547,10 +1546,7 @@ static bool track_design_place_ride(TrackDesign* td6, int16_t x, int16_t y, int1 int32_t tempZ = z - TrackCoordinates[trackType].z_begin; for (const rct_preview_track* trackBlock = trackBlockArray[trackType]; trackBlock->index != 0xFF; trackBlock++) { - int16_t tmpX = x; - int16_t tmpY = y; - map_offset_with_rotation(&tmpX, &tmpY, trackBlock->x, trackBlock->y, rotation); - CoordsXY tile = { tmpX, tmpY }; + auto tile = CoordsXY{ x, y } + CoordsXY{ trackBlock->x, trackBlock->y }.Rotate(rotation); if (tile.x < 0 || tile.y < 0 || tile.x >= (256 * 32) || tile.y >= (256 * 32)) { continue; @@ -1588,7 +1584,9 @@ static bool track_design_place_ride(TrackDesign* td6, int16_t x, int16_t y, int1 } const rct_track_coordinates* track_coordinates = &TrackCoordinates[trackType]; - map_offset_with_rotation(&x, &y, track_coordinates->x, track_coordinates->y, rotation); + auto offsetAndRotatedTrack = CoordsXY{ x, y } + CoordsXY{ track_coordinates->x, track_coordinates->y }.Rotate(rotation); + x = offsetAndRotatedTrack.x; + y = offsetAndRotatedTrack.y; z -= track_coordinates->z_begin; z += track_coordinates->z_end; diff --git a/src/openrct2/world/Location.hpp b/src/openrct2/world/Location.hpp index 2f835c933e..edb3e2b30d 100644 --- a/src/openrct2/world/Location.hpp +++ b/src/openrct2/world/Location.hpp @@ -224,6 +224,11 @@ struct CoordsXYZ : public CoordsXY { } + const CoordsXYZ operator+(const CoordsXYZ& rhs) const + { + return { x + rhs.x, y + rhs.y, z + rhs.z }; + } + bool operator==(const CoordsXYZ& other) const { return x == other.x && y == other.y && z == other.z; diff --git a/src/openrct2/world/Map.cpp b/src/openrct2/world/Map.cpp index 9cf0b95803..2003135da0 100644 --- a/src/openrct2/world/Map.cpp +++ b/src/openrct2/world/Map.cpp @@ -2349,16 +2349,6 @@ TileElement* map_get_track_element_at_with_direction_from_ride( return nullptr; }; -void map_offset_with_rotation(int16_t* x, int16_t* y, int16_t offsetX, int16_t offsetY, uint8_t rotation) -{ - TileCoordsXY offsets = { offsetX, offsetY }; - TileCoordsXY newCoords = { *x, *y }; - newCoords += offsets.Rotate(rotation); - - *x = (int16_t)newCoords.x; - *y = (int16_t)newCoords.y; -} - WallElement* map_get_wall_element_at(int32_t x, int32_t y, int32_t z, int32_t direction) { TileElement* tileElement = map_get_first_element_at(x >> 5, y >> 5); diff --git a/src/openrct2/world/Map.h b/src/openrct2/world/Map.h index f4fdf3bf82..59091b97aa 100644 --- a/src/openrct2/world/Map.h +++ b/src/openrct2/world/Map.h @@ -231,7 +231,6 @@ bool map_large_scenery_get_origin( int32_t x, int32_t y, int32_t z, int32_t direction, int32_t sequence, int32_t* outX, int32_t* outY, int32_t* outZ, LargeSceneryElement** outElement); -void map_offset_with_rotation(int16_t* x, int16_t* y, int16_t offsetX, int16_t offsetY, uint8_t rotation); ScreenCoordsXY translate_3d_to_2d_with_z(int32_t rotation, const CoordsXYZ& pos); TrackElement* map_get_track_element_at(int32_t x, int32_t y, int32_t z);