Prev: 40384 Up: Map Next: 40650
40492: Animate: Laser Beam
XOR the four beam pulses onto the screen and drop the slot when they have all expired.
Input
IX Actor slot
LaserBeam_Animate 40492 CALL TestLaserHits Call TestLaserHits.
40495 LD D,(IX+1) Fetch the beam Y.
40498 LD A,(IX+2) Fetch pulse 1.
40501 BIT 2,A Jump to LaserBeam_Animate_WalkPulses if bit 2 is reset.
40503 JR Z,LaserBeam_Animate_WalkPulses
Move pulse 1 on and invert the screen byte there.
40505 LD L,A Copy the pulse X into L.
40506 LD A,8 A=8.
40508 BIT 0,L Jump to LaserBeam_Animate_StepX if bit 0 of the pulse X is reset.
40510 JR Z,LaserBeam_Animate_StepX
40512 NEG Negate the step.
Add the step to pulse 1 and find the screen byte there.
LaserBeam_Animate_StepX 40514 ADD A,L Add the step to the pulse X.
40515 LD E,A Copy the new X into E.
40516 LD H,D Copy the beam Y into H.
40517 PUSH HL Stash the beam position on the stack.
40518 CALL ScreenAddress Call ScreenAddress.
40521 LD (IX+2),E Write the new X back as pulse 1.
Invert the screen byte, then find the attribute square.
40524 LD A,255 A=255.
40526 XOR (HL) Invert the screen byte.
40527 LD (HL),A Write it back.
40528 POP HL Restore the beam position from the stack.
40529 CALL AttributeAddress Call AttributeAddress.
Colour the attribute square, then count the beam timer down.
40532 LD A,(IX+7) Fetch the beam colour.
40535 LD (HL),A Write it to the attribute square.
40536 LD A,(IX+6) Fetch the beam timer.
40539 SUB 8 Subtract 8.
40541 LD (IX+6),A Write it back.
40544 AND %11111000 Keep only bits 3-7.
40546 JR NZ,LaserBeam_Animate_WalkPulses Jump to LaserBeam_Animate_WalkPulses if any of those bits remain.
40548 RES 2,(IX+2) Reset bit 2 of pulse 1.
Set up the pixel masks in the shadow registers, then walk pulses 2-4.
LaserBeam_Animate_WalkPulses 40552 EXX Switch to the shadow registers.
40553 LD BC,796 BC'=796.
40556 LD E,224 E'=224.
40558 EXX Switch back to the main registers.
40559 LD E,3 E=3.
40561 PUSH IX Copy the slot pointer into BC (using the stack).
40563 POP BC
40564 INC BC Move BC onto pulse 2.
40565 INC BC
40566 INC BC
Walk the pulses, skipping any on pulse 1's character column.
LaserBeam_Animate_Loop 40567 LD A,(BC) Fetch this pulse X.
40568 XOR (IX+2) Compare it against pulse 1.
40571 AND %11111000 Keep only bits 3-7.
40573 JR NZ,LaserBeam_Animate_TestBit Jump to LaserBeam_Animate_TestBit if the pulses are not on the same character column.
40575 EXX Switch to the shadow registers.
40576 LD A,B Rotate the mask bytes.
40577 LD B,C
40578 LD C,E
40579 EXX Switch back to the main registers.
40580 INC BC Move onto the next pulse.
40581 DEC E Decrease the pulse counter by one.
40582 JR NZ,LaserBeam_Animate_Loop Jump back to LaserBeam_Animate_Loop if any pulses remain.
Free the actor slot once every pulse has been skipped.
40584 LD (IX+0),0 Write 0 to the slot type.
40588 RET Return.
If this pulse is not moving yet, wait on the beam timer and then start it.
LaserBeam_Animate_TestBit 40589 LD A,(BC) Fetch this pulse X.
40590 BIT 2,A Jump to LaserBeam_Animate_DrawPulse if bit 2 is set.
40592 JR NZ,LaserBeam_Animate_DrawPulse
Count the beam timer down and return until its low bits reach zero.
40594 DEC (IX+6) Decrease the beam timer by one.
40597 LD A,(IX+6) Fetch the beam timer.
40600 AND %00000111 Keep only bits 0-2.
40602 RET NZ Return if the timer is still running.
Fold bits 0-1 of RandomNumber into the beam timer and start this pulse moving.
40603 LD A,(24128) Fetch RandomNumber.
40606 AND %00000011 Keep only bits 0-1.
40608 OR %00000100 Set bit 2.
40610 OR (IX+6) Merge in the beam timer.
40613 LD (IX+6),A Write it back.
40616 LD A,(BC) Fetch this pulse X.
40617 OR %00000100 Set bit 2.
40619 LD (BC),A Write it back.
40620 RET Return.
Move this pulse on and XOR its mask onto the screen.
LaserBeam_Animate_DrawPulse 40621 LD A,(BC) Fetch this pulse X.
40622 LD L,A Copy it into L.
40623 LD A,8 A=8.
40625 BIT 0,L Jump to LaserBeam_Animate_AdvancePulse if bit 0 of the pulse X is reset.
40627 JR Z,LaserBeam_Animate_AdvancePulse
40629 NEG Negate the step.
LaserBeam_Animate_AdvancePulse 40631 ADD A,L Add the step to the pulse X.
40632 LD (BC),A Write the new X back.
Draw this pulse by XORing its mask onto the screen byte.
40633 LD H,D Copy the beam Y into H.
40634 CALL ScreenAddress Call ScreenAddress.
40637 EXX Switch to the shadow registers.
40638 LD A,B Rotate the mask bytes.
40639 LD B,C
40640 LD C,E
40641 EXX Switch back to the main registers.
40642 XOR (HL) Flip the screen pixels that are set in the mask in A, so the pulse is drawn, or erased if it is already there.
40643 LD (HL),A Write it back.
40644 INC BC Move onto the next pulse.
40645 DEC E Decrease the pulse counter by one.
40646 JP NZ,LaserBeam_Animate_Loop Jump back to LaserBeam_Animate_Loop if any pulses remain.
40649 RET Return.
View the equivalent code in;
Prev: 40384 Up: Map Next: 40650