Prev: A7E7 Up: Map Next: A89C
A7F3: Spawns cars
A new traffic car goes into an empty hazard slot each time the self modified spawn counter reaches zero. Nothing happens while perp_caught_phase or dont_spawn_cars is set, or while allow_spawning is zero. The counter comes down by allow_spawning, 1 or 2, per call; when it fires the next delay is taken from car_spawn_delay plus a random 0 to 15, and 25 more once the perp has been sighted.
The five non-perp hazard slots are then walked for a free one. If three or more vehicles are already out it gives up. Otherwise the template is copied into the slot, a random lane is picked and clamped to the road, the starting horizontal position and speed come from hazard_pos_speed, and a random car bitmap is assigned - avoiding the one that looks like the perp once the perp has been sighted.
Used by the routines at main_loop and drive_attract_demo.
Return without spawning anything if perp_caught_phase is non-zero or the dont_spawn_cars flag is set.
spawn_cars A7F3 LD A,($A230) Load perp_caught_phase as C
A7F6 LD C,A
A7F7 LD A,($A225) Load dont_spawn_cars as A
A7FA OR C Merge them together
A7FB RET NZ Return if either has set bits
Return without spawning anything if allow_spawning is zero.
A7FC LD A,($A254) Load allow_spawning
A7FF AND A Return if it's zero
A800 RET Z
Reduce inline spawn delay counter by the value of allow_spawning (1 or 2 here).
A801 NEG Calculate <self modified counter> - allow_spawning
A803 ADD A,$14
A805 LD ($A804),A Self modify above ADD instruction
A808 RET C Return unless counter hits zero (adding positive delay counter to negative A will normally carry)
Start spawning cars.
A809 CALL rng Generate a random byte
A80C AND $0F Take the bottom four bits of the result
A80E LD C,A Put it in C
A80F LD A,($A22E) Load and test sighted_flag
A812 AND A
A813 LD A,($5D1A) Load the current stage's car_spawn_delay
A816 JR Z,sc_set_spawn_delay Jump if sighted_flag was zero (don't increase the spawn delay)
Perp was sighted so increase the spawn delay by 25.
sc_increase_spawn_delay A818 ADD A,$19 Increase spawn delay by 25
sc_set_spawn_delay A81A ADD A,C Add random factor (0..15) in C to delay
A81B LD ($A804),A Self modify spawn delay counter above
Now walk the hazards array to find an unused slot.
A81E LD BC,$0500 B = 5 iterations; C = is-a-vehicle flags initialised to zero
A821 LD IX,$A19C Point IX at hazards[1]
A825 LD DE,$0014 Stride of hazards is 20 bytes
sc_find_unused_hazard_loop A828 RLC (IX+$00) If hazard is unused jump to sc_fill_in
A82C JR NC,sc_fill_in
A82E LD A,(IX+$0F) Read IX[15]. Top bit is set for vehicles
A831 RLA If the top bit is clear then it's not a vehicle, continue to next hazard
A832 JP NC,sc_continue
A835 RL C Shift is-a-vehicle flag into C
sc_continue A837 ADD IX,DE Advance to next hazard
A839 DJNZ sc_find_unused_hazard_loop Loop to sc_loop while B > 0
A83B RET Return
Don't spawn if there are three or more cars already spawned.
sc_fill_in A83C BIT 2,C Return if bit 2 of flags is set
A83E RET NZ
Copy template hazard to unused slot.
A83F PUSH IX Copy destination address to DE so we can LDIR
A841 POP DE
A842 LD BC,$0014 Size of hazard is 20 bytes
A845 LD HL,$A623 Point HL at hazard_template
A848 LDIR Copy hazard_template
Select a random lane in which to spawn the hazard.
A84A LD C,$14 Buffer offset of 20 for get_spawn_lanes
A84C CALL get_spawn_lanes Call get_spawn_lanes to get valid spawning range (B,C = min,max)
A84F CALL rng Generate a random byte
A852 AND $03 Take the bottom two bits of the result
Clamp new lane to valid range.
A854 ADD A,B Add to minimum lane, result is new lane
A855 CP C Compare new lane to maximum lane
A856 JR C,sc_set_lane Jump if less than or equal
A858 LD A,C Otherwise set to maximum lane
sc_set_lane A859 LD (IX+$11),A Set IX[17] to new lane
A85C LD (IX+$12),A Set IX[18] to new lane [but what's the difference between the two?]
Copy hazard_pos_speed values to hazard position and speed.
A85F LD HL,$A7E6 Load address of hazard_pos_speed table (but start a byte earlier so it's 1-indexed)
A862 LD B,$00 Index the table
A864 LD C,A
A865 ADD HL,BC
A866 LD A,(HL) Load horizontal position from table
A867 LD (IX+$05),A Set new horizontal position
A86A LD A,($A22E) Load and test sighted_flag
A86D AND A
A86E LD A,$04 Set offset to 4 by default
A870 JR Z,sc_have_offset Jump if not sighted
A872 ADD A,A Double offset to 8 if sighted
sc_have_offset A873 LD C,A Add offset to previously computed table address (B is zero)
A874 ADD HL,BC
A875 LD A,(HL) Set speed from table
A876 LD (IX+$0D),A
Now pick a random car LOD to show.
A879 CALL rng Generate a random byte with which we shall select a LOD
A87C AND $06 Isolate two bits, shifted up by one (giving a valid array byte offset of 0/2/4/6)
A87E LD C,A Copy to C
If we've sighted the perp then don't spawn any generic cars (offset 6) since they look just like the perp's. Instead use offset 4.
A87F LD A,($A22E) Load and test sighted_flag
A882 AND A
A883 JR Z,sc_set_lod Jump if not sighted - use random offset
A885 LD A,$06 If sighted set A to 6 (LOD offset of generic car)
A887 CP C Compare with random LOD offset
A888 JR NZ,sc_set_lod Jump to sc_set_lod if different
A88A DEC C Decrement offset from 6 to 4
A88B DEC C
sc_set_lod A88C LD B,$00 Clear B so we can use full offset as BC
A88E LD HL,$5D12 Load address of lods_vehicles (first of generic car LODs)
A891 ADD HL,BC Index array
A892 LD A,(HL) Set hazard's LOD address to HL (IX+9)
A893 INC HL
A894 LD (IX+$09),A
A897 LD A,(HL)
A898 LD (IX+$0A),A
A89B RET Return
Prev: A7E7 Up: Map Next: A89C