Prev: AB78 Up: Map Next: AC68
ABE5: Move Rope
Used by the routine at Update_Rope.
Makes the rope swing. The velocity of the end of the rope (Rope_Velocity) is changed by four towards the middle of the swing (it is increased when the displacement is negative and decreased when it is positive) and then it is multiplied by 20 and added to the displacement (Rope_Displacement).
When the rope is already at rest nothing changes. When the end of the rope is moving towards the middle, the change of velocity is left out on one call in eight (the test is made on the tick counter at GameTimer for a negative displacement and on FRAMES for a positive one).
If the length of the rope is less than 80 the displacement is limited to the length multiplied by B0 and divided by 0100. When it would go further, the displacement is set to the limit and the velocity and the fraction are set to zero. For a longer rope the displacement is not limited.
Input
IX Object record
Find out if the rope is at rest (no displacement and no velocity).
Move_Rope ABE5 LD A,($AAA4) Fetch the displacement of the end of the rope.
ABE8 LD HL,$AAA2 Point at the velocity of the end of the rope.
ABEB AND A Jump to Move_Rope_Change_Velocity if the rope is not hanging straight down (the displacement is not zero).
ABEC JR NZ,Move_Rope_Change_Velocity
ABEE EX AF,AF' Keep the displacement in AF'.
ABEF LD A,(HL) Fetch the velocity of the end of the rope.
ABF0 AND A Return if the rope is at rest (the velocity is zero).
ABF1 RET Z
ABF2 EX AF,AF' Fetch the displacement again from AF'.
Change the velocity. A negative displacement adds four to it and a positive one subtracts four.
Move_Rope_Change_Velocity ABF3 AND %10000000 Keep only bit 7 (the sign of the displacement).
ABF5 JR Z,Move_Rope_Positive_Displacement Jump to Move_Rope_Positive_Displacement if the displacement is positive.
ABF7 BIT 7,(HL) Jump to Move_Rope_Add_Four if the velocity is negative.
ABF9 JR NZ,Move_Rope_Add_Four
ABFB LD A,($8ED6) Fetch the tick counter from GameTimer.
ABFE AND %00000111 Keep only bits 0 to 2.
AC00 JR Z,Move_Rope_Move_End Jump to Move_Rope_Move_End without changing the velocity if the result is zero (once in every eight passes).
Move_Rope_Add_Four AC02 INC (HL) Add four to the velocity, to pull the end of the rope back towards the middle.
AC03 INC (HL)
AC04 INC (HL)
AC05 INC (HL)
AC06 JR Move_Rope_Move_End Jump to Move_Rope_Move_End.
Move_Rope_Positive_Displacement AC08 BIT 7,(HL) Jump to Move_Rope_Subtract_Four if the velocity is positive.
AC0A JR Z,Move_Rope_Subtract_Four
AC0C LD A,($5C78) Fetch the low byte of FRAMES.
AC0F AND %00000111 Keep only bits 0 to 2.
AC11 JR Z,Move_Rope_Move_End Jump to Move_Rope_Move_End without changing the velocity if the result is zero (once in every eight passes).
Move_Rope_Subtract_Four AC13 DEC (HL) Subtract four from the velocity, to pull the end of the rope back towards the middle.
AC14 DEC (HL)
AC15 DEC (HL)
AC16 DEC (HL)
Multiply the velocity by 20 and add it to the displacement.
Move_Rope_Move_End AC17 LD A,(HL) Fetch the velocity of the end of the rope.
AC18 AND A Test the sign of the velocity.
AC19 LD D,$00 Clear the high byte of the velocity.
AC1B JP P,Move_Rope_Sign_Extended Jump to Move_Rope_Sign_Extended if the velocity is positive.
AC1E LD D,$FF Set the high byte of the velocity to FF to extend the sign.
Move_Rope_Sign_Extended AC20 LD E,A Copy the velocity to E.
AC21 EX DE,HL Move the velocity (as a word) to HL.
AC22 ADD HL,HL Multiply the velocity by 20.
AC23 ADD HL,HL
AC24 ADD HL,HL
AC25 ADD HL,HL
AC26 ADD HL,HL
AC27 LD DE,($AAA3) Fetch the displacement (the fraction is in the low byte).
AC2B ADD HL,DE Add the velocity to the displacement.
AC2C PUSH HL Stash the new displacement on the stack.
AC2D LD DE,$00B0 Set the multiplier for the limit of the displacement to B0.
AC30 LD HL,($AAA5) Fetch the length of the rope.
AC33 SRL H Halve the length of the rope.
AC35 RR L
AC37 LD A,L Copy the low byte to A.
AC38 AND %11000000 Keep only bits 6 and 7.
AC3A JR Z,Move_Rope_Find_Limit Jump to Move_Rope_Find_Limit if the length is less than 80.
AC3C POP HL Fetch the new displacement again from the stack.
AC3D JR Move_Rope_Store_Displacement Jump to Move_Rope_Store_Displacement to store it without a limit.
Find the limit of the displacement, which is the length of the rope multiplied by B0 and divided by 0100.
Move_Rope_Find_Limit AC3F LD A,($AAA5) Fetch the low byte of the length of the rope.
AC42 CALL MultiplyAByDE Multiply it by B0.
AC45 LD A,H Copy the high byte of the result (the limit) to A.
AC46 POP HL Fetch the new displacement again from the stack.
AC47 BIT 7,H Jump to Move_Rope_Negative_Limit if the displacement is negative.
AC49 JR NZ,Move_Rope_Negative_Limit
AC4B CP H Jump to Move_Rope_Beyond_Limit if the displacement is beyond the limit.
AC4C JR C,Move_Rope_Beyond_Limit
AC4E LD ($AAA3),HL Store the new displacement.
AC51 RET Return.
Move_Rope_Negative_Limit AC52 NEG Make the limit negative.
AC54 CP H Jump to Move_Rope_Store_Displacement if the displacement is at the limit.
AC55 JR Z,Move_Rope_Store_Displacement
AC57 JR NC,Move_Rope_Beyond_Limit Jump to Move_Rope_Beyond_Limit if the displacement is beyond the limit.
Move_Rope_Store_Displacement AC59 LD ($AAA3),HL Store the new displacement.
AC5C RET Return.
The displacement is beyond the limit. Set it to the limit and stop the swing.
Move_Rope_Beyond_Limit AC5D LD ($AAA4),A Set the displacement to the limit.
AC60 XOR A Clear the fraction of the displacement and the velocity.
AC61 LD ($AAA3),A
AC64 LD ($AAA2),A
AC67 RET Return.
Prev: AB78 Up: Map Next: AC68