Actions

SCHG How-to

Fix ARZ Boss Walking on Air Glitch

From Sonic Retro

Revision as of 10:03, 18 June 2012 by KingofHarts (talk | contribs) (Added another fix, on my iOS for the 1st time, please excuse the quality...)
(diff) ← Older revision | Latest revision (diff) | Newer revision → (diff)

The Bug

When fighting the ARZ boss with both Sonic & Tails, it's possible to activate the classic "walking on air" glitch. It's hard to trigger accidentally, but if you defeat the boss with one character, while the other character is standing on one of the two pillars at either side of the screen, that character will suffer from the glitch.

The Fix

Locate the label loc_30B4A. The code should look like this: <asm> loc_30B4A:         move.b  #1,(Screen_Shaking_Flag).w         addi.w  #1,y_pos(a0)         cmpi.w  #$510,y_pos(a0)         blt.s   BranchTo2_JmpTo37_DisplaySprite         move.b  #0,(Screen_Shaking_Flag).w         bra.w   JmpTo55_DeleteObject </asm> Now add to it so it looks just like this: <asm> loc_30B4A:         move.b  status(a0),d0         andi.b  #standing_mask|pushing_mask,d0  ; is someone touching the pillar?         beq.s   Pillar_Lower                    ; if not, branch         move.b  d0,d1         andi.b  #p1_standing|p1_pushing,d1      ; is it the main character?         beq.s   +                               ; if not, branch         andi.b  #$D7,(MainCharacter+status).w         ori.b   #2,(MainCharacter+status).w     ; prevent Sonic from walking in the air +         andi.b  #p2_standing|p2_pushing,d0      ; is it the sidekick?         beq.s   Pillar_Lower                    ; if not, branch         andi.b  #$D7,(Sidekick+status).w         ori.b   #2,(Sidekick+status).w          ; prevent Tails from walking in the air

Pillar_Lower:

        move.b  #1,(Screen_Shaking_Flag).w         addi.w  #1,y_pos(a0)         cmpi.w  #$510,y_pos(a0)         blt.s   BranchTo2_JmpTo37_DisplaySprite         move.b  #0,(Screen_Shaking_Flag).w         bra.w   JmpTo55_DeleteObject </asm> Everything up to the label Pillar_Lower is new and what it does is check if any character is interacting with the pillar and clears their interaction bits if necessary.

A Little More

Alternatively, if you want the pillars to stay solid even while the are being lowered into the ground, change the code to this: <asm> loc_30B4A:         move.w  #$23,d1         move.w  #$44,d2         move.w  #$45,d3         move.w  x_pos(a0),d4         move.w  y_pos(a0),-(sp)         addi.w  #4,y_pos(a0)         bsr.w   JmpTo26_SolidObject         move.w  (sp)+,y_pos(a0)

        move.b  #1,(Screen_Shaking_Flag).w         addi.w  #1,y_pos(a0)         cmpi.w  #$510,y_pos(a0)         blt.s   BranchTo2_JmpTo37_DisplaySprite

        move.b  status(a0),d0         andi.b  #standing_mask|pushing_mask,d0  ; is someone touching the pillar?         beq.s   Pillar_Lower                    ; if not, branch         move.b  d0,d1         andi.b  #p1_standing|p1_pushing,d1      ; is it the main character?         beq.s   +                               ; if not, branch         andi.b  #$D7,(MainCharacter+status).w         ori.b   #2,(MainCharacter+status).w     ; prevent Sonic from walking in the air +         andi.b  #p2_standing|p2_pushing,d0      ; is it the sidekick?         beq.s   Pillar_Lower                    ; if not, branch         andi.b  #$D7,(Sidekick+status).w         ori.b   #2,(Sidekick+status).w          ; prevent Tails from walking in the air

Pillar_Lower:         move.b  #0,(Screen_Shaking_Flag).w         bra.w   JmpTo55_DeleteObject </asm>

Explanation

For an object to have solidity, which for instance allows the player objects to stand on top of it, it has to call one of the SolidObject routines. These routines handle player positioning and flags in such a way so as to make the object appear solid. When a character stands on an object, its on-object status bit is set. When this bit is set, the character no longer follows the level's terrain, but instead walks in a straight line along the object's surface, ignoring gravity. Walking off the edge of an object will cause the SolidObject routine to clear the on-object flag and make the character subject to gravity again. Should an object stop calling SolidObject while a player is standing on it, that player's on-object bit won't be reset and this causes the walking on air glitch. In the case of the ARZ boss's pillars, SolidObject is called in every state except the "moving down" state which is triggered when the boss is defeated. This causes the pillars to eventually vanish without making sure the player's on-object bits are cleared.