Ledge Grab: Difference between revisions

(stole from pannen lul, surprised we dont have a page on this yet tbh)
 
(programmatically expand page a la Talk:Action and Eaten_By_Bubba)
 
(7 intermediate revisions by 3 users not shown)
Line 1: Line 1:
{{stub}}
{{stub}}
{{rewrite}}
{{needs_image}}
{{needs_image}}
A ledge grab works as follows: While Mario is falling with non-positive vertical speed, the game checks if there's a wall 30 units above him and that there's no wall 150 units above him. If this passes, then it considers a point 60 units towards the wall from Mario (i.e. 10 units into the wall) and 160 units above Mario. It then checks what the highest floor is from 78 units above that point to 100 units below that point. If a floor is found, then Mario grabs the ledge.


Given these conditions, a ledge grab normally raises Mario between 30 units (inclusive) and 150 units (exclusive). However, it's possible to exploit this logic to do a glitchy ledge grab and raise Mario more than 150 units (though 238 units is the max possible raise).
{{Action_infobox
|title= Ledge Grab
|image=
|official name=
|hex= 0x0800034B
|flags= stationary, pause exit
|group= Automatic
|id= 0x14B
|into= (common automatic cancel: [[Water Plunge]]), [[Soft Bonk]], [[Ledge Climb Fast]], [[Ledge Climb Slow 1]]
|out of= [[Water Jump]], (<code>common_air_action_step</code> + <code>AIR_STEP_CHECK_LEDGE_GRAB</code>: [[Jump]], [[Double Jump]], [[Freefall]], [[Hold Jump]], [[Hold Freefall]], [[Side Flip]], [[Wall Kick Air]], [[Long Jump]])
|animation= 0x33 (idle on ledge)
|related=
}}


Anyway, the condition that makes glitchy ledge grabs rarely possible in practice is that there can't be a wall 150 units above Mario. Fortunately, even minor deviations from perfect geometry can cause there to be no wall 150 units above Mario. For example:
A '''ledge grab''' can occur when Mario's position is in the air and his next [[Quarter Steps|quarter step]] would move him inside a wall<ref>https://github.com/n64decomp/sm64/blob/master/src/game/mario_step.c#L472</ref>. If this happens, the game will verify several conditions:
(1) If the wall is slightly slanted forward
 
(2) If there are 2 walls meant to be coplanar that aren't
*Mario's vertical velocity is non-positive
(3) If there are 2 parallel walls with the lower one jutting out more
*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|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 <code>common_air_action_step</code> (if the action passes the <code>AIR_STEP_CHECK_LEDGE_GRAB</code> flag)<ref>https://github.com/n64decomp/sm64/blob/9921382a68bb0c865e5e45eb594d9c64db59b1af/src/game/mario_actions_airborne.c#L431</ref>, 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:<ref>https://github.com/n64decomp/sm64/blob/9921382a68bb0c865e5e45eb594d9c64db59b1af/src/game/mario_actions_automatic.c#L543</ref>
 
#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), [[Ledge Grab#Let go of ledge|let go of ledge]] (see below)
#If Z is pressed or Mario is not on the floor, [[Ledge Grab#Let go of ledge|let go of ledge]]
#Let <code>hasSpaceForMario</code> = is Mario's ceiling height at least 160 units above the floor height?
#If A is pressed and <code>hasSpaceForMario</code>, [[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
##[[Ledge Grab#Let go of ledge|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, [[Ledge Grab#Let go of ledge|let go of ledge]]
##Else if <code>hasSpaceForMario</code>, [[Ledge Climb Slow 1]]
#If the floor at 30 units behind Mario is higher than 100 units below Mario's current floor and <code>hasSpaceForMario</code>, [[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==
<references />
 
{{actions}}

Latest revision as of 20:30, 12 January 2025


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.
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)

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:

  1. The wall is slightly slanted forward
  2. There are 2 walls meant to be coplanar that aren't
  3. 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:

  1. If Mario is more than 100 units below the water level, do stuff, Water Plunge (similar to Walking)
  2. Set quicksand depth to 0

Behavior

Upon a ledge grab:[3]

  1. Increment Mario's actionTimer unless it reached 10
  2. Note: Mario's position is presumably on the floor he's grabbed onto
  3. If Mario's floor is too steep (y normal < 0.9063078), let go of ledge (see below)
  4. If Z is pressed or Mario is not on the floor, let go of ledge
  5. Let hasSpaceForMario = is Mario's ceiling height at least 160 units above the floor height?
  6. If A is pressed and hasSpaceForMario, Ledge Climb Fast
  7. If Mario is stomped:
    1. 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
    2. Let go of ledge
  8. If the actionTimer is 10, the analog stick is pulled enough, and not(EU version while holding A)
    1. If the analog stick's intended direction is NOT within 4000 angle of Mario's facing angle, let go of ledge
    2. Else if hasSpaceForMario, Ledge Climb Slow 1
  9. If the floor at 30 units behind Mario is higher than 100 units below Mario's current floor and hasSpaceForMario, Ledge Climb Fast
  10. Set velocities to zero and set Mario's y position to the floor
  11. Set animation to MARIO_ANIM_IDLE_ON_LEDGE

Let go of ledge

  1. Set y velocity to 0
  2. Set forward velocity to -8
  3. Subtract 60sin(facing angle) from Mario's x position
  4. Subtract 60cos(facing angle) from Mario's z position
  5. If the floor below Mario is within 100 units vertically, snap Mario to the floor, else subtract 100 from Mario's y position
  6. Soft Bonk

References