diff --git a/src/event_object_movement.c b/src/event_object_movement.c index 5ce8a8e986..9e02edfef4 100644 --- a/src/event_object_movement.c +++ b/src/event_object_movement.c @@ -4873,6 +4873,28 @@ static u8 GetCollisionInDirection(struct ObjectEvent *objectEvent, u8 direction) u8 GetCollisionAtCoords(struct ObjectEvent *objectEvent, s16 x, s16 y, u32 dir) { u8 direction = dir; + u8 currentBehavior = MapGridGetMetatileBehaviorAt(objectEvent->currentCoords.x, objectEvent->currentCoords.y); + u8 nextBehavior = MapGridGetMetatileBehaviorAt(x, y); + + //sideways stairs checks + if (MetatileBehavior_IsSidewaysStairsLeftSideTop(nextBehavior) && dir == DIR_EAST) + return COLLISION_IMPASSABLE; //moving onto left-side top edge east from regular ground -> nope + else if (MetatileBehavior_IsSidewaysStairsRightSideTop(nextBehavior) && dir == DIR_WEST) + return COLLISION_IMPASSABLE; //moving onto left-side top edge east from regular ground -> nope + else if (MetatileBehavior_IsSidewaysStairsRightSideBottom(nextBehavior) && (dir == DIR_EAST || dir == DIR_SOUTH)) + return COLLISION_IMPASSABLE; //moving into right-side bottom edge from regular ground -> nah + else if (MetatileBehavior_IsSidewaysStairsLeftSideBottom(nextBehavior) && (dir == DIR_WEST || dir == DIR_SOUTH)) + return COLLISION_IMPASSABLE; //moving onto left-side bottom edge from regular ground -> nah + else if ((MetatileBehavior_IsSidewaysStairsLeftSideTop(currentBehavior) || MetatileBehavior_IsSidewaysStairsRightSideTop(currentBehavior)) + && dir == DIR_NORTH) + return COLLISION_IMPASSABLE; //trying to move north off of top-most tile onto same level doesn't work + else if (!(MetatileBehavior_IsSidewaysStairsLeftSideTop(currentBehavior) || MetatileBehavior_IsSidewaysStairsRightSideTop(currentBehavior)) + && dir == DIR_SOUTH && (MetatileBehavior_IsSidewaysStairsLeftSideTop(nextBehavior) || MetatileBehavior_IsSidewaysStairsRightSideTop(nextBehavior))) + return COLLISION_IMPASSABLE; //trying to move south onto top stair tile at same level from non-stair -> no + else if (!(MetatileBehavior_IsSidewaysStairsLeftSideBottom(currentBehavior) || MetatileBehavior_IsSidewaysStairsRightSideBottom(currentBehavior)) + && dir == DIR_NORTH && (MetatileBehavior_IsSidewaysStairsLeftSideBottom(nextBehavior) || MetatileBehavior_IsSidewaysStairsRightSideBottom(nextBehavior))) + return COLLISION_IMPASSABLE; //trying to move north onto top stair tile at same level from non-stair -> no + if (IsCoordOutsideObjectEventMovementRange(objectEvent, x, y)) return COLLISION_OUTSIDE_RANGE; else if (MapGridIsImpassableAt(x, y) || GetMapBorderIdAt(x, y) == -1 || IsMetatileDirectionallyImpassable(objectEvent, x, y, direction)) diff --git a/src/field_player_avatar.c b/src/field_player_avatar.c index e156774d42..dd52e3a612 100644 --- a/src/field_player_avatar.c +++ b/src/field_player_avatar.c @@ -745,49 +745,40 @@ u8 CheckForObjectEventCollision(struct ObjectEvent *objectEvent, s16 x, s16 y, u } //sideways stairs logic - if (MetatileBehavior_IsSidewaysStairsLeftSideTop(metatileBehavior) && direction == DIR_EAST) - return COLLISION_IMPASSABLE; //moving onto left-side top edge east from ground -> cannot move - else if (MetatileBehavior_IsSidewaysStairsRightSideTop(metatileBehavior) && direction == DIR_WEST) - return COLLISION_IMPASSABLE; //moving onto left-side top edge east from ground -> cannot move - else if (MetatileBehavior_IsSidewaysStairsRightSideBottom(metatileBehavior) && (direction == DIR_EAST || direction == DIR_SOUTH)) - return COLLISION_IMPASSABLE; - else if (MetatileBehavior_IsSidewaysStairsLeftSideBottom(metatileBehavior) && (direction == DIR_WEST || direction == DIR_SOUTH)) - return COLLISION_IMPASSABLE; - else if ((MetatileBehavior_IsSidewaysStairsLeftSideTop(currentBehavior) || MetatileBehavior_IsSidewaysStairsRightSideTop(currentBehavior)) - && direction == DIR_NORTH && collision == COLLISION_NONE) - return COLLISION_IMPASSABLE; //trying to move north off of top-most tile onto same level doesn't work - - if (MetatileBehavior_IsSidewaysStairsLeftSide(metatileBehavior)) + if (direction == DIR_WEST || direction == DIR_EAST) { - //moving ONTO left side stair - if (direction == DIR_WEST && currentBehavior != metatileBehavior) - return collision; //moving onto top part of left-stair going left, so no diagonal - else - return COLLISION_SIDEWAYS_STAIRS_TO_LEFT; // move diagonally - } - else if (MetatileBehavior_IsSidewaysStairsRightSide(metatileBehavior)) - { - //moving ONTO right side stair - if (direction == DIR_EAST && currentBehavior != metatileBehavior) - return collision; //moving onto top part of right-stair going right, so no diagonal - else - return COLLISION_SIDEWAYS_STAIRS_TO_RIGHT; - } - else if (MetatileBehavior_IsSidewaysStairsLeftSideAny(currentBehavior)) - { - //moving OFF of any left side stair - if (direction == DIR_WEST && metatileBehavior != currentBehavior) - return COLLISION_SIDEWAYS_STAIRS_TO_LEFT; //moving off of left stairs onto non-stair -> move diagonal - else - return collision; //moving off of left side stair to east -> move east - } - else if (MetatileBehavior_IsSidewaysStairsRightSideAny(currentBehavior)) - { - //moving OFF of any right side stair - if (direction == DIR_EAST && metatileBehavior != currentBehavior) - return COLLISION_SIDEWAYS_STAIRS_TO_RIGHT; //moving off right stair onto non-stair -> move diagonal - else - return collision; + if (MetatileBehavior_IsSidewaysStairsLeftSide(metatileBehavior)) + { + //moving ONTO left side stair + if (direction == DIR_WEST && currentBehavior != metatileBehavior) + return collision; //moving onto top part of left-stair going left, so no diagonal + else + return COLLISION_SIDEWAYS_STAIRS_TO_LEFT; // move diagonally + } + else if (MetatileBehavior_IsSidewaysStairsRightSide(metatileBehavior)) + { + //moving ONTO right side stair + if (direction == DIR_EAST && currentBehavior != metatileBehavior) + return collision; //moving onto top part of right-stair going right, so no diagonal + else + return COLLISION_SIDEWAYS_STAIRS_TO_RIGHT; + } + else if (MetatileBehavior_IsSidewaysStairsLeftSideAny(currentBehavior)) + { + //moving OFF of any left side stair + if (direction == DIR_WEST && metatileBehavior != currentBehavior) + return COLLISION_SIDEWAYS_STAIRS_TO_LEFT; //moving off of left stairs onto non-stair -> move diagonal + else + return collision; //moving off of left side stair to east -> move east + } + else if (MetatileBehavior_IsSidewaysStairsRightSideAny(currentBehavior)) + { + //moving OFF of any right side stair + if (direction == DIR_EAST && metatileBehavior != currentBehavior) + return COLLISION_SIDEWAYS_STAIRS_TO_RIGHT; //moving off right stair onto non-stair -> move diagonal + else + return collision; + } } return collision;