Ledge Grab
![]() |
![]() |
Ledge Grab | |
Properties | |
Hex | 0x0800034B |
Action Flags | stationary, pause exit |
Action Group | Automatic |
ID | 0x14B |
Transitions | |
Into | (common automatic cancel: Water Plunge), Soft Bonk, Ledge Climb Fast, Ledge Climb Slow 1 |
Out of | Water Jump, (common_air_action_step + AIR_STEP_CHECK_LEDGE_GRAB : Jump, Double Jump, Freefall, Hold Jump, Hold Freefall, Side Flip, Wall Kick Air, Long Jump)
|
Other | |
Animation | 0x33 (idle on ledge) |
A ledge grab can occur when Mario's position is in the air and his next quarter step would move him inside a wall[1]. If this happens, the game will verify several conditions:
- Mario's vertical velocity is non-positive
- There is a wall 30 units above Mario.
- There is no wall 150 units above him.
If all conditions pass, the game searches for a potential ledge to grab. From Mario's position, it considers a point 60 units in the direction perpendicular to the wall and 160 units above. This point ends up being 10 units into the wall due to Mario's 50 unit radius. From that point, it searches top-down for the first floor hitbox. If a floor hitbox is found, Mario will ledge grab onto it.
Given these conditions, a ledge grab normally raises Mario between 30 units (inclusive) and 150 units (exclusive). Note that despite the search point starting 160 units higher than Mario's position, only a 150 unit raise is ordinarily possible because there would otherwise be a wall at the point 150 units above Mario.
It's possible to exploit the logic to do a glitchy ledge grab, allowing Mario to ledge grab a floor up to 238 units above. However, glitchy ledge grabs are rarely possible in practice due to the fact that ledge grabs are not possible where there is a wall 150 units above Mario. Fortunately, minor deviations from perfect geometry can cause there to be no wall 150 units above Mario.
Examples include:
- The wall is slightly slanted forward
- There are 2 walls meant to be coplanar that aren't
- If there are 2 parallel walls with the lower one jutting out more
Transition In
The above conditions are checked for during every common_air_action_step
(if the action passes the AIR_STEP_CHECK_LEDGE_GRAB
flag)[2], and the airborne action Water Jump. An air action will transition into a ledge grab upon a corresponding air step.
Then common automatic action steps are done:
- If Mario is more than 100 units below the water level, do stuff, Water Plunge (similar to Walking)
- Set quicksand depth to 0
Behavior
Upon a ledge grab:[3]
- Increment Mario's actionTimer unless it reached 10
- Note: Mario's position is presumably on the floor he's grabbed onto
- If Mario's floor is too steep (y normal < 0.9063078), let go of ledge (see below)
- If Z is pressed or Mario is not on the floor, let go of ledge
- Let
hasSpaceForMario
= is Mario's ceiling height at least 160 units above the floor height? - If A is pressed and
hasSpaceForMario
, Ledge Climb Fast - If Mario is stomped:
- If Mario's interaction status has the knockback damage flag, increment the hurt counter by 12 or 18 depending on whether Mario has his cap
- Let go of ledge
- If the actionTimer is 10, the analog stick is pulled enough, and not(EU version while holding A)
- If the analog stick's intended direction is NOT within 4000 angle of Mario's facing angle, let go of ledge
- Else if
hasSpaceForMario
, Ledge Climb Slow 1
- If the floor at 30 units behind Mario is higher than 100 units below Mario's current floor and
hasSpaceForMario
, Ledge Climb Fast - Set velocities to zero and set Mario's y position to the floor
- Set animation to MARIO_ANIM_IDLE_ON_LEDGE
Let go of ledge
- Set y velocity to 0
- Set forward velocity to -8
- Subtract 60sin(facing angle) from Mario's x position
- Subtract 60cos(facing angle) from Mario's z position
- If the floor below Mario is within 100 units vertically, snap Mario to the floor, else subtract 100 from Mario's y position
- Soft Bonk
References
- ↑ https://github.com/n64decomp/sm64/blob/master/src/game/mario_step.c#L472
- ↑ https://github.com/n64decomp/sm64/blob/9921382a68bb0c865e5e45eb594d9c64db59b1af/src/game/mario_actions_airborne.c#L431
- ↑ https://github.com/n64decomp/sm64/blob/9921382a68bb0c865e5e45eb594d9c64db59b1af/src/game/mario_actions_automatic.c#L543