![]() |
Routines |
| Prev: EB8D | Up: Map | Next: ED35 |
|
Used by the routine at InitialiseGame.
Walks the player, tests the floor under their feet, unlocks matching doors, and starts a fall if they step off.
|
||||
| Handler_Player | EBD8 | LD IX,$F231 | Point IX at TablePlayerAttributes. | |
| EBDC | LD A,$10 | Set INK: CYAN (05). | ||
| EBDE | RST $10 | |||
| EBDF | LD A,$05 | |||
| EBE1 | RST $10 | |||
| EBE2 | XOR A | Clear *PlayerWalkReady for this frame. | ||
| EBE3 | LD ($F32F),A | |||
|
Skip the floor test while on a lift, on a ladder, or moving vertically.
|
||||
| EBE6 | LD A,($E820) | Jump to Handler_Player_OnFloor if *FlagLiftCollision shows a lift overlap. | ||
| EBE9 | CP $00 | |||
| EBEB | JR NZ,Handler_Player_OnFloor | |||
| EBED | LD A,(IX+$11) | Jump to Handler_Player_OnFloor if *PlayerActionState is on a ladder. | ||
| EBF0 | CP $03 | |||
| EBF2 | JR Z,Handler_Player_OnFloor | |||
| EBF4 | LD A,(IX+$05) | Jump to Handler_Player_OnFloor if *PlayerVerticalMovement is moving vertically. | ||
| EBF7 | CP $00 | |||
| EBF9 | JR NZ,Handler_Player_OnFloor | |||
| EBFB | LD A,(IX+$03) | Jump to Handler_Player_StartFall if *PlayerVerticalPosition is not 03 (not standing on a character row). | ||
| EBFE | CP $03 | |||
| EC00 | JP NZ,Handler_Player_StartFall | |||
|
Only test for a floor on the five walkable row bands.
|
||||
| EC03 | LD A,(IX+$01) | Jump to Handler_Player_TestWalkMasks if *PlayerVerticalCoordinate is 1A. | ||
| EC06 | CP $1A | |||
| EC08 | JR Z,Handler_Player_TestWalkMasks | |||
| EC0A | CP $15 | Jump to Handler_Player_TestWalkMasks if *PlayerVerticalCoordinate is 15. | ||
| EC0C | JR Z,Handler_Player_TestWalkMasks | |||
| EC0E | CP $10 | Jump to Handler_Player_TestWalkMasks if *PlayerVerticalCoordinate is 10. | ||
| EC10 | JR Z,Handler_Player_TestWalkMasks | |||
| EC12 | CP $0B | Jump to Handler_Player_TestWalkMasks if *PlayerVerticalCoordinate is 0B. | ||
| EC14 | JR Z,Handler_Player_TestWalkMasks | |||
| EC16 | CP $06 | Jump to Handler_Player_StartFall if *PlayerVerticalCoordinate is not 06. | ||
| EC18 | JR NZ,Handler_Player_StartFall | |||
|
AND the walk masks with the three screen bytes under the player's feet.
|
||||
| Handler_Player_TestWalkMasks | EC1A | LD C,(IX+$00) | C=*TablePlayerAttributes. | |
| EC1D | LD B,(IX+$01) | B=*PlayerVerticalCoordinate. | ||
| EC20 | DEC B | Move up three rows to the feet. | ||
| EC21 | DEC B | |||
| EC22 | DEC B | |||
| EC23 | CALL $0DD9 | Call CL_SET. | ||
| EC26 | LD HL,($5C84) | HL=*DF_CC. | ||
| EC29 | LD A,($F32C) | Fetch the left foot mask from *PlayerCollisionMasks. | ||
| EC2C | AND (HL) | AND it with the left foot pixels. | ||
| EC2D | JR NZ,Handler_Player_OnFloor | Jump to Handler_Player_OnFloor if those pixels are solid. | ||
| EC2F | INC HL | Advance to the middle foot column. | ||
| EC30 | LD A,($F32D) | Fetch the middle foot mask from *PlayerCollisionMask_Middle. | ||
| EC33 | AND (HL) | AND it with the middle foot pixels. | ||
| EC34 | JR NZ,Handler_Player_OnFloor | Jump to Handler_Player_OnFloor if those pixels are solid. | ||
| EC36 | INC HL | Advance to the right foot column. | ||
| EC37 | LD A,($F32E) | Fetch the right foot mask from *PlayerCollisionMask_Right. | ||
| EC3A | AND (HL) | AND it with the right foot pixels. | ||
| EC3B | JR NZ,Handler_Player_OnFloor | Jump to Handler_Player_OnFloor if those pixels are solid. | ||
|
Nothing solid underfoot, so start counting a fall.
|
||||
| Handler_Player_StartFall | EC3D | DEC (IX+$05) | Decrease *PlayerVerticalMovement by one. | |
| EC40 | LD A,($F33A) | Increment *PlayerStepCounter while there is no floor. | ||
| EC43 | INC A | |||
| EC44 | LD ($F33A),A | |||
| EC47 | JR Handler_Player_ApplyDeltas | Jump to Handler_Player_ApplyDeltas. | ||
|
Floor (or lift/ ladder) is present.
|
||||
| Handler_Player_OnFloor | EC49 | LD A,($F33F) | Fetch *PlayerFallenFlag to see if the player has already fallen. | |
| EC4C | LD ($FFFC),A | Copy it to *SoundFlag_PlayerCollision. | ||
| EC4F | CP $00 | Jump to LoseLife if the player has already fallen. | ||
| EC51 | JP NZ,LoseLife | |||
| EC54 | LD A,$00 | Reset *PlayerStepCounter; the player is on solid ground. | ||
| EC56 | LD ($F33A),A | |||
| Handler_Player_ApplyDeltas | EC59 | CALL ApplyMovementDeltas | Apply the player's movement deltas. | |
| EC5C | LD A,C | Jump to Handler_Player_ClearMovement if the player walked off the right. | ||
| EC5D | CP $22 | |||
| EC5F | JP Z,Handler_Player_ClearMovement | |||
| EC62 | CP $03 | Jump to Handler_Player_ClearMovement if the player walked off the left. | ||
| EC64 | JP Z,Handler_Player_ClearMovement | |||
| EC67 | LD A,B | Jump to Handler_Player_ClearMovement if the player walked off the top. | ||
| EC68 | CP $18 | |||
| EC6A | JP Z,Handler_Player_ClearMovement | |||
| EC6D | CP $04 | Jump to LoseLife if the player walked off the bottom. | ||
| EC6F | JP Z,LoseLife | |||
| EC72 | LD A,C | Jump to Handler_Player_MarkReprint if *TablePlayerAttributes changed. | ||
| EC73 | CP (IX+$00) | |||
| EC76 | JR NZ,Handler_Player_MarkReprint | |||
| EC78 | LD A,B | Jump to Handler_Player_MarkReprint if *PlayerVerticalCoordinate changed. | ||
| EC79 | CP (IX+$01) | |||
| EC7C | JR NZ,Handler_Player_MarkReprint | |||
| EC7E | LD A,(IX+$03) | Jump to Handler_Player_StorePosition if *PlayerVerticalPosition did not change. | ||
| EC81 | CP D | |||
| EC82 | JR Z,Handler_Player_StorePosition | |||
| Handler_Player_MarkReprint | EC84 | LD A,$01 | Set *PlayerWalkReady so this walk step will reprint. | |
| EC86 | LD ($F32F),A | |||
| EC89 | PUSH DE | Stash the new position and offsets on the stack. | ||
| EC8A | PUSH BC | |||
| EC8B | LD A,(IX+$11) | Jump to Handler_Player_SeekDoorLeft if the player is not facing right. | ||
| EC8E | CP $13 | |||
| EC90 | JR NZ,Handler_Player_SeekDoorLeft | |||
| EC92 | DEC C | Adjust the test column when facing right. | ||
| EC93 | DEC C | |||
| Handler_Player_SeekDoorLeft | EC94 | CALL FindKeyAtPosition | Look for a key or locked door at this position. | |
| EC97 | POP BC | Restore the new position and offsets from the stack. | ||
| EC98 | POP DE | |||
| EC99 | CP $FF | Jump to Handler_Player_StorePosition if there is no door here. | ||
| EC9B | JR Z,Handler_Player_StorePosition | |||
| EC9D | CP (IX+$10) | Jump to Handler_Player_ClearMovement if the player is not holding this door's key. | ||
| ECA0 | JR NZ,Handler_Player_ClearMovement | |||
| ECA2 | CALL Handler_UnlockDoor | Unlock the door. | ||
| Handler_Player_StorePosition | ECA5 | LD (IX+$00),C | Write the new horizontal co-ordinate to *TablePlayerAttributes. | |
| ECA8 | LD (IX+$01),B | Write the new vertical co-ordinate to *PlayerVerticalCoordinate. | ||
| ECAB | LD (IX+$02),E | Write the new horizontal offset to *PlayerHorizontalPosition. | ||
| ECAE | LD (IX+$03),D | Write the new vertical offset to *PlayerVerticalPosition. | ||
| ECB1 | PUSH DE | Stash the offsets on the stack. | ||
| ECB2 | CALL EraseSpriteTrail | Erase the player's previous sprite. | ||
| ECB5 | POP DE | Restore the offsets from the stack. | ||
| ECB6 | LD (IX+$02),E | Write the horizontal offset back to *PlayerHorizontalPosition. | ||
| ECB9 | LD (IX+$03),D | Write the vertical offset back to *PlayerVerticalPosition. | ||
| ECBC | LD A,($F33A) | Call Action_Falling if *PlayerStepCounter shows the player has been stepping into air. | ||
| ECBF | CP $08 | |||
| ECC1 | CALL NC,Action_Falling | |||
|
Reprint the player and refresh the walk masks.
|
||||
| ECC4 | LD HL,$8978 | Write 8978 to *CHARS. | ||
| ECC7 | LD ($5C36),HL | |||
| ECCA | CALL PrintShiftedSprite | Print the player. | ||
| ECCD | LD A,($A10B) | Copy the left walk mask from WalkMaskSources. | ||
| ECD0 | LD ($F32C),A | |||
| ECD3 | LD A,($A12B) | Copy the middle walk mask from WalkMaskSources_Middle. | ||
| ECD6 | LD ($F32D),A | |||
| ECD9 | LD A,($A14B) | Copy the right walk mask from WalkMaskSources_Right. | ||
| ECDC | LD ($F32E),A | |||
| ECDF | LD A,(IX+$00) | Copy the horizontal co-ordinate to the previous-horizontal slot. | ||
| ECE2 | LD (IX+$0D),A | |||
| ECE5 | LD A,(IX+$01) | Copy the vertical co-ordinate to the previous-vertical slot. | ||
| ECE8 | LD (IX+$0E),A | |||
| ECEB | LD A,(IX+$03) | Copy the vertical offset to the previous-vertical-offset slot. | ||
| ECEE | LD (IX+$0F),A | |||
| ECF1 | LD A,(IX+$02) | Copy the horizontal offset to the previous-offset slot. | ||
| ECF4 | LD (IX+$0B),A | |||
| ECF7 | LD A,($F32F) | Jump to Handler_Player_ClearMovement if *PlayerWalkReady does not need a door check. | ||
| ECFA | CP $00 | |||
| ECFC | JR Z,Handler_Player_ClearMovement | |||
| ECFE | LD C,(IX+$00) | C=the player's horizontal co-ordinate. | ||
| ED01 | LD B,(IX+$01) | B=the player's vertical co-ordinate. | ||
| ED04 | LD A,(IX+$11) | Jump to Handler_Player_HandleDoor if the player is not facing right. | ||
| ED07 | CP $13 | |||
| ED09 | JR NZ,Handler_Player_HandleDoor | |||
| ED0B | DEC C | Adjust the test column when facing right. | ||
| ED0C | DEC C | |||
| Handler_Player_HandleDoor | ED0D | CALL Handler_KeysAndLockedDoors | Handle any key or locked door at the player's feet. | |
|
Clear this frame's movement.
|
||||
| Handler_Player_ClearMovement | ED10 | LD (IX+$04),$00 | Clear horizontal movement. | |
| ED14 | LD (IX+$05),$00 | Clear vertical movement. | ||
| ED18 | RET | Return. | ||
|
Player is falling; switch to the falling animation.
|
||||
| Action_Falling | ED19 | LD A,$01 | Set *PlayerFallenFlag; the player is falling. | |
| ED1B | LD ($F33F),A | |||
| ED1E | LD (IX+$11),$02 | Set the action state to blocked / no walk. | ||
| ED22 | LD A,(IX+$06) | Jump to SetFallingSprite if the sprite is not already a falling frame. | ||
| ED25 | CP $9E | |||
| ED27 | JR C,SetFallingSprite | |||
| ED29 | ADD A,$06 | Advance to the next falling frame. | ||
| ED2B | CP $B0 | Jump to SetPlayerSprite if the falling animation has not wrapped. | ||
| ED2D | JR NZ,SetPlayerSprite | |||
| SetFallingSprite | ED2F | LD A,$9E | Set A to 9E, the first frame of the "falling" animation. | |
| SetPlayerSprite | ED31 | LD (IX+$06),A | Write the frame to the player sprite ID. | |
| ED34 | RET | Return. | ||
| Prev: EB8D | Up: Map | Next: ED35 |