Prev: 59848 Up: Map Next: 60032
59861: Update a character's animatory state and location and update the SRB
Used by the routines at 25420, 25789, 26224, 29149, 30989, 31204, 31476, 31670, 31713, 60347, 60506, 62264, 62325, 63281, 63558, 63954, 64131 and 64227. Sets the new animatory state and location of a character, and updates the screen refresh buffer (SRB) accordingly.
Input
A New animatory state
D New y-coordinate
E New x-coordinate
H Character number (215-230)
59861 LD L,2 Point HL at byte 2 of the character's buffer
59863 LD (HL),D Fill in the new y-coordinate
59864 DEC L L=1
59865 LD (HL),E Fill in the new x-coordinate
59866 DEC L L=0
59867 LD (HL),A Fill in the new animatory state
This entry point is used by the routine at 59848.
59868 LD BC,514 B=2, C=2
59871 LD A,(HL) A=character's animatory state
59872 AND 127 Clear the 'direction' bit (bit 7)
59874 ADD A,136 Is the animatory state >= 120?
59876 JR C,59889 Jump if so
59878 LD BC,1283 B=5, C=3
59881 INC A Is the animatory state equal to 7 mod 8?
59882 AND 7
59884 JR NZ,59889 Jump if not
59886 LD BC,773 B=3, C=5
Now B holds the height of the sprite in tiles, and C holds the width.
59889 LD A,(32767) A=Y, the y-coordinate of the topmost row of the play area on screen (2-20)
59892 SUB B A=Y-B
59893 JR C,59897 Jump if B>Y
59895 CP D Is the character entirely above the portion of the play area currently on screen?
59896 RET NC Return if so
59897 ADD A,B A=Y
59898 ADD A,19 A=y-coordinate of the bottom row of the play area on screen (21-39)
59900 SUB D Is the character entirely below the portion of the play area currently on screen?
59901 RET C Return if so
59902 CPL A=4*(D-Y+4)
59903 ADD A,24
59905 ADD A,A
59906 ADD A,A
59907 LD D,A Copy this value (0, 4, 8, 12,...92) to D
59908 LD A,(32766) A=X, the x-coordinate of the leftmost column of the play area on screen
59911 SUB C A=X-C
59912 JR C,59916 Jump if C>X
59914 CP E Is the character entirely off-screen to the left?
59915 RET NC Return if so
59916 ADD A,C A=X
59917 ADD A,31 A=x-coordinate of the rightmost column of the play area on screen
59919 SUB E Is the character entirely off-screen to the right?
59920 RET C Return if so
If we get here, then the character's sprite (or at least a portion of it) is on-screen.
59921 CPL A=E-X: the character's screen x-coordinate (-4 to 31)
59922 ADD A,32
59924 PUSH AF Save this temporarily
59925 LD A,(HL) A=character's animatory state
59926 AND 7 Set the zero flag if the animatory state is 0 mod 8
59928 LD A,(HL) A=character's animatory state
59929 JR NZ,59933 Jump unless the animatory state is 0 mod 8
59931 ADD A,2 Add 2 if the animatory state is congruent to 0 mod 8
59933 PUSH BC Push the sprite dimensions onto the stack
59934 EXX
59935 POP BC Retrieve the sprite dimensions in BC'
59936 LD H,215 Page 215 holds sprite tile references for the top-left tile (tile 0) in the left-facing sprites
59938 LD D,B D'=sprite height (2, 3 or 5)
59939 RLCA Set bit 7 of A, and set the carry flag if the character is facing right
59940 SCF
59941 RRA
59942 LD L,A L'=character's animatory state (with bit 7 set)
59943 JR NC,59956 Jump if the character is facing left
59945 XOR A D'=-B' (negative sprite height)
59946 SUB B
59947 LD D,A
59948 LD E,C E'=C'-1 (sprite width minus 1)
59949 DEC E
59950 LD A,H A=215 (page containing references for sprite tile 0)
59951 ADD A,B A=215+B'*(C'-1)
59952 DEC E
59953 JR NZ,59951
59955 LD H,A Copy this value to H'
Now HL' points at the sprite tile reference for the top-left tile in the character's sprite.
59956 POP AF Restore the character's screen x-coordinate to A
59957 LD E,A Copy it to E'
59958 JR C,59967 Jump if E'>=0 (meaning that the leftmost tiles in the character's sprite are on-screen)
59960 LD A,H A=H'-D'*E' (sprite tile reference page number); C'=C'+E'
59961 ADD A,D
59962 DEC C
59963 INC E
59964 JR NZ,59961
59966 LD H,A Copy the sprite tile reference page number to H'
Now HL' points at the sprite tile reference for the tile in the top row and the leftmost column of the character's sprite that is on-screen. C' holds the number of tile columns of the character's sprite that are to the right of the left edge of the screen.
59967 LD A,E A=leftmost column of the screen occupied by the sprite (0-31)
59968 EXX
59969 LD E,A E=leftmost column of the screen occupied by the sprite
59970 AND 7 Point BC at byte 21 of page 160+(E%8)
59972 ADD A,160
59974 LD B,A
59975 LD C,21
59977 LD A,(BC) Pick up the contents in A
59978 LD C,A Copy them to C
Now C holds 1, 2, 4, 8, 16, 32, 64 or 128. The bit set in C corresponds to the bit that needs to be set in the relevant byte of the screen refresh buffer (SRB).
59979 LD A,E A=leftmost column of the screen occupied by the sprite (0-31)
59980 RRCA Set A to the LSB of the first byte of the SRB that needs to be modified: D+INT(E/8)
59981 RRCA
59982 RRCA
59983 AND 3
59985 ADD A,D
59986 LD B,A Copy this LSB to B
59987 LD D,127 The SRB is in page 127
59989 EXX
Here we enter a loop to set the appropriate bits in the SRB. At this point B' holds the number of tile rows in the sprite (2, 3, or 5) and C' holds the number of tile columns of the sprite that are to the right of the left edge of the screen.
59990 PUSH BC Save the tile row and column counters temporarily
59991 LD E,0 Start at sprite tile row 0 (top row)
59993 LD A,(HL) Pick up the sprite tile reference in A
59994 AND A Is this the 'null' tile (blank square)?
59995 JR Z,60007 Jump if so (no need to set a bit in the SRB)
59997 LD A,E A=sprite tile row number (0-4)
59998 EXX
59999 ADD A,A Multiply by 4 (the number of bytes of the SRB that correspond to one row of the screen)
60000 ADD A,A
60001 ADD A,B Point DE at the relevant byte of the SRB
60002 LD E,A
60003 LD A,(DE) Pick up the SRB byte in A
60004 OR C Make sure the appropriate bit is set
60005 LD (DE),A Restore the SRB byte with the appropriate bit set
60006 EXX
60007 INC H Point HL' at the reference for the next tile in the sprite (one row down)
60008 INC E Next row down in this column of the sprite
60009 DJNZ 59993 Jump back until we've set all the SRB bits for this tile column of the sprite
60011 LD A,H Point HL' at the reference for the tile in the top row of the next column of the sprite
60012 ADD A,D
60013 POP BC
60014 SUB B
60015 LD H,A
60016 EXX
60017 RRC C Move the SRB marker bit in C one place to the right (possibly wrapping round to bit 7)
60019 JR NC,60026 Jump if there are still bits to be set in the current SRB byte
60021 INC B Otherwise move along to the next byte in the SRB
60022 LD A,B A=LSB of the next SRB byte
60023 AND 3 Does the next SRB byte correspond to a segment in the leftmost 8 columns of the screen (i.e. have we wrapped around from right to left)?
60025 RET Z Return if so (any remaining sprite tile columns are off-screen to the right)
60026 EXX
60027 DEC C Next sprite tile column
60028 JR NZ,59990 Jump back until the relevant SRB bits for every sprite tile column have been set
60030 EXX
60031 RET
Prev: 59848 Up: Map Next: 60032