| Routines

60812: Determine the next move a character should make to reach his destination

Used by the routines at 29361, 31126, 31362 and 62976. Returns with A holding a value that indicates the next move the character should make (if any) to reach his destination.
A | Meaning the character should...
--- | ---
0 | Do nothing (the character is already at his destination)
1 | Go right
2 | Go left
3 | Go up
4 | Go down
5 | Open a door from the inside
6 | Knock on a door or use a key
Input
H | Character number (215-230)
60812 | CALL 31808 | Deal with the case where the character will soon be entering or leaving the hotel; otherwise return here
60815 | LD L,13 | Initialise the location/destination indicator in byte 13 of the character's buffer to 0
60817 | LD (HL),0
60819 | AND A | Is the character on the sidewalk or the road?
60820 | JR NZ,60883 | Jump if not
60822 | DEC L | L=12
60823 | LD A,(HL) | A=destination location identifier (see 60726)
60824 | AND A | Is the character's destination on the sidewalk or the road?
60825 | JR NZ,60842 | Jump if not
The next section of code deals with the case where the character can reach his destination simply by continuing to move left or right. The routine at 31808 re-enters here (from the opening CALL in this routine) if the character is on the front steps of the hotel, and his destination is on the first floor or the front steps of the hotel.
60827 | LD L,10 | Point HL at byte 10 of the character's buffer
60829 | LD E,(HL) | E=destination x-coordinate
60830 | LD A,E | Copy this to A
60831 | LD L,1 | Does the character's x-coordinate match the destination x-coordinate?
60833 | CP (HL)
60834 | LD A,0 | Return with A=0 (do nothing) if so
60836 | RET Z
60837 | LD A,1 | Return with A=1 (go right) if the character's x-coordinate is less than the destination x-coordinate
60839 | RET NC
60840 | INC A | A=2 (go left)
60841 | RET |
The character is on the sidewalk or the road, and his destination is somewhere other than the sidewalk or the road. Move the character left or right towards the building he's destined for, or make him go up a step if he's reached the front steps of the building.
60842 | AND 240 | Keep only the region identifier bits (bits 4-7) of the destination
60844 | RRCA | Shift them into bits 1-4
60845 | RRCA
60846 | RRCA
60847 | ADD A,150 | A=152+2n (n=0-11, 13 or 14)
60849 | LD C,A | Point BC at the entry in the table of building entrance x-coordinates at 65432 that corresponds to the character's destination
60850 | LD B,255
60852 | LD L,1 | Point HL at byte 1 of the character's buffer
60854 | LD A,(BC) | Pick up the lower x-coordinate of the building entrance
60855 | LD E,A | Copy it to E
60856 | CP (HL) | Compare it with the character's x-coordinate
60857 | LD A,L | A=1 (go right)
60858 | JR NZ,60865 | Jump unless the x-coordinates match
60860 | DEC L | L=0
60861 | BIT 7,(HL) | Is the character facing right?
60863 | JR NZ,60877 | Jump if so
60865 | RET NC | Return with A=1 (go right)
60866 | INC C | Pick up the upper x-coordinate of the building entrance
60867 | LD A,(BC)
60868 | LD E,A | Copy it to E
60869 | CP (HL) | Compare it with the character's x-coordinate
60870 | LD A,2 | A=2 (go left)
60872 | RET NZ | Return unless the x-coordinates match
60873 | DEC L | L=0
60874 | BIT 7,(HL) | Is the character facing right?
60876 | RET NZ | Return with A=2 (go left) if so
60877 | LD L,13 | Set byte 13 of the character's buffer to 1 (indicating that the character is no longer on the sidewalk or the road, and is in the same region as his destination)
60879 | INC (HL)
60880 | LD A,3 | A=3 (go up)
60882 | RET |
The character is on neither the sidewalk nor the road.
60883 | INC (HL) | Set byte 13 of the character's buffer to 1 (indicating that the character is on neither the sidewalk nor the road)
60884 | DEC L | L=12
60885 | INC A | Is the character on the fire escape of the apartment building next to no. 19?
60886 | JR NZ,60925 | Jump if not
The character is on the fire escape of the apartment building next to no. 19.
60888 | LD A,(HL) | A=destination location identifier (see 60726)
60889 | INC A | Set the zero flag if the destination is on the fire escape
60890 | SCF | Set the carry flag: the character will go back up the fire escape (if his destination is not on the fire escape)
60891 | JR NZ,60900 | Jump if the destination is not on the fire escape
60893 | DEC L | L=11
60894 | LD A,(HL) | A=character's destination y-coordinate
60895 | LD L,2 | Point HL at byte 2 of the character's buffer
60897 | CP (HL) | Does the character's y-coordinate match that of his destination?
60898 | JR Z,60827 | If so, move the character left or right towards his destination
60900 | PUSH AF | Save the carry flag briefly
60901 | PUSH HL | Save the character number briefly
60902 | CALL 60179 | Obtain descriptors for the character's current location
60905 | POP HL | Restore the character number to H
60906 | POP AF | Restore the carry flag
60907 | LD A,C | Copy the direction descriptor bits (see 60179) to A
60908 | JR NC,60917 | Jump if the character's y-coordinate is less than that of his destination
The character is on the fire escape of the apartment building next to no. 19, and his destination is either not on the fire escape, or somewhere further up the fire escape. In this case the character will go up the fire escape.
60910 | AND 16 | Set the zero flag unless the character is next to a step going up to the right
60912 | LD A,3 | A=3 (go up)
60914 | RET NZ | Return if the character is next to a step going up to the right
60915 | DEC A | A=2 (go left)
60916 | RET |
The character is on the fire escape of the apartment building next to no. 19, and his destination is somewhere further down the fire escape. In this case the character will go down the fire escape.
60917 | AND 8 | Set the zero flag unless the character is next to a step going down to the left
60919 | LD A,4 | A=4 (go down)
60921 | RET NZ | Return if the character is next to a step going down to the left
60922 | LD A,1 | A=1 (go right)
60924 | RET |
The character is on neither the sidewalk nor the road, nor on the fire escape of the apartment building next to no. 19.
60925 | DEC A | A=identifier for the character's current location (see 60726)
60926 | LD B,(HL) | B=destination location identifier (see 60726)
60927 | INC B | Is the destination on the fire escape of the apartment building next to no. 19?
60928 | JR NZ,60937 | Jump if not
60930 | CP 253 | Is the character on the rim of the roof of the apartment building next to no. 19?
60932 | JR NZ,60937 | Jump if not
60934 | LD A,4 | A=4 (go down)
60936 | RET |
The character is on neither the sidewalk nor the road, nor on the fire escape of the apartment building next to no. 19; in addition, either his destination is not on the fire escape, or he is not on the rim of the roof of the apartment building next to no. 19.
60937 | LD B,A | B=identifier for the character's current location (see 60726)
60938 | AND 240 | Keep only the region identifier bits (bits 4-7)
60940 | LD C,A | Copy them to C
60941 | LD A,(HL) | Collect the destination location identifier from byte 12 of the character's buffer
60942 | AND 240 | Keep only the region identifier bits (bits 4-7)
60944 | CP C | Is the character in the same region as his destination?
60945 | JP NZ,61100 | Jump if not
The character is in the same region as his destination.
60948 | LD A,B | A=identifier for the character's current location (see 60726)
60949 | CP (HL) | Compare it with the identifier for the character's destination
60950 | JR NZ,60966 | Jump unless they match
The character is in the same region as his destination, and also on the same floor.
60952 | LD L,11 | A=character's destination y-coordinate
60954 | LD A,(HL)
60955 | LD L,2 | Compare this with the character's current y-coordinate
60957 | CP (HL)
60958 | JP Z,60827 | If they match, move the character left or right towards his destination
60961 | LD A,3 | A=3 (go up)
60963 | RET C | Return if the character's current y-coordinate is greater than that of his destination
60964 | INC A | A=4 (go down)
60965 | RET |
The character is in the same region as his destination, but either on a different floor, or outside the entrance to a shop or building when the destination is on the first floor inside (or vice versa).
60966 | JR C,61036 | Jump if the character is below his destination
60968 | AND 15 | Keep only bits 0-3 of the identifier for the character's current location
60970 | CP 4 | Is the character in a shop or on the first floor of a building (inside)?
60972 | JR NZ,61022 | Jump if not
60974 | LD A,(HL) | A=destination location identifier
60975 | AND 15 | Keep only bits 0-3
60977 | CP 2 | Set the zero flag if the destination is outside the entrance
60979 | LD L,1 | Point HL at byte 1 of the character's buffer
60981 | JR NZ,61001 | Jump unless the destination is outside the entrance
60983 | LD A,(HL) | A=character's x-coordinate
60984 | LD L,10 | Does it match the destination x-coordinate?
60986 | CP (HL)
60987 | JR NZ,60999 | Jump if not
60989 | PUSH DE | Save the staircase endpoint x-coordinates briefly
60990 | PUSH HL | Save the character number briefly
60991 | CALL 60179 | Obtain descriptors for the character's current location
60994 | POP HL | Restore the character number to H
60995 | POP DE | Restore the staircase endpoint x-coordinates to DE
60996 | SUB 3 | Is the character standing at the (open) entrance to a building?
60998 | RET Z | Return with A=0 (do nothing) if so
60999 | LD L,1 | Point HL at byte 1 of the character's buffer
61001 | LD A,(HL) | A=character's x-coordinate
61002 | CP D | Is the character standing at the top of the steps down to the sidewalk or the floor below?
61003 | JR NZ,61017 | If not, send the character towards the top of the steps
61005 | PUSH HL | Save the character number briefly
61006 | CALL 60179 | Obtain descriptors for the character's current location
61009 | POP HL | Restore the character number to H
61010 | INC A | Is the character standing next to the open entrance to a building?
61011 | CP 4
61013 | RET Z | Return with A=4 (go down) if so
61014 | LD A,5 | A=5 (open the door)
61016 | RET |
61017 | LD A,1 | A=1 (go right)
61019 | RET C |
61020 | INC A | A=2 (go left)
61021 | RET |
Either the character is in the same region as his destination, but above it, and not in a shop or on the first floor of a building (inside); or the character is not in the same region as his destination, and is inside a building somewhere above the first floor.
61022 | BIT 0,A | Set the zero flag unless the character is on a staircase between floors
61024 | LD A,4 | A=4 (go down)
61026 | RET NZ | Return if the character is on a staircase between floors
61027 | LD L,1 | Point HL at byte 1 of the character's buffer
61029 | LD A,(HL) | A=character's x-coordinate
61030 | CP D | Compare it with the x-coordinate of the top of the staircase leading down to the floor below
61031 | LD A,4 | A=4 (go down)
61033 | RET Z | Return if the character is standing at the top of the staircase leading down to the floor below
61034 | JR 61017 | Send the character towards the top of the staircase
The character is in the same region as his destination, but below it.
61036 | CALL 28803 | Deal with the case where the character is on the roof of the police station or the apartment building next to no. 19 and is destined for the edge of that roof; otherwise return here
61039 | NOP |
61040 | JR NZ,61084 | Jump unless the character is standing outside the entrance to a shop or other building
61042 | LD A,(HL) | A=destination location identifier (see 60726)
61043 | AND 15 | Keep only bits 0-3
61045 | CP 4 | Set the zero flag if the destination is inside the shop or on the first floor of the building outside the entrance to which the character is standing
61047 | LD L,1 | Point HL at byte 1 of the character's buffer
61049 | JR NZ,61067 | Jump unless the destination is inside the shop or on the first floor of the building outside the entrance to which the character is standing
61051 | LD A,(HL) | A=character's x-coordinate
61052 | LD L,10 | Compare this with the destination x-coordinate
61054 | CP (HL)
61055 | JR NZ,61067 | Jump unless they match
61057 | PUSH DE | Save the staircase endpoint x-coordinates briefly
61058 | PUSH HL | Save the character number briefly
61059 | CALL 60179 | Obtain descriptors for the character's current location
61062 | POP HL | Restore the character number to H
61063 | POP DE | Restore the staircase endpoint x-coordinates to DE
61064 | SUB 3 | Is the entrance next to which the character is standing open?
61066 | RET Z | Return with A=0 (do nothing) if so
61067 | NOP |
The character is standing outside the entrance to a shop or other building, and his destination is somewhere inside that shop or building.
61068 | CALL 63749 | Is the character standing at the right spot to enter the building or knock on the door?
61071 | JR NZ,61096 | Jump if not
61073 | PUSH HL | Save the character number briefly
61074 | CALL 60179 | Obtain descriptors for the character's current location
61077 | POP HL | Restore the character number to H
61078 | CP 3 | Set the zero flag if the entrance is open
61080 | JP 63774 | Check whether the character should enter the building or knock first
61083 | NOP | This instruction is never executed
If we get here, then either the character is in the same region as his destination, but below it, and is not standing outside the entrance to a shop or other building; or the character is inside or on the roof of the police station and heading for no. 27 (or vice versa), and will be going via the roofs (instead of going down to the sidewalk).
61084 | BIT 0,A | Bit 0 of A is set if the character is on a staircase
61086 | LD A,3 | A=3 (go up)
61088 | RET NZ | Return if the character is on a staircase
61089 | LD L,1 | Point HL at byte 1 of the character's buffer
61091 | LD A,(HL) | A=character's x-coordinate
61092 | CP E | Compare this with the x-coordinate of the bottom of the staircase leading to the floor above
61093 | LD A,3 | Return with A=3 (go up) if the character is at the bottom of the staircase leading to the floor above
61095 | RET Z
61096 | LD A,L | Return with A=1 (go right) if the character is to the left of either the bottom of the staircase leading to the floor above, or the correct spot at which to enter the building or knock on the door
61097 | RET C
61098 | INC A | A=2 (go left)
61099 | RET |
The character is not in the same region as his destination.
61100 | INC L | Set byte 13 of the character's buffer to 2 (to indicate that the character is not on the sidewalk or the road, and is heading for some region other than the one he's in)
61101 | INC (HL)
61102 | DEC L | L=12
61103 | CP 96 | Is the character going to the police station?
61105 | JR Z,61118 | Jump if so
61107 | CP 112 | Is the character going to no. 27?
61109 | JR NZ,61130 | Jump if not
The character is going to no. 27, and is not in the same region as that building.
61111 | LD A,C | A=region identifier for the character's current location
61112 | CP 96 | Is the character inside or on the roof of the police station?
61114 | JR NZ,61130 | Jump if not
61116 | JR 61123 |
The character is going to the police station, and is not in the same region as that building.
61118 | LD A,C | A=region identifier for the character's current location
61119 | CP 112 | Is the character inside or on the roof of no. 27?
61121 | JR NZ,61130 | Jump if not
The character is either inside or on the roof of no. 27 and heading for the police station, or inside or on the roof of the police station and heading for no. 27.
61123 | LD A,B | A=identifier for the character's current location (96-109 if it's the police station, or 112-125 if it's no. 27; see 60726)
61124 | ADD A,(HL) | Add the destination location identifier
61125 | CP 225 | Reset the carry flag if it would be quicker to go via the roofs than back down to the sidewalk
61127 | LD A,B | A=identifier for the character's current location (see 60726)
61128 | JR NC,61084 | Jump if it would be quicker to go via the roofs than back down to the sidewalk
The character is not in the same region as his destination. Figure out his next move towards the destination via the sidewalk.
61130 | LD A,B | A=identifier for the character's current location (see 60726)
61131 | AND 15 | Keep only bits 0-3
61133 | CP 4 | Is the character inside a shop or on the first floor of a building (inside)?
61135 | JP Z,60999 | If so, send him towards the entrance
61138 | CP 1 | Is the character on the front steps of a building below the first floor?
61140 | JP NZ,61022 | If not, send the character towards the top of the staircase leading down to the floor below
The character is not in the same region as his destination, and is on the front steps of a building below the first floor. Figure out which direction to take down the steps towards the destination.
61143 | PUSH HL | Save the character number briefly
61144 | CALL 60179 | Obtain descriptors for the character's current location
61147 | POP HL | Restore the character number to H
61148 | LD L,1 | Point HL at byte 1 of the character's buffer
61150 | LD A,(HL) | A=character's x-coordinate
61151 | LD L,10 | Compare this with the character's destination x-coordinate
61153 | CP (HL)
61154 | LD A,C | Copy the direction descriptor bits (see 60179) to A
61155 | JR NC,61173 | Jump if the character's x-coordinate is greater than or equal to the destination x-coordinate
61157 | AND 4 | Is the character next to a step going down to the right?
61159 | JR NZ,61164 | Jump if not
61161 | LD A,4 | A=4 (go down)
61163 | RET |
61164 | LD L,0 | Point HL at byte 0 of the character's buffer
61166 | BIT 7,(HL) | Is the character facing right?
61168 | JR NZ,61161 | Jump if so to set A=4 (go down)
61170 | LD A,1 | A=1 (go right)
61172 | RET |
61173 | AND 8 | Is the character standing next to a step going down to the left?
61175 | JR Z,61161 | Jump if not to set A=4 (go down)
61177 | LD L,0 | Point HL at byte 0 of the character's buffer
61179 | BIT 7,(HL) | Is the character facing left?
61181 | JR Z,61161 | Jump if so to set A=4 (go down)
61183 | LD A,2 | A=2 (go left)
61185 | RET |