Prev: AFDA Up: Map Next: B2CA
B079: Handle Flying Creature
Handler for the object types 30 to 33 (eagles) and 40 to 43 (vultures). The creature flies towards Sabreman, bounces off the decorations and the bubbles, bounces off the frame of the room and flies out of the room through its gaps.
If the creature is in a different room from Sabreman it is moved by Move_Creature_Horizontally (when the room x is different) or by Move_Creature_Vertically (when the room y is different).
In Sabreman's room, an eagle that is above him and touches him picks him up (the type changes to 5C and Handle_Carrying_Eagle takes over). Bit 0 of the type is the frame of the animation and changes every two ticks, and bit 1 follows the direction of the x velocity.
The x velocity and the y velocity (bytes 08 and 09 of the record) each change by two on every call, in the direction of Sabreman, up to a limit of 40. A thrown weapon destroys the creature (see Destroy_Flying_Creature). If the creature touches Sabreman he is pushed away with an x velocity of 03 and tumbles.
The contact flags (byte 0B of the record) use the same bits as the flags of the room (see Draw_Room), and they are combined with those flags in E.
Input
IX Object record
Handle_Flying_Creature B079 CALL Read_World_Map Read the world map entry of the room that the creature is in. The flags of the room are returned in E.
B07C LD A,(IX+$0B) Fetch the contact flags of the creature.
B07F OR E Combine them with the flags of the room.
B080 LD E,A Store the result in E.
B081 LD A,($8F1C) Fetch the room x of Sabreman.
B084 CP (IX+$02) Jump to Move_Creature_Horizontally if the creature is in a different room x.
B087 JP NZ,Move_Creature_Horizontally
B08A LD A,($8F1E) Fetch the room y of Sabreman.
B08D CP (IX+$04) Jump to Move_Creature_Vertically if the creature is in a different room y.
B090 JP NZ,Move_Creature_Vertically
B093 CALL StoreEntity Save the state of the creature.
Only an eagle that has been drawn and is inside the room can pick up Sabreman, and only if he is not hanging on the rope.
B096 LD A,(IX+$00) Fetch the type of the creature.
B099 AND %11111100 Ignore the low two bits.
B09B CP $30 Jump to Handle_Flying_Creature_Animate if the creature is not an eagle.
B09D JR NZ,Handle_Flying_Creature_Animate
B09F BIT 0,(IX+$0F) Jump to Handle_Flying_Creature_Animate if the creature has just been created.
B0A3 JR NZ,Handle_Flying_Creature_Animate
B0A5 LD A,(IX+$01) Fetch the x position of the creature.
B0A8 CP $D0 Jump to Handle_Flying_Creature_Animate if the x position is D0 or more.
B0AA JR NC,Handle_Flying_Creature_Animate
B0AC CP $18 Jump to Handle_Flying_Creature_Animate if the x position is less than 18.
B0AE JR C,Handle_Flying_Creature_Animate
B0B0 LD A,(IX+$03) Fetch the y position of the creature.
B0B3 CP $A8 Jump to Handle_Flying_Creature_Animate if the y position is A8 or more.
B0B5 JR NC,Handle_Flying_Creature_Animate
B0B7 CP $41 Jump to Handle_Flying_Creature_Animate if the y position is less than 41.
B0B9 JR C,Handle_Flying_Creature_Animate
B0BB LD A,($8F1A) Fetch the type of Sabreman.
B0BE CP $09 Jump to Handle_Flying_Creature_Animate if Sabreman is hanging on the rope (the type is less than 09).
B0C0 JR C,Handle_Flying_Creature_Animate
B0C2 CALL Check_Sabreman_Contact Check for contact with Sabreman. Bit 2 of C is set if the creature touches him and bit 1 is set if he is above the creature.
B0C5 LD A,C Copy the result to A.
B0C6 AND %00000110 Keep only bits 1 and 2.
B0C8 CP $04 Jump to Handle_Flying_Creature_Animate unless the creature touches Sabreman and he is not above it.
B0CA JR NZ,Handle_Flying_Creature_Animate
B0CC DI Disable interrupts while the frame counter is changed.
B0CD LD (IX+$00),$5C Change the type of the creature to 5C which makes it carry Sabreman (see Handle_Carrying_Eagle).
B0D1 LD A,$40 Write 40 to the redraw flags of Sabreman (Sabreman_Redraw_Flags), which marks him as being carried (bit 6).
B0D3 LD ($8F29),A
B0D6 LD A,($5C78) Fetch the low byte of the frame counter.
B0D9 OR %01000000 Set bit 6.
B0DB LD ($5C78),A Store it. The carry ends when this byte next wraps round to zero (see Handle_Carrying_Eagle).
B0DE LD ($8EF2),A Store it in Previous_Type_5C_Active_Flag as well, as a non-zero value.
B0E1 JP Handle_Carrying_Eagle_Carry Jump to Handle_Carrying_Eagle_Carry to carry on as an eagle that carries Sabreman.
Work out the type of the creature. Bit 0 follows bit 1 of the tick counter and bit 1 is set when the x velocity is negative.
Handle_Flying_Creature_Animate B0E4 LD A,($8ED6) Fetch the tick counter.
B0E7 RRA Move bit 1 into bit 0.
B0E8 AND %00000001 Keep only that bit.
B0EA LD C,A Keep the frame bit in C.
B0EB LD A,(IX+$00) Fetch the type of the creature.
B0EE AND %11111110 Clear bit 0.
B0F0 ADD A,C Add the frame bit.
B0F1 BIT 7,(IX+$08) Jump to Handle_Flying_Creature_Clear_Direction if the x velocity is positive.
B0F5 JR Z,Handle_Flying_Creature_Clear_Direction
B0F7 OR %00000010 Set bit 1.
B0F9 JR Handle_Flying_Creature_Store_Type Jump to Handle_Flying_Creature_Store_Type.
Handle_Flying_Creature_Clear_Direction B0FB AND %11111101 Clear bit 1.
Handle_Flying_Creature_Store_Type B0FD LD (IX+$00),A Store the type of the creature.
Change the x velocity by two in the direction of Sabreman, up to a limit of 40 in either direction.
B100 LD A,($8F1B) Fetch the x position of Sabreman.
B103 SUB (IX+$01) Subtract the x position of the creature.
B106 LD A,(IX+$08) Fetch the x velocity of the creature.
B109 JP C,Handle_Flying_Creature_Steer_Left Jump to Handle_Flying_Creature_Steer_Left if Sabreman is on the left of the creature.
B10C ADD A,$02 Add two to the x velocity.
B10E BIT 7,A Jump to Handle_Flying_Creature_Store_X_Velocity if the x velocity is negative.
B110 JR NZ,Handle_Flying_Creature_Store_X_Velocity
B112 CP $40 Jump to Handle_Flying_Creature_Steer_Vertically if the x velocity has reached 40.
B114 JR NC,Handle_Flying_Creature_Steer_Vertically
Handle_Flying_Creature_Store_X_Velocity B116 LD (IX+$08),A Store the x velocity.
Do the same with the y velocity.
Handle_Flying_Creature_Steer_Vertically B119 LD A,($8F1D) Fetch the y position of Sabreman.
B11C SUB (IX+$03) Subtract the y position of the creature.
B11F LD A,(IX+$09) Fetch the y velocity of the creature.
B122 JP C,Handle_Flying_Creature_Steer_Up Jump to Handle_Flying_Creature_Steer_Up if Sabreman is above the creature.
B125 ADD A,$02 Add two to the y velocity.
B127 BIT 7,A Jump to Handle_Flying_Creature_Store_Y_Velocity if the y velocity is negative.
B129 JR NZ,Handle_Flying_Creature_Store_Y_Velocity
B12B CP $40 Jump to Handle_Flying_Creature_Check_Contact if the y velocity has reached 40.
B12D JR NC,Handle_Flying_Creature_Check_Contact
Handle_Flying_Creature_Store_Y_Velocity B12F LD (IX+$09),A Store the y velocity.
This entry point is used by the routine at Handle_Jellyfish.
Check for contact with a thrown weapon and with Sabreman. This is also the entry point for the jellyfish.
Handle_Flying_Creature_Check_Contact B132 PUSH DE Stash the flags of the room on the stack.
B133 BIT 0,(IX+$0F) Jump to Handle_Flying_Creature_Check_Obstacles if the creature has just been created.
B137 JR NZ,Handle_Flying_Creature_Check_Obstacles
B139 CALL Check_Weapon_Hit Check whether a thrown weapon has hit the creature. D is FF if one has.
B13C LD A,D Copy the result to A.
B13D AND A Jump to Destroy_Flying_Creature if a weapon has hit the creature.
B13E JP NZ,Destroy_Flying_Creature
B141 CALL Check_Sabreman_Contact Check for contact with Sabreman.
B144 BIT 2,C Jump to Handle_Flying_Creature_Check_Obstacles if the creature is not touching him.
B146 JR Z,Handle_Flying_Creature_Check_Obstacles
B148 XOR A Clear A, which collects the new redraw flags of Sabreman.
B149 BIT 7,C Test bit 7 of C, which is set when the creature is on the right of Sabreman.
B14B LD B,$03 Use an x velocity of 03 to push Sabreman to the right.
B14D JR Z,Handle_Flying_Creature_Push_Sabreman Jump to Handle_Flying_Creature_Push_Sabreman if the creature is on the left of Sabreman.
B14F LD B,$FD Use an x velocity of FD to push Sabreman to the left.
B151 LD A,$10 Set bit 4 of A.
Handle_Flying_Creature_Push_Sabreman B153 OR %00001000 Set bit 3 of A.
B155 LD C,A Copy the new redraw flags to C.
B156 LD A,($8F29) Fetch the redraw flags of Sabreman.
B159 OR C Combine them with the new bits. Bit 3 makes him tumble (see Tumble_Sabreman).
B15A LD ($8F29),A Store the redraw flags of Sabreman.
B15D LD A,B Copy the x velocity to A.
B15E LD ($8F20),A Store it as the x velocity of Sabreman (Sabreman_X_Velocity).
Check for contact with the decorations and the bubbles, and bounce off them.
Handle_Flying_Creature_Check_Obstacles B161 CALL Check_Decoration_Contact Check for contact with the decorations. C holds the result.
B164 LD D,C Store the result in D.
B165 CALL Check_Bubble_Contact Check for contact with the bubbles.
B168 LD A,C Copy the result to A.
B169 OR D Combine it with the result for the decorations.
B16A LD C,A Store the combined result in C.
B16B POP DE Restore DE from the stack.
B16C BIT 2,C Jump to Handle_Flying_Creature_Move_Sideways if the creature is not touching anything.
B16E JR Z,Handle_Flying_Creature_Move_Sideways
B170 BIT 1,C Jump to Handle_Flying_Creature_Test_Underside if the creature is not on top of the object.
B172 JR Z,Handle_Flying_Creature_Test_Underside
B174 BIT 5,C Jump to Handle_Flying_Creature_Bounce_Sideways if the object is a bubble and the creature is away from the middle of it.
B176 JR NZ,Handle_Flying_Creature_Bounce_Sideways
B178 LD A,(IX+$09) Fetch the y velocity.
B17B DEC A Subtract two.
B17C DEC A
B17D JP M,Handle_Flying_Creature_Move_Sideways Jump to Handle_Flying_Creature_Move_Sideways if the result is negative, as the creature is already moving up.
B180 CPL Invert the y velocity, to send the creature up.
B181 LD (IX+$09),A Store the y velocity.
B184 LD A,(IX+$03) Fetch the y position.
B187 SUB $02 Subtract two.
B189 LD (IX+$03),A Store the y position.
B18C JR Handle_Flying_Creature_Move_Sideways Jump to Handle_Flying_Creature_Move_Sideways.
Handle_Flying_Creature_Test_Underside B18E BIT 0,C Jump to Handle_Flying_Creature_Bounce_Sideways if the creature is away from the middle of the object.
B190 JR NZ,Handle_Flying_Creature_Bounce_Sideways
B192 LD A,(IX+$09) Fetch the y velocity.
B195 INC A Add two.
B196 INC A
B197 JP P,Handle_Flying_Creature_Bounce_Sideways Jump to Handle_Flying_Creature_Bounce_Sideways if the result is positive, as the creature is already moving down.
B19A CPL Invert the y velocity, to send the creature down.
B19B LD (IX+$09),A Store the y velocity.
Handle_Flying_Creature_Bounce_Sideways B19E LD A,(IX+$08) Fetch the x velocity.
B1A1 BIT 7,C Jump to Handle_Flying_Creature_Bounce_Left if the creature is on the left of the object.
B1A3 JR Z,Handle_Flying_Creature_Bounce_Left
B1A5 INC A Add two.
B1A6 INC A
B1A7 JP P,Handle_Flying_Creature_Move_Sideways Jump to Handle_Flying_Creature_Move_Sideways if the result is positive, as the creature is already moving right.
B1AA CPL Invert the x velocity, to send the creature right.
B1AB LD (IX+$08),A Store the x velocity.
B1AE JR Handle_Flying_Creature_Move_Sideways Jump to Handle_Flying_Creature_Move_Sideways.
Handle_Flying_Creature_Bounce_Left B1B0 DEC A Subtract two.
B1B1 DEC A
B1B2 JP M,Handle_Flying_Creature_Move_Sideways Jump to Handle_Flying_Creature_Move_Sideways if the result is negative, as the creature is already moving left.
B1B5 CPL Invert the x velocity, to send the creature left.
B1B6 LD (IX+$08),A Store the x velocity.
Move the creature sideways. Reset bits 0 and 4 of the contact flags first.
Handle_Flying_Creature_Move_Sideways B1B9 LD A,(IX+$0B) Fetch the contact flags.
B1BC AND %11101110 Reset bits 0 and 4.
B1BE LD (IX+$0B),A Store the contact flags.
B1C1 LD L,(IX+$08) Fetch the x velocity into L.
B1C4 BIT 7,L Test the sign of the x velocity.
B1C6 LD H,$00 Clear the high byte of the x velocity (as a word).
B1C8 JR Z,Handle_Flying_Creature_Add_X_Velocity Jump to Handle_Flying_Creature_Add_X_Velocity if the x velocity is positive.
B1CA LD H,$FF Set the high byte of the x velocity to FF to extend the sign.
Handle_Flying_Creature_Add_X_Velocity B1CC CALL Move_Object_Horizontally Add the x velocity to the x position (see Move_Object_Horizontally). A is the new x position, and the zero flag is set when it is less than 80.
B1CF JP Z,Handle_Flying_Creature_Test_Left_Edge Jump to Handle_Flying_Creature_Test_Left_Edge if the x position is less than 80.
B1D2 CP $D0 Jump to Handle_Flying_Creature_Store_X if the x position is less than D0.
B1D4 JR C,Handle_Flying_Creature_Store_X
B1D6 BIT 2,E Jump to Handle_Flying_Creature_Test_Right_Gap if the room has no right wall.
B1D8 JP Z,Handle_Flying_Creature_Test_Right_Gap
B1DB LD A,(IX+$08) Fetch the x velocity.
B1DE CPL Invert it, to bounce off the right wall.
B1DF LD (IX+$08),A Store the x velocity.
B1E2 LD A,$CF Set the x position to CF.
Handle_Flying_Creature_Store_X B1E4 LD (IX+$01),A Store the x position.
Move the creature up or down. Reset bits 2 and 6 of the contact flags first.
B1E7 LD A,(IX+$0B) Fetch the contact flags.
B1EA AND %10111011 Reset bits 2 and 6.
B1EC LD (IX+$0B),A Store the contact flags.
B1EF LD L,(IX+$09) Fetch the y velocity into L.
B1F2 BIT 7,L Test the sign of the y velocity.
B1F4 LD H,$00 Clear the high byte of the y velocity (as a word).
B1F6 JR Z,Handle_Flying_Creature_Add_Y_Velocity Jump to Handle_Flying_Creature_Add_Y_Velocity if the y velocity is positive.
B1F8 LD H,$FF Set the high byte of the y velocity to FF to extend the sign.
Handle_Flying_Creature_Add_Y_Velocity B1FA CALL Move_Object_Vertically Add the y velocity to the y position (see Move_Object_Vertically). A is the new y position, and the zero flag is set when it is less than 80.
B1FD JP Z,Handle_Flying_Creature_Test_Top_Edge Jump to Handle_Flying_Creature_Test_Top_Edge if the y position is less than 80.
B200 CP $9F Jump to Handle_Flying_Creature_Store_Y if the y position is less than 9F.
B202 JR C,Handle_Flying_Creature_Store_Y
B204 BIT 4,E Jump to Handle_Flying_Creature_Test_Bottom_Gap if the room has no floor.
B206 JP Z,Handle_Flying_Creature_Test_Bottom_Gap
B209 LD A,(IX+$09) Fetch the y velocity.
B20C CPL Invert it, to bounce off the floor.
B20D LD (IX+$09),A Store the y velocity.
B210 LD A,$9F Set the y position to 9F.
Handle_Flying_Creature_Store_Y B212 LD (IX+$03),A Store the y position.
B215 JP Update_Object_Sprite Jump to Update_Object_Sprite.
Sabreman is on the left of the creature, so subtract two from the x velocity, down to a limit of C0.
Handle_Flying_Creature_Steer_Left B218 SUB $02 Subtract two from the x velocity.
B21A BIT 7,A Jump to Handle_Flying_Creature_Store_X_Velocity if the x velocity is positive.
B21C JP Z,Handle_Flying_Creature_Store_X_Velocity
B21F CP $C0 Jump to Handle_Flying_Creature_Steer_Vertically if the x velocity is less than C0.
B221 JP C,Handle_Flying_Creature_Steer_Vertically
B224 JP Handle_Flying_Creature_Store_X_Velocity Jump to Handle_Flying_Creature_Store_X_Velocity.
Sabreman is above the creature, so subtract two from the y velocity, down to a limit of C0.
Handle_Flying_Creature_Steer_Up B227 SUB $02 Subtract two from the y velocity.
B229 BIT 7,A Jump to Handle_Flying_Creature_Store_Y_Velocity if the y velocity is positive.
B22B JP Z,Handle_Flying_Creature_Store_Y_Velocity
B22E CP $C0 Jump to Handle_Flying_Creature_Check_Contact if the y velocity is less than C0.
B230 JP C,Handle_Flying_Creature_Check_Contact
B233 JP Handle_Flying_Creature_Store_Y_Velocity Jump to Handle_Flying_Creature_Store_Y_Velocity.
The x position is less than 80. The creature bounces off the left wall if there is one, and leaves the room by the gap otherwise.
Handle_Flying_Creature_Test_Left_Edge B236 CP $18 Jump to Handle_Flying_Creature_Store_X if the x position is 18 or more.
B238 JP NC,Handle_Flying_Creature_Store_X
B23B BIT 6,E Jump to Handle_Flying_Creature_Test_Left_Gap if the room has no left wall.
B23D JR Z,Handle_Flying_Creature_Test_Left_Gap
B23F LD A,(IX+$08) Fetch the x velocity.
B242 CPL Invert it, to bounce off the left wall.
B243 LD (IX+$08),A Store the x velocity.
B246 LD A,$18 Set the x position to 18.
B248 JP Handle_Flying_Creature_Store_X Jump to Handle_Flying_Creature_Store_X.
Handle_Flying_Creature_Test_Left_Gap B24B CP $08 Jump to Handle_Flying_Creature_Set_Gap_Flags if the x position is 08 or more.
B24D JR NC,Handle_Flying_Creature_Set_Gap_Flags
B24F DEC (IX+$02) Move the creature to the room on the left.
B252 LD (IX+$01),$D0 Set the x position to D0.
B256 BIT 0,(IX+$0F) Return if the creature has not been drawn yet.
B25A RET NZ
B25B JP RemoveEntity Erase the sprite of the creature.
Handle_Flying_Creature_Test_Right_Gap B25E CP $E7 Jump to Handle_Flying_Creature_Set_Gap_Flags if the x position is less than E7.
B260 JR C,Handle_Flying_Creature_Set_Gap_Flags
B262 INC (IX+$02) Move the creature to the room on the right.
B265 LD (IX+$01),$18 Set the x position to 18.
B269 BIT 0,(IX+$0F) Return if the creature has not been drawn yet.
B26D RET NZ
B26E JP RemoveEntity Erase the sprite of the creature.
The creature is in a gap in the left or right wall, so set bits 0 and 4 in the contact flags and in E, which makes the ceiling and the floor seem to be present.
Handle_Flying_Creature_Set_Gap_Flags B271 EX AF,AF' Save the new position in AF'.
B272 LD A,(IX+$0B) Fetch the contact flags.
B275 OR %00010001 Set bits 0 and 4.
B277 LD (IX+$0B),A Store the contact flags.
B27A LD A,E Copy the flags of the room to A.
B27B OR %00010001 Set bits 0 and 4.
B27D LD E,A Store them in E.
B27E EX AF,AF' Restore the new position from AF'.
B27F JP Handle_Flying_Creature_Store_X Jump to Handle_Flying_Creature_Store_X.
The y position is less than 80. The creature bounces off the ceiling if there is one, and leaves the room by the gap otherwise.
Handle_Flying_Creature_Test_Top_Edge B282 CP $4C Jump to Handle_Flying_Creature_Store_Y if the y position is 4C or more.
B284 JR NC,Handle_Flying_Creature_Store_Y
B286 BIT 0,E Jump to Handle_Flying_Creature_Test_Top_Gap if the room has no ceiling.
B288 JP Z,Handle_Flying_Creature_Test_Top_Gap
B28B LD A,(IX+$09) Fetch the y velocity.
B28E CPL Invert it, to bounce off the ceiling.
B28F LD (IX+$09),A Store the y velocity.
B292 LD A,$4C Set the y position to 4C.
B294 JP Handle_Flying_Creature_Store_Y Jump to Handle_Flying_Creature_Store_Y.
Handle_Flying_Creature_Test_Top_Gap B297 CP $2A Jump to Handle_Flying_Creature_Set_Vertical_Gap_Flags if the y position is 2A or more.
B299 JR NC,Handle_Flying_Creature_Set_Vertical_Gap_Flags
B29B DEC (IX+$04) Move the creature to the room above.
B29E LD (IX+$03),$90 Set the y position to 90.
B2A2 BIT 0,(IX+$0F) Return if the creature has not been drawn yet.
B2A6 RET NZ
B2A7 JP RemoveEntity Erase the sprite of the creature.
Handle_Flying_Creature_Test_Bottom_Gap B2AA CP $BF Jump to Handle_Flying_Creature_Set_Vertical_Gap_Flags if the y position is less than BF.
B2AC JR C,Handle_Flying_Creature_Set_Vertical_Gap_Flags
B2AE INC (IX+$04) Move the creature to the room below.
B2B1 LD (IX+$03),$40 Set the y position to 40.
B2B5 BIT 0,(IX+$0F) Return if the creature has not been drawn yet.
B2B9 RET NZ
B2BA JP RemoveEntity Erase the sprite of the creature.
The creature is in a gap in the ceiling or the floor, so set bits 2 and 6 in the contact flags and in AF', which makes the side walls seem to be present.
Handle_Flying_Creature_Set_Vertical_Gap_Flags B2BD EX AF,AF' Save the new position in AF'.
B2BE LD A,(IX+$0B) Fetch the contact flags.
B2C1 OR %01000100 Set bits 2 and 6.
B2C3 LD (IX+$0B),A Store the contact flags.
B2C6 EX AF,AF' Restore the new position from AF'.
B2C7 JP Handle_Flying_Creature_Store_Y Jump to Handle_Flying_Creature_Store_Y.
Prev: AFDA Up: Map Next: B2CA