设为首页收藏本站

 找回密码
 立即注册
搜索
查看: 208|回复: 0

[原创] [FC][Mapper19][IRQ学习源码]

[复制链接]

签到天数: 39 天

[LV.5]常住居民I

发表于 2023-7-16 20:16:44 | 显示全部楼层 |阅读模式
  1. ;[FC][Mapper19 IRQ]
    5 z2 A4 `: n+ E. E8 ~' M$ Q1 z
  2. ;FlameCyclone 202307100 v5 |. X; t- p3 W( o

  3. ) b6 @5 k1 S; s
  4. ;文件头
    $ N, e# {6 x! P' i  J0 R8 y" i
  5. ;======================================================================
    $ @, ?; ]! e, J( J! h1 p
  6. .INESPRG 4                                              ;16KB PRG 数量& G! a) {4 R9 \7 r9 r
  7. .INESCHR 1                                               ;8KB CHR 数量
    4 o' H" y2 g8 ]4 s  k
  8. .INESMAP 19                                                 ;mapper 19
    ' F* f) q& {+ m) n
  9. .INESMIR 1                                   ;命名表镜像 0水平 1垂直
    ( F6 q  |2 H/ h" `
  10. , Y6 X5 y& E. _+ d* o+ ?) Y- G
  11. ;必要条件
    4 Y: D9 c/ R% P7 I. x. g5 ]. Q  j7 I$ ^
  12. ;1.持有CHR ROM+ X+ O. j# ?) z- Z( q
  13. ;2.背景Tile和精灵Tile必须使用不同的图案表, 如背景图案$0000, 精灵图案$1000% q8 V0 k* t" I
  14. ;3.精灵内存(OAM)不为空8 W% L" b3 E2 b

  15. 5 n$ O9 {1 [4 t; Z# `
  16. ;==================================================& Y. u" }( R/ r! Q! q9 k2 n& @3 H
  17. ;NES端口常量: Z' C  z+ b. l$ E
  18. PPU_CTRL                =   $2000   ;PPU控制寄存器
    ; V) H5 S- {, U7 j9 }! G9 K% G
  19. PPU_MASK                =   $2001   ;PPU掩码寄存器( A+ D* y9 L8 _% @- j/ B, b
  20. PPU_STATUS              =   $2002   ;PPU状态寄存器:读取后PPU_SCROLL和PPU_ADDRESS被复位,下一个写到PPU_SCROLL的数据是水平的,写到PPU_ADDRESS的数据是高位
    : p/ T. d/ P8 T* y" @
  21. PPU_OAM_ADDR            =   $2003   ;精灵RAM地址:用来设置通过PPU_OAM_DATA访问的256字节精灵RAM地址。每次访问PPU_OAM_DATA后该地址增加17 T5 L9 m3 O. d8 h1 b! ?: G
  22. PPU_OAM_DATA            =   $2004   ;精灵RAM数据:用来读/写精灵内存。地址通过PPU_OAM_ADDR来设置,每次访问后地址增加11 h6 D( e1 ?" ~" i8 t; Y
  23. PPU_SCROLL              =   $2005   ;屏幕滚动偏移:第一个写的值会进入垂直滚动寄存器(若>239,被忽略)。第二个值出现在水平滚动寄存器
    ' J4 d8 c& X$ _0 }5 ~: S3 Q
  24. PPU_ADDRESS             =   $2006   ;VRAM地址:设置PPU_DATA访问的VRAM地址。第一个写地址的高6位。第二个写低8位。每次访问PPU_DATA后地址增加" m, ^2 ~  t4 y  U
  25. PPU_DATA                =   $2007   ;VRAM数据:用来访问VRAM数据,通过PPU_ADDRESS设置的地址在每次访问之后会增加1或32 " {: J$ Y+ s2 `; G& [
  26. OAM_DMA                 =   $4014   ;DMA访问精灵RAM:通过写一个值xx到这个端口,引起CPU内存地址为$xx00-$xxFF的区域传送到精灵内存
    $ F6 H( {1 s& {1 X. g% u
  27. APU_STATUS              =   $4015   ;声音通道切换
    , _! ^4 ^" b) N' n0 {, ^6 d5 _
  28. JOY1_FRAME              =   $4016   ;手柄1 + 选通
    $ h# [% I% g" U& n
  29. JOY2_FRAME              =   $4017   ;手柄2 + 选通. n! K! H! t& Y) g" {

  30. / f9 A  O! G2 A
  31. ;==================================================
    6 u6 }  a; {9 ?  w% m
  32. ;MAPPER 19端口常量  C! j5 a# Y  K4 D/ b8 Z
  33. M19_CHR_0000    =   $8000- a6 B0 }6 T$ q0 b. C
  34. M19_CHR_0400    =   $8800
    , o1 H- E# f% J7 p; Y! y
  35. M19_CHR_0800    =   $9000
    " ]7 g/ s! ?5 S* n
  36. M19_CHR_0C00    =   $9800" E0 ]% L  Z8 s* W% n: T. |% A5 j
  37. M19_CHR_1000    =   $A000) H1 u) ~& k& X4 i2 j
  38. M19_CHR_1400    =   $A800& V+ c, y% _: p! M
  39. M19_CHR_1800    =   $B000
    & Y/ X* f3 w& c
  40. M19_CHR_1C00    =   $B800
    2 R" s$ l, e" Q9 V5 ^- |1 ]
  41. M19_NT_2000     =   $C000
    $ x! J* X' T; O7 W. ^9 {$ t
  42. M19_NT_2400     =   $C800
    8 m& J/ C/ m; M; {% f
  43. M19_NT_2800     =   $D000* R, L- Q8 Z0 u% k, e+ M& A) v6 X- U
  44. M19_NT_2C00     =   $D8000 n# S. O# a* S) w$ O! \+ C; l. S2 P
  45. M19_PRG_8000    =   $E000
    8 T: u" ^6 ^" o& Q: E
  46. M19_PRG_A000    =   $E8005 S' |0 V: r7 `; i" f8 A7 M2 i
  47. M19_PRG_C000    =   $F000+ C  J, F: S( j
  48. M19_IRQ_COUNT_L =   $5000
    ) R. u! n- B5 l: m
  49. M19_IRQ_COUNT_H =   $5800; A& \6 _; C% O6 B( }* Q. o
  50. 0 b% [* A8 O# H* a- J- B8 U
  51. ;==================================================7 b# ~9 N' \$ V6 W2 S; d( v
  52. ;程序块配置
    6 _) ~( O' v" N* K
  53. BANK_DATA_MASK          = $07
    7 k9 s& D5 D) ]. c" B" V% {4 r  A
  54. ;--------------------------------------------------
    4 a3 \/ I+ w# D+ ~& r8 _! z
  55. RESET_BANK              = $07
    4 H( M1 Y: N7 h! z+ F0 m7 A
  56. RESET_ADDR              = $FC00
    ; k/ K/ V, b6 E" \$ |
  57. * H7 Z3 z% O' A
  58. ;==================================================& G! m7 Y, [& L. A7 b
  59. ;图像块配置7 k" S" \9 s1 g& ?- W7 K, }
  60. CHR_DATA_BANK           = $08
    7 N% U( t* ]% Y! N

  61. 6 K8 r1 }0 p8 f9 O( L2 O, N$ ?
  62. ;==================================================$ q$ a# J8 t/ N2 ~4 Z
  63. ;零页内存地址配置5 G& q6 V* Z9 ~4 y" M& D" S
  64. Use_Ram_Addr            = $80" F; L4 @: m5 h. x
  65. PPU_Ctrl_Buf            = Use_Ram_Addr# z7 m! \& e. b. a- [' o
  66. PPU_Msak_Buf            = PPU_Ctrl_Buf + $01
    $ d2 C) ~7 Z4 C7 R  a, _  {  \
  67. PPU_Scroll_H            = PPU_Msak_Buf + $013 W% F1 u& a$ F/ J* \+ E
  68. PPU_Scroll_V            = PPU_Scroll_H + $01' O4 h& t& U/ z8 g! K: G4 a
  69. FC_Data_L               = PPU_Scroll_V + $01
    7 j4 Q. \! W5 Z
  70. FC_Data_H               = FC_Data_L + $01
    ! M/ [( R5 k2 |, w
  71. FC_Data_Buf             = FC_Data_H + $01! ]! f1 g/ a, _8 i
  72. ;==================================================
    + [' _1 H! |' }3 R' Z

  73. " R- u1 W  ?; B, w3 R
  74. GAMEPAD_MERGE_FLAG = $04
    ( ]/ l* G+ U' \. L3 c9 q7 J" _* r
  75. # a5 e6 _6 _5 W% W6 j" u; K+ @6 B
  76. Gamepad_Keep            =       FC_Data_Buf + 1. S- y' r9 G! ?& ~+ T7 P
  77. Gamepad_Once            =       Gamepad_Keep + 25 ^3 h3 ]; X7 X! F4 B& b5 C1 ^' [
  78. Gamepad_Temp            =       Gamepad_Once + 2
    6 i8 f/ e) A1 o4 h1 H
  79.                                 
    1 z5 J! ^% |. m3 g7 c. ~5 c0 l% U
  80. Gamepad_0_State         =       Gamepad_Temp + 2; j9 ^: ^, s/ O0 _8 R8 g6 b
  81. Gamepad_1_State         =       Gamepad_0_State + 1/ }3 S0 ^1 \8 y+ C5 U# D
  82. Gamepad_0_Value         =       Gamepad_1_State + 1
    . L9 z( e; A' W! @' k+ J/ m
  83. Gamepad_1_Value         =       Gamepad_0_Value + 1
    , }. i9 K+ m, v
  84. Gamepad_Port_Value      =       Gamepad_1_Value + 1
    ; N4 B9 K% M! t
  85. Gamepad_Merge           =       Gamepad_Port_Value + 1
    5 q+ J/ b! E8 a% g5 b4 O, t
  86. 3 F2 O, z. C0 R; f
  87. ;==================================================
    # `: c' j+ t. [
  88. IRQ_Index               =       Gamepad_Merge + $01+ [  T1 M% r) u$ e0 p( M
  89. ;==================================================
    8 C( O% `, J+ \. d5 U3 m1 |* I" k

  90. ' @7 |! Z# l& v  p. \* z3 ]  t
  91. ;CHR图形数据' p- R& ~; i; d- @
  92. ;==================================================. v) r& s% `' g% K) X+ j
  93. .BANK CHR_DATA_BANK9 `8 ]7 Q" ]" X
  94. .INCBIN "chr_bank/chr_data.chr"
    9 m: o) t; Q. C1 B, g' v- Z

  95. 4 D5 E: A; ^: i; E' h; z8 l( K' ~
  96. .BANK RESET_BANK & BANK_DATA_MASK! ~' Y: p. ~) a
  97. .ORG RESET_ADDR
    : Z1 d7 L/ _; K7 p0 N& ~
  98. . f$ J' ?) Q9 `
  99. ;--------------------------------------------------6 D6 z% f/ P  q4 X8 Y+ A
  100. Attributes_Data
    / x$ y2 g7 k% r2 X- z/ L& i
  101. ;命名表属性
    # t+ h& u. O( [! M
  102. .DB $00,$00,$00,$00,$00,$00,$00,$00,$00,$00,$00,$00,$00,$00,$00,$00: O3 J+ M  H$ S; b9 I
  103. .DB $50,$50,$50,$50,$50,$50,$50,$50,$FF,$FF,$FF,$FF,$BB,$AA,$AA,$AA
    ; T+ s& L- c+ s+ j$ v( \: w& W/ l
  104. .DB $0F,$0F,$0F,$0F,$0B,$0A,$0A,$0A,$AA,$AA,$AA,$AA,$AA,$AA,$AA,$AA
    ! @9 D' [0 U8 l
  105. .DB $AA,$AA,$AA,$AA,$AA,$AA,$AA,$55,$55,$55,$55,$55,$55,$55,$55,$55* ^) n# w% ^8 ]3 m5 G9 L' I
  106. ;--------------------------------------------------
    0 Y' ^& X: I% D" J# B- U
  107. ;调色板数据
    6 [# X+ T6 g5 E
  108. Palette_Data
    0 [$ v7 ?; j& Z; u7 N/ [; F5 Q
  109. .DB $0F,$27,$20,$0F,$0F,$24,$20,$0F,$0F,$21,$20,$0F,$0F,$25,$20,$0F
    % {) t8 {6 [& ]2 V% x
  110. .DB $0F,$24,$20,$0F,$0F,$24,$20,$0F,$0F,$24,$20,$0F,$0F,$24,$20,$0F& q* H" v# y9 N7 a+ _/ H$ R6 p1 U7 V

  111. 0 z* l1 M4 N3 y1 Q( ?1 s
  112. ;==================================================
    5 x( V7 e( Y% ]
  113. ;命名表初始化7 D; J$ U7 Z: x% s* W
  114. Init_Name_Table
    + [4 C. w. A0 T. t7 P3 e6 O
  115. LDA #$20
    5 h; K# H% ^, E3 b$ z8 S( ~
  116. STA PPU_ADDRESS, [$ b2 _2 G/ U4 H! ~7 ~( m
  117. LDA #$005 Y+ ~2 r+ K0 k
  118. STA PPU_ADDRESS
    ' d- w/ y6 ^2 N, h
  119. LDA #$00
    ! z; @, q* ~- J0 G8 ^6 g) y
  120. LDY #$00
    ) {% ]0 a: u! G# W' N/ @- T+ Z* Z
  121. LDX #$104 ^1 {5 i# Q2 l7 d
  122. Init_Name_Table_Write
    + G1 J- r" l  w* Y4 b( c$ G
  123. STA PPU_DATA# D4 K3 ~/ L, N/ E
  124. INY0 l$ S  q0 |! R2 A
  125. BNE Init_Name_Table_Write! y+ z( h( f' q' |0 |) g- A9 t
  126. DEX' H: K$ f( V9 u5 R$ D' k
  127. BNE Init_Name_Table_Write
    4 W7 l& \7 Q& V- N: M9 t2 Q
  128. RTS
    * I) u9 Q# x* U
  129. . W7 D6 i& G& ]! C
  130. ;==================================================! N  g" x4 p* Q" O3 a( F$ ~
  131. ;调色板初始化
    5 O; R6 S; h0 m. Y8 x1 X, Z
  132. Init_Palette/ u! ~/ K- R$ Z- H$ V( ^* x, L
  133. BIT PPU_STATUS2 S1 f4 J1 B7 v" J2 }
  134. LDA #$3F- T& c. f3 f; C* x" q/ I- o/ L
  135. STA PPU_ADDRESS' U* {: O' x3 [4 Z! g( n
  136. LDA #$00
    4 J! b: H( j& D3 T" u
  137. STA PPU_ADDRESS
    1 Y0 R. O9 u$ x$ B
  138. LDX #$00! |& |! C% F" T/ }; g3 l
  139. Init_Palette_Write
    / f. }. t& \6 Y# ?  M
  140. LDA Palette_Data,X# N( y% P6 v. A# s  ]8 `4 n0 h, X
  141. STA PPU_DATA/ G/ R6 [$ |* K# _
  142. INX
    0 e% {7 v/ P  `% A: Y
  143. CPX #$20
    + S0 Q* T7 @8 t7 u- K% D& o# Y
  144. BCC Init_Palette_Write! T" }1 G9 W3 e8 e! ~' ~! U
  145. RTS
    ) Q6 U1 F! C2 {. a. X/ n& H7 A* |
  146. 6 |9 e) t: `& T* I
  147. ;==================================================3 Q% @; ?  ^1 g1 V
  148. ;设置命名表属性
    1 |& w2 D; z% \. O' P
  149. Init_NameTable_Attributes/ G5 H7 X9 o9 v! K* ~$ ^
  150. BIT PPU_STATUS
    5 w" K0 u+ i. A  I# z! W$ P. l" a
  151. LDA #$23
    7 ^6 M& S: n2 }2 D& z# N
  152. STA PPU_ADDRESS
    " i! j- I3 b3 C( u7 t8 u" Y3 ?
  153. LDA #$C0! Z1 S3 U) `0 b& p
  154. STA PPU_ADDRESS0 R7 E! u! E! ?/ g  C
  155. LDX #$00+ {$ H1 v5 A0 V( k) K' M5 a
  156. Init_NameTable_Attributes_Write
    . Q5 b, M3 S  Z' G1 o/ X* d+ @" N. i
  157. LDA Attributes_Data,X
    ! d( i3 U4 n1 g
  158. STA PPU_DATA8 b" X* l9 y, `7 t# u
  159. INX
    : d( X. v# ?: M
  160. CPX #$40) i; H& p4 y8 Y; b  n+ {5 o
  161. BCC Init_NameTable_Attributes_Write
      M; L2 A$ F) I$ U
  162. RTS
    / b6 H# O1 ~) n! r- \  y5 K

  163. ) p  Z0 z& _8 E3 w) Z% B
  164. ;==================================================
    5 Y# C# B5 _4 t/ H4 c* g  W6 S! b
  165. ;初始化命名表文本4 V: n* ^$ C" V* T  t
  166. Init_Name_Table_Text
      X' G6 z7 H6 b# n
  167. BIT PPU_STATUS
    + z! i# v# G! k" S3 t
  168. LDA #$20- _6 u& I" ~  X! g3 M2 S
  169. STA PPU_ADDRESS2 `! ?3 A( }- Y& N: k) [
  170. LDA #$00% y$ `$ l5 Y& i: Z) s
  171. STA PPU_ADDRESS+ M  ^2 {! L8 ]
  172. LDA #$00
    : G$ i: ]; U# q% G) D$ Q$ }
  173. STA FC_Data_Buf
    2 M: p( L3 }5 f. x8 z
  174. LDY #30  \3 w+ {4 z( G" y
  175. Init_Name_Table_Text_Write
    ' W# T0 ^/ |$ `# l" ?0 p
  176. LDX #32% Y1 V( {. {% q8 L8 c9 s
  177. Init_Name_Table_Text_Write_Char) B; S6 g5 u* m' D8 ~- \9 ]
  178. LDA #'0'4 N: N7 V) J! p; z
  179. CLC: c; C+ M! t/ k9 G8 t2 `2 g7 x
  180. ADC FC_Data_Buf3 b& K( v& n4 f: Q; R: W; p( ~( j' D
  181. STA PPU_DATA
    3 q3 Q5 c7 p! ?* c8 I: {6 z
  182. DEX
    6 a& c+ w* T1 y- e2 q# [9 A6 a
  183. LDA #$14
    9 b0 [# B% W4 l- M
  184. STA PPU_DATA' |8 b- x0 {9 ]  q3 k, K
  185. DEX( C$ v- Z& Y  V) F+ c5 r1 k$ |
  186. BNE Init_Name_Table_Text_Write_Char
    ( f5 ]5 R8 n8 f# d2 T. U
  187. INC FC_Data_Buf7 o0 W9 {3 `/ {3 m# _# z; A/ [8 }) d' Y
  188. DEY6 |% M- \  J8 ?. M4 [+ B3 y
  189. BNE Init_Name_Table_Text_Write2 x: W( c) t- C/ e9 N( L; A( ]
  190. RTS" p3 Y4 c: v4 x( H+ ?! Z( o

  191. 6 u* p  {) g* h' z8 }! s; g, i
  192. ;==============================( f1 H/ L  y+ S" c$ C* o
  193. Init_OAM_Ram;初始化精灵内存
    9 F# F9 t3 [0 ^. ~+ S4 E
  194. LDX #$00
    : _' d  b8 a1 S# N1 l* ]
  195. LDA #$00+ i+ @  d' R" w$ m$ H- H4 F
  196. STA PPU_OAM_ADDR3 O( @0 c) ]1 v+ v! N& O
  197. LDA #$F83 u/ L. W8 k+ \0 s3 u) D
  198. Init_OAM_Ram_Write2 r$ L- S6 b5 n+ h4 T6 h. X9 s- O
  199. STA PPU_OAM_DATA/ G" b, J" A5 e; f+ l
  200. INX( `3 |7 l' J  L' Z) X% c
  201. BNE Init_OAM_Ram_Write* Y% `6 L! h  I5 \
  202. RTS
    ' p; O1 U( }3 `. j, \8 i

  203. 4 S  k/ W- c1 J" D/ P" a' P2 ?5 C
  204. GamepadProcess;手柄处理2 {( l1 |$ q/ O% V1 _' ~" b; b
  205. JSR GamepadDatacan& F( z% u) Z+ \  `
  206. LDA <Gamepad_0_Value; [/ L5 h' t9 c
  207. STA <Gamepad_0_State
    ( V" E, g% q2 i+ H* X1 d
  208. LDA <Gamepad_1_Value
    / u' Z1 {; S; @) @! B( H& B: k
  209. STA <Gamepad_1_State/ V0 A! N) ~; J! ~5 P
  210. JSR GamepadDatacan, U& _* C. r; }8 E
  211. LDX #$01
    & g" j  j; g# F8 b" U  s6 p; {
  212. GamepadMergeCheck;合并手柄输入检查0 @/ y/ \( C8 A/ S
  213. LDA <Gamepad_0_Value,X
    . a" ~- Y+ j# H, `* \$ [. ~& h
  214. CMP <Gamepad_0_State,X
    ; T" Q0 \5 x  `/ e# l" N
  215. BEQ GamepadMergeInput
    # n2 a: e3 o. P6 K  j
  216. LDA <Gamepad_Temp,X
    ; s3 w  T1 U4 ~/ g. B2 p0 K* d; G
  217. STA <Gamepad_0_Value,X7 y6 p1 |1 N1 U! G
  218. GamepadMergeInput;合并手柄输入1 o1 {6 G$ z  C3 g& @$ ^
  219. DEX; A- ~3 K' k: Q  l7 b; d: v
  220. BPL GamepadMergeCheck% _5 m) G3 f! e* N
  221. LDA <Gamepad_Merge' Q3 T& Y* r2 I$ W5 ~0 D
  222. AND #GAMEPAD_MERGE_FLAG
    4 d7 C2 R3 \  H3 ^% B* j7 C
  223. BNE GamepadStateProcess' j0 F  ]: U  ?9 m- U( a
  224. LDA <Gamepad_0_Value
    0 l* H8 K& @5 @: ~- o& ~, B$ S
  225. ORA <Gamepad_1_Value# \3 k0 W' @+ b
  226. STA <Gamepad_0_Value. D$ v8 `0 Y$ Q9 Y# q
  227. GamepadStateProcess;手柄状态处理, u- U1 C: M" Q8 V$ V- L) G
  228. LDX #$011 ]% E+ G5 `6 }: a
  229. GamepadStateSave;手柄状态保存! z- ]) R- R$ g. z, O9 f  F
  230. LDA <Gamepad_0_Value,X" z" j7 N; Z+ \( S0 e
  231. TAY
    / r7 F, O( [  m$ G; L: y
  232. EOR <Gamepad_Temp,X4 ^& n3 w5 o% K; d
  233. AND <Gamepad_0_Value,X- k% P: F: R8 w1 Y6 U% B+ F
  234. STA <Gamepad_Once,X4 |$ g6 B8 R% c/ k
  235. STY <Gamepad_Keep,X& y4 n6 Y) W0 l  j1 U
  236. STY <Gamepad_Temp,X
    - @9 q: i$ e$ c4 Z/ {4 `9 K
  237. DEX1 c, E8 {9 h6 C) U: ]
  238. BPL GamepadStateSave
    * k, @, h) _9 N+ W
  239. RTS0 c, F' L% `: b  [3 `6 G1 D
  240. 5 R8 ]& @1 ?( b; c7 W& j
  241. GamepadDatacan;手柄数据扫描& C2 g6 s) |  r6 T* g' i- g
  242. LDX #$01
    ! M8 i# \, C' Y
  243. STX $4016
    & l+ C/ O+ W2 [: q  ]7 H
  244. DEX( G0 D' u. F5 r( u
  245. STX $4016
    6 l% c6 Y0 a" H6 l8 d" i9 q
  246. LDY #$08
    3 V/ Q  X1 g& O( I: O
  247. GamepadPortScan;手柄端口扫描  M/ T: R0 \. c2 f% C
  248. LDA $4016
    7 W, |; g7 K3 i+ g
  249. STA <Gamepad_Port_Value
    7 z" R' j1 x& n
  250. LSR A
    ! L7 ?: }. }) K7 m! ~5 J
  251. ORA <Gamepad_Port_Value6 D4 u2 L2 ~& D2 |0 C$ J9 A* _
  252. LSR A
    + C; r( K6 T" R6 L4 P2 L2 F8 I
  253. ROL <Gamepad_0_Value
    % s% }3 J6 D  {# ~
  254. LDA $4017
    9 C5 B- R, {! Z  ^$ s9 e8 ]* P
  255. STA <Gamepad_Port_Value* ^/ @& w. _9 T) y; c4 U6 a3 b
  256. LSR A
    0 W4 I1 M6 b/ R5 S1 J" q
  257. ORA <Gamepad_Port_Value, F( ~% C9 J: m& D- Q
  258. LSR A
    2 V, J8 o6 U6 H  L% P0 G% ]
  259. ROL <Gamepad_1_Value
    5 x) g4 l4 [# A! D2 A
  260. DEY/ p; {: E! }5 ?$ f2 \9 L. m5 r
  261. BNE GamepadPortScan' D/ J% ]: p! \: F* {+ Q2 z
  262. RTS
    ( v* R8 d- {& B

  263. 2 U: ^0 s$ _. x2 J+ ^( U4 @) h
  264. ;==================================================1 I4 j! l  C: d8 U
  265. ;PPU处理
      W7 L6 q2 ~$ e
  266. PPU_Process/ Y5 [2 Y3 t( {" ?' M
  267. LDA #$00
    ( n$ i: s# v# Z5 J2 J0 G" O8 I
  268. STA PPU_MASK
    8 W& o% c  m3 o# x, {5 q# m; t5 |

  269. $ q0 `% }; f+ g" Z, m
  270. BIT PPU_STATUS( k! z$ b6 E/ l: x( U$ z
  271. LDA #$20& y  B/ l  @  S0 B5 \# m
  272. STA PPU_ADDRESS
    9 J% @+ C: U& P
  273. LDA #$00
    5 e  U) G  |! o2 ^: |
  274. STA PPU_ADDRESS8 \. i; k, [: l' ^4 F
  275. 0 ~5 b* G  B8 x5 A0 m- V
  276. STA PPU_SCROLL
      {% b5 [6 T  L9 Z; E$ K: x7 G
  277. STA PPU_SCROLL
    ( H( v3 n( J( E& o+ u  t
  278. ( h) B; ^& B  u* Y! ]* p
  279. LDA PPU_Msak_Buf0 i& I6 j  ?- H. p* o: p  Z
  280. STA PPU_MASK+ f% u0 t! Y& @4 ~8 k9 h# a

  281. + F! p2 E8 I4 W
  282. RTS
    - u: E) }* k; c; R1 X5 w3 G) K

  283. + Z2 H7 C2 X; g8 Z. H
  284. ;==============================4 g: J) I6 A7 N& c7 ~' t2 r" J
  285. Time_For_Vblank;延时等待1 H( X2 r7 ~) x6 r' S4 z
  286. LDA PPU_STATUS
    / o! l1 K; A" X7 }0 A. V% |
  287. BPL Time_For_Vblank7 `2 y- F( Z+ i) ]' ?" r2 m$ a. e  W
  288. RTS6 n7 X) C) z' A- V1 }

  289. - }. y, }5 ~' B' ?) F
  290. ;==============================
    ' z$ p. i" Y6 L  b/ x$ `7 {) z
  291. ;初始化MAPPER19" N) e& f$ r; o3 r) Q# Z4 L# J
  292. Init_Mapper19
    : e& _; @8 P0 }, O9 j; z" Q0 G; Z
  293. LDA #$00
    - A9 v( D( O6 g( [8 r4 e7 C
  294. STA M19_CHR_0000# N' A: n; u- H9 O  V! F! f& J4 S
  295. LDA #$01
    9 j, U4 m" P) }* x7 D8 u, H
  296. STA M19_CHR_0400. Z5 v6 l3 Z* I# [# ?' B
  297. LDA #$028 ~9 E8 t7 y7 g" [) b  [
  298. STA M19_CHR_0800, [" o% Z8 _# b
  299. LDA #$03
    * h/ l" S! B1 u$ Z# Q6 d
  300. STA M19_CHR_0C00
    3 c- @& S! }% x6 [4 `& `
  301. LDA #$04; ^( V% ^5 H1 L* S9 Q: [8 F) G
  302. STA M19_CHR_1000  v+ l) B( N8 a
  303. LDA #$05
    6 ]3 C9 t' Y; y$ i" L  |  z
  304. STA M19_CHR_1400
    1 z# L+ R, T* O9 [. s
  305. LDA #$06  Y/ {) C$ A9 a- h" V! N
  306. STA M19_CHR_1800$ F8 h  w) e3 m2 b9 f- @
  307. LDA #$07  z  k- H( c* A2 A+ h8 e
  308. STA M19_CHR_1C00
    ! u2 ~0 g: F5 X( j

  309. & N& `0 ?! I0 X4 T6 K
  310. ;禁用IRQ
    7 `+ X7 v7 D" K4 a8 b
  311. LDA M19_IRQ_COUNT_H$ {; w( _4 `  M8 c# l
  312. AND #$7F
    / p9 h; o' l6 H9 h9 T4 ]
  313. STA M19_IRQ_COUNT_H
    * D7 r2 n  P  E+ E6 Y6 x( ~

  314. ( w! ^% A& ?7 b1 z9 K# X5 [
  315. ;命名表6 n: r9 T2 `1 n
  316. LDA #$E0% Q' I. ^4 a$ x5 g- x' \0 r* T
  317. STA M19_NT_20003 u$ z/ b1 B+ [9 H' v8 }! q* Y* f# e
  318. STA M19_NT_2400
    6 X; f. ?5 P+ w( n7 W

  319. 0 t1 o! \- W$ h$ F/ V7 B
  320. ;命名表6 [2 U# ~# S6 q7 Q& ?
  321. LDA #$E1  w2 e6 s9 T0 w( \
  322. STA M19_NT_2800
    3 t3 `) |3 N6 x& s) ?
  323. STA M19_NT_2C00% P0 V: z: S' R* c( e; T
  324. 2 g# A0 E+ O5 ]" `4 t8 I
  325. RTS0 m; b  N# e/ k2 I8 t* y9 a% H

  326. ! q; {; ~& d8 }" @8 Z
  327. ;==================================================) v3 x! D8 V0 @
  328. ;重置中断处理9 r( k0 ~8 B# K2 ]+ j6 l9 O: T5 _
  329. ResetProgram
    $ G5 L. E4 l$ e; ?& _$ w
  330. SEI" V/ M6 x7 ]& G: c2 C  u. C5 R
  331. CLD3 f+ ]8 Y' v& _4 X! ~0 A/ x5 P  u
  332. LDA #$00
    ! j* v6 p8 ~& M* p- C' C
  333. STA PPU_CTRL
    : C6 k! _) m4 a5 B: V, E: |
  334. STA PPU_MASK5 i0 g# w& Z" U; k- z( p
  335. STA PPU_STATUS
    & \1 f) ?& d3 _  W
  336. STA JOY2_FRAME
    - I9 [0 U/ h# b# A' h1 S$ W& q, `
  337. STA APU_STATUS/ b- V+ k, d4 {: G/ E- G; S

  338. 6 y5 k' d1 a0 V8 l' }' L+ A
  339. LDA #$C0
    ; \5 k/ \9 a$ j  Q, m
  340. STA JOY2_FRAME
    7 U( B# S$ J  G
  341. 2 a( X$ h8 C, C" J: R# c2 R2 o
  342. ;等待vblank/ H  W. N4 b( T8 M/ l
  343. LDX #$02
    $ K( Q+ P4 c' d, o" P. z
  344. Vblank_Wait_1
    . v) Y3 `8 ?7 W" G
  345. BIT PPU_STATUS
    3 y: X; F* y+ N0 Y5 s6 g3 Y
  346. BPL Vblank_Wait_17 z' s' Y" ?! P# R  t( |, ?! ], R8 V
  347. Vblank_Wait_2
    ! ?9 `6 G2 E, D) d
  348. BIT PPU_STATUS
    : p* Q/ x: H/ \& ?
  349. BMI Vblank_Wait_2
    ) y: }) c& X5 |7 F1 w) S. j% }
  350. DEX
    . O. H  q8 o4 Z; h
  351. BNE Vblank_Wait_1
    + ]/ E# k* a& o! ^

  352. 9 V' M8 a2 g2 K7 X5 T
  353. LDX #$FF* R+ v% }* @" E2 i2 e
  354. TXS* ?1 `" N+ d- {; A; L/ R* V' f9 x. C
  355. . j) q. Y4 o! q: e; y3 W4 v
  356. ;初始化MAPPER19
    & {6 [  y- r. |$ m
  357. JSR Init_Mapper193 e( w. |% F! _  P8 ^& n8 S
  358. 8 b9 h6 B( N: a8 D- T, G9 P
  359. ;==============================
    $ t9 W' d9 s4 I5 y+ O
  360. ;RAM初始化. b) [" Z0 \: ]7 p
  361. Nes_Ram_Init) w( z9 d" t; O, w4 E
  362. LDY #$00" p7 {. _: d9 N$ \7 X. Z
  363. LDX #$08
    4 I4 r5 p, M4 F
  364. LDA #$009 o: S1 U) _  _( T6 f! c4 ?; C
  365. STA <$00
    - B; ~5 E3 B- x: k* i' ~# b
  366. STA <$01
    : c) D6 e! C) Q
  367. Nes_Ram_Init_Write! B/ V8 d- u. S$ I9 {5 s
  368. STA [$00],Y1 D1 L% R+ d8 J$ x/ ?
  369. INY
    0 t7 o9 r/ n$ q$ m9 Q, o) u, S  ?
  370. BNE Nes_Ram_Init_Write" R( Y/ ?3 y7 ~9 P7 w" e0 I. c6 e
  371. INC <$01
    3 i- i" f2 p7 a  e" ?- p
  372. DEX* r# O5 \9 @6 u2 g! j
  373. BNE Nes_Ram_Init_Write
    % P8 S* v' D! k/ `
  374. + W7 q; S( l! q
  375. ;初始化命名表2 e1 m, @; ]' G
  376. JSR Init_Name_Table; v' Z# R( k% ], u
  377. 0 u5 H+ y& N4 j) S* R6 d4 |+ n7 p
  378. ;初始化调色板+ Q$ E/ o2 V! s1 Y- j4 j
  379. JSR Init_Palette
    ' L5 h% M- k/ A8 J& q4 A

  380. ) ?9 x/ r4 u& z
  381. ;初始化命名表属性$ {* v" K$ m/ I6 ^/ D9 A
  382. JSR Init_NameTable_Attributes1 N0 |# g5 @3 k0 F* ]+ A* Q
  383. : Q* v. S. r- l4 D/ S
  384. ;初始化精灵内存
    7 ~* h/ J; _, ^, `
  385. JSR Init_OAM_Ram" {* \: B. s  A) J0 Q, E3 r' G7 `

  386. 5 l& C# B' v9 r* Z/ ^- H" R! g
  387. ;在屏幕上写点东西
    5 ^  b4 q; E% G' O8 j# u
  388. JSR Init_Name_Table_Text
    6 `5 X' p) k) }. d% J; \# J! J7 [7 p
  389. 6 A5 [( i' j2 u! w5 r. \1 E0 J
  390. JSR Time_For_Vblank0 f. ?/ o$ @# D3 W) I/ C$ i
  391. ;开启PPU控制
    5 Z. U) I1 J  D2 k' e' `( g! j
  392. LDA #$A8
    5 a. a% V0 z! J5 F' i: _
  393. STA PPU_Ctrl_Buf
    : K: P; ?4 w/ t! p' r# x2 X5 ~3 O
  394. STA PPU_CTRL% c) Y$ [; W- w; F
  395. & J/ H6 n' u' g2 g7 I/ P3 s" ~: A
  396. ;开启PPU显示
    - P0 d, o% e# ~" F5 l- A! r
  397. LDA #$1E
    * x, t5 {. N$ [2 ], H  w
  398. STA PPU_Msak_Buf
      K9 H- d0 t! ]! e3 |+ B9 W" @0 e
  399. 2 s% E9 |' z- N" G6 {3 V! g
  400. CLI! Q  Q+ p6 `" R5 T, o6 \
  401. JMP Loop
    6 b- i  r1 y' j3 r
  402. , Z) y- j" _. o4 J7 _6 Z5 _, f
  403. ;==============================5 O0 f; v; E  P% F, r
  404. ;死循环, 等待NMI中断
    - T, @) S% Q( d/ U' X, E
  405. Loop+ _& H- z- G" H( J/ K9 u6 @: U
  406. JMP Loop
    4 @( u8 g( i" c+ f

  407. 0 ]3 O  ^, M0 M
  408. ;每行扫描线1789772.5Hz / (262 * 59.94) = 113.9671 a. w1 n! y8 J7 J

  409. 2 p! U' l1 p) `8 {$ _1 D  O
  410. ;BEGIN_LINE_CYCLES_START = 32768 - ((260 - 240 + 16) * 113.967)& y) X0 r9 K' ]0 n3 R' E
  411. BEGIN_LINE_CYCLES_START = 32768 - (4103)
    5 c5 R& R/ |1 W9 F$ \, `7 `
  412. ;==================================================
    5 a6 R! H: o* `0 D$ U
  413. ;NMI中断处理
    : O3 P3 o* a- ], n  J( U
  414. NmiProgram8 L: n! K% k6 R
  415. PHA
      g4 i1 R2 g9 R1 V1 P; j+ d
  416. TXA
    7 D4 e0 o& T0 z8 ~0 l/ ?/ b0 p
  417. PHA& d" v7 L* U8 P# c2 t
  418. TYA
    3 z) ~& E0 m2 [
  419. PHA, M1 F1 H  Y* D/ I1 g! Y' ^

  420. $ F7 r; {1 Y) I" {/ c( I6 Y
  421. BIT PPU_STATUS
    " B& T/ o! p3 y+ j7 y; X( J

  422. 5 _' b' s! C1 N: D9 \+ k
  423. LDA #$00
    - f3 g7 o0 D: I* K6 }6 ?+ }% \- W
  424. STA IRQ_Index( s$ T! t0 Q- w8 Q4 l* y. C# `

  425. ' S* \& D) T* w6 G% e/ \4 I' X6 N
  426. ;Mapper 19 的IRQ是基于CPU周期的, 为了IRQ稳定, 首先开启IRQ, 避免PPU处理周期不稳定导致IRQ抖动" ^) Q  v( o3 k5 W8 m5 [
  427. LDA #LOW(BEGIN_LINE_CYCLES_START); z: _, A" X) Q0 P
  428. STA M19_IRQ_COUNT_L; P7 ^  e' G9 `5 Z  O4 t
  429. LDA #HIGH(BEGIN_LINE_CYCLES_START)! [5 Y' [1 n! T4 i0 Y" J  C3 a
  430. ORA #$806 e) r/ H% T2 X: \
  431. STA M19_IRQ_COUNT_H
    & g+ S. ]5 t+ a( l' ~" S
  432. CLI
    2 P* ^. e! L6 |' p% X0 Y$ q
  433. : ]; b! c7 Q* i# Q2 K: I
  434. ;关闭PPU控制: O. l8 l( }8 S% `( h+ Q
  435. LDA #$00. F5 f4 A! r6 R8 r
  436. STA PPU_CTRL) ~, p" v- b% U
  437. . v0 B. h8 f: Q: A! ?+ K; i! R4 G
  438. ;处理PPU+ L  l3 v% }. ^5 {! H
  439. JSR PPU_Process( u; z. t3 P# R4 I- ~2 y

  440. ) j9 J% t$ v0 g& Q' q8 `
  441. ;开启PPU控制/ I) Y4 N) P1 o
  442. LDA PPU_Ctrl_Buf' J- y* S& {' D& X
  443. STA PPU_CTRL
    0 S- C6 T6 G8 E+ R) t

  444. 1 L( N. ]% P0 z: O. ?( a
  445. ;手柄处理  j  ^* g' [5 b, b
  446. JSR GamepadProcess
    8 N( c  V0 L4 I; s& C# t/ m

  447. 5 f% t. G/ C3 I. g5 H
  448. LDA #$00$ e$ z4 z3 y3 T
  449. STA IRQ_Index2 s. _9 F1 b. `7 |1 b$ m- e

  450. 4 r' n& \0 G- i  Z5 C* \
  451. PLA
    - }$ Y' b8 W* x9 Z; a* K$ E# ?, ?4 z! W! E
  452. TAY
    4 w# @/ t! P4 c" F
  453. PLA& H# k* c4 W' Y* x
  454. TAX) c( T) X. @) Y1 Y7 a! X  r+ ]
  455. PLA; S+ i7 t$ [/ X9 ]" G' ]* `
  456. RTI
    . K" d, v( D3 c, T+ c% b
  457. 2 r3 f4 A9 b1 ?! Z, m
  458. ;每行扫描线113.67& Y* O( \5 k. w5 [9 U
  459. ;BEGIN_LINE_CYCLES = 32768 - (16 * 113.967)
    0 B; G) j& p  d1 n' t
  460. BEGIN_LINE_CYCLES = 32768 - (1824) + 27 + 7: ?$ K6 Y+ _4 i! q* d4 H
  461. ;==================================================
    0 O$ Q- z3 p  w
  462. ;IRQ中断处理( i  T! z2 H' p* p: W: c% |1 b7 N
  463. IrqProgram+ j- ]0 k  q; K+ ]* ~* Y
  464. PHA0 V8 F1 Q* S& E, G, B7 ?( J* |
  465. TXA! A! x" |! G& Y( t; `" n% U
  466. PHA
    2 l7 ?6 d- s  p" ?2 \" p0 ]3 y5 X
  467. TYA
    ( a2 D" z$ ~7 n3 W1 t- p! Z
  468. PHA
    $ I8 n- s& c/ [8 }/ \
  469. 7 u" D& Z. `" R9 P1 m9 T3 m
  470. ;16条扫描线后触发IRQ
    0 }5 D3 X: c, S( L2 w
  471. LDA #LOW(BEGIN_LINE_CYCLES)$ c) r+ A) W! J0 W/ W
  472. STA M19_IRQ_COUNT_L$ w7 n8 @0 _  k7 T3 O/ r5 j# T0 f
  473. LDA #HIGH(BEGIN_LINE_CYCLES)3 P) g9 R# _/ A- N5 m3 ^! ^
  474. ORA #$80+ H3 `- _4 {9 F0 s9 @
  475. STA M19_IRQ_COUNT_H# d6 F* j& P. P' x

  476. # g" ^  E% t' s0 G
  477. LDA <IRQ_Index8 r3 S% r1 C1 E& ?) d% W
  478. BNE * + 4
    - v6 U4 L: P' _. w% P0 H% p
  479. INC <PPU_Scroll_H) D! y8 M1 U3 P- C! G; v

  480. / A3 h& X- J5 A; {
  481. ;设置屏幕滚动
    ; j; C* b: D' @5 a5 h$ n- X. A
  482. LDA <IRQ_Index7 G" J, b0 ]0 |+ p' W, ~' s; G. }
  483. AND #$01% c) [$ i; T8 |+ o
  484. BEQ Irq_Scroll_Right
    ) v+ W  B* }) z! f: ]; X6 l
  485. # z: a+ K4 E( o! b% Y
  486. Irq_Scroll_Left8 q  D, i5 z: [  q) C: S) `
  487. BIT PPU_STATUS
    " V$ R4 s! M  l7 d: k  H
  488. LDA <PPU_Scroll_H0 P: D; w$ D: t2 O9 A/ Q
  489. STA PPU_SCROLL7 @9 V$ \* z9 P, j8 t
  490. STA PPU_SCROLL6 ]3 h! ]; d+ B5 n
  491. JMP Irq_Scroll_Over
    1 s+ R: H( H! M3 S, |9 K

  492. ' p( K2 H9 N* P6 Z5 M9 L
  493. Irq_Scroll_Right8 L  {, L  z3 F# U3 [
  494. SEC
    " W. Z7 h9 p$ A  f2 @% }
  495. SBC <PPU_Scroll_H, X- Q7 h: U& `& K
  496. STA PPU_SCROLL/ a# S* p, y8 t; l
  497. STA PPU_SCROLL
    & n$ Y5 \7 ^" p4 [- N+ ~  d: ~1 K
  498. Irq_Scroll_Over
    & M& C# m  H& w0 Z8 v. J

  499. * g5 {' q4 a7 d0 R; D, q! k6 a
  500. INC <IRQ_Index  i5 I9 _3 P4 B  I: C9 s( n$ |$ b

  501. 2 [: H6 q! F% W* n) ^
  502. LDA <IRQ_Index
      M# I  z. u# R" ^' c- T
  503. CMP #14; s, ^* \4 ~. g& q) v6 T% F# f
  504. BCC * + 10( ]$ a( t3 g' y
  505. LDA #$00, V" F! D& a: V
  506. STA M19_IRQ_COUNT_L& G4 A& P$ @- R6 M
  507. STA M19_IRQ_COUNT_H
    ; y5 |9 W6 [4 G+ \5 T

  508. 0 }* F' U! C/ ]( q* z8 x: T1 m
  509. IrqProgramEnd
    % y7 {9 @( V5 u/ ]8 \0 l% Q
  510. PLA
    : \' v8 [3 P) r4 Q
  511. TAY
    - ]1 h7 G& d) K( D* u$ z
  512. PLA
    ) ?' W3 ~' ~3 u3 g; t
  513. TAX
    6 R. y- i$ X/ X( \% m5 z
  514. PLA9 \" b6 W3 D/ G/ }4 C4 M
  515. RTI% K. W; u$ e, }# {
  516. $ t' d5 p$ A3 o
  517. ;==================================================
    * N- j/ k5 ^2 J2 S
  518. ;中断表! w( z, c% |6 w8 f, g9 S9 s' I
  519. .ORG $FFFA
    " B+ O+ r- t2 |  t* Z6 q: |' @
  520. .WORD NmiProgram0 t3 C: ]. [" F+ a
  521. .WORD ResetProgram
    6 l! y; i& p7 ?2 h4 B
  522. .WORD IrqProgram
复制代码

) S4 p1 G: H! Q0 m

本帖子中包含更多资源

您需要 登录 才可以下载或查看,没有账号?立即注册

×
您需要登录后才可以回帖 登录 | 立即注册

本版积分规则

Archiver|手机版|小黑屋|国治模拟精品屋 ( 沪ICP备15012945号-1 )

GMT+8, 2026-4-26 19:19

Powered by Discuz! X3.5

© 2001-2026 Discuz! Team.

快速回复 返回顶部 返回列表