So, as mentioned in
this bug report, I've noticed in general a lot of inconsistencies in regards to how climbers behave.
Essentially, these all come from two simple facts:
1. The climber checks for the top during the first 4 frames of his animation, and moves upwards on the rest.
2. Both of these have a terrain check, but they get triggered at different times.
In general - what happens is that, when a climber meets an overhang at the same height, how many frames it takes before he falls depends on whether that overhang is at the top of the climb or not. I've attached a level to illustrate this. The level has climbs with overhangs - in both "overhang is at top" and "overhang is in middle" varieties - at various heights from 7 pixels to 22 pixels.
A summary of the current behaviour, in mostly-human-readable language, and with stuff relating to the implementation of gimmicks stripped out, is:
(Keep in mind - the climber's X position is one pixel
inside the wall, similar to how when walking the lemming's Y position is one pixel inside the ground.)
If the Climber animation is on frame 0, 1, 2 or 3:
>> Check for no solid pixel at the climber's X position, and (7 pixels + current frame number) above the climber's Y position
>>>> If no solid pixel is found, check for solid pixels one pixel behind the climber, and (6 pixels + current frame number) above the climber's Y position; if this is not the first cycle through its animation, also check 5 pixels above*; just remember the result for now
>>>> Move the lemming to the top of the wall
>>>> If a solid pixel was found before, move the lemming down one pixel, turn around, change to a faller, and move forward one pixel (in new direction; ie: away from the wall)
>>>> Otherwise, change to a hoister
>> If there was a solid pixel there (remember - this is the wall itself, not an overhang), do nothing except continue the animation
* Skipping this check on the first cycle is to allow them to climb through an overhang at 6 pixels from the ground.
If the Climber animation is on frame 4, 5, 6, or 7:
>> Decrease the lemming's Y position by 1
>> Check for any of the following:
- Solid pixel 1 pixel behind the lemming and 7 above it
- Solid pixel 1 pixel behind the lemming and 6 above it, if this is frame 4 of the first cycle*
- A blocker or one-way-field trigger area in the opposite of the lemming's current direction, at the exact X and Y coordinates of the lemming
>>>> If any of those were the case, move downwards 1 pixel, turn around, change to a faller, and move forward one pixel (in new direction; ie: away from the wall)
* Performing this check is to prevent climbing through an overhang at exactly 7 pixels when it isn't the top of the climbAny change here has the potential to break a lot of replays; it isn't so likely to break too many levels (but we never know - those that rely on very accurate timing may be broken). But, unless we accept this inconsistency (which I am open to as an option, but feel it needs to be discussed), some change is needed - the question is what exactly that should be.
To those who want to look at the code itself - keep in mind it has some gimmick-related stuff in there too, as well as some dud stuff like conditionals that will always be false (which I've removed now in my copy), and does
not yet have the fix for the 7-pixel-not-at-top overhang in the current latest code (V1.42n's) - look at the "TLemmingGame.HandleClimbing" function,
beginning at (or near) line 7090 in LemGame.pas which I've copy-pasted an up-to-date version of in
this post.
EDIT: I added a second test map, with the situations described in
Nepster's post in this topic.
Both test maps require the respective VGASPEC (also attached), but this aside do not require any custom styles.