-
Notifications
You must be signed in to change notification settings - Fork 1
/
Copy pathBank $A0.asm
10077 lines (8997 loc) · 484 KB
/
Bank $A0.asm
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
180
181
182
183
184
185
186
187
188
189
190
191
192
193
194
195
196
197
198
199
200
201
202
203
204
205
206
207
208
209
210
211
212
213
214
215
216
217
218
219
220
221
222
223
224
225
226
227
228
229
230
231
232
233
234
235
236
237
238
239
240
241
242
243
244
245
246
247
248
249
250
251
252
253
254
255
256
257
258
259
260
261
262
263
264
265
266
267
268
269
270
271
272
273
274
275
276
277
278
279
280
281
282
283
284
285
286
287
288
289
290
291
292
293
294
295
296
297
298
299
300
301
302
303
304
305
306
307
308
309
310
311
312
313
314
315
316
317
318
319
320
321
322
323
324
325
326
327
328
329
330
331
332
333
334
335
336
337
338
339
340
341
342
343
344
345
346
347
348
349
350
351
352
353
354
355
356
357
358
359
360
361
362
363
364
365
366
367
368
369
370
371
372
373
374
375
376
377
378
379
380
381
382
383
384
385
386
387
388
389
390
391
392
393
394
395
396
397
398
399
400
401
402
403
404
405
406
407
408
409
410
411
412
413
414
415
416
417
418
419
420
421
422
423
424
425
426
427
428
429
430
431
432
433
434
435
436
437
438
439
440
441
442
443
444
445
446
447
448
449
450
451
452
453
454
455
456
457
458
459
460
461
462
463
464
465
466
467
468
469
470
471
472
473
474
475
476
477
478
479
480
481
482
483
484
485
486
487
488
489
490
491
492
493
494
495
496
497
498
499
500
501
502
503
504
505
506
507
508
509
510
511
512
513
514
515
516
517
518
519
520
521
522
523
524
525
526
527
528
529
530
531
532
533
534
535
536
537
538
539
540
541
542
543
544
545
546
547
548
549
550
551
552
553
554
555
556
557
558
559
560
561
562
563
564
565
566
567
568
569
570
571
572
573
574
575
576
577
578
579
580
581
582
583
584
585
586
587
588
589
590
591
592
593
594
595
596
597
598
599
600
601
602
603
604
605
606
607
608
609
610
611
612
613
614
615
616
617
618
619
620
621
622
623
624
625
626
627
628
629
630
631
632
633
634
635
636
637
638
639
640
641
642
643
644
645
646
647
648
649
650
651
652
653
654
655
656
657
658
659
660
661
662
663
664
665
666
667
668
669
670
671
672
673
674
675
676
677
678
679
680
681
682
683
684
685
686
687
688
689
690
691
692
693
694
695
696
697
698
699
700
701
702
703
704
705
706
707
708
709
710
711
712
713
714
715
716
717
718
719
720
721
722
723
724
725
726
727
728
729
730
731
732
733
734
735
736
737
738
739
740
741
742
743
744
745
746
747
748
749
750
751
752
753
754
755
756
757
758
759
760
761
762
763
764
765
766
767
768
769
770
771
772
773
774
775
776
777
778
779
780
781
782
783
784
785
786
787
788
789
790
791
792
793
794
795
796
797
798
799
800
801
802
803
804
805
806
807
808
809
810
811
812
813
814
815
816
817
818
819
820
821
822
823
824
825
826
827
828
829
830
831
832
833
834
835
836
837
838
839
840
841
842
843
844
845
846
847
848
849
850
851
852
853
854
855
856
857
858
859
860
861
862
863
864
865
866
867
868
869
870
871
872
873
874
875
876
877
878
879
880
881
882
883
884
885
886
887
888
889
890
891
892
893
894
895
896
897
898
899
900
901
902
903
904
905
906
907
908
909
910
911
912
913
914
915
916
917
918
919
920
921
922
923
924
925
926
927
928
929
930
931
932
933
934
935
936
937
938
939
940
941
942
943
944
945
946
947
948
949
950
951
952
953
954
955
956
957
958
959
960
961
962
963
964
965
966
967
968
969
970
971
972
973
974
975
976
977
978
979
980
981
982
983
984
985
986
987
988
989
990
991
992
993
994
995
996
997
998
999
1000
;;; General notes ;;;
{
; Loading the game:
; $8A1E - load enemies - at $80:A0CA (start gameplay)
; $8CD7 - initialise enemies and transfer tiles to VRAM - at $82:80C9/80F9/814C (game state 6/1Fh/28h), executed 6 times for 6 frames
; Main gameplay (game state 8):
; $8EB6 - determine which enemies to process
; $9785 - Samus / projectile interaction handler
; $8FD4 - main enemy routine
; $9758 - enemy collision handling
; $C26A - process enemy instructions
; $9423 - add enemy to drawing queue
; $A8F0 - Samus / solid enemy collision detection, executed at least twice
; $9894 - enemy projectile / Samus collision detection
; $996C - enemy projectile / projectile collision detection
; $A306 - process enemy power bomb interaction
; $884D - draw Samus, projectiles, enemies and enemy projectiles
; $944A - write enemy OAM
; $88C4 - execute enemy graphics drawn hook
; $9726 - handle queuing enemy BG2 tilemap VRAM transfer
; $8687 - handle room shaking
; $9169 - decrement Samus hurt timers and clear active enemy indices
; Door transition whilst screen is fading out (game state Ah/Bh):
; $8EB6 - determine which enemies to process
; $8FD4 - main enemy routine
; $884D - draw Samus, enemies and enemy projectiles
; Door transition whilst screen is scrolling (game state Bh):
; Enemy tiles are processed via enemy set data by $82:DFD1 during door transition function $E4A9
; $8A1E - load enemies - at $82:E4A9
; $896F - load enemy set data (just mirrors enemy set into RAM ($7E:D559), debug/pointless)
; $8A6D - clear enemy data and process enemy set
; $8D64 - process enemy set (from ROM directly) (loads enemy palettes and allocates space for tiles ($0E5A, $7E:EF5C))
; $8C6C - load enemy tile data (loads enemy tiles into $7E:7000 from enemy loading data ($0E5A), this data is then DMA'd by $8CD7 (but not $8A9E))
; $8A9E - initialise enemies - at $82:E4A9 (clear enemy tiles ($7E:7000), load enemy population data into enemy data)
; $8BF3 - load enemy GFX indices (determines enemy VRAM tiles index and palette index ($0F98/96 / $7E:7006/08) from enemy set (again, from ROM directly))
; $88D0 - record enemy spawn data (mirrors enemy population data to $7E:701E..39)
; $8BE9 - execute enemy initialisation AI
; Door transition whilst screen is fading in (game state Bh):
; $8EB6 - determine which enemies to process
; $8FD4 - main enemy routine
; $884D - draw Samus, enemies and enemy projectiles
; $9726 - handle queuing enemy BG2 tilemap VRAM transfer
}
;;; $8000..8686: Common to all enemy banks ;;;
{
;;; $8000..45: Common enemy AI ;;;
{
;;; $8000: Grapple AI - no interaction. Also unfreezes enemies(!) ;;;
{
; Used by skultera, Draygon body, fire arc, Phantoon, etecoon, dachora and WS ghost
$A0:8000 22 6D 9F A0 JSL $A09F6D[$A0:9F6D] ; Switch enemy AI to main AI
$A0:8004 6B RTL
}
;;; $8005: Grapple AI - Samus latches on ;;;
{
; Used by gripper and Crocomire
$A0:8005 22 7D 9F A0 JSL $A09F7D[$A0:9F7D] ; Samus latches on with grapple
$A0:8009 6B RTL
}
;;; $800A: Grapple AI - kill enemy ;;;
{
; Common
$A0:800A 22 C4 9F A0 JSL $A09FC4[$A0:9FC4] ; Enemy grapple death
$A0:800E 6B RTL
}
;;; $800F: Grapple AI - cancel grapple beam ;;;
{
; Common
$A0:800F 22 DF 9F A0 JSL $A09FDF[$A0:9FDF] ; Switch to frozen AI
$A0:8013 6B RTL
}
;;; $8014: Grapple AI - Samus latches on - no invincibility ;;;
{
; Used by powamp
$A0:8014 22 E9 9F A0 JSL $A09FE9[$A0:9FE9] ; Samus latches on with grapple - no invincibility
$A0:8018 6B RTL
}
;;; $8019: Unused. Grapple AI - Samus latches on - paralyse enemy ;;;
{
$A0:8019 22 3E A0 A0 JSL $A0A03E[$A0:A03E] ; Samus latches on with grapple - paralyse enemy
$A0:801D 6B RTL
}
;;; $801E: Grapple AI - hurt Samus ;;;
{
; Used by WS spark
; Hurt reaction happens in $9B:B932
$A0:801E 22 70 A0 A0 JSL $A0A070[$A0:A070] ; Switch to frozen AI
$A0:8022 6B RTL
}
;;; $8023: Normal enemy touch AI ;;;
{
$A0:8023 22 77 A4 A0 JSL $A0A477[$A0:A477] ; Normal enemy touch AI
$A0:8027 6B RTL
}
;;; $8028: Normal touch AI - no death check ;;;
{
$A0:8028 22 97 A4 A0 JSL $A0A497[$A0:A497] ; Normal enemy touch AI - no death check
$A0:802C 6B RTL
}
;;; $802D: Normal enemy shot AI ;;;
{
$A0:802D 22 3D A6 A0 JSL $A0A63D[$A0:A63D] ; Normal enemy shot AI
$A0:8031 6B RTL
}
;;; $8032: Normal enemy shot AI - no death check, no enemy shot graphic ;;;
{
$A0:8032 22 A7 A6 A0 JSL $A0A6A7[$A0:A6A7] ; Normal enemy shot AI - no death check, no enemy shot graphic
$A0:8036 6B RTL
}
;;; $8037: Normal enemy power bomb AI ;;;
{
$A0:8037 22 97 A5 A0 JSL $A0A597[$A0:A597] ; Normal enemy power bomb AI
$A0:803B 6B RTL
}
;;; $803C: Normal enemy power bomb AI - no death check ;;;
{
; Kraid's power bomb AI
$A0:803C 22 B7 A5 A0 JSL $A0A5B7[$A0:A5B7] ; Normal enemy power bomb AI - no death check
$A0:8040 6B RTL
}
;;; $8041: Normal enemy frozen AI ;;;
{
$A0:8041 22 7E 95 A0 JSL $A0957E[$A0:957E] ; Normal enemy frozen AI
$A0:8045 6B RTL
}
}
;;; $8046: Creates a dud shot ;;;
{
$A0:8046 22 BC A8 A0 JSL $A0A8BC[$A0:A8BC]
$A0:804A 6B RTL
}
;;; $804B: RTS ;;;
{
$A0:804B 60 RTS
}
;;; $804C: RTL ;;;
{
$A0:804C 6B RTL
}
;;; $804D: Spritemap - nothing ;;;
{
$A0:804D dw 0000
}
;;; $804F: Extended spritemap - nothing ;;;
{
$A0:804F dw 0001, 0000,0000,804D,8059
}
;;; $8059: Hitbox - nothing ;;;
{
; [n entries] [[left offset] [top offset] [right offset] [bottom offset] [p touch] [p shot]]...
$A0:8059 dw 0001, 0000,0000,0000,0000,8023,802D
}
;;; $8067: Instruction list - delete enemy ;;;
{
$A0:8067 dw 807C
}
;;; $8069: Two NOPs ;;;
{
; Used as palette by respawning enemy placeholder and Draygon's eye o_O
$A0:8069 EA NOP
$A0:806A EA NOP
}
;;; $806B..8186: Instructions ;;;
{
;;; $806B: Instruction - enemy $0FB2 = [[Y]] ;;;
{
; Used only by torizos (for enemy movement function) and escape etecoon (for enemy function)
$A0:806B B9 00 00 LDA $0000,y
$A0:806E 9D B2 0F STA $0FB2,x
$A0:8071 C8 INY
$A0:8072 C8 INY
$A0:8073 6B RTL
}
;;; $8074: Instruction - enemy $0FB2 = RTS ;;;
{
$A0:8074 A9 7B 80 LDA #$807B
$A0:8077 9D B2 0F STA $0FB2,x
$A0:807A 6B RTL
$A0:807B 60 RTS
}
;;; $807C: Instruction - delete enemy ;;;
{
$A0:807C BD 86 0F LDA $0F86,x ;\
$A0:807F 09 00 02 ORA #$0200 ;} Mark enemy for deletion
$A0:8082 9D 86 0F STA $0F86,x ;/
$A0:8085 68 PLA ;\
$A0:8086 F4 AE C2 PEA $C2AE ;} Terminate enemy instruction processing
$A0:8089 6B RTL
}
;;; $808A: Instruction - call function [[Y]] ;;;
{
$A0:808A B9 00 00 LDA $0000,y
$A0:808D 85 12 STA $12 [$7E:0012]
$A0:808F 5A PHY
$A0:8090 DA PHX
$A0:8091 F4 96 80 PEA $8096
$A0:8094 6C 12 00 JMP ($0012)
$A0:8097 FA PLX
$A0:8098 7A PLY
$A0:8099 C8 INY
$A0:809A C8 INY
$A0:809B 6B RTL
}
;;; $809C: Instruction - call function [[Y]] with A = [[Y] + 2] ;;;
{
$A0:809C B9 00 00 LDA $0000,y
$A0:809F 85 12 STA $12 [$7E:0012]
$A0:80A1 B9 02 00 LDA $0002,y
$A0:80A4 5A PHY
$A0:80A5 DA PHX
$A0:80A6 F4 AB 80 PEA $80AB
$A0:80A9 6C 12 00 JMP ($0012)
$A0:80AC FA PLX
$A0:80AD 7A PLY
$A0:80AE 98 TYA
$A0:80AF 18 CLC
$A0:80B0 69 04 00 ADC #$0004
$A0:80B3 A8 TAY
$A0:80B4 6B RTL
}
;;; $80B5: Unused. Instruction - call external function [[Y]] ;;;
{
$A0:80B5 B9 00 00 LDA $0000,y
$A0:80B8 85 12 STA $12 [$7E:0012]
$A0:80BA B9 01 00 LDA $0001,y
$A0:80BD 85 13 STA $13 [$7E:0013]
$A0:80BF DA PHX
$A0:80C0 5A PHY
$A0:80C1 22 CB 80 A0 JSL $A080CB[$A0:80CB]
$A0:80C5 7A PLY
$A0:80C6 FA PLX
$A0:80C7 C8 INY
$A0:80C8 C8 INY
$A0:80C9 C8 INY
$A0:80CA 6B RTL
$A0:80CB DC 12 00 JML [$0012]
}
;;; $80CE: Unused. Instruction - call external function [[Y]] with A = [[Y] + 3] ;;;
{
$A0:80CE B9 00 00 LDA $0000,y
$A0:80D1 85 12 STA $12 [$7E:0012]
$A0:80D3 B9 01 00 LDA $0001,y
$A0:80D6 85 13 STA $13 [$7E:0013]
$A0:80D8 B9 03 00 LDA $0003,y
$A0:80DB DA PHX
$A0:80DC 5A PHY
$A0:80DD 22 EA 80 A0 JSL $A080EA[$A0:80EA]
$A0:80E1 7A PLY
$A0:80E2 FA PLX
$A0:80E3 98 TYA
$A0:80E4 18 CLC
$A0:80E5 69 05 00 ADC #$0005
$A0:80E8 A8 TAY
$A0:80E9 6B RTL
$A0:80EA DC 12 00 JML [$0012]
}
;;; $80ED: Instruction - go to [[Y]] ;;;
{
$A0:80ED B9 00 00 LDA $0000,y
$A0:80F0 A8 TAY
$A0:80F1 6B RTL
}
;;; $80F2: Instruction - go to [[Y]] + ±[[Y]] ;;;
{
$A0:80F2 84 12 STY $12 [$7E:0012]
$A0:80F4 88 DEY
$A0:80F5 B9 00 00 LDA $0000,y
$A0:80F8 EB XBA
$A0:80F9 30 05 BMI $05 [$8100]
$A0:80FB 29 FF 00 AND #$00FF
$A0:80FE 80 03 BRA $03 [$8103]
$A0:8100 09 00 FF ORA #$FF00
$A0:8103 18 CLC
$A0:8104 65 12 ADC $12 [$7E:0012]
$A0:8106 A8 TAY
$A0:8107 6B RTL
}
;;; $8108: Instruction - decrement timer and go to [[Y]] if non-zero ;;;
{
$A0:8108 DE 90 0F DEC $0F90,x
$A0:810B D0 E0 BNE $E0 [$80ED]
$A0:810D C8 INY
$A0:810E C8 INY
$A0:810F 6B RTL
}
;;; $8110: Instruction - decrement timer and go to [[Y]] if non-zero ;;;
{
$A0:8110 DE 90 0F DEC $0F90,x
$A0:8113 D0 D8 BNE $D8 [$80ED]
$A0:8115 C8 INY
$A0:8116 C8 INY
$A0:8117 6B RTL
}
;;; $8118: Instruction - decrement timer and go to [Y] + ±[[Y]] if non-zero ;;;
{
$A0:8118 E2 20 SEP #$20
$A0:811A DE 90 0F DEC $0F90,x
$A0:811D C2 20 REP #$20
$A0:811F D0 D1 BNE $D1 [$80F2]
$A0:8121 C8 INY
$A0:8122 6B RTL
}
;;; $8123: Instruction - timer = [[Y]] ;;;
{
$A0:8123 B9 00 00 LDA $0000,y
$A0:8126 9D 90 0F STA $0F90,x
$A0:8129 C8 INY
$A0:812A C8 INY
$A0:812B 6B RTL
}
;;; $812C: Instruction - skip next instruction ;;;
{
$A0:812C C8 INY
$A0:812D C8 INY
$A0:812E 6B RTL
}
;;; $812F: Instruction - sleep ;;;
{
$A0:812F 88 DEY ;\
$A0:8130 88 DEY ;|
$A0:8131 98 TYA ;} Enemy instruction list pointer = [Y] - 2
$A0:8132 9D 92 0F STA $0F92,x ;/
$A0:8135 68 PLA ;\
$A0:8136 F4 AE C2 PEA $C2AE ;} Terminate enemy instruction processing
$A0:8139 6B RTL
}
;;; $813A: Instruction - wait [[Y]] frames ;;;
{
; Set instruction timer and terminate processing enemy instructions
; Used for running a delay that doesn't update graphics,
; useful for e.g. GT eye beam attack ($AA:D10D), implemented by an instruction list that has no graphical instructions,
; which allows it to be called from multiple different poses
$A0:813A B9 00 00 LDA $0000,y ;\
$A0:813D 9D 94 0F STA $0F94,x ;} Enemy instruction list timer = [[Y]]
$A0:8140 C8 INY ;\
$A0:8141 C8 INY ;|
$A0:8142 98 TYA ;} Enemy instruction list pointer = [Y] + 2
$A0:8143 9D 92 0F STA $0F92,x ;/
$A0:8146 68 PLA ;\
$A0:8147 F4 AE C2 PEA $C2AE ;} Terminate enemy instruction processing
$A0:814A 6B RTL
}
;;; $814B: Instruction - transfer [[Y]] bytes from [[Y] + 2] to VRAM [[Y] + 5] ;;;
{
$A0:814B DA PHX
$A0:814C AE 30 03 LDX $0330 [$7E:0330]
$A0:814F B9 00 00 LDA $0000,y
$A0:8152 95 D0 STA $D0,x
$A0:8154 B9 02 00 LDA $0002,y
$A0:8157 95 D2 STA $D2,x
$A0:8159 B9 03 00 LDA $0003,y
$A0:815C 95 D3 STA $D3,x
$A0:815E B9 05 00 LDA $0005,y
$A0:8161 95 D5 STA $D5,x
$A0:8163 8A TXA
$A0:8164 18 CLC
$A0:8165 69 07 00 ADC #$0007
$A0:8168 8D 30 03 STA $0330 [$7E:0330]
$A0:816B 98 TYA
$A0:816C 18 CLC
$A0:816D 69 07 00 ADC #$0007
$A0:8170 A8 TAY
$A0:8171 FA PLX
$A0:8172 6B RTL
}
;;; $8173: Instruction - enable off-screen processing ;;;
{
$A0:8173 BD 86 0F LDA $0F86,x
$A0:8176 09 00 08 ORA #$0800
$A0:8179 9D 86 0F STA $0F86,x
$A0:817C 6B RTL
}
;;; $817D: Instruction - disable off-screen processing ;;;
{
$A0:817D BD 86 0F LDA $0F86,x
$A0:8180 29 FF F7 AND #$F7FF
$A0:8183 9D 86 0F STA $0F86,x
$A0:8186 6B RTL
}
}
;;; $8187: Common enemy speeds - linearly increasing ;;;
{
; Speed, subspeed, negated speed, negated subspeed
$A0:8187 dw 0000,0000,0000,0000, 0000,1000,FFFF,F000, 0000,2000,FFFF,E000, 0000,3000,FFFF,D000,
0000,4000,FFFF,C000, 0000,5000,FFFF,B000, 0000,6000,FFFF,A000, 0000,7000,FFFF,9000,
0000,8000,FFFF,8000, 0000,9000,FFFF,7000, 0000,A000,FFFF,6000, 0000,B000,FFFF,5000,
0000,C000,FFFF,4000, 0000,D000,FFFF,3000, 0000,E000,FFFF,2000, 0000,F000,FFFF,1000,
0001,0000,FFFF,0000, 0001,1000,FFFE,F000, 0001,2000,FFFE,E000, 0001,3000,FFFE,D000,
0001,4000,FFFE,C000, 0001,5000,FFFE,B000, 0001,6000,FFFE,A000, 0001,7000,FFFE,9000,
0001,8000,FFFE,8000, 0001,9000,FFFE,7000, 0001,A000,FFFE,6000, 0001,B000,FFFE,5000,
0001,C000,FFFE,4000, 0001,D000,FFFE,3000, 0001,E000,FFFE,2000, 0001,F000,FFFE,1000,
0002,0000,FFFE,0000, 0002,1000,FFFD,F000, 0002,2000,FFFD,E000, 0002,3000,FFFD,D000,
0002,4000,FFFD,C000, 0002,5000,FFFD,B000, 0002,6000,FFFD,A000, 0002,7000,FFFD,9000,
0002,8000,FFFD,8000, 0002,9000,FFFD,7000, 0002,A000,FFFD,6000, 0002,B000,FFFD,5000,
0002,C000,FFFD,4000, 0002,D000,FFFD,3000, 0002,E000,FFFD,2000, 0002,F000,FFFD,1000,
0003,0000,FFFD,0000, 0003,1000,FFFC,F000, 0003,2000,FFFC,E000, 0003,3000,FFFC,D000,
0003,4000,FFFC,C000, 0003,5000,FFFC,B000, 0003,6000,FFFC,A000, 0003,7000,FFFC,9000,
0003,8000,FFFC,8000, 0003,9000,FFFC,7000, 0003,A000,FFFC,6000, 0003,B000,FFFC,5000,
0003,C000,FFFC,4000, 0003,D000,FFFC,3000, 0003,E000,FFFC,2000, 0003,F000,FFFC,1000,
0004,0000,FFFC,0000
}
;;; $838F: Common enemy speeds - quadratically increasing ;;;
{
; I.e. gravity
; Used by e.g. Botwoon when dying and falling to the floor
; Subspeed, speed, negated subspeed, negated speed
$A0:838F dw 0000,0000,0000,0000, 0109,0000,FEF7,FFFF, 031B,0000,FCE5,FFFF, 0636,0000,F9CA,FFFF,
0A5A,0000,F5A6,FFFF, 0F87,0000,F079,FFFF, 15BD,0000,EA43,FFFF, 1CFC,0000,E304,FFFF,
2544,0000,DABC,FFFF, 2E95,0000,D16B,FFFF, 38EF,0000,C711,FFFF, 4452,0000,BBAE,FFFF,
50BE,0000,AF42,FFFF, 5E33,0000,A1CD,FFFF, 6CB1,0000,934F,FFFF, 7C38,0000,83C8,FFFF,
8CC8,0000,7338,FFFF, 9E61,0000,619F,FFFF, B103,0000,4EFD,FFFF, C4AE,0000,3B52,FFFF,
D962,0000,269E,FFFF, EF1F,0000,10E1,FFFF, 05E5,0000,FA1B,FFFF, 14B4,0001,EB4C,FFFE,
2D8C,0001,D274,FFFE, 476D,0001,B893,FFFE, 6257,0001,9DA9,FFFE, 7E4A,0001,81B6,FFFE,
9B46,0001,64BA,FFFE, B94B,0001,46B5,FFFE, D859,0001,27A7,FFFE, F870,0001,0790,FFFE,
1090,0002,EF70,FFFD, 32B9,0002,CD47,FFFD, 55EB,0002,AA15,FFFD, 7A26,0002,85DA,FFFD,
9F6A,0002,6096,FFFD, C5B7,0002,3A49,FFFD, ED0D,0002,12F3,FFFD, 0C6C,0003,F394,FFFC,
35D4,0003,CA2C,FFFC, 6045,0003,9FBB,FFFC, 8BBF,0003,7441,FFFC, B842,0003,47BE,FFFC,
E5CE,0003,1A32,FFFC, 0B63,0004,F49D,FFFB, 3B01,0004,C4FF,FFFB, 6BA8,0004,9458,FFFB,
9D58,0004,62A8,FFFB, D011,0004,2FEF,FFFB, 03D3,0004,FC2D,FFFB, 2F9E,0005,D062,FFFA,
6572,0005,9A8E,FFFA, 9C4F,0005,63B1,FFFA, D435,0005,2BCB,FFFA, 0424,0006,FBDC,FFF9,
3E1C,0006,C1E4,FFF9, 791D,0006,86E3,FFF9, B527,0006,4AD9,FFF9, F23A,0006,0DC6,FFF9,
2756,0007,D8AA,FFF8, 667B,0007,9985,FFF8, A6A9,0007,5957,FFF8, E7E0,0007,1820,FFF8,
2120,0008,DEE0,FFF7, 6469,0008,9B97,FFF7, A8BB,0008,5745,FFF7, EE16,0008,11EA,FFF7,
2B7A,0009,D486,FFF6, 72E7,0009,8D19,FFF6, BB5D,0009,44A3,FFF6, 04DC,0009,FB24,FFF6,
4664,000A,B99C,FFF5, 91F5,000A,6E0B,FFF5, DE8F,000A,2171,FFF5, 2332,000B,DCCE,FFF4,
71DE,000B,8E22,FFF4, C193,000B,3E6D,FFF4, 0951,000C,F6AF,FFF3, 5B18,000C,A4E8,FFF3,
ADE8,000C,5218,FFF3, 01C1,000C,FE3F,FFF3, 4DA3,000D,B25D,FFF2, A38E,000D,5C72,FFF2,
FA82,000D,057E,FFF2, 497F,000E,B681,FFF1, A285,000E,5D7B,FFF1, FC94,000E,036C,FFF1,
4EAC,000F,B154,FFF0, AACD,000F,5533,FFF0, 07F7,000F,F809,FFF0, 5D2A,0010,A2D6,FFEF,
BC66,0010,439A,FFEF, 13AB,0011,EC55,FFEE, 74F9,0011,8B07,FFEE
}
}
;;; $8687..884C: Room shaking ;;;
{
;;; $8687: Handle room shaking ;;;
{
; Enemy projectile shaking is handled by $86:8427
$A0:8687 8B PHB
$A0:8688 F4 00 A0 PEA $A000 ;\
$A0:868B AB PLB ;} DB = $A0
$A0:868C AB PLB ;/
$A0:868D C2 30 REP #$30
$A0:868F AD 40 18 LDA $1840 [$7E:1840] ;\
$A0:8692 F0 79 BEQ $79 [$870D] ;} If [earthquake timer] = 0: go to BRANCH_RETURN
$A0:8694 AD 78 0A LDA $0A78 [$7E:0A78] ;\
$A0:8697 D0 74 BNE $74 [$870D] ;} If time is frozen: go to BRANCH_RETURN
$A0:8699 AD 3E 18 LDA $183E [$7E:183E] ;\
$A0:869C C9 24 00 CMP #$0024 ;} If [earthquake type] >= 24h: go to BRANCH_RETURN
$A0:869F 10 6C BPL $6C [$870D] ;/
$A0:86A1 0A ASL A ;\
$A0:86A2 0A ASL A ;|
$A0:86A3 0A ASL A ;} X = [earthquake type] * 8
$A0:86A4 AA TAX ;/
$A0:86A5 AD 40 18 LDA $1840 [$7E:1840] ;\
$A0:86A8 89 02 00 BIT #$0002 ;} If [earthquake timer] / 2 % 2 != 0:
$A0:86AB F0 32 BEQ $32 [$86DF] ;/
$A0:86AD BD 2D 87 LDA $872D,x[$A0:8845] ;\
$A0:86B0 49 FF FF EOR #$FFFF ;|
$A0:86B3 1A INC A ;|
$A0:86B4 18 CLC ;} BG1 X scroll -= [$872D + [X]]
$A0:86B5 65 B1 ADC $B1 [$7E:00B1] ;|
$A0:86B7 85 B1 STA $B1 [$7E:00B1] ;/
$A0:86B9 BD 2F 87 LDA $872F,x[$A0:8847] ;\
$A0:86BC 49 FF FF EOR #$FFFF ;|
$A0:86BF 1A INC A ;|
$A0:86C0 18 CLC ;} BG1 Y scroll -= [$872D + [X] + 2]
$A0:86C1 65 B3 ADC $B3 [$7E:00B3] ;|
$A0:86C3 85 B3 STA $B3 [$7E:00B3] ;/
$A0:86C5 BD 31 87 LDA $8731,x[$A0:8849] ;\
$A0:86C8 49 FF FF EOR #$FFFF ;|
$A0:86CB 1A INC A ;|
$A0:86CC 18 CLC ;} BG2 X scroll -= [$872D + [X] + 4]
$A0:86CD 65 B5 ADC $B5 [$7E:00B5] ;|
$A0:86CF 85 B5 STA $B5 [$7E:00B5] ;/
$A0:86D1 BD 33 87 LDA $8733,x[$A0:884B] ;\
$A0:86D4 49 FF FF EOR #$FFFF ;|
$A0:86D7 1A INC A ;|
$A0:86D8 18 CLC ;} BG2 Y scroll -= [$872D + [X] + 6]
$A0:86D9 65 B7 ADC $B7 [$7E:00B7] ;|
$A0:86DB 85 B7 STA $B7 [$7E:00B7] ;/
$A0:86DD 80 20 BRA $20 [$86FF]
$A0:86DF A5 B1 LDA $B1 [$7E:00B1] ;\ Else ([earthquake timer] / 2 % 2 = 0):
$A0:86E1 18 CLC ;|
$A0:86E2 7D 2D 87 ADC $872D,x[$A0:8845] ;} BG1 X scroll += [$872D + [X]]
$A0:86E5 85 B1 STA $B1 [$7E:00B1] ;/
$A0:86E7 A5 B3 LDA $B3 [$7E:00B3] ;\
$A0:86E9 18 CLC ;|
$A0:86EA 7D 2F 87 ADC $872F,x[$A0:8847] ;} BG1 Y scroll += [$872D + [X] + 2]
$A0:86ED 85 B3 STA $B3 [$7E:00B3] ;/
$A0:86EF A5 B5 LDA $B5 [$7E:00B5] ;\
$A0:86F1 18 CLC ;|
$A0:86F2 7D 31 87 ADC $8731,x[$A0:8849] ;} BG2 X scroll += [$872D + [X] + 4]
$A0:86F5 85 B5 STA $B5 [$7E:00B5] ;/
$A0:86F7 A5 B7 LDA $B7 [$7E:00B7] ;\
$A0:86F9 18 CLC ;|
$A0:86FA 7D 33 87 ADC $8733,x[$A0:884B] ;} BG2 Y scroll += [$872D + [X] + 6]
$A0:86FD 85 B7 STA $B7 [$7E:00B7] ;/
$A0:86FF CE 40 18 DEC $1840 [$7E:1840] ; Decrement earthquake timer
$A0:8702 AD 3E 18 LDA $183E [$7E:183E] ;\
$A0:8705 C9 12 00 CMP #$0012 ;} If [earthquake type] >= 12h:
$A0:8708 30 03 BMI $03 [$870D] ;/
$A0:870A 20 12 87 JSR $8712 [$A0:8712] ; Set all active enemies to shake horizontally for two frames
; BRANCH_RETURN
$A0:870D EE 42 18 INC $1842 [$7E:1842] ; Increment $1842 (never read)
$A0:8710 AB PLB
$A0:8711 6B RTL
}
;;; $8712: Set all active enemies to shake horizontally for two frames ;;;
{
$A0:8712 5A PHY
$A0:8713 DA PHX
$A0:8714 A0 00 00 LDY #$0000 ; Y = 0 (active enemy indices index)
; LOOP
$A0:8717 B9 AC 17 LDA $17AC,y[$7E:17AC] ;\
$A0:871A C9 FF FF CMP #$FFFF ;} If [active enemy index] != FFFFh:
$A0:871D F0 0B BEQ $0B [$872A] ;/
$A0:871F AA TAX ; X = [active enemy index] (enemy index)
$A0:8720 A9 02 00 LDA #$0002 ;\
$A0:8723 9D A2 0F STA $0FA2,x[$7E:0FA2] ;} Enemy shake timer = 2
$A0:8726 C8 INY ;\
$A0:8727 C8 INY ;} Y += 2
$A0:8728 80 ED BRA $ED [$8717] ; Go to LOOP
$A0:872A FA PLX
$A0:872B 7A PLY
$A0:872C 60 RTS
}
;;; $872D: BG shake displacements ;;;
{
; Enemy projectile shaking displacements are at $86:846B
; /----horizontal---\ /-----vertical----\ /-----diagonal----\
; BG1X BG1Y BG2X BG2Y
$A0:872D dw 0001,0000,0000,0000, 0000,0001,0000,0000, 0001,0001,0000,0000, ;\
0002,0000,0000,0000, 0000,0002,0000,0000, 0002,0002,0000,0000, ;} BG1 only
0003,0000,0000,0000, 0000,0003,0000,0000, 0003,0003,0000,0000, ;/
0001,0000,0001,0000, 0000,0001,0000,0001, 0001,0001,0001,0001, ;\
0002,0000,0002,0000, 0000,0002,0000,0002, 0002,0002,0002,0002, ;} BG1 and BG2
0003,0000,0003,0000, 0000,0003,0000,0003, 0003,0003,0003,0003, ;/
0001,0000,0001,0000, 0000,0001,0000,0001, 0001,0001,0001,0001, ;\
0002,0000,0002,0000, 0000,0002,0000,0002, 0002,0002,0002,0002, ;} BG1 and BG2 and enemies
0003,0000,0003,0000, 0000,0003,0000,0003, 0003,0003,0003,0003, ;/
0000,0000,0001,0000, 0000,0000,0000,0001, 0000,0000,0001,0001, ;\
0000,0000,0002,0000, 0000,0000,0000,0002, 0000,0000,0002,0002, ;} BG2 only and enemies
0000,0000,0003,0000, 0000,0000,0000,0003, 0000,0000,0003,0003 ;/
}
}
;;; $884D: Draw Samus, projectiles, enemies and enemy projectiles ;;;
{
$A0:884D 8B PHB
$A0:884E F4 00 A0 PEA $A000 ;\
$A0:8851 AB PLB ;} DB = $A0
$A0:8852 AB PLB ;/
$A0:8853 C2 30 REP #$30
$A0:8855 22 32 BD B4 JSL $B4BD32[$B4:BD32] ; Draw sprite objects
$A0:8859 22 4D 83 93 JSL $93834D[$93:834D] ; Draw bombs and projectile explosions
$A0:885D 22 90 83 86 JSL $868390[$86:8390] ; Draw high priority enemy projectiles
$A0:8861 9C 32 0E STZ $0E32 [$7E:0E32] ; Enemy layer = 0
; LOOP_MAIN
$A0:8864 AD 32 0E LDA $0E32 [$7E:0E32] ;\
$A0:8867 C9 08 00 CMP #$0008 ;} If [enemy layer] = 8: go to BRANCH_FINISH
$A0:886A F0 50 BEQ $50 [$88BC] ;/
$A0:886C C9 03 00 CMP #$0003 ;\
$A0:886F D0 06 BNE $06 [$8877] ;} If [enemy layer] = 3:
$A0:8871 22 35 EB 90 JSL $90EB35[$90:EB35] ; Draw Samus and projectiles
$A0:8875 80 09 BRA $09 [$8880]
$A0:8877 C9 06 00 CMP #$0006 ;\ Else ([enemy layer] != 3):
$A0:887A D0 04 BNE $04 [$8880] ;} If [enemy layer] = 6:
$A0:887C 22 B2 83 86 JSL $8683B2[$86:83B2] ; Draw low priority enemy projectiles
$A0:8880 AD 32 0E LDA $0E32 [$7E:0E32] ;\
$A0:8883 0A ASL A ;} Y = [enemy layer] * 2
$A0:8884 A8 TAY ;/
$A0:8885 B9 68 0F LDA $0F68,y[$7E:0F68] ; A = [enemy drawing queue size]
$A0:8888 F0 2D BEQ $2D [$88B7] ; If [enemy drawing queue size] = 0: go to BRANCH_NEXT
$A0:888A 8D 36 0E STA $0E36 [$7E:0E36] ; Enemy drawing queue size backup = [enemy drawing queue size]
$A0:888D B9 33 B1 LDA $B133,y[$A0:B137] ;\
$A0:8890 8D 3A 0E STA $0E3A [$7E:0E3A] ;} Enemy drawing queue address = [$B133 + [enemy layer] * 2]
$A0:8893 A9 00 00 LDA #$0000 ; A = 0
$A0:8896 99 68 0F STA $0F68,y[$7E:0F6C] ; Enemy drawing queue size = 0
; LOOP_OAM
$A0:8899 8D 38 0E STA $0E38 [$7E:0E38] ; Enemy drawing queue index = [A]
$A0:889C 18 CLC ;\
$A0:889D 6D 3A 0E ADC $0E3A [$7E:0E3A] ;} X = [enemy drawing queue address] + [enemy drawing queue index]
$A0:88A0 AA TAX ;/
$A0:88A1 BD 00 00 LDA $0000,x[$7E:0EA6] ;\
$A0:88A4 9E 00 00 STZ $0000,x[$7E:0EA6] ;} Enemy index = [[X]], [X] = 0
$A0:88A7 8D 54 0E STA $0E54 [$7E:0E54] ;/
$A0:88AA 20 4A 94 JSR $944A [$A0:944A] ; Write enemy OAM
$A0:88AD AD 38 0E LDA $0E38 [$7E:0E38] ;\
$A0:88B0 1A INC A ;} A = [enemy drawing queue index] + 2
$A0:88B1 1A INC A ;/
$A0:88B2 CD 36 0E CMP $0E36 [$7E:0E36] ;\
$A0:88B5 D0 E2 BNE $E2 [$8899] ;} If [A] != [enemy drawing queue size]: go to LOOP_OAM
; BRANCH_NEXT
$A0:88B7 EE 32 0E INC $0E32 [$7E:0E32] ; Increment enemy layer
$A0:88BA 80 A8 BRA $A8 [$8864] ; Go to LOOP_MAIN
; BRANCH_FINISH
$A0:88BC 8B PHB
$A0:88BD 22 C4 88 A0 JSL $A088C4[$A0:88C4] ; Execute enemy graphics drawn hook
$A0:88C1 AB PLB
$A0:88C2 80 0A BRA $0A [$88CE] ; Return
$A0:88C4 AD 8E 17 LDA $178E [$7E:178E]
$A0:88C7 EB XBA
$A0:88C8 48 PHA
$A0:88C9 AB PLB
$A0:88CA AB PLB
$A0:88CB DC 8C 17 JML [$178C][$A0:804C]
$A0:88CE AB PLB
$A0:88CF 6B RTL
}
;;; $88D0..8EB5: Enemy loading ;;;
{
;;; $88D0: Record enemy spawn data ;;;
{
;; Parameters:
;; Y: Enemy index
; Used almost exclusively by debug enemy spawner. Rinka uses X/Y position
$A0:88D0 DA PHX
$A0:88D1 5A PHY
$A0:88D2 BB TYX
$A0:88D3 BD 78 0F LDA $0F78,x[$7E:0F78] ;\
$A0:88D6 9F 1E 70 7E STA $7E701E,x[$7E:701E];} $7E:701E + [Y] = [enemy ID]
$A0:88DA BD 7A 0F LDA $0F7A,x[$7E:0F7A] ;\
$A0:88DD 9F 20 70 7E STA $7E7020,x[$7E:7020];} $7E:7020 + [Y] = [enemy X position]
$A0:88E1 BD 7E 0F LDA $0F7E,x[$7E:0F7E] ;\
$A0:88E4 9F 22 70 7E STA $7E7022,x[$7E:7022];} $7E:7022 + [Y] = [enemy Y position]
$A0:88E8 BD 92 0F LDA $0F92,x[$7E:0F92] ;\
$A0:88EB 9F 24 70 7E STA $7E7024,x[$7E:7024];} $7E:7024 + [Y] = [enemy initialisation parameter]
$A0:88EF BD 86 0F LDA $0F86,x[$7E:0F86] ;\
$A0:88F2 9F 26 70 7E STA $7E7026,x[$7E:7026];} $7E:7026 + [Y] = [enemy properties]
$A0:88F6 BD 88 0F LDA $0F88,x[$7E:0F88] ;\
$A0:88F9 9F 28 70 7E STA $7E7028,x[$7E:7028];} $7E:7028 + [Y] = [enemy extra properties]
$A0:88FD BD B4 0F LDA $0FB4,x[$7E:0FB4] ;\
$A0:8900 9F 2A 70 7E STA $7E702A,x[$7E:702A];} $7E:702A + [Y] = [enemy parameter 1]
$A0:8904 BD B6 0F LDA $0FB6,x[$7E:0FB6] ;\
$A0:8907 9F 2C 70 7E STA $7E702C,x[$7E:702C];} $7E:702C + [Y] = [enemy parameter 2]
$A0:890B 64 12 STZ $12 [$7E:0012] ;\
$A0:890D 64 14 STZ $14 [$7E:0014] ;|
$A0:890F 64 16 STZ $16 [$7E:0016] ;|
$A0:8911 64 18 STZ $18 [$7E:0018] ;|
$A0:8913 64 1A STZ $1A [$7E:001A] ;|
$A0:8915 64 1C STZ $1C [$7E:001C] ;|
$A0:8917 DA PHX ;|
$A0:8918 BD 78 0F LDA $0F78,x[$7E:0F78] ;|
$A0:891B AA TAX ;|
$A0:891C BF 3E 00 A0 LDA $A0003E,x[$A0:E27D];|
$A0:8920 F0 25 BEQ $25 [$8947] ;|
$A0:8922 AA TAX ;|
$A0:8923 BF 00 00 B4 LDA $B40000,x[$B4:E0D1];|
$A0:8927 85 12 STA $12 [$7E:0012] ;|
$A0:8929 BF 02 00 B4 LDA $B40002,x[$B4:E0D3];|
$A0:892D 85 14 STA $14 [$7E:0014] ;|
$A0:892F BF 04 00 B4 LDA $B40004,x[$B4:E0D5];|
$A0:8933 85 16 STA $16 [$7E:0016] ;|
$A0:8935 BF 06 00 B4 LDA $B40006,x[$B4:E0D7];|
$A0:8939 85 18 STA $18 [$7E:0018] ;} Copy Ch bytes from (enemy name) to $7E:702E + [Y]
$A0:893B BF 08 00 B4 LDA $B40008,x[$B4:E0D9];|
$A0:893F 85 1A STA $1A [$7E:001A] ;|
$A0:8941 BF 0C 00 B4 LDA $B4000C,x[$B4:E0DD];|
$A0:8945 85 1C STA $1C [$7E:001C] ;|
;|
$A0:8947 FA PLX ;|
$A0:8948 A5 12 LDA $12 [$7E:0012] ;|
$A0:894A 9F 2E 70 7E STA $7E702E,x[$7E:702E];|
$A0:894E A5 14 LDA $14 [$7E:0014] ;|
$A0:8950 9F 30 70 7E STA $7E7030,x[$7E:7030];|
$A0:8954 A5 16 LDA $16 [$7E:0016] ;|
$A0:8956 9F 32 70 7E STA $7E7032,x[$7E:7032];|
$A0:895A A5 18 LDA $18 [$7E:0018] ;|
$A0:895C 9F 34 70 7E STA $7E7034,x[$7E:7034];|
$A0:8960 A5 1A LDA $1A [$7E:001A] ;|
$A0:8962 9F 36 70 7E STA $7E7036,x[$7E:7036];|
$A0:8966 A5 1C LDA $1C [$7E:001C] ;|
$A0:8968 9F 38 70 7E STA $7E7038,x[$7E:7038];/
$A0:896C 7A PLY
$A0:896D FA PLX
$A0:896E 6B RTL
}
;;; $896F: Debug. Load enemy set data ;;;
{
; This enemy set data is never used, not even by the enemy debugger. This routine serves no purpose
$A0:896F A9 00 00 LDA #$0000 ;\
$A0:8972 A2 00 00 LDX #$0000 ;|
$A0:8975 A0 A0 00 LDY #$00A0 ;|
;|
$A0:8978 9F 52 D5 7E STA $7ED552,x[$7E:D552];|
$A0:897C E8 INX ;} $7E:D552..F1 = 0
$A0:897D E8 INX ;|
$A0:897E 88 DEY ;|
$A0:897F 88 DEY ;|
$A0:8980 D0 F6 BNE $F6 [$8978] ;/
$A0:8982 AD D1 07 LDA $07D1 [$7E:07D1] ;\
$A0:8985 38 SEC ;|
$A0:8986 E9 07 00 SBC #$0007 ;} X = [enemies allowed pointer] - 7
$A0:8989 AA TAX ;/
$A0:898A BF 00 00 B4 LDA $B40000,x[$B4:9211];\
$A0:898E 8F 52 D5 7E STA $7ED552[$7E:D552] ;|
$A0:8992 BF 02 00 B4 LDA $B40002,x[$B4:9213];|
$A0:8996 8F 54 D5 7E STA $7ED554[$7E:D554] ;|
$A0:899A BF 04 00 B4 LDA $B40004,x[$B4:9215];} Enemy set name = 8 bytes from $B4:0000 + [X] (harmless one byte overflow)
$A0:899E 8F 56 D5 7E STA $7ED556[$7E:D556] ;|
$A0:89A2 BF 06 00 B4 LDA $B40006,x[$B4:9217];|
$A0:89A6 8F 58 D5 7E STA $7ED558[$7E:D558] ;/
$A0:89AA A0 07 00 LDY #$0007 ; Y = 7 (working enemy set data index)
$A0:89AD AD D1 07 LDA $07D1 [$7E:07D1] ;\
$A0:89B0 AA TAX ;} X = [enemies set pointer] (enemies set entry)
; LOOP
$A0:89B1 BF 00 00 B4 LDA $B40000,x[$B4:9218]; A = [$B4:0000 + [X]] (enemy ID)
$A0:89B5 C9 FF FF CMP #$FFFF ;\
$A0:89B8 F0 63 BEQ $63 [$8A1D] ;} If enemy ID = FFFFh: return
$A0:89BA DA PHX
$A0:89BB AA TAX ;\
$A0:89BC BF 3E 00 A0 LDA $A0003E,x[$A0:E27D];} A = [$A0:003E + [A]] (enemy set entry name)
$A0:89C0 D0 03 BNE $03 [$89C5] ; If enemy set entry name = 0:
$A0:89C2 A9 89 DD LDA #$DD89 ; Enemy set entry name = $DD89 ("NODATA ")
$A0:89C5 AA TAX ;\
$A0:89C6 BF 00 00 B4 LDA $B40000,x[$B4:DD89];|
$A0:89CA 85 12 STA $12 [$7E:0012] ;|
$A0:89CC BF 02 00 B4 LDA $B40002,x[$B4:DD8B];|
$A0:89D0 85 14 STA $14 [$7E:0014] ;|
$A0:89D2 BF 04 00 B4 LDA $B40004,x[$B4:DD8D];|
$A0:89D6 85 16 STA $16 [$7E:0016] ;|
$A0:89D8 BF 06 00 B4 LDA $B40006,x[$B4:DD8F];|
$A0:89DC 85 18 STA $18 [$7E:0018] ;|
$A0:89DE BF 08 00 B4 LDA $B40008,x[$B4:DD91];|
$A0:89E2 85 1A STA $1A [$7E:001A] ;|
$A0:89E4 BB TYX ;} Enemy name = [enemy set entry name] (Ah bytes)
$A0:89E5 A5 12 LDA $12 [$7E:0012] ;|
$A0:89E7 9F 52 D5 7E STA $7ED552,x[$7E:D559];|
$A0:89EB A5 14 LDA $14 [$7E:0014] ;|
$A0:89ED 9F 54 D5 7E STA $7ED554,x[$7E:D55B];|
$A0:89F1 A5 16 LDA $16 [$7E:0016] ;|
$A0:89F3 9F 56 D5 7E STA $7ED556,x[$7E:D55D];|
$A0:89F7 A5 18 LDA $18 [$7E:0018] ;|
$A0:89F9 9F 58 D5 7E STA $7ED558,x[$7E:D55F];|
$A0:89FD A5 1A LDA $1A [$7E:001A] ;|
$A0:89FF 9F 5A D5 7E STA $7ED55A,x[$7E:D561];/
$A0:8A03 FA PLX
$A0:8A04 DA PHX
$A0:8A05 BF 02 00 B4 LDA $B40002,x[$B4:921A];\
$A0:8A09 BB TYX ;} Enemy palette index = [enemy set entry palette index]
$A0:8A0A 9F 5C D5 7E STA $7ED55C,x[$7E:D563];/
$A0:8A0E FA PLX
$A0:8A0F 98 TYA ;\
$A0:8A10 18 CLC ;|
$A0:8A11 69 0C 00 ADC #$000C ;} Y += Ch (next working enemy set entry)
$A0:8A14 A8 TAY ;/
$A0:8A15 8A TXA ;\
$A0:8A16 18 CLC ;|
$A0:8A17 69 04 00 ADC #$0004 ;} X += 4 (next enemies set entry)
$A0:8A1A AA TAX ;/
$A0:8A1B 80 94 BRA $94 [$89B1] ; Go to LOOP
$A0:8A1D 6B RTL
}
;;; $8A1E: Load enemies (load and process enemy set, clear enemy data, load enemy tile data) ;;;
{
; Called when loading the game, and during door transition
; This routine loads enemy tile data, which during door transition has already loaded by $82:DFD1, making the call to $8C6C a fairly hefty waste of time
; Aside from loading tile data, this routine also loads palette data, and the enemy GFX data needed for respawn
$A0:8A1E 08 PHP
$A0:8A1F 8B PHB
$A0:8A20 F4 00 A0 PEA $A000 ;\
$A0:8A23 AB PLB ;} DB = $A0
$A0:8A24 AB PLB ;/
$A0:8A25 C2 30 REP #$30
$A0:8A27 22 6F 89 A0 JSL $A0896F[$A0:896F] ; Debug. Load enemy set data
$A0:8A2B 9C 5E 18 STZ $185E [$7E:185E] ; Enemy time is frozen flag = 0
$A0:8A2E 9C 9C 17 STZ $179C [$7E:179C] ; Boss number = 0
$A0:8A31 A9 A0 00 LDA #$00A0 ;\
$A0:8A34 8D 8E 17 STA $178E [$7E:178E] ;|
$A0:8A37 A9 4C 80 LDA #$804C ;} Enemy graphics drawn hook = RTL
$A0:8A3A 8D 8C 17 STA $178C [$7E:178C] ;/
$A0:8A3D A9 A0 00 LDA #$00A0 ;\
$A0:8A40 8D 92 17 STA $1792 [$7E:1792] ;|
$A0:8A43 A9 4C 80 LDA #$804C ;} $1790 = RTL
$A0:8A46 8D 90 17 STA $1790 [$7E:1790] ;/
$A0:8A49 A9 00 08 LDA #$0800 ;\
$A0:8A4C 8D 9A 17 STA $179A [$7E:179A] ;} Enemy BG2 tilemap size = 800h
$A0:8A4F 9C 9E 17 STZ $179E [$7E:179E] ; $179E = 0
$A0:8A52 9C A0 17 STZ $17A0 [$7E:17A0] ; $17A0 = 0
$A0:8A55 9C 9C 17 STZ $179C [$7E:179C] ; Boss number = 0 (again)
$A0:8A58 22 6D 8A A0 JSL $A08A6D[$A0:8A6D] ; Clear enemy data and process enemy set
$A0:8A5C 22 6C 8C A0 JSL $A08C6C[$A0:8C6C] ; Load enemy tile data
$A0:8A60 9C 7C 0E STZ $0E7C [$7E:0E7C] ; Enemy tiles VRAM update source address = 0
$A0:8A63 9C AE 18 STZ $18AE [$7E:18AE] ; Enable Samus / projectile interaction
$A0:8A66 22 97 BD B4 JSL $B4BD97[$B4:BD97] ; Clear sprite objects
$A0:8A6A AB PLB
$A0:8A6B 28 PLP
$A0:8A6C 6B RTL
}
;;; $8A6D: Clear enemy data and process enemy set ;;;
{
$A0:8A6D 08 PHP
$A0:8A6E 8B PHB
$A0:8A6F F4 00 A0 PEA $A000 ;\
$A0:8A72 AB PLB ;} DB = $A0
$A0:8A73 AB PLB ;/
$A0:8A74 C2 30 REP #$30
$A0:8A76 A9 00 00 LDA #$0000 ;\
$A0:8A79 A0 00 08 LDY #$0800 ;|
$A0:8A7C A2 00 00 LDX #$0000 ;|
;|
$A0:8A7F 9F 78 0F 00 STA $000F78,x[$7E:0F78];|
$A0:8A83 E8 INX ;} Clear enemy data
$A0:8A84 88 DEY ;|
$A0:8A85 E8 INX ;|
$A0:8A86 88 DEY ;|
$A0:8A87 D0 F6 BNE $F6 [$8A7F] ;/
$A0:8A89 AE CF 07 LDX $07CF [$7E:07CF] ;\
$A0:8A8C BF 00 00 A1 LDA $A10000,x[$A1:E88A];|
$A0:8A90 C9 FF FF CMP #$FFFF ;} If no enemy population data:
$A0:8A93 D0 03 BNE $03 [$8A98] ;/
$A0:8A95 4C 9B 8A JMP $8A9B [$A0:8A9B] ; Return
$A0:8A98 20 64 8D JSR $8D64 [$A0:8D64] ; Process enemy set
$A0:8A9B AB PLB
$A0:8A9C 28 PLP
$A0:8A9D 6B RTL
}
;;; $8A9E: Initialise enemies ;;;
{
$A0:8A9E 08 PHP
$A0:8A9F 8B PHB
$A0:8AA0 A0 00 14 LDY #$1400 ;\
$A0:8AA3 A2 00 00 LDX #$0000 ;|
$A0:8AA6 A9 00 00 LDA #$0000 ;|
;|
$A0:8AA9 9F 00 70 7E STA $7E7000,x[$7E:7000];} $7E:7000..97FF = 0 (extra enemy RAM, but also a load of other random purposes)
$A0:8AAD E8 INX ;|
$A0:8AAE E8 INX ;|
$A0:8AAF 88 DEY ;|
$A0:8AB0 D0 F7 BNE $F7 [$8AA9] ;/
$A0:8AB2 F4 00 A0 PEA $A000 ;\
$A0:8AB5 AB PLB ;} DB = $A0
$A0:8AB6 AB PLB ;/
$A0:8AB7 C2 30 REP #$30
$A0:8AB9 9C 4E 0E STZ $0E4E [$7E:0E4E] ; Number of enemies = 0
$A0:8ABC 9C 50 0E STZ $0E50 [$7E:0E50] ; Number of enemies killed = 0
$A0:8ABF 9C 3C 18 STZ $183C [$7E:183C] ; Disable global off-screen enemy processing
$A0:8AC2 A2 1E 01 LDX #$011E ;\
$A0:8AC5 A9 00 00 LDA #$0000 ;|
;|
$A0:8AC8 9F 80 F3 7E STA $7EF380,x[$7E:F49E];} $7E:F380..F49F = 0 (extra enemy projectile RAM)
$A0:8ACC CA DEX ;|
$A0:8ACD CA DEX ;|
$A0:8ACE 10 F8 BPL $F8 [$8AC8] ;/
$A0:8AD0 A2 22 00 LDX #$0022 ;\
$A0:8AD3 A9 FF FF LDA #$FFFF ;|
;|
$A0:8AD6 9F 10 F4 7E STA $7EF410,x[$7E:F432];} $7E:F410..33 = FFFFh (enemy projectile killed enemy indices, for respawning enemies)
$A0:8ADA CA DEX ;|
$A0:8ADB CA DEX ;|
$A0:8ADC 10 F8 BPL $F8 [$8AD6] ;/
$A0:8ADE AE CF 07 LDX $07CF [$7E:07CF] ; X = [enemy population pointer] (enemy population entry address)
$A0:8AE1 BF 00 00 A1 LDA $A10000,x[$A1:E88A];\
$A0:8AE5 C9 FF FF CMP #$FFFF ;} If [$A1:0000 + [X]] = FFFFh:
$A0:8AE8 D0 03 BNE $03 [$8AED] ;/
$A0:8AEA 4C E6 8B JMP $8BE6 [$A0:8BE6] ; Return
$A0:8AED 9C 48 0E STZ $0E48 [$7E:0E48] ; $0E48 = 0
$A0:8AF0 A0 00 00 LDY #$0000 ; Y = 0 (enemy index)
; LOOP
$A0:8AF3 20 F3 8B JSR $8BF3 [$A0:8BF3] ; Load enemy GFX indices
$A0:8AF6 DA PHX
$A0:8AF7 BF 00 00 A1 LDA $A10000,x[$A1:E88A]; A = [$A1:0000 + [X]] (enemy ID)
$A0:8AFB AA TAX