Merge pull request #8560 from richard-fine/directions

Begin cleanup of direction handling
This commit is contained in:
Michael Steenbeek 2019-01-18 19:09:39 +01:00 committed by GitHub
commit b4bef2fe7d
No known key found for this signature in database
GPG Key ID: 4AEE18F83AFDEB23
20 changed files with 115 additions and 92 deletions

View File

@ -1017,7 +1017,7 @@ static void footpath_remove_tile_element(TileElement* tileElement)
if (tileElement->AsPath()->IsSloped())
{
uint8_t slopeDirection = tileElement->AsPath()->GetSlopeDirection();
slopeDirection ^= 2;
slopeDirection = direction_reverse(slopeDirection);
if (slopeDirection == gFootpathConstructDirection)
{
z += 2;
@ -1025,7 +1025,7 @@ static void footpath_remove_tile_element(TileElement* tileElement)
}
// Find a connected edge
int32_t edge = gFootpathConstructDirection ^ 2;
int32_t edge = direction_reverse(gFootpathConstructDirection);
if (!(tileElement->AsPath()->GetEdges() & (1 << edge)))
{
edge = (edge + 1) & 3;
@ -1037,7 +1037,7 @@ static void footpath_remove_tile_element(TileElement* tileElement)
edge = (edge - 1) & 3;
if (!(tileElement->AsPath()->GetEdges() & (1 << edge)))
{
edge ^= 2;
edge = direction_reverse(edge);
}
}
}
@ -1048,7 +1048,7 @@ static void footpath_remove_tile_element(TileElement* tileElement)
gFootpathConstructFromPosition.x, gFootpathConstructFromPosition.y, tileElement->base_height, GAME_COMMAND_FLAG_APPLY);
// Move selection
edge ^= 2;
edge = direction_reverse(edge);
x = gFootpathConstructFromPosition.x - CoordsDirectionDelta[edge].x;
y = gFootpathConstructFromPosition.y - CoordsDirectionDelta[edge].y;
gFootpathConstructFromPosition.x = x;
@ -1086,7 +1086,7 @@ static TileElement* footpath_get_tile_element_to_remove()
{
if (tileElement->AsPath()->IsSloped())
{
if (((tileElement->AsPath()->GetSlopeDirection()) ^ 2) != gFootpathConstructDirection)
if (direction_reverse(tileElement->AsPath()->GetSlopeDirection()) != gFootpathConstructDirection)
{
continue;
}

View File

@ -1293,7 +1293,7 @@ static void window_map_set_peep_spawn_tool_update(int32_t x, int32_t y)
gMapSelectPositionA.y = mapY;
gMapSelectPositionB.x = mapX;
gMapSelectPositionB.y = mapY;
gMapSelectArrowDirection = direction ^ 2;
gMapSelectArrowDirection = direction_reverse(direction);
gMapSelectArrowPosition.x = mapX;
gMapSelectArrowPosition.y = mapY;
gMapSelectArrowPosition.z = mapZ;

View File

@ -376,7 +376,7 @@ static void window_maze_construction_entrance_tooldown(int32_t x, int32_t y, rct
}
money32 cost = game_do_command(
x, GAME_COMMAND_FLAG_APPLY | ((direction ^ 2) << 8), y, rideIndex | (entranceExitType << 8),
x, GAME_COMMAND_FLAG_APPLY | (direction_reverse(direction) << 8), y, rideIndex | (entranceExitType << 8),
GAME_COMMAND_PLACE_RIDE_ENTRANCE_OR_EXIT, gRideEntranceExitPlaceStationIndex, 0);
if (cost == MONEY32_UNDEFINED)

View File

@ -1714,7 +1714,7 @@ static void window_ride_construction_construct(rct_window* w)
// game_command_callback_ride_construct_placed_front/back Please update both ends if there are any changes here
if (_rideConstructionState == RIDE_CONSTRUCTION_STATE_BACK)
{
trackDirection = _currentTrackPieceDirection ^ 2;
trackDirection = direction_reverse(_currentTrackPieceDirection);
x = _currentTrackBeginX;
y = _currentTrackBeginY;
z = _currentTrackBeginZ;
@ -2571,7 +2571,7 @@ void sub_6C94D8()
if (direction >= 4)
direction += 4;
if (_rideConstructionState == RIDE_CONSTRUCTION_STATE_BACK)
direction ^= 2;
direction = direction_reverse(direction);
gMapSelectArrowDirection = direction;
gMapSelectFlags &= ~MAP_SELECT_FLAG_ENABLE_ARROW;
if (_currentTrackSelectionFlags & TRACK_SELECTION_FLAG_ARROW)
@ -3611,7 +3611,8 @@ void ride_construction_toolupdate_construct(int32_t screenX, int32_t screenY)
pathsByDir[i] = map_get_footpath_element((x >> 5) + DirOffsets[i].x, (y >> 5) + DirOffsets[i].y, (z >> 3) - 2);
if (pathsByDir[i]
&& (!(pathsByDir[i])->AsPath()->IsSloped() || (pathsByDir[i])->AsPath()->GetSlopeDirection() != (i ^ 2)))
&& (!(pathsByDir[i])->AsPath()->IsSloped()
|| (pathsByDir[i])->AsPath()->GetSlopeDirection() != direction_reverse(i)))
{
pathsByDir[i] = nullptr;
}
@ -3678,13 +3679,13 @@ void ride_construction_toolupdate_entrance_exit(int32_t screenX, int32_t screenY
gMapSelectPositionA.y = y;
gMapSelectPositionB.x = x;
gMapSelectPositionB.y = y;
gMapSelectArrowDirection = direction ^ 2;
gMapSelectArrowDirection = direction_reverse(direction);
gMapSelectArrowPosition.x = x;
gMapSelectArrowPosition.y = y;
gMapSelectArrowPosition.z = _unkF44188.z * 8;
map_invalidate_selection_rect();
direction = gRideEntranceExitPlaceDirection ^ 2;
direction = direction_reverse(gRideEntranceExitPlaceDirection);
stationNum = gRideEntranceExitPlaceStationIndex;
if (!(_currentTrackSelectionFlags & TRACK_SELECTION_FLAG_ENTRANCE_OR_EXIT) || x != gRideEntranceExitGhostPosition.x
|| y != gRideEntranceExitGhostPosition.y || direction != gRideEntranceExitGhostPosition.direction
@ -3933,7 +3934,7 @@ static void ride_construction_tooldown_entrance_exit(int32_t screenX, int32_t sc
game_command_callback = game_command_callback_place_ride_entrance_or_exit;
game_do_command(
_unkF44188.x, (GAME_COMMAND_FLAG_APPLY) | ((gRideEntranceExitPlaceDirection ^ 2) << 8), _unkF44188.y,
_unkF44188.x, (GAME_COMMAND_FLAG_APPLY) | (direction_reverse(gRideEntranceExitPlaceDirection) << 8), _unkF44188.y,
gRideEntranceExitPlaceRideIndex | (gRideEntranceExitPlaceType << 8), GAME_COMMAND_PLACE_RIDE_ENTRANCE_OR_EXIT,
gRideEntranceExitPlaceStationIndex, 0);
}

View File

@ -1615,7 +1615,7 @@ static void sub_6E1F34(
if (tile_element->AsPath()->IsSloped())
{
if (rotation != ((tile_element->AsPath()->GetSlopeDirection()) ^ 2))
if (rotation != direction_reverse(tile_element->AsPath()->GetSlopeDirection()))
{
z += 2;
}

View File

@ -499,7 +499,7 @@ namespace Editor
int32_t x = parkEntrance.x;
int32_t y = parkEntrance.y;
int32_t z = parkEntrance.z / 8;
int32_t direction = parkEntrance.direction ^ 2;
int32_t direction = direction_reverse(parkEntrance.direction);
switch (footpath_is_connected_to_map_edge(x, y, z, direction, 0))
{

View File

@ -78,7 +78,7 @@ void banner_paint(paint_session* session, uint8_t direction, int32_t height, con
sub_98197C(session, image_id, 0, 0, 1, 1, 0x15, height, boundBoxOffsetX, boundBoxOffsetY, boundBoxOffsetZ);
// Opposite direction
direction ^= 2;
direction = direction_reverse(direction);
direction--;
// If text not showing / ghost
if (direction >= 2 || (tile_element->flags & TILE_ELEMENT_FLAG_GHOST))

View File

@ -1069,7 +1069,7 @@ void surface_paint(paint_session* session, uint8_t direction, uint16_t height, c
{
sub_98196C(session, SPR_TERRAIN_SELECTION_SQUARE_SIMPLE, 0, 0, 32, 32, 16, spawn.z);
const int32_t offset = ((spawn.direction ^ 2) + rotation) & 3;
const int32_t offset = (direction_reverse(spawn.direction) + rotation) & 3;
const uint32_t image_id = (PEEP_SPAWN_ARROW_0 + offset) | 0x20380000;
sub_98196C(session, image_id, 0, 0, 32, 32, 19, spawn.z);
}

View File

@ -3271,7 +3271,7 @@ void rct_peep::UpdateBuying()
sprite_direction ^= 0x10;
destination_x = next_x + 16;
destination_y = next_y + 16;
direction ^= 2;
direction = direction_reverse(direction);
SetState(PEEP_STATE_WALKING);
return;
@ -4052,7 +4052,7 @@ void rct_peep::UpdateRideLeaveVehicle()
CoordsXYZD platformLocation;
platformLocation.z = ride->stations[current_ride_station].Height;
platformLocation.direction = exitLocation.direction ^ (1 << 1);
platformLocation.direction = direction_reverse(exitLocation.direction);
if (!ride_type_has_flag(ride->type, RIDE_TYPE_FLAG_16))
{
@ -4096,7 +4096,7 @@ void rct_peep::UpdateRideLeaveVehicle()
specialDirection &= 3;
if (vehicle->var_CD == 6)
specialDirection ^= (1 << 1);
specialDirection = direction_reverse(specialDirection);
}
}
@ -4437,7 +4437,7 @@ void rct_peep::UpdateRideApproachExitWaypoints()
auto exit = ride_get_exit_location(current_ride, current_ride_station);
actionX = exit.x;
actionY = exit.y;
uint8_t exit_direction = exit.direction ^ 2;
uint8_t exit_direction = direction_reverse(exit.direction);
actionX *= 32;
actionY *= 32;
@ -4699,7 +4699,7 @@ void rct_peep::UpdateRideLeaveSpiralSlide()
actionX = exit.x * 32 + 16;
actionY = exit.y * 32 + 16;
exit.direction ^= 2;
exit.direction = direction_reverse(exit.direction);
int16_t xShift = word_981D6C[exit.direction].x;
int16_t yShift = word_981D6C[exit.direction].y;
@ -4807,7 +4807,7 @@ void rct_peep::UpdateRideMazePathfinding()
if (openHedges == 0)
return;
uint8_t mazeLastEdge = maze_last_edge ^ (1 << 1);
uint8_t mazeLastEdge = direction_reverse(maze_last_edge);
openHedges &= ~(1 << mazeLastEdge);
if (openHedges == 0)
openHedges |= (1 << mazeLastEdge);

View File

@ -144,7 +144,7 @@ static int32_t guest_surface_path_finding(rct_peep* peep)
{
x += CoordsDirectionDelta[randDirection].x;
y += CoordsDirectionDelta[randDirection].y;
uint8_t backwardsDirection = randDirection ^ (1 << 1);
uint8_t backwardsDirection = direction_reverse(randDirection);
if (!fence_in_the_way(x, y, z, z + 4, backwardsDirection))
{
@ -169,7 +169,7 @@ static int32_t guest_surface_path_finding(rct_peep* peep)
{
x += CoordsDirectionDelta[randDirection].x;
y += CoordsDirectionDelta[randDirection].y;
uint8_t backwardsDirection = randDirection ^ (1 << 1);
uint8_t backwardsDirection = direction_reverse(randDirection);
if (!fence_in_the_way(x, y, z, z + 4, backwardsDirection))
{
@ -189,7 +189,7 @@ static int32_t guest_surface_path_finding(rct_peep* peep)
{
x += CoordsDirectionDelta[randDirection].x;
y += CoordsDirectionDelta[randDirection].y;
uint8_t backwardsDirection = randDirection ^ (1 << 1);
uint8_t backwardsDirection = direction_reverse(randDirection);
if (!fence_in_the_way(x, y, z, z + 4, backwardsDirection))
{
@ -342,7 +342,7 @@ static uint8_t footpath_element_dest_in_dir(
return PATH_SEARCH_WIDE;
uint8_t edges = path_get_permitted_edges(tileElement);
edges &= ~(1 << (chosenDirection ^ 2));
edges &= ~(1 << direction_reverse(chosenDirection));
loc.z = tileElement->base_height;
for (direction = 0; direction < 4; direction++)
@ -1489,13 +1489,13 @@ int32_t peep_pathfind_choose_direction(TileCoordsXYZ loc, rct_peep* peep)
peep->pathfind_history[i].direction &= ~(1 << chosen_edge);
/* Also remove the edge through which the peep
* entered the junction from those left to try. */
peep->pathfind_history[i].direction &= ~(1 << (peep->direction ^ 2));
peep->pathfind_history[i].direction &= ~(1 << direction_reverse(peep->direction));
#if defined(DEBUG_LEVEL_1) && DEBUG_LEVEL_1
if (gPathFindDebug)
{
log_verbose(
"Updating existing pf_history (in index: %d) for %d,%d,%d without entry edge %d & exit edge %d.", i,
loc.x, loc.y, loc.z, peep->direction ^ 2, chosen_edge);
loc.x, loc.y, loc.z, direction_reverse(peep->direction), chosen_edge);
}
#endif // defined(DEBUG_LEVEL_1) && DEBUG_LEVEL_1
return chosen_edge;
@ -1514,13 +1514,13 @@ int32_t peep_pathfind_choose_direction(TileCoordsXYZ loc, rct_peep* peep)
peep->pathfind_history[i].direction &= ~(1 << chosen_edge);
/* Also remove the edge through which the peep
* entered the junction from those left to try. */
peep->pathfind_history[i].direction &= ~(1 << (peep->direction ^ 2));
peep->pathfind_history[i].direction &= ~(1 << direction_reverse(peep->direction));
#if defined(DEBUG_LEVEL_1) && DEBUG_LEVEL_1
if (gPathFindDebug)
{
log_verbose(
"Storing new pf_history (in index: %d) for %d,%d,%d without entry edge %d & exit edge %d.", i, loc.x, loc.y,
loc.z, peep->direction ^ 2, chosen_edge);
loc.z, direction_reverse(peep->direction), chosen_edge);
}
#endif // defined(DEBUG_LEVEL_1) && DEBUG_LEVEL_1
}
@ -1788,7 +1788,7 @@ static void get_ride_queue_end(TileCoordsXYZ& loc)
if (!tileElement->AsPath()->IsSloped())
break;
if (tileElement->AsPath()->GetSlopeDirection() != (direction ^ 2))
if (tileElement->AsPath()->GetSlopeDirection() != direction_reverse(direction))
break;
baseZ -= 2;
@ -1803,7 +1803,7 @@ static void get_ride_queue_end(TileCoordsXYZ& loc)
if (!tileElement->AsPath()->IsQueue())
break;
if (!(tileElement->AsPath()->GetEdges() & (1 << (direction ^ (1 << 1)))))
if (!(tileElement->AsPath()->GetEdges() & (1 << direction_reverse(direction))))
break;
if (firstPathElement == nullptr)
@ -1819,7 +1819,7 @@ static void get_ride_queue_end(TileCoordsXYZ& loc)
if (tileElement->AsPath()->GetEdges() & (1 << (direction)))
continue;
direction ^= (1 << 1);
direction = direction_reverse(direction);
// More queue to go.
if (tileElement->AsPath()->GetEdges() & (1 << (direction)))
continue;
@ -1901,7 +1901,7 @@ int32_t guest_path_finding(rct_peep* peep)
edges = adjustedEdges;
}
int8_t direction = peep->direction ^ (1 << 1);
int8_t direction = direction_reverse(peep->direction);
// Check if in a dead end (i.e. only edge is where the peep came from)
if (!(edges & ~(1 << direction)))
{

View File

@ -2413,7 +2413,7 @@ static bool peep_update_queue_position(rct_peep* peep, uint8_t previous_action)
*/
static void peep_return_to_centre_of_tile(rct_peep* peep)
{
peep->direction ^= (1 << 1);
peep->direction = direction_reverse(peep->direction);
peep->destination_x = (peep->x & 0xFFE0) + 16;
peep->destination_y = (peep->y & 0xFFE0) + 16;
peep->destination_tolerance = 5;
@ -2544,7 +2544,7 @@ static void peep_interact_with_entrance(
uint8_t entranceDirection = tile_element->GetDirection();
if (entranceDirection != peep->direction)
{
if ((entranceDirection ^ (1 << 1)) != peep->direction)
if (direction_reverse(entranceDirection) != peep->direction)
{
peep_return_to_centre_of_tile(peep);
return;
@ -2642,7 +2642,7 @@ static void peep_interact_with_entrance(
break;
}
if ((slopeDirection ^ (1 << 1)) != entranceDirection)
if (direction_reverse(slopeDirection) != entranceDirection)
continue;
if (z - 2 != nextTileElement->base_height)
@ -2926,7 +2926,7 @@ static void peep_interact_with_path(rct_peep* peep, int16_t x, int16_t y, TileEl
if ((tile_element->AsPath()->HasQueueBanner())
&& (tile_element->AsPath()->GetQueueBannerDirection()
== ((peep->direction) ^ 2)) // Ride sign is facing the direction the peep is walking
== direction_reverse(peep->direction)) // Ride sign is facing the direction the peep is walking
)
{
/* Peep is approaching the entrance of a ride queue.
@ -3099,7 +3099,7 @@ bool is_valid_path_z_and_direction(TileElement* tileElement, int32_t currentZ, i
}
else
{
slopeDirection ^= 2;
slopeDirection = direction_reverse(slopeDirection);
if (slopeDirection != currentDirection)
return false;
if (currentZ != tileElement->base_height + 2)

View File

@ -1070,10 +1070,10 @@ static bool staff_path_finding_handyman(rct_peep* peep)
}
else
{
pathDirections &= ~(1 << (peep->direction ^ (1 << 1)));
pathDirections &= ~(1 << direction_reverse(peep->direction));
if (pathDirections == 0)
{
pathDirections |= 1 << (peep->direction ^ (1 << 1));
pathDirections |= 1 << direction_reverse(peep->direction);
}
}
@ -1137,7 +1137,7 @@ static uint8_t staff_direction_surface(rct_peep* peep, uint8_t initialDirection)
if (fence_in_the_way(peep->next_x, peep->next_y, peep->next_z, peep->next_z + 4, direction) == true)
continue;
if (fence_in_the_way(peep->next_x, peep->next_y, peep->next_z, peep->next_z + 4, direction ^ (1 << 1)) == true)
if (fence_in_the_way(peep->next_x, peep->next_y, peep->next_z, peep->next_z + 4, direction_reverse(direction)) == true)
continue;
LocationXY16 chosenTile = { static_cast<int16_t>(peep->next_x + CoordsDirectionDelta[direction].x),
@ -1225,10 +1225,10 @@ static uint8_t staff_mechanic_direction_path(rct_peep* peep, uint8_t validDirect
}
// Check if this is dead end - i.e. only way out is the reverse direction.
pathDirections &= ~(1 << (peep->direction ^ (1 << 1)));
pathDirections &= ~(1 << direction_reverse(peep->direction));
if (pathDirections == 0)
{
pathDirections |= (1 << (peep->direction ^ (1 << 1)));
pathDirections |= (1 << direction_reverse(peep->direction));
}
direction = bitscanforward(pathDirections);
@ -1361,10 +1361,10 @@ static uint8_t staff_direction_path(rct_peep* peep, uint8_t validDirections, Til
return staff_direction_surface(peep, scenario_rand() & 3);
}
pathDirections &= ~(1 << (peep->direction ^ (1 << 1)));
pathDirections &= ~(1 << direction_reverse(peep->direction));
if (pathDirections == 0)
{
pathDirections |= (1 << (peep->direction ^ (1 << 1)));
pathDirections |= (1 << direction_reverse(peep->direction));
}
direction = bitscanforward(pathDirections);

View File

@ -676,7 +676,7 @@ bool track_block_get_previous_from_zero(
Ride* ride = get_ride(rideIndex);
uint8_t directionStart = direction;
direction ^= (1 << 1);
direction = direction_reverse(direction);
if (!(direction & (1 << 2)))
{
@ -690,7 +690,7 @@ bool track_block_get_previous_from_zero(
outTrackBeginEnd->end_x = x;
outTrackBeginEnd->end_y = y;
outTrackBeginEnd->begin_element = nullptr;
outTrackBeginEnd->begin_direction = directionStart ^ (1 << 1);
outTrackBeginEnd->begin_direction = direction_reverse(directionStart);
return 0;
}
@ -752,7 +752,7 @@ bool track_block_get_previous_from_zero(
- nextTrackBlock->z;
outTrackBeginEnd->begin_direction = nextRotation;
outTrackBeginEnd->end_direction = directionStart ^ (1 << 1);
outTrackBeginEnd->end_direction = direction_reverse(directionStart);
return 1;
} while (!(tileElement++)->IsLastForTile());
@ -760,7 +760,7 @@ bool track_block_get_previous_from_zero(
outTrackBeginEnd->end_y = y;
outTrackBeginEnd->begin_z = z;
outTrackBeginEnd->begin_element = nullptr;
outTrackBeginEnd->end_direction = directionStart ^ (1 << 1);
outTrackBeginEnd->end_direction = direction_reverse(directionStart);
return 0;
}
@ -1191,7 +1191,7 @@ void ride_remove_peeps(Ride* ride)
exitZ = (exitZ * 8) + 2;
// Reverse direction
exitDirection ^= 2;
exitDirection = direction_reverse(exitDirection);
exitDirection *= 8;
}
@ -1675,7 +1675,7 @@ void ride_construction_set_default_next_piece()
x = _currentTrackBeginX;
y = _currentTrackBeginY;
z = _currentTrackBeginZ;
direction = _currentTrackPieceDirection ^ 2;
direction = direction_reverse(_currentTrackPieceDirection);
if (!track_block_get_next_from_zero(x, y, z, rideIndex, direction, &xyElement, &z, &direction, false))
{
ride_construction_reset_current_piece();
@ -3539,7 +3539,7 @@ static void ride_shop_connected(Ride* ride)
entrance_directions >>= 1;
// Flip direction north<->south, east<->west
uint8_t face_direction = count ^ 2;
uint8_t face_direction = direction_reverse(count);
int32_t y2 = y - CoordsDirectionDelta[face_direction].y;
int32_t x2 = x - CoordsDirectionDelta[face_direction].x;
@ -4420,7 +4420,7 @@ static void sub_6B5952(ride_id_t rideIndex)
continue;
int32_t direction = tileElement->GetDirection();
footpath_chain_ride_queue(rideIndex, i, x, y, tileElement, direction ^ 2);
footpath_chain_ride_queue(rideIndex, i, x, y, tileElement, direction_reverse(direction));
} while (!(tileElement++)->IsLastForTile());
}
}
@ -6297,7 +6297,7 @@ void game_command_callback_ride_construct_placed_back(
int32_t trackDirection, x, y, z;
track_begin_end trackBeginEnd;
trackDirection = _currentTrackPieceDirection ^ 2;
trackDirection = direction_reverse(_currentTrackPieceDirection);
x = _currentTrackBeginX;
y = _currentTrackBeginY;
z = _currentTrackBeginZ;
@ -7192,8 +7192,8 @@ void ride_get_entrance_or_exit_position_from_screen_position(
continue;
if (tileElement->AsTrack()->GetTrackType() == TRACK_ELEM_INVERTED_90_DEG_UP_TO_FLAT_QUARTER_LOOP)
{
gRideEntranceExitPlaceDirection = direction ^ 2;
*outDirection = direction ^ 2;
gRideEntranceExitPlaceDirection = direction_reverse(direction);
*outDirection = direction_reverse(direction);
return;
}
if (tileElement->AsTrack()->GetStationIndex() != gRideEntranceExitPlaceStationIndex)
@ -7204,8 +7204,8 @@ void ride_get_entrance_or_exit_position_from_screen_position(
[tileElement->AsTrack()->GetSequenceIndex()]
& (1 << eax))
{
gRideEntranceExitPlaceDirection = direction ^ 2;
*outDirection = direction ^ 2;
gRideEntranceExitPlaceDirection = direction_reverse(direction);
*outDirection = direction_reverse(direction);
return;
}
} while (!(tileElement++)->IsLastForTile());
@ -7276,7 +7276,7 @@ void ride_get_entrance_or_exit_position_from_screen_position(
}
direction = loc_6CD18E(*outX, *outY, entranceMinX - 32, entranceMinY - 32, entranceMaxX + 32, entranceMaxY + 32);
if (direction != -1 && direction != stationDirection && direction != (stationDirection ^ 2))
if (direction != -1 && direction != stationDirection && direction != direction_reverse(stationDirection))
{
gRideEntranceExitPlaceDirection = direction;
*outDirection = direction;
@ -7319,7 +7319,7 @@ bool ride_select_forwards_from_back()
x = _currentTrackBeginX;
y = _currentTrackBeginY;
z = _currentTrackBeginZ;
direction = _currentTrackPieceDirection ^ 2;
direction = direction_reverse(_currentTrackPieceDirection);
CoordsXYE next_track;
if (track_block_get_next_from_zero(x, y, z, _currentRideIndex, direction, &next_track, &z, &direction, false))
@ -8511,7 +8511,7 @@ bool ride_has_adjacent_station(Ride* ride)
if (found)
break;
/* Check the other side of the station */
direction ^= 2;
direction = direction_reverse(direction);
found = check_for_adjacent_station(stationX, stationY, stationZ, direction);
if (found)
break;

View File

@ -1331,7 +1331,7 @@ static money32 track_place(
int32_t temp_direction = (direction + dl) & 3;
temp_x += CoordsDirectionDelta[temp_direction].x;
temp_y += CoordsDirectionDelta[temp_direction].y;
temp_direction ^= (1 << 1);
temp_direction = direction_reverse(temp_direction);
wall_remove_intersecting_walls(temp_x, temp_y, baseZ, clearanceZ, temp_direction & 3);
}
}

View File

@ -604,7 +604,7 @@ static void track_design_mirror_ride(rct_track_td6* td6)
entrance->y = -entrance->y;
if (entrance->direction & 1)
{
entrance->direction ^= (1 << 1);
entrance->direction = direction_reverse(entrance->direction);
}
}
}
@ -629,7 +629,7 @@ static void track_design_mirror_maze(rct_track_td6* td6)
{
if (maze->direction & 1)
{
maze->direction ^= (1 << 1);
maze->direction = direction_reverse(maze->direction);
}
continue;
}

View File

@ -2872,7 +2872,7 @@ static bool vehicle_can_depart_synchronised(rct_vehicle* vehicle)
y = location.y * 32;
// Other search direction.
direction = (direction ^ 2) & 3;
direction = direction_reverse(direction) & 3;
spaceBetween = maxCheckDistance;
while (_lastSynchronisedVehicle < &_synchronisedVehicles[SYNCHRONISED_VEHICLE_COUNT - 1])
{
@ -7518,7 +7518,7 @@ static void vehicle_update_handle_scenery_door(rct_vehicle* vehicle)
int32_t y = vehicle->track_y;
int32_t z = (vehicle->track_z - trackBlock->z + trackCoordinates->z_begin) >> 3;
int32_t direction = (vehicle->track_direction + trackCoordinates->rotation_begin) & 3;
direction ^= 2;
direction = direction_reverse(direction);
TileElement* tileElement = map_get_wall_element_at(x, y, z, direction);
if (tileElement == nullptr)

View File

@ -180,7 +180,7 @@ static void loc_6A6620(int32_t flags, int32_t x, int32_t y, TileElement* tileEle
{
int32_t direction = tileElement->AsPath()->GetSlopeDirection();
int32_t z = tileElement->base_height;
wall_remove_intersecting_walls(x, y, z, z + 6, direction ^ 2);
wall_remove_intersecting_walls(x, y, z, z + 6, direction_reverse(direction));
wall_remove_intersecting_walls(x, y, z, z + 6, direction);
// Removing walls may have made the pointer invalid, so find it again
tileElement = map_get_footpath_element(x / 32, y / 32, z);
@ -494,7 +494,7 @@ static money32 footpath_place_real(
direction = direction & 0xF;
// It is possible, let's remove walls between the old and new piece of path
wall_remove_intersecting_walls(
x, y, z, z + 4 + ((slope & TILE_ELEMENT_SURFACE_RAISED_CORNERS_MASK) ? 2 : 0), direction ^ 2);
x, y, z, z + 4 + ((slope & TILE_ELEMENT_SURFACE_RAISED_CORNERS_MASK) ? 2 : 0), direction_reverse(direction));
wall_remove_intersecting_walls(
x - CoordsDirectionDelta[direction].x, y - CoordsDirectionDelta[direction].y, z, z + 4, direction);
}
@ -1124,14 +1124,14 @@ static void footpath_connect_corners(int32_t initialX, int32_t initialY, TileEle
x += CoordsDirectionDelta[direction].x;
y += CoordsDirectionDelta[direction].y;
tileElement[1] = footpath_connect_corners_get_neighbour(x, y, z, (1 << (direction ^ 2)));
tileElement[1] = footpath_connect_corners_get_neighbour(x, y, z, (1 << direction_reverse(direction)));
if (tileElement[1] == nullptr)
continue;
direction = (direction + 1) & 3;
x += CoordsDirectionDelta[direction].x;
y += CoordsDirectionDelta[direction].y;
tileElement[2] = footpath_connect_corners_get_neighbour(x, y, z, (1 << (direction ^ 2)));
tileElement[2] = footpath_connect_corners_get_neighbour(x, y, z, (1 << direction_reverse(direction)));
if (tileElement[2] == nullptr)
continue;
@ -1139,7 +1139,7 @@ static void footpath_connect_corners(int32_t initialX, int32_t initialY, TileEle
x += CoordsDirectionDelta[direction].x;
y += CoordsDirectionDelta[direction].y;
// First check link to previous tile
tileElement[3] = footpath_connect_corners_get_neighbour(x, y, z, (1 << (direction ^ 2)));
tileElement[3] = footpath_connect_corners_get_neighbour(x, y, z, (1 << direction_reverse(direction)));
if (tileElement[3] == nullptr)
continue;
// Second check link to initial tile
@ -1272,7 +1272,7 @@ static TileElement* footpath_get_element(int32_t x, int32_t y, int32_t z0, int32
if (!tileElement->AsPath()->IsSloped())
break;
slope = tileElement->AsPath()->GetSlopeDirection() ^ 2;
slope = direction_reverse(tileElement->AsPath()->GetSlopeDirection());
if (slope != direction)
break;
@ -1384,7 +1384,8 @@ static void loc_6A6D7E(
}
if (z - 2 == tileElement->base_height)
{
if (!tileElement->AsPath()->IsSloped() || tileElement->AsPath()->GetSlopeDirection() != (direction ^ 2))
if (!tileElement->AsPath()->IsSloped()
|| tileElement->AsPath()->GetSlopeDirection() != direction_reverse(direction))
{
return;
}
@ -1406,7 +1407,8 @@ static void loc_6A6D7E(
{
return;
}
uint16_t dx = ((direction - tileElement->GetDirection()) & TILE_ELEMENT_DIRECTION_MASK) ^ 2;
uint16_t dx = direction_reverse(
(direction - tileElement->GetDirection()) & TILE_ELEMENT_DIRECTION_MASK);
if (!(FlatRideTrackSequenceProperties[trackType][trackSequence] & (1 << dx)))
{
return;
@ -1421,7 +1423,7 @@ static void loc_6A6D7E(
case TILE_ELEMENT_TYPE_ENTRANCE:
if (z == tileElement->base_height)
{
if (entrance_has_direction(tileElement, (direction - tileElement->GetDirection()) ^ 2))
if (entrance_has_direction(tileElement, direction_reverse(direction - tileElement->GetDirection())))
{
if (query)
{
@ -1447,7 +1449,7 @@ static void loc_6A6D7E(
loc_6A6F1F:
if (query)
{
if (fence_in_the_way(x, y, tileElement->base_height, tileElement->clearance_height, direction ^ 2))
if (fence_in_the_way(x, y, tileElement->base_height, tileElement->clearance_height, direction_reverse(direction)))
{
return;
}
@ -1480,7 +1482,7 @@ static void loc_6A6D7E(
else
{
footpath_disconnect_queue_from_path(x, y, tileElement, 1 + ((flags >> 6) & 1));
tileElement->AsPath()->SetEdges(tileElement->AsPath()->GetEdges() | (1 << (direction ^ 2)));
tileElement->AsPath()->SetEdges(tileElement->AsPath()->GetEdges() | (1 << direction_reverse(direction)));
if (tileElement->AsPath()->IsQueue())
{
footpath_queue_chain_push(tileElement->AsPath()->GetRideIndex());
@ -1672,7 +1674,7 @@ void footpath_chain_ride_queue(
if (!tileElement->AsPath()->IsSloped())
break;
if ((tileElement->AsPath()->GetSlopeDirection() ^ 2) != direction)
if (direction_reverse(tileElement->AsPath()->GetSlopeDirection()) != direction)
break;
z -= 2;
@ -1690,7 +1692,7 @@ void footpath_chain_ride_queue(
int32_t numEdges = bitcount(edges);
if (numEdges >= 2)
{
int32_t requiredEdgeMask = 1 << (direction ^ 2);
int32_t requiredEdgeMask = 1 << direction_reverse(direction);
if (!(edges & requiredEdgeMask))
{
break;
@ -1698,7 +1700,7 @@ void footpath_chain_ride_queue(
}
tileElement->AsPath()->SetHasQueueBanner(false);
tileElement->AsPath()->SetEdges(tileElement->AsPath()->GetEdges() | (1 << (direction ^ 2)));
tileElement->AsPath()->SetEdges(tileElement->AsPath()->GetEdges() | (1 << direction_reverse(direction)));
tileElement->AsPath()->SetRideIndex(rideIndex);
tileElement->AsPath()->SetStationIndex(entranceIndex);
@ -1716,7 +1718,7 @@ void footpath_chain_ride_queue(
if (tileElement->AsPath()->GetEdges() & (1 << direction))
continue;
direction ^= 2;
direction = direction_reverse(direction);
if (tileElement->AsPath()->GetEdges() & (1 << direction))
continue;
}
@ -1871,7 +1873,7 @@ static int32_t footpath_is_connected_to_map_edge_recurse(
if (tileElement->AsPath()->IsSloped() && (slopeDirection = tileElement->AsPath()->GetSlopeDirection()) != direction)
{
if ((slopeDirection ^ 2) != direction)
if (direction_reverse(slopeDirection) != direction)
continue;
if (tileElement->base_height + 2 != z)
continue;
@ -1894,7 +1896,7 @@ static int32_t footpath_is_connected_to_map_edge_recurse(
footpath_fix_ownership(x, y);
}
edges = tileElement->AsPath()->GetEdges();
direction ^= 2;
direction = direction_reverse(direction);
if (!(flags & (1 << 7)))
{
if (tileElement[1].GetType() == TILE_ELEMENT_TYPE_BANNER)
@ -2427,7 +2429,7 @@ static void footpath_remove_edges_towards_here(
footpath_queue_chain_push(tileElement->AsPath()->GetRideIndex());
}
int32_t d = direction ^ 2;
int32_t d = direction_reverse(direction);
tileElement->AsPath()->SetEdges(tileElement->AsPath()->GetEdges() & ~(1 << d));
int32_t cd = ((d - 1) & 3);
tileElement->AsPath()->SetCorners(tileElement->AsPath()->GetCorners() & ~(1 << cd));
@ -2494,7 +2496,7 @@ static void footpath_remove_edges_towards(int32_t x, int32_t y, int32_t z0, int3
if (!tileElement->AsPath()->IsSloped())
break;
uint8_t slope = tileElement->AsPath()->GetSlopeDirection() ^ 2;
uint8_t slope = direction_reverse(tileElement->AsPath()->GetSlopeDirection());
if (slope != direction)
break;
@ -2523,7 +2525,7 @@ bool tile_element_wants_path_connection_towards(TileCoordsXYZD coords, const Til
if (!tileElement->AsPath()->IsSloped())
// The footpath is flat, it can be connected to from any direction
return true;
else if (tileElement->AsPath()->GetSlopeDirection() == (coords.direction ^ 2))
else if (tileElement->AsPath()->GetSlopeDirection() == direction_reverse(coords.direction))
// The footpath is sloped and its lowest point matches the edge connection
return true;
}

View File

@ -149,10 +149,30 @@ struct TileCoordsXYZ
int32_t x = 0, y = 0, z = 0;
};
/**
* Cardinal directions are represented by the Direction type. It has four
* possible values:
* 0 is X-decreasing
* 1 is Y-increasing
* 2 is X-increasing
* 3 is Y-decreasing
* Direction is not used to model up/down, or diagonal directions.
*/
typedef uint8_t Direction;
/**
* Given a direction, return the direction that points the other way,
* on the same axis.
*/
constexpr Direction direction_reverse(Direction dir)
{
return dir ^ 2;
}
struct CoordsXYZD
{
int32_t x, y, z;
uint8_t direction;
Direction direction;
bool isNull() const
{
@ -163,7 +183,7 @@ struct CoordsXYZD
struct TileCoordsXYZD
{
int32_t x, y, z;
uint8_t direction;
Direction direction;
bool isNull() const
{

View File

@ -626,7 +626,7 @@ bool map_coord_is_connected(int32_t x, int32_t y, int32_t z, uint8_t faceDirecti
if (z == tileElement->base_height + 2)
return true;
}
else if ((slopeDirection ^ 2) == faceDirection && z == tileElement->base_height)
else if (direction_reverse(slopeDirection) == faceDirection && z == tileElement->base_height)
{
return true;
}

View File

@ -996,7 +996,7 @@ rct_peep* Park::GenerateGuest()
const auto spawn = get_random_peep_spawn();
if (spawn != nullptr)
{
auto direction = spawn->direction ^ 2;
auto direction = direction_reverse(spawn->direction);
peep = peep_generate(spawn->x, spawn->y, spawn->z);
if (peep != nullptr)
{