|
- ;[FC][MMC3 精灵碰撞]
7 H5 X) a8 z" M+ U6 G$ g - ;FlameCyclone 20230710
- }& e, v$ B2 ^! z; J N - 7 T3 t2 `7 k3 C) M) L/ X, M. ]% r
- ;文件头
$ G" L* P/ @1 l1 b1 D) q7 r. t - ;======================================================================" o2 G4 m5 k/ I/ ]; Q
- .INESPRG 4 ;16KB PRG 数量
" h" n# }4 }7 d& B9 k6 D - .INESCHR 1 ;8KB CHR 数量6 \5 W/ V1 L* ^9 z' {/ R
- .INESMAP 4 ;mapper 4
% g7 l2 y \/ }6 t2 ~/ T - .INESMIR 1 ;命名表镜像 0水平 1垂直4 [! Z; C7 z2 |* G- o2 A
+ z$ `1 z, _+ G- I) L- ;必要条件0 v6 `/ u3 u: Q( W. D2 l+ G
- ;1.持有CHR ROM, U1 _: D/ _5 W! u" Z+ D
- ;2.背景Tile和精灵Tile必须使用不同的图案表, 如背景图案$0000, 精灵图案$10001 [! a5 n9 r M* m: L' q
- ;3.精灵内存(OAM)不为空
8 \; |) x2 C3 }' m3 A
$ D2 X( H: i2 O" }# v: c- ;==================================================* ]5 f4 D+ o2 b6 I+ W J- `
- ;NES端口常量/ s, K9 H+ X% q2 x4 U6 E- M1 E
- PPU_CTRL = $2000 ;PPU控制寄存器7 u0 z. Y, W# p# F' K$ }" R( |$ [
- PPU_MASK = $2001 ;PPU掩码寄存器* {5 o3 g9 R `/ C. R; w9 N
- PPU_STATUS = $2002 ;PPU状态寄存器:读取后PPU_SCROLL和PPU_ADDRESS被复位,下一个写到PPU_SCROLL的数据是水平的,写到PPU_ADDRESS的数据是高位
& e/ g6 X5 {3 B- D; ] - PPU_OAM_ADDR = $2003 ;精灵RAM地址:用来设置通过PPU_OAM_DATA访问的256字节精灵RAM地址。每次访问PPU_OAM_DATA后该地址增加1
) u" b5 i/ c; b9 | - PPU_OAM_DATA = $2004 ;精灵RAM数据:用来读/写精灵内存。地址通过PPU_OAM_ADDR来设置,每次访问后地址增加1
0 `( [1 `8 t$ w6 a% i& G - PPU_SCROLL = $2005 ;屏幕滚动偏移:第一个写的值会进入垂直滚动寄存器(若>239,被忽略)。第二个值出现在水平滚动寄存器
2 w0 w3 [$ C; w" ^- }0 n - PPU_ADDRESS = $2006 ;VRAM地址:设置PPU_DATA访问的VRAM地址。第一个写地址的高6位。第二个写低8位。每次访问PPU_DATA后地址增加; H* M+ {% H6 c# {! r U0 ~" J
- PPU_DATA = $2007 ;VRAM数据:用来访问VRAM数据,通过PPU_ADDRESS设置的地址在每次访问之后会增加1或32 + L, i4 c$ e0 W6 ^- W7 J' A
- OAM_DMA = $4014 ;DMA访问精灵RAM:通过写一个值xx到这个端口,引起CPU内存地址为$xx00-$xxFF的区域传送到精灵内存
& {" _ H2 F5 q+ o6 u& ` - APU_STATUS = $4015 ;声音通道切换
9 @' u* x# l0 R$ {& o* N; U0 M C - JOY1_FRAME = $4016 ;手柄1 + 选通
" X+ k' ]& ?/ S/ ]5 U. x - JOY2_FRAME = $4017 ;手柄2 + 选通
8 _$ O6 {7 Z% E
! o% R% H0 F0 K4 R" c0 E- ;==================================================+ c9 W# x1 x* K* b) J( y# h4 O6 h7 w
- ;MMC3端口常量' N* r. k7 C2 f( V, a0 j% j
- MMC3_BANK_CTRL = $8000: V% x8 n! n+ H- J) K( L. p
- MMC3_BANK_DATA = $8001+ F; P% ]# a& f& m" |1 u% i% s
- MMC3_MIRRORING = $A000& ]4 L( `2 ^/ q) y# A8 L
- MMC3_PRG_RAM_PROTECT = $A001
; {1 M2 P7 k. [ - MMC3_IRQ_LATCH = $C000
. n" {# X5 b7 L9 N* F ^ - MMC3_IRQ_RELOAD = $C001
$ ?+ B6 X3 g9 R. r; F - MMC3_IRQ_DISABLE = $E000- R- ~- I& f& D0 L* `3 M/ D4 b
- MMC3_IRQ_ENABLE = $E001 s Q% v6 p q6 j& A0 T
- 3 I( v3 F- A1 |% T/ l6 w$ |
- ;==================================================' ?: N# N/ x( ?9 r- f
- ;程序块配置3 e+ g6 B7 p. ~+ C
- BANK_DATA_MASK = $07' r( k0 F8 w* Y K6 T
- ;--------------------------------------------------4 M- h8 W' `: I8 O/ Q
- RESET_BANK = $078 {0 `6 A5 E! J5 b1 d
- RESET_ADDR = $FC001 a9 {) J6 a k) `8 y( ]
7 R$ w5 u/ j! X; W# v/ x5 v$ \# T- ;==================================================
$ e1 ?; I* F: F - ;图像块配置8 |' e" ^3 H: Q; ^
- CHR_DATA_BANK = $08
+ F# |) D1 B7 P, c* y! {
" Q. b4 K# K) b+ g2 D7 }- ;==================================================# }; J) D+ e' r5 P
- ;零页内存地址配置
) d; _. s8 j H - Use_Ram_Addr = $80
: O; W* e$ C- a/ r9 \, O; w - PPU_Ctrl_Buf = Use_Ram_Addr0 d, U3 W- C0 F2 @: Y C9 P& p
- PPU_Msak_Buf = PPU_Ctrl_Buf + $01, @2 P- V$ t( W: b8 o
- PPU_Scroll_H = PPU_Msak_Buf + $01) {; [6 C4 q- e H1 r# L
- PPU_Scroll_V = PPU_Scroll_H + $01
+ r8 S7 R8 P. a7 d+ J - FC_Data_L = PPU_Scroll_V + $01% U2 r0 V m, Y
- FC_Data_H = FC_Data_L + $01
- n) R& x; z- M6 t6 M9 G - FC_Data_Buf = FC_Data_H + $01& f0 b$ q* W8 C/ L- c+ K& S( u3 h
- ;==================================================
6 G/ k! F% k" `# u6 a0 @- x ? - ' V7 h: N7 w9 {- ?3 g
- GAMEPAD_MERGE_FLAG = $04- D2 ?! u2 v2 x
- " B0 f4 U! q) R8 w) T, S% |. d1 Q
- Gamepad_Keep = FC_Data_Buf + 19 V6 j, k/ x/ ` J6 a8 \/ e
- Gamepad_Once = Gamepad_Keep + 2
/ z0 g3 v+ `, J4 i3 N% U+ c - Gamepad_Temp = Gamepad_Once + 2, R1 O! y8 D6 ]
- 3 a( Z; |) M* k2 X; S
- Gamepad_0_State = Gamepad_Temp + 2
6 y. n* Z8 g2 O& s8 j9 I; c - Gamepad_1_State = Gamepad_0_State + 1" \0 M% T& e" v7 b0 R+ P
- Gamepad_0_Value = Gamepad_1_State + 17 ]* f' [+ d8 O" b# r
- Gamepad_1_Value = Gamepad_0_Value + 1$ y n, p+ H" F p. C
- Gamepad_Port_Value = Gamepad_1_Value + 1 `) a. f+ W, K8 F+ p
- Gamepad_Merge = Gamepad_Port_Value + 16 b& j' D2 _4 B! |
- $ x0 W( I3 M+ v
- ;==================================================: L' d1 k$ B. h8 D# f5 R
- IRQ_Index = Gamepad_Merge + $01
2 u1 @) c; ?& N$ g6 R - Sprite_0_Y = IRQ_Index + $01: k+ B( G" ]$ H* ?1 c
- Sprite_0_Tile = Sprite_0_Y + $01
- B/ G2 t% y& A" R - Sprite_0_Mode = Sprite_0_Tile + $013 S: r2 q4 m: R2 ?5 q
- Sprite_0_X = Sprite_0_Mode + $01
$ d/ v' \) Q; h2 C8 H0 `6 ~' S - Sprite_0_Hit_Move_Direction = Sprite_0_X + $01
3 |7 {3 s% X/ [6 l5 ] - ;==================================================4 K& P K R8 j A0 N5 L
- - d* m( W6 N* R
- ;CHR图形数据
4 G6 j$ _9 o5 u7 D% ^# a0 x. N - ;==================================================
! a6 m' g6 u( c% e' o: D6 `2 Y4 a - .BANK CHR_DATA_BANK5 n1 S5 `" o, B; \
- .INCBIN "chr_bank/chr_data.chr"8 P3 h! \. e" n$ H; I4 g
- 6 S" ~) b. e* a2 G5 L
- .BANK RESET_BANK & BANK_DATA_MASK, t- L3 l7 b! p4 V# O
- .ORG RESET_ADDR+ a$ T3 t* l* S% K; d$ f c
-
+ q5 K) v* ]7 M& s - ;--------------------------------------------------
" U5 e5 q. q: j; v" g - Attributes_Data
4 e k* p( D6 y% [! i* _ - ;命名表属性+ I9 o& Q! ~" W/ T
- .DB $00,$00,$00,$00,$00,$00,$00,$00,$00,$00,$00,$00,$00,$00,$00,$00
8 r6 n* N5 |7 a2 ]9 X- B( S/ J - .DB $50,$50,$50,$50,$50,$50,$50,$50,$FF,$FF,$FF,$FF,$BB,$AA,$AA,$AA6 }+ a( |" h) K6 R! m: E) t
- .DB $0F,$0F,$0F,$0F,$0B,$0A,$0A,$0A,$AA,$AA,$AA,$AA,$AA,$AA,$AA,$AA5 ?0 U G+ h) L) J; J. G+ U9 X
- .DB $AA,$AA,$AA,$AA,$AA,$AA,$AA,$55,$55,$55,$55,$55,$55,$55,$55,$55
8 W+ A2 b4 \+ \+ n - ;--------------------------------------------------& @& h) l7 z* i4 P
- ;调色板数据
! g8 U, ?5 a: Y% W - Palette_Data
0 h/ | O4 q! n8 m, R, c- n - .DB $0F,$27,$20,$0F,$0F,$24,$20,$0F,$0F,$21,$20,$0F,$0F,$25,$20,$0F$ q! ?- I4 t j- B
- .DB $0F,$24,$20,$0F,$0F,$24,$20,$0F,$0F,$24,$20,$0F,$0F,$24,$20,$0F
4 Y' q. v! i1 A - % g' n) b/ d5 }
- ;==================================================+ n1 q% O& \' p3 F- f& W
- ;命名表初始化" |) m. G5 \2 i: x. Y
- Init_Name_Table L2 Y; I) m% ~
- LDA #$20+ O- I7 V, B3 W% c! O
- STA PPU_ADDRESS
7 J* X- S; {5 v, S$ |& z! p - LDA #$00
6 c( e1 `; P1 y' O" h% t+ f' n - STA PPU_ADDRESS
, `, u4 _- ]* t' M" p% y% L - LDA #$009 F5 x! ^! ~+ b8 o: G" F
- LDY #$00
) A p5 ^) {! G t$ ] - LDX #$101 M9 V5 W5 v7 I, y' x! \: l" V
- Init_Name_Table_Write$ i4 k+ o/ o: U: a4 Y5 w
- STA PPU_DATA
" m/ ^3 }% ~7 R- A0 B - INY
8 F u; B" {" y) w) h- \ - BNE Init_Name_Table_Write1 c; ]5 S$ u' @4 a" {
- DEX
; g- B# e! y0 k7 o2 B - BNE Init_Name_Table_Write! ~& n: i2 q# M+ Q5 G% K
- RTS
' Z, z3 a- N% J- J - 0 Y0 A( ?; H+ G4 D
- ;==================================================
& h7 D7 G1 q A! E2 y - ;调色板初始化
, L: {! I4 R/ ?' w4 s2 O. `( t - Init_Palette+ Q _+ f4 B+ X* }8 i
- BIT PPU_STATUS7 R6 U/ z, F" S$ G) n
- LDA #$3F% q f$ ]3 D& u5 y
- STA PPU_ADDRESS: j' t* v; F$ U. \, d- ^1 r1 w) L
- LDA #$00
9 K* \5 ]# T8 q+ i( `( B/ X7 [$ T - STA PPU_ADDRESS
; o& `/ {) [# u. I/ W( A5 ] - LDX #$00/ J* g X4 y7 A- ]+ `. q B
- Init_Palette_Write
; J8 I6 n# ]$ d4 [8 Y7 e6 J/ E ? - LDA Palette_Data,X
% r+ i+ @7 O5 Z - STA PPU_DATA
9 ^$ k' K! b$ c; I" }- n - INX
]$ Y3 H# L9 h. e - CPX #$20% K1 B& t3 A o; k# Z& @# v9 Z! {# O
- BCC Init_Palette_Write- }7 h( r/ P1 x) I' `0 i
- RTS
3 e) P9 w+ p% E7 M3 P - 3 J/ f( i) e8 S/ `! d1 N
- ;==================================================% q& i6 A: K% J% l
- ;设置命名表属性
0 M- z* S+ ]2 W$ e - Init_NameTable_Attributes
. N: K- l* |: W6 g+ A6 ?! b - BIT PPU_STATUS
# Q" t8 j5 B! M/ U6 B - LDA #$234 b2 e5 D2 U! W: o
- STA PPU_ADDRESS) l& Q) d. f8 A6 K1 k
- LDA #$C0
* l+ H' B* n. v! J0 y - STA PPU_ADDRESS
9 x& ]" q) u& a7 q' b" w - LDX #$00
) {" K( V' E# F& p1 M( D& a - Init_NameTable_Attributes_Write
, ]: C* B* v# K9 C! \ w - LDA Attributes_Data,X( E5 Z* D0 a3 B. f3 H
- STA PPU_DATA
- ?* A& o' w8 T" G& H8 i# O8 M - INX
% z! o, [" y7 T% S8 L* `1 K- i - CPX #$40( y3 a0 t7 s. _2 G E/ }* X
- BCC Init_NameTable_Attributes_Write
( m2 S9 m0 b E l* j3 C5 K( n - RTS
9 Z' r+ ~4 g: n3 F* S( \* j- l' L - t7 \5 _) j# ~4 N
- ;==================================================2 q: K' z7 D9 u4 P0 k* Y- Y
- ;初始化命名表文本
4 U, M# C4 x3 \7 s7 ]9 x; |1 j t* R6 o - Init_Name_Table_Text1 ?4 A" M' B( R+ u! Z. b' Y2 P9 N! [
- BIT PPU_STATUS, d2 E7 H' i% {
- LDA #$20: ~! F* z! w& |1 D& u0 H
- STA PPU_ADDRESS
3 z) @) H7 l5 m/ g7 ~: J - LDA #$00
! X4 N3 A/ t) a - STA PPU_ADDRESS
+ B* h$ n( y: L) |- ~% } - LDA #$003 K, H& f! o+ h; g) `& h- q6 P
- STA FC_Data_Buf: x% L# w. w j2 m$ B f
- LDY #30" `1 h+ p2 F: \' ~! N
- Init_Name_Table_Text_Write6 Y& Y B6 D: }0 Y9 d
- LDX #32
5 S1 H! O- `0 G% g: L# x% S - Init_Name_Table_Text_Write_Char
9 f8 D6 y! v5 ]3 m7 I' N/ U, y0 p* | - LDA #'0'5 h8 s4 ~1 T0 f( r1 x! J% i
- CLC4 i2 S; ]0 g. i) J2 ?% c
- ADC FC_Data_Buf
' A& Z7 b+ r' Y; D( ^ - STA PPU_DATA: G3 i& r+ a l8 P; x" U) ~& P9 ?
- DEX
9 t5 B4 \$ g m5 F8 F$ P* T - LDA #$14) ]* i6 ^* |$ _) o4 G! f
- STA PPU_DATA- |& v N+ ~7 R4 f% w
- DEX
) e. s; f t: {- v* J. t! Q - BNE Init_Name_Table_Text_Write_Char
8 @ F& r8 x! {/ U - INC FC_Data_Buf
6 q% J, C7 V) f1 s3 L- `! d - DEY
2 |% Q% o r/ i+ N( q1 F' Q - BNE Init_Name_Table_Text_Write3 C& t- N( c% u1 I U* l6 u6 \3 c
- RTS3 h0 F/ G3 _% n) R T
4 O8 {/ k1 I! d2 C. s6 f- ;==============================4 s, R ^7 B/ Q+ \# r0 U* K7 B
- Init_OAM_Ram;初始化精灵内存
* Q. |5 i8 o" [ T% [; {& c - LDX #$00
9 o" `+ c, x! w - LDA #$00* F7 r! ~9 `. M0 f" g
- STA PPU_OAM_ADDR
7 J; y/ p5 N, K: D - LDA #$F8
- h X; \8 P) B) G: I8 R" d - Init_OAM_Ram_Write/ y& Y+ O5 @" S
- STA PPU_OAM_DATA
9 M+ ^' @9 N/ u% ^3 Y1 l8 v - INX; k T( q+ q' x O% e8 h
- BNE Init_OAM_Ram_Write6 y1 M9 Z, {% z
- RTS
! b+ @0 c% N7 ]0 V$ w9 @7 B0 a' ?$ W -
/ r8 u; a3 T h4 p2 q5 C: c/ R$ z% j - GamepadProcess;手柄处理
2 C ]. @$ ~8 m0 m6 a; c9 p - JSR GamepadDatacan# ]7 h- y, |( p
- LDA <Gamepad_0_Value
4 w, y/ z" k1 U( j - STA <Gamepad_0_State9 w" d2 H! R9 U: D2 v6 i4 P
- LDA <Gamepad_1_Value
' o$ ]2 a) b7 B* P. x+ M - STA <Gamepad_1_State
1 s# Q% K' Y) {0 i* W% E - JSR GamepadDatacan
$ g$ W% x$ R, V9 B9 [ - LDX #$01( f# j8 ~4 l: t/ B/ i6 B) Q% m5 E
- GamepadMergeCheck;合并手柄输入检查
! |' o7 A( T. [: B* D1 R - LDA <Gamepad_0_Value,X
8 Y' W) k3 }# ~1 G. n* J - CMP <Gamepad_0_State,X
) K1 u& j3 O* P% K9 @( n - BEQ GamepadMergeInput" F- Z; M6 G1 L5 j
- LDA <Gamepad_Temp,X
) o. [7 f2 {1 x: ^5 o+ D6 [ - STA <Gamepad_0_Value,X
! c1 E; r7 i& X+ c# { - GamepadMergeInput;合并手柄输入. z3 x/ \4 N7 d4 W% u9 x
- DEX
) f6 l' u/ B! T4 e+ L# a6 S - BPL GamepadMergeCheck/ Y% e1 R* W* Q6 L5 P! B
- LDA <Gamepad_Merge
( g3 ~8 }" V3 M+ N& |- v# \ - AND #GAMEPAD_MERGE_FLAG# i3 R6 `# T0 T0 j+ ^# ]% ^# `
- BNE GamepadStateProcess
9 r: j+ u% |5 t/ A6 S - LDA <Gamepad_0_Value
W) ~: E( ?$ b" ?2 U: k3 Y, O - ORA <Gamepad_1_Value
1 m0 F6 p9 ^7 w - STA <Gamepad_0_Value
* A0 n0 L$ z3 ]0 N5 y/ A! {$ }* ] - GamepadStateProcess;手柄状态处理7 p/ o- x/ U3 N! G9 T- s N
- LDX #$01+ l& U1 Z1 k' d( v- `* k
- GamepadStateSave;手柄状态保存, W7 g9 X% G4 W+ t. n7 y0 c
- LDA <Gamepad_0_Value,X
- g g( N4 _+ n - TAY9 \3 e; G. ~$ L; k
- EOR <Gamepad_Temp,X
/ J: M5 n0 H9 i4 Z7 X - AND <Gamepad_0_Value,X
* V* J m/ ]; z, j - STA <Gamepad_Once,X4 |7 I" X V$ v: ~, z
- STY <Gamepad_Keep,X& J. S* k8 r4 }1 r; ] T) z3 A; B
- STY <Gamepad_Temp,X$ c- Y" V4 e2 \: k7 Z% u& V2 q
- DEX
: _9 P$ {# ~+ u2 b0 L - BPL GamepadStateSave
) ]. f' e4 x. Q+ I( ^7 N - RTS8 m+ r+ i) u4 M: s+ K4 q- W
. O6 m* b$ u6 A0 s- GamepadDatacan;手柄数据扫描' I- ]7 h g# O/ n, X
- LDX #$01) |! f; E" g; R0 \4 {
- STX $4016# C; f8 e& e' F; `
- DEX2 G/ g: p. _6 q- [9 D$ w
- STX $4016" t2 G. ~4 P/ r" z+ E
- LDY #$08
# ^- s) f) z( d u9 R - GamepadPortScan;手柄端口扫描
# Q7 i/ h* i* E2 R% V3 L - LDA $4016
. {6 s6 |7 ^7 b& s; y' ]" j - STA <Gamepad_Port_Value
6 F/ s7 l9 H) q3 e - LSR A1 Z' d# x2 m: u5 i' |
- ORA <Gamepad_Port_Value
: F; E4 c7 f4 Z - LSR A* u$ _; k- b8 G& d
- ROL <Gamepad_0_Value. d: e7 K, `) _4 m# S$ X
- LDA $4017% ]( g/ f2 K5 C. K- q2 Y
- STA <Gamepad_Port_Value( X; [; G: X9 e+ I" S
- LSR A( X" h7 H8 P* x |+ m
- ORA <Gamepad_Port_Value8 K9 l& ]# T7 D$ j6 n" m3 i
- LSR A
0 S4 {* E, L6 K8 ~ - ROL <Gamepad_1_Value
' H2 n* B( s) T, E - DEY. d; H0 u: d8 O7 D. L
- BNE GamepadPortScan
; r; x; ?' s# K4 ^ - RTS1 [% b1 U' H( _* d$ \# J. L
-
' L4 J: U" f3 Q5 \ - ;==================================================6 a" L0 O4 T: B' n0 @: _
- ;PPU处理
9 t1 n4 D# ]1 U$ y - PPU_Process1 K& x: ?. V' v0 N7 B
- LDA #$00, G* b' s& Y; `+ e! W; Z
- STA PPU_MASK) G7 J/ r1 S+ G
-
% f# {- ]* ~" m5 g y; [+ H6 s$ W/ C - BIT PPU_STATUS! d" M2 a1 v1 A: X" t. p- {5 x/ [) R
- LDA #$20
* B$ Z+ C1 g7 n" [! M - STA PPU_ADDRESS+ n9 w) ?, V7 h; N
- LDA #$00
' W. A, W) B/ r' v" m) U0 Z- A - STA PPU_ADDRESS
! ?" O$ n8 G# } - ; J. ?! V* P. f9 A% }: g
- STA PPU_SCROLL
. n" F, O8 D, G+ u4 j - STA PPU_SCROLL
4 t4 h x! X8 o, X$ g$ j2 v -
" B a( u, c c6 U. W+ q - LDA PPU_Msak_Buf
# F8 ?4 _+ \6 N& g - STA PPU_MASK
% T4 d% I( V/ X& [6 ]9 Q8 v - 0 O5 u1 I. H) I; y
- RTS8 p# s) I( T. _4 Y' X
-
' T J! P+ K) D - ;==============================
$ H4 A$ _; E! r# O# I- q) ^+ x+ T - Time_For_Vblank;延时等待1 I' d9 P' {4 [/ x |; |$ U
- LDA PPU_STATUS
1 R* D& t, C# W! f - BPL Time_For_Vblank
" I+ I m6 \ ~. q7 F8 g - RTS
" a% V; ^& F* a' ~/ p" l. u! s -
' b. C9 S$ c, o8 ?7 K+ w* A, c - ;==================================================
) j' W" [" ~6 m5 \" a$ N6 G - ;初始化MMC3
6 T5 k/ _& c2 r- y8 i# k - Init_MMC36 }+ E! L5 p" {* m6 R
- STA MMC3_IRQ_DISABLE8 ?9 K$ x. C" M h: m c. G1 [
-
# j5 M/ q; d v& y7 B - ;设置MMC3水平镜像
8 g# l% o+ a7 A$ ^# Y* D" q3 } - LDA #$01& X0 x# ^6 s( c" {. P
- STA MMC3_MIRRORING
; D5 z8 b) n" M6 E3 ~ - * R& J& u0 |: e5 H! i
- LDX #$055 c4 `9 x B) B6 r8 I
- Init_MMC3_Chr_Bank_Write
+ H$ A E6 @, U3 r4 W; f - STX MMC3_BANK_CTRL- F* x! q1 k% m7 `5 R$ `
- LDA MMC3_Chr_Bank_Data,X' o5 x0 _% N3 P# u9 w( H
- STA MMC3_BANK_DATA. x: c% m# Y$ P- y
- DEX) @3 [( \: R+ F
- BPL Init_MMC3_Chr_Bank_Write0 W5 M6 f8 B* a k
- RTS3 k ~# f7 y( ?( L8 ]7 U/ Z
- ;--------------------------------------------------
) { ]+ V& e4 I: H) ^' }& R1 R - MMC3_Chr_Bank_Data* `1 Q9 M9 M1 X9 x
- .DB $00,$02,$04,$05,$06,$07
' \6 G. F+ L( T% S9 Q2 G- U* l+ t
7 `' G( h# I) S2 K- ;==================================================
6 ^, w& N' l( j$ | - ;重置中断处理; Z* D) r( n4 @$ n
- ResetProgram& X6 Y" y- ?, ?7 H2 u; V3 @0 b
- SEI
2 U/ O. l( `/ J7 L( u2 f6 v+ j& l2 p - CLD
% T# j/ y3 \& p3 b2 N2 W - LDA #$004 I* A2 \' H' k4 M/ `
- STA PPU_CTRL$ D* I, L+ \4 n: y
- STA PPU_MASK
* [: R8 @, F/ y7 `. O: O - STA PPU_STATUS7 @! y: J/ I9 k# P- O
- STA JOY2_FRAME `" x) W9 C2 [7 U: u% [
- STA APU_STATUS
9 A- R) v* W9 s( Q" r3 a+ f -
( r& X4 P& A" H* y/ n - LDA #$C0
- Z: w2 |' N! A! I$ A$ i+ y - STA JOY2_FRAME
7 W9 D' [. S3 p, M) g+ B; s - 8 s6 E& ]1 T2 y+ R
- ;等待vblank
! |+ P* I0 U7 c1 @ - LDX #$024 K' l) v$ O( I' A2 {9 _/ X
- Vblank_Wait_1& l8 D# v. k. k& I' i5 j
- BIT PPU_STATUS
0 H; @. a9 H4 g; ^, a" @ - BPL Vblank_Wait_14 \& m+ R( K# a) C; S1 o8 x
- Vblank_Wait_25 H5 d; F7 ]7 e$ N* K
- BIT PPU_STATUS. ~/ Y' C% \ T6 M, N
- BMI Vblank_Wait_26 H( ]% B+ |) v1 r: [! @
- DEX& Z* V: _- F# A: K9 G' }
- BNE Vblank_Wait_1
* m W4 z! J, }4 T& O1 d - 4 C: w9 u# x- Y$ F" e! y$ ^7 y9 u. T
- LDX #$FF
6 f# Y1 r4 w$ v# W. L - TXS
8 X" \- @0 [1 q* J+ t8 N0 V: e, J$ Y; l - % ~# P K3 a! F, I0 `
- ;初始化MMC3+ S4 B' Z1 j/ D" ^# w& V
- JSR Init_MMC3
; k& N7 T( o) B$ k: P0 L; ~ -
: f6 U% d1 [2 p' h: F, P( V$ w - ;==============================, q1 _! V: Z1 S+ B3 w
- ;RAM初始化' e! q/ K/ h% n
- Nes_Ram_Init
8 W( w N2 x- q' A, \ - LDY #$00. W* T" ]4 n% P$ x. W5 J/ ?! z
- LDX #$08, Z4 i8 P+ ?- Z$ V! |) l- s9 r
- LDA #$00
" h& a) B B. s: i7 q - STA <$00; C, v* ]2 J- W- V
- STA <$01/ V- ^: r2 j! ~8 t# l% `0 }
- Nes_Ram_Init_Write0 ^7 ]6 k) F9 m9 f! C" N
- STA [$00],Y* c( n1 K$ I. Z! [2 [! J
- INY
3 U/ K/ D0 h* t1 ]2 s - BNE Nes_Ram_Init_Write2 g# W3 ~; d3 _2 p& H$ t5 T
- INC <$01
8 E$ m% C. W9 g7 D: I& L) P4 j - DEX
" [$ i J4 d% g/ ]3 Z3 s+ ~+ R. j - BNE Nes_Ram_Init_Write
- s( v$ V4 |9 z2 O - 6 q- [) K$ h3 F9 w
- ;初始化命名表
# b4 ^! _" {' v, x' F& d8 s/ E - JSR Init_Name_Table
. o D2 `# @( G4 ?3 @1 F) X( w -
- v7 m/ g$ G, w( d" w' b - ;初始化调色板8 y; e+ ?: |5 E4 j: ~* R
- JSR Init_Palette
7 a7 _ e; {6 w t" Q -
4 d7 Q% s. F/ t7 [+ J" }- | - ;初始化命名表属性
1 r! n( S" n% {, B. F8 o* M, q' w - JSR Init_NameTable_Attributes
$ C/ n0 ?7 n4 s( s/ C, V# ^- _ - 2 l, f) X5 C& f2 E
- ;初始化精灵内存0 P6 A6 W* L2 X ?
- JSR Init_OAM_Ram
5 @( E0 E; h' z - ! ]" |4 M' x! ~8 ~
- ;在屏幕上写点东西& [0 f9 w+ n$ N* |
- JSR Init_Name_Table_Text" q; o: M! W1 E# U
- b# d2 G! ^3 c" f+ g5 \* K$ G6 J9 |
- JSR Time_For_Vblank# Z, [+ `' W$ \2 k, U: Z
- ;开启PPU控制* \4 Y) P4 s; }
- LDA #$80
n9 E) P- \' Y, D1 W/ ~1 e+ u - STA PPU_Ctrl_Buf
) p8 g5 `+ ~5 D$ ]+ s - STA PPU_CTRL& c4 t9 |: }- A: g% g& x0 t
- % u) q* r+ P4 u3 F4 L8 U3 m) j* H
- ;开启PPU显示
8 L8 p* j) j0 J; Q8 m! U9 Z! r - LDA #$1E) a0 E, U8 [* l7 @4 P
- STA PPU_Msak_Buf6 Z. U& j% ^; `* T' Q' Z+ J! J
- 6 ?) B2 U7 d% t+ Q' n r0 n
- LDA #77
. D- l. P9 P1 f - STA Sprite_0_Y
5 [ h6 h& x4 |4 u, K4 \ - LDA #$1E5 ]$ |! o; b& ~5 t6 A+ O: ~7 t4 U+ k
- STA Sprite_0_Tile
5 U: B8 m' r2 m! x% r7 @# D% b9 ? - LDA #$20
! M$ R3 `/ Q; g+ t3 C" o - STA Sprite_0_Mode$ G O$ u" C' ], z. B) T: u, o
- LDA #$00; ^1 }; Z! g# B4 k# P' e ?
- STA Sprite_0_X
+ n9 c. g* p+ U5 R4 p ` -
3 @! c+ R% O$ S( Z# l7 N# ]: T - CLI
, G. C! [5 ^- Y - JMP Loop" V8 z$ z( B6 U G
-
3 S0 H! b' b5 T/ i. y: Y - ;==============================7 q# e9 G& t7 {
- ;死循环, 等待NMI中断; i% t+ D; S% S3 z
- Loop
' i7 u1 ^* P9 s! T! W+ O - JMP Loop
, B3 X! U; f7 G; O, }6 X! W+ b - 0 w% V: ^9 I5 l4 G' p
- ;==================================================& s, i" [8 ^& L7 d, A
- ;NMI中断处理
( |6 F% Q/ }6 f0 E# I" Q, r( H - NmiProgram9 b# L L) w8 h5 q& [5 n6 Z# [
- PHA' n2 M( S/ Z$ z; n. b
- TXA, P% B9 i2 y* M# i' ]% F
- PHA
. E. X9 S" T8 F! m - TYA
$ p! z5 c, @- Q# u: O - PHA
3 O8 T0 U+ N# s$ f$ ~# ~0 K -
8 S( g; g$ t- u, H! T7 n/ C - BIT PPU_STATUS, e5 O, Z& J- R+ S# g( p# Q
-
( \' B2 b" D! f& m - ;关闭PPU控制
5 a2 z3 ?% V# p o6 p% U* l - LDA #$00 i$ X! h1 I/ D7 J8 a
- STA PPU_CTRL$ D+ k+ e- i+ q* K2 e4 F3 g
-
! E( n1 V' G8 K4 o% p9 V - ;处理PPU
3 a7 R W( m F6 _4 o) f3 H - JSR PPU_Process
) q" o+ C/ Q3 q B/ o6 J -
) Q/ d$ w$ }. v& I/ W6 V5 H - LDA #$00% Q1 U, Y I9 o
- STA PPU_OAM_ADDR
: v5 x$ U+ v- I) n9 } \ - LDA <Sprite_0_Y& c5 E. Z6 S. ?1 j6 I, S6 h: m
- STA PPU_OAM_DATA
$ o0 h$ V! Y) n- \' T - LDA <Sprite_0_Tile8 `7 J% ?/ P9 v5 W- s
- STA PPU_OAM_DATA: N$ n/ W6 A+ Q5 A
- LDA <Sprite_0_Mode+ ?5 @( ^) {6 Y- s9 H7 j) b I/ _0 h3 O
- STA PPU_OAM_DATA4 i' {. {0 M* E! N6 e
- LDA <Sprite_0_X
# ]1 B2 P+ D" U7 S& P - STA PPU_OAM_DATA$ G( {2 O9 E- }2 y- V; I
- - A- y; I0 z" W
- ;开启PPU控制
; l }1 O) C0 A/ W" y - LDA PPU_Ctrl_Buf
5 s5 Q- W2 g. D. ` - STA PPU_CTRL
+ f: h/ }2 O5 e5 R1 k8 p -
0 b' k: q* G( w' V) @ - ;屏幕滚动$ _) O3 I; K# h1 w( F
- LDA <PPU_Scroll_H
5 j! }* [9 X2 D8 W - STA PPU_SCROLL2 ?* _. ], j5 i$ ]
- LDA #$006 D1 d& I/ T8 {+ I
- STA PPU_SCROLL
1 a' Y; H1 x8 ]0 o6 z A - 6 v$ E6 W4 x- l! [' l
- ;手柄处理
: p/ ^3 n; t# K - JSR GamepadProcess
; G7 `# m' u3 Q' Y9 g* H; r - 5 r* V4 ?& ]7 i# }+ G
- INC <PPU_Scroll_H9 E7 H: _1 v! s: G" M% V9 l2 Z4 \( e
-
, y2 O! J6 `4 c& |, q5 g - ;启动0号精灵碰撞检测
" |0 ^. ~0 R7 H5 L3 } - LDA #$01
' {& c8 U: @7 S1 t. @" Q' \/ P - STA Sprite_0_Hit_Move_Direction
0 v7 f( t; X; `: d' z - JSR Sprite_Hit_Test
1 `+ s" @$ X) o. k* D - ) y! X; s" o/ \# J8 h h$ U/ C
- PLA
+ R% d+ \5 g1 q8 o; b4 K8 F6 Q# ^ - TAY
: x0 o5 x2 `7 S! P% B - PLA" H# v* }+ J4 {
- TAX9 Q0 T1 m/ S# G, [2 n8 d
- PLA
4 a" A& \2 B" g9 R7 y, M0 p - RTI
. s7 c6 x9 k/ ?$ T - & s u( K- @) l
- ;==============================1 ^1 }4 K# O: E2 O6 B& [
- ;0号精灵碰撞测试
! M' v# N% A. s0 [+ F. w+ [ - Sprite_Hit_Test
6 b6 f) b% E; U: ^ - , U W! ~/ [. v5 M) A
- ;------------------------------" Y z; F+ D2 ]0 P# G: `) d
- ;等待0号精灵碰撞状态取消
( T D* n( B8 c1 N, k8 o - LDA PPU_STATUS
% N* D( q7 i/ N0 o( T - ASL A- A0 s: i- w2 L% G; T$ u
- BMI * - 4
/ w1 U+ y. U# G; u1 ]! r -
. x" a' ^! e; Y i* Q7 b I+ c% G - ;------------------------------' {1 ~# H, w" X2 }& A
- ;等待0号精灵碰撞发生/ A, N, e* X* V% _* K
- LDA PPU_STATUS1 S1 z) P. v& `, x
- ASl A
, R9 A6 k- \- u# _1 P - BPL * - 4
6 B7 i% G$ d0 q$ k) w- x - 1 r& k. D5 L$ F! U
- ;------------------------------4 ?# X: v# N, z
- ;行消隐等待2 z; f( p9 O! \+ B! p+ L
- Sprite_Hit_Scroll_Wait$ @1 Y. C7 V& G2 X$ G- r( ?, b
- LDX #$284 q. ~ }. m% _& F8 _) P: a
- DEX- Y/ ~. O- J" S+ f+ l! ^
- BNE * - 1
1 e" t5 b7 I/ |: Z \3 g' _3 o -
& ?9 Q {5 X+ I% [) S' K h0 D+ R - LDA Sprite_0_Hit_Move_Direction
1 ]( ^$ I8 Q6 K: B; `! L - AND #$01
9 G# e* n* l) m' }# B( X - BNE Sprite_Hit_Scroll_Set_Right5 p5 @/ M4 e8 @. L* s$ O
- ; k4 o* u: ?& Y0 R4 f
- ;------------------------------
) m; d& W/ W" N4 Q& {5 W: ]7 F! S& k" l - ;分割画面向左滚动" I G4 V1 ?9 d) w
- Sprite_Hit_Scroll_Set_Left t" r4 P2 M. H% v+ g! r7 A( K& p
- LDA PPU_STATUS5 r0 B5 t- z, p* M$ U5 k
- LDA <PPU_Scroll_H
/ X; M, Q6 {. T, F5 a - STA PPU_SCROLL
* `4 i }" g. q9 M, m - LDA #$00
8 y4 i* z( }/ X( k4 b - STA PPU_SCROLL
% A2 b6 W: N* z: h2 E* { - RTS
6 A8 H: p5 A( D/ J
) o! l/ b) ]7 I' R- ;------------------------------
. W4 x, i; N" J9 {3 g: ?( X - ;分割画面向右滚动7 K, n; k" S6 E7 G/ k/ B
- Sprite_Hit_Scroll_Set_Right
9 o% t! w, p# u2 M, I: s* a - LDA PPU_STATUS6 i% i2 h4 U# i3 T/ U" k3 q- s
- LDA #$000 E! c1 Q, y& g% s; p
- SEC" E( u# Y e9 j; W4 {' K
- SBC <PPU_Scroll_H7 ^; O, E }! T) w
- STA PPU_SCROLL
7 \0 \; E& Y( q I4 @1 U& l/ r - LDA #$00( ~: o# L2 N% B
- STA PPU_SCROLL
# l: c' x" w! A' z% M$ y - RTS
% R0 J$ D/ d* ^ - & ]7 I3 ~) x" b4 ~
- ;==================================================8 ^, _& S9 z2 H6 x; k: C+ z2 U
- ;IRQ中断处理' f. X# m% I. _ @
- IrqProgram
' t6 K$ p- m; }! r - PHA- ]8 P' a$ g4 F( o3 Y" b
- TXA3 L6 o8 U- ]. m( h
- PHA# t3 _! Y/ n8 M2 v1 f
- TYA
3 z* d8 U2 U- _9 H" @/ b - PHA
( I! `! \7 _: e - 4 _) v" w( Z- B5 _5 I, W9 ?1 l
- ;关闭IRQ2 L1 A7 \) x; \
- STA MMC3_IRQ_DISABLE
\2 Q, a) J5 r$ x, d( s, e& C -
- G0 F7 D; z. T' S - ;允许下个IRQ触发9 F- p: A3 J/ H
- STA MMC3_IRQ_ENABLE" M. |/ F, j2 i$ O4 m6 h# Z2 r) _
- 8 y f7 f& W- j1 O1 s
- ;IRQ处理, 15线后继续触发7 B2 }$ D- L" k
- LDA #15
' l0 p& l' O) P' O5 b- }5 i - STA MMC3_IRQ_LATCH
; l- V9 u! m+ R3 P! L* X0 ~. G -
: h, ]. S2 T* x2 V+ r4 W, Q - LDA <IRQ_Index
- x3 k5 }8 i# @/ }' T2 d& q8 j - BNE * + 4
$ k/ [1 i9 q- f8 d: Y8 w - INC <PPU_Scroll_H. l" ^* s8 t+ I$ ^9 Z3 ` T. u
-
, w. y, H: c+ W/ t3 r' u- S/ T - ;设置屏幕滚动. O) M% y8 w" g: K; f
- LDA <IRQ_Index
4 s8 f9 m. X* G+ Y' ~ - AND #$013 R% U7 n( S7 P: p# b* {
- BEQ Irq_Scroll_Right
$ h& q9 m& |3 Q' V5 B+ G6 d' g - 9 R( x( a# K6 Z0 F8 S4 m7 E9 N6 u( I
- Irq_Scroll_Left
! l: j" h0 M1 R& G' u" Z. D( A+ F - BIT PPU_STATUS
P; A( `+ t+ D" }* I r0 {& _. A" m - LDA <PPU_Scroll_H" H# Y/ |, k. C5 Q: E
- STA PPU_SCROLL
5 Z; M& r @% R3 |9 ^* Q - STA PPU_SCROLL
9 B/ d3 H5 }; M+ U, M/ } - JMP Irq_Scroll_Over6 U- {( h6 U$ y2 I
-
5 y- X& j/ i' ~' L - Irq_Scroll_Right
9 `# `2 _& V( X7 m) z - SEC
' H' l, A8 P2 ^0 L7 {* x - SBC <PPU_Scroll_H3 r7 i$ R3 N$ X: w1 l @
- STA PPU_SCROLL
$ Y; c5 v1 k1 p - STA PPU_SCROLL* M" _% J9 b" ?% b3 i
- Irq_Scroll_Over
0 Y3 m" ^- U6 y1 |& M' r0 F. S - $ g/ l. q4 r+ _. z
- INC <IRQ_Index9 @% ]; e- @) k8 X3 A5 k3 Y. W
-
0 `1 m: ~7 i# H0 K' {! |' Z- ? ^ - LDA <IRQ_Index# t( E+ @8 G- T/ O
- CMP #14
/ N5 L8 M0 b$ o. j - BCC * + 5
1 I) I+ ^& M& D7 V3 l$ V, @2 h3 |8 ^$ X - ;关闭IRQ* n5 r" Q% E7 H6 _6 J9 ]: g& I5 `
- STA MMC3_IRQ_DISABLE1 P) o9 v$ u( }( S! c: [* H
- 4 v+ k* A; M6 Z7 C. m, e
- IrqProgramEnd0 S2 @* l1 y2 W" K3 r$ M3 k- \0 g
- PLA0 P( R) H4 q( ?9 ^8 j* \3 f
- TAY
) R! O- f7 m, H3 g! M( D - PLA
. a8 D! @* i$ | - TAX- d5 n' V2 z- A. p1 F
- PLA
8 |6 Z6 @9 f" E- M6 ~' E& G - RTI' V( C5 U" U6 k2 i% H
-
4 R0 w' {: W" K1 ? - ;==================================================
& k! G7 T3 h1 g8 O( m - ;中断表
. T) L/ ~. p; Z- l! i# \ - .ORG $FFFA
j# t+ R5 J9 p6 y. X) x - .WORD NmiProgram
' }1 d. E9 x! X2 ]3 S# m/ v. g - .WORD ResetProgram/ s* e2 v9 j# o
- .WORD IrqProgram
复制代码 5 ?. g' M& H$ P! D B0 K! k0 {2 }% t
|
评分
-
1
查看全部评分
-
|