设为首页收藏本站

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

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

[复制链接]

签到天数: 39 天

[LV.5]常住居民I

发表于 2023-7-16 20:16:44 | 显示全部楼层 |阅读模式
  1. ;[FC][Mapper19 IRQ]; \: d# T- V  P" r; F
  2. ;FlameCyclone 20230710
    & o& c4 }  f+ ]* L* c# g
  3. % }% c7 C7 \2 D' d% B' k
  4. ;文件头
    & v* S6 q" c) e  x* x/ M& D/ b, W
  5. ;======================================================================. j- M  r1 ]  r& P) o
  6. .INESPRG 4                                              ;16KB PRG 数量
    9 n" {) P4 j+ }1 ?7 Y! ?0 H
  7. .INESCHR 1                                               ;8KB CHR 数量2 W  @9 p% m) c! d7 N& T# U
  8. .INESMAP 19                                                 ;mapper 19
    % v* s+ K6 K) M% |* J( l0 ], t
  9. .INESMIR 1                                   ;命名表镜像 0水平 1垂直
    / ?( j) x4 E7 V' P

  10. 5 {8 O9 u7 f/ o+ d9 x6 g9 E
  11. ;必要条件
    3 r8 k1 k: L% r2 G
  12. ;1.持有CHR ROM" l1 q: b% D! N* p9 @* Q# h0 p3 N/ j
  13. ;2.背景Tile和精灵Tile必须使用不同的图案表, 如背景图案$0000, 精灵图案$1000# @; n- V7 ?8 |6 i6 N8 G( z- ^
  14. ;3.精灵内存(OAM)不为空
    & X( F# C6 b  W2 B. B" x

  15. * L+ w  d2 d  V; J, G, I
  16. ;==================================================
    % _' b2 O4 h- ~& F
  17. ;NES端口常量( M* c& e6 f$ o" x% S; a
  18. PPU_CTRL                =   $2000   ;PPU控制寄存器( J0 F% p( G* i/ v
  19. PPU_MASK                =   $2001   ;PPU掩码寄存器
    ( J' l; n' C% E, K; M
  20. PPU_STATUS              =   $2002   ;PPU状态寄存器:读取后PPU_SCROLL和PPU_ADDRESS被复位,下一个写到PPU_SCROLL的数据是水平的,写到PPU_ADDRESS的数据是高位, O2 S; @: l0 F* j3 }! F1 B
  21. PPU_OAM_ADDR            =   $2003   ;精灵RAM地址:用来设置通过PPU_OAM_DATA访问的256字节精灵RAM地址。每次访问PPU_OAM_DATA后该地址增加1
    . O7 l$ [& h3 s5 `& [
  22. PPU_OAM_DATA            =   $2004   ;精灵RAM数据:用来读/写精灵内存。地址通过PPU_OAM_ADDR来设置,每次访问后地址增加1
    * w0 ^# y0 H: Q& q  q
  23. PPU_SCROLL              =   $2005   ;屏幕滚动偏移:第一个写的值会进入垂直滚动寄存器(若>239,被忽略)。第二个值出现在水平滚动寄存器
    ; i, Y8 `. X% M. e" r
  24. PPU_ADDRESS             =   $2006   ;VRAM地址:设置PPU_DATA访问的VRAM地址。第一个写地址的高6位。第二个写低8位。每次访问PPU_DATA后地址增加6 o3 V6 o' W( j) n
  25. PPU_DATA                =   $2007   ;VRAM数据:用来访问VRAM数据,通过PPU_ADDRESS设置的地址在每次访问之后会增加1或32
    - S5 e  K$ T4 M) ^2 L
  26. OAM_DMA                 =   $4014   ;DMA访问精灵RAM:通过写一个值xx到这个端口,引起CPU内存地址为$xx00-$xxFF的区域传送到精灵内存* D( F2 ~0 I9 v% q8 u7 I
  27. APU_STATUS              =   $4015   ;声音通道切换
    0 q4 Y9 L1 c$ ]! }3 n0 j
  28. JOY1_FRAME              =   $4016   ;手柄1 + 选通
    - o- ~( `0 T, B6 L
  29. JOY2_FRAME              =   $4017   ;手柄2 + 选通- n+ o9 X  \% H. V% [6 |3 P

  30. $ U0 t- }9 X; F8 B: W6 Z3 i
  31. ;==================================================: V0 f# n! U  G" h- I
  32. ;MAPPER 19端口常量* C1 Y* R# m  O- m8 s
  33. M19_CHR_0000    =   $8000
    $ h$ y6 e2 z% [7 ^6 p& k$ x
  34. M19_CHR_0400    =   $8800; T( h% B% O% s( b
  35. M19_CHR_0800    =   $9000! v+ n; Y9 p# \" a6 a6 v
  36. M19_CHR_0C00    =   $98008 E! h. w2 {4 O7 J  a, k  W; M
  37. M19_CHR_1000    =   $A000+ x, I7 J  h* t9 b! n
  38. M19_CHR_1400    =   $A800
    6 e6 X  Y, p3 _/ C, c  n9 ]
  39. M19_CHR_1800    =   $B000
    . u. ^$ Z  t6 i3 [5 I# L
  40. M19_CHR_1C00    =   $B800
    8 j9 G$ h" Y* ?, z( p! ?7 n" ~
  41. M19_NT_2000     =   $C000
    % G( L) ~$ o0 i3 f6 p4 ?
  42. M19_NT_2400     =   $C800
    1 S% j$ E% G9 C; B8 B2 d
  43. M19_NT_2800     =   $D000
    / @, }3 ]- D: E# [9 e8 j  V
  44. M19_NT_2C00     =   $D800
    , o, c7 r0 L+ p/ ]
  45. M19_PRG_8000    =   $E000
    5 |0 Q# D" q/ U/ ~
  46. M19_PRG_A000    =   $E800
    # b# \7 w$ g  Y5 H' c+ ^
  47. M19_PRG_C000    =   $F000
    2 X: E7 R& K- s$ [8 n3 H0 `  N- c
  48. M19_IRQ_COUNT_L =   $5000
    8 }: E) n! C  \6 J$ p( ^* @9 {9 x
  49. M19_IRQ_COUNT_H =   $5800
      s2 x* P* k  [# o: @* `0 [9 p
  50. 8 a( I, s1 w$ M# _
  51. ;==================================================
    / @/ J- f/ z1 d0 o8 I
  52. ;程序块配置
    $ ~4 f5 Z3 i$ u7 O' y( t
  53. BANK_DATA_MASK          = $07
    9 v7 Y( Y# O( t  X: o. R/ u" B) _
  54. ;--------------------------------------------------, \, f; j2 c# q- ^, y( ^# O
  55. RESET_BANK              = $070 W! A1 w* D/ a+ Z- G0 ~+ l
  56. RESET_ADDR              = $FC008 ?+ {, Y+ s  R) |
  57. 2 T! v' l5 p0 u' z
  58. ;==================================================
    * i* L' M! P% T8 N- m7 l" S
  59. ;图像块配置
    # C. m( o; i" M) F$ U% H
  60. CHR_DATA_BANK           = $08, b) P; L# q9 r, ]' V
  61. , A& j) \: V3 A2 V; x5 n/ ?
  62. ;==================================================$ H% B1 c# k" K. {( f
  63. ;零页内存地址配置+ O5 V* ]  w7 U$ @0 S/ l& J
  64. Use_Ram_Addr            = $808 i  p# H1 y1 v% l# Y/ X% r- D
  65. PPU_Ctrl_Buf            = Use_Ram_Addr
    : [: b* |" f" T, V3 M9 l- d. U
  66. PPU_Msak_Buf            = PPU_Ctrl_Buf + $01
    : E8 F8 B! E  b1 L9 X  C
  67. PPU_Scroll_H            = PPU_Msak_Buf + $010 _, n6 t) h. q9 ~# Y, x
  68. PPU_Scroll_V            = PPU_Scroll_H + $01
    ! P' C2 K) b" H
  69. FC_Data_L               = PPU_Scroll_V + $01" |# `0 q3 ?( v# z2 N2 V# H: L
  70. FC_Data_H               = FC_Data_L + $012 ?" {  Y$ G; @8 S+ L& z
  71. FC_Data_Buf             = FC_Data_H + $014 I0 j5 R6 T$ R
  72. ;==================================================
    ) O1 {# s& A1 B  h& g
  73. 8 Q! z5 O6 S- }$ I; z+ f2 R
  74. GAMEPAD_MERGE_FLAG = $04* a3 x' k3 a, \! J% U2 P0 Z

  75. % I; c, D, P* h: x8 k9 [, A
  76. Gamepad_Keep            =       FC_Data_Buf + 1
    / U# V! b, n/ J% M% @, g
  77. Gamepad_Once            =       Gamepad_Keep + 2
    0 w$ o& `3 \$ p$ u. S
  78. Gamepad_Temp            =       Gamepad_Once + 2/ |* B/ F( R8 q% Z1 @9 i
  79.                                 
    % T+ j0 V: m* p! O" {
  80. Gamepad_0_State         =       Gamepad_Temp + 27 `( W! |, e2 h" \
  81. Gamepad_1_State         =       Gamepad_0_State + 1
    / z' m; s2 l3 [( }
  82. Gamepad_0_Value         =       Gamepad_1_State + 1  D" ]3 n: `: J% l3 N4 u/ i0 z
  83. Gamepad_1_Value         =       Gamepad_0_Value + 12 [0 S+ y' n) h5 B  |
  84. Gamepad_Port_Value      =       Gamepad_1_Value + 1
      s$ o8 D9 c7 B8 i
  85. Gamepad_Merge           =       Gamepad_Port_Value + 1; H. A5 z2 ~: x4 O
  86. , K) W( \* [+ s4 ~
  87. ;==================================================
      e% Z3 x! C3 c5 U" R  Z: M* V
  88. IRQ_Index               =       Gamepad_Merge + $01# L1 b- W: ?( D# j0 E$ g; j
  89. ;==================================================
    3 ?) K. D7 I- y  p* E

  90. 6 t4 D! x9 v* s7 `0 B+ u  n
  91. ;CHR图形数据: G9 ^$ K1 g& Q
  92. ;==================================================
    5 k( P: s% M$ Z% Q
  93. .BANK CHR_DATA_BANK8 u  v) O3 J: ?6 `) S0 i$ q% u
  94. .INCBIN "chr_bank/chr_data.chr"
    3 i# c0 w9 o! Q* M$ n

  95. ( n) l0 v& |$ l2 t" R  ~+ r  _
  96. .BANK RESET_BANK & BANK_DATA_MASK
    1 E- R2 H- H9 A7 a* j! |
  97. .ORG RESET_ADDR
    0 u$ b8 T7 l$ J( r; `5 V1 ]8 t
  98. . r( e  q0 P3 @4 R: {+ U# s
  99. ;--------------------------------------------------3 l% H* E) e3 ?. B! j. F+ R
  100. Attributes_Data
    9 G- r; r5 d, u
  101. ;命名表属性2 d7 V2 v4 Z& Y2 h0 {5 P# i$ U
  102. .DB $00,$00,$00,$00,$00,$00,$00,$00,$00,$00,$00,$00,$00,$00,$00,$007 u0 Y. y1 L& M6 J
  103. .DB $50,$50,$50,$50,$50,$50,$50,$50,$FF,$FF,$FF,$FF,$BB,$AA,$AA,$AA
    , j3 o0 z& D( n6 n8 `
  104. .DB $0F,$0F,$0F,$0F,$0B,$0A,$0A,$0A,$AA,$AA,$AA,$AA,$AA,$AA,$AA,$AA
    & i( h0 w; S4 o% j+ u
  105. .DB $AA,$AA,$AA,$AA,$AA,$AA,$AA,$55,$55,$55,$55,$55,$55,$55,$55,$55
    * D( f* t0 r8 `* w4 G
  106. ;--------------------------------------------------; p. {$ O9 Q% `4 A' F: g
  107. ;调色板数据
    ! |5 R  ?# n& h5 ~8 G; l
  108. Palette_Data
    % A+ F6 ^* M  p$ t3 ?
  109. .DB $0F,$27,$20,$0F,$0F,$24,$20,$0F,$0F,$21,$20,$0F,$0F,$25,$20,$0F7 W9 M6 P2 Q" D0 Z
  110. .DB $0F,$24,$20,$0F,$0F,$24,$20,$0F,$0F,$24,$20,$0F,$0F,$24,$20,$0F# C0 S' [6 O- B& `) _
  111. 8 @8 w2 L/ s1 Z+ C3 \
  112. ;==================================================# N/ R& c% P- S+ L  a/ z! L
  113. ;命名表初始化- O- `! U( ~& _8 \
  114. Init_Name_Table
    % y& i5 B3 A) I0 }8 b6 `
  115. LDA #$20' |! J4 e$ t1 U
  116. STA PPU_ADDRESS
    ' @) h+ U7 S. s4 Z8 Q4 Q: ?  A) b0 z
  117. LDA #$009 f0 n8 B7 I! ?
  118. STA PPU_ADDRESS
    $ M, j; S, N) q9 [; h
  119. LDA #$00( n" G6 Z" R4 Y- V
  120. LDY #$00
    . H% u2 D5 K: T! b& i
  121. LDX #$10, L6 v2 d* ]2 e7 ?- H* |# W7 {
  122. Init_Name_Table_Write
    5 B7 v. v; I9 H1 ~2 n( f
  123. STA PPU_DATA1 z' _: z" V7 B7 J
  124. INY
    ' m% y+ A; Z, i/ k
  125. BNE Init_Name_Table_Write' f% R$ f* _$ _( X9 ?+ h
  126. DEX, P8 f) K/ A+ o3 U  M' b0 }
  127. BNE Init_Name_Table_Write, u. Y0 G8 ?; v5 y5 ~
  128. RTS# v; P! S  B6 A8 n8 K" h  E9 S) N
  129. 5 H! \0 I" `! z! ]! g
  130. ;==================================================1 B4 |8 F& Y$ D) P- `' ^5 b
  131. ;调色板初始化
    / L) L- [# Y0 J, L: f% k2 I* i, M
  132. Init_Palette+ Q+ E% v6 [0 _
  133. BIT PPU_STATUS* B+ @# U, ^8 y' X0 P/ w# f
  134. LDA #$3F
    % {: K( z6 F) K* u+ b1 R
  135. STA PPU_ADDRESS
    $ d( a2 A0 }1 ^, W/ Y- M
  136. LDA #$00& G9 E& P; E3 B0 j  b, D
  137. STA PPU_ADDRESS& y; ~5 O% A# F6 T2 B" ]: ]$ h  S
  138. LDX #$00- l! S# d4 }' f' i4 l$ G
  139. Init_Palette_Write
    / Z/ y  {7 u8 v1 L( S8 k$ T. O3 z
  140. LDA Palette_Data,X+ s* h! i- A3 |$ r8 y8 Z% P' G
  141. STA PPU_DATA
    ' M" T2 J0 D& K( T, S
  142. INX
    5 }7 t! y! N, O/ @/ |5 N9 o
  143. CPX #$206 z5 E. |/ X4 H6 D+ H4 M3 ~
  144. BCC Init_Palette_Write
    * I1 l( y( n( ]# N
  145. RTS* }% A( v6 v% g) d$ \. j, R: x

  146. % S9 ~$ }4 I6 H1 o
  147. ;==================================================
    5 ?- X$ A% V! S: s# o+ z
  148. ;设置命名表属性
    & s2 G4 `) q4 Y0 ?+ j: z$ a
  149. Init_NameTable_Attributes
    6 c: H$ ^: Z9 Z
  150. BIT PPU_STATUS
    ) S7 E. @' f. E
  151. LDA #$23. v8 Q2 o0 B. M3 L: {+ j
  152. STA PPU_ADDRESS
    # n; t( T1 _( p" `
  153. LDA #$C0
    6 O8 }6 R4 l& n& j8 k
  154. STA PPU_ADDRESS$ K+ S$ I0 u, k: l' u
  155. LDX #$00
    % A* R) [4 q9 a$ }, [9 N% ~
  156. Init_NameTable_Attributes_Write% y& K" `& u2 ~: R; X' F" S" B. }. {: d
  157. LDA Attributes_Data,X
    , f$ b0 A4 x3 V) e) r6 @0 B
  158. STA PPU_DATA! C, U7 I9 I, V$ Q! p2 F6 \! B
  159. INX
    * x, ^# p5 b' z' i' l6 w; g
  160. CPX #$40
    ( G2 l- D; c* }. d( {# V6 \& o
  161. BCC Init_NameTable_Attributes_Write! G5 j: v6 Y) g( S" U. B! F& v
  162. RTS
    3 |9 _$ a% S( U( L( ^

  163. ! O, ^1 n- a; ~0 F' R/ c
  164. ;==================================================
    0 s! W8 O7 E+ k
  165. ;初始化命名表文本
    9 ^( V( b0 }8 O* d/ h! f( `) x
  166. Init_Name_Table_Text
    ) w' H# _4 m1 @% a4 L7 Y
  167. BIT PPU_STATUS
    4 R) i+ y9 w! `
  168. LDA #$20
    - q( D" p/ r7 j; @) \4 S% x
  169. STA PPU_ADDRESS2 v8 }/ }6 m. y! G. i3 Z
  170. LDA #$00
    6 ?; Q' @" B$ Z( e+ z  s2 o- T
  171. STA PPU_ADDRESS# g; m, O: x$ `3 v7 h$ l! s
  172. LDA #$00
    , A; v9 }% b# ]
  173. STA FC_Data_Buf
    7 h4 d1 d, s* o. V7 [* X' k7 W
  174. LDY #30
    # R! k0 q; Q1 K" k( s; G0 ^$ q* w* D
  175. Init_Name_Table_Text_Write3 `) O/ u  n, y7 Z# W8 f
  176. LDX #327 ]6 }/ q6 z+ O
  177. Init_Name_Table_Text_Write_Char
    % [# f. l! z" E9 @( j! T1 W
  178. LDA #'0'
    & ^. @* {5 h5 Q9 J4 E; H. ^9 r
  179. CLC
    % ]8 e0 P9 m" _* f& q
  180. ADC FC_Data_Buf
    - }8 B: [" E! T/ X. K1 v
  181. STA PPU_DATA
    3 v/ F6 A) [% Z+ h! Y; I; D' r
  182. DEX
    $ a& `3 F- p& f$ ^1 o6 c! j
  183. LDA #$14
    7 K, W# n+ V! s2 U- H) w
  184. STA PPU_DATA
      \7 _) W! T$ ~+ S$ a
  185. DEX
    4 C, x) p: i) L  \8 [
  186. BNE Init_Name_Table_Text_Write_Char
    $ y: {) z" K5 N/ ^7 O- N2 _
  187. INC FC_Data_Buf! J' Q4 D) @& P. @4 z
  188. DEY
    ! i0 N( k1 T: V' ?0 Q! Q  q2 Q; ?
  189. BNE Init_Name_Table_Text_Write; U# R/ D! M' l: X: n
  190. RTS
    % e; _: H# }. G  K5 u2 D6 ~- D

  191. & }- h) d4 t8 R& Z2 G* t
  192. ;==============================$ |' j3 C7 }- v  l. Q1 w; O
  193. Init_OAM_Ram;初始化精灵内存4 e8 R2 Z2 R! T6 }
  194. LDX #$00
    ! u1 u5 j3 S: m+ G! x
  195. LDA #$00* \+ S' e4 g0 ]$ S, y1 I5 V  \
  196. STA PPU_OAM_ADDR
    / b% X2 S* T; n6 e* z
  197. LDA #$F8
    . m; r: K4 \  ~- W. \
  198. Init_OAM_Ram_Write
    ; Q1 {) s8 o0 m
  199. STA PPU_OAM_DATA, \( ]! t% L6 E! `
  200. INX
      L0 F0 t3 V( v. v& B  U+ \$ a( C( S
  201. BNE Init_OAM_Ram_Write
    . v( n  k- X7 p& T
  202. RTS
    * w- L* t' m, a# G( Q

  203. 8 f, `: v! a/ p2 x/ W! \$ Y/ [
  204. GamepadProcess;手柄处理
    . G' r1 K6 C; u1 ^1 d+ |/ I
  205. JSR GamepadDatacan
    , ]) D0 W0 C6 c# I9 Z1 m1 _: V
  206. LDA <Gamepad_0_Value  C- v$ P  N: }# h$ j& h
  207. STA <Gamepad_0_State
    & ?. ^, \) Q8 t- A. j
  208. LDA <Gamepad_1_Value
    ( H  V) Y8 i5 P  b1 F" l& c& a
  209. STA <Gamepad_1_State
    $ h( ?2 C  F8 n7 E3 V& z; x7 A6 S
  210. JSR GamepadDatacan0 k9 w$ O5 }2 m) l4 R9 r- P# ]: g- v
  211. LDX #$01
    8 {/ r! |: `0 P, Y# P
  212. GamepadMergeCheck;合并手柄输入检查6 {( n6 y- a- Q# t- K; l7 F- I7 m1 g  |
  213. LDA <Gamepad_0_Value,X; y) D  s0 W/ F/ |  K+ {' n
  214. CMP <Gamepad_0_State,X
    , Q6 K. \. C3 y5 M( i: t
  215. BEQ GamepadMergeInput. X, Q* u( t: y7 T: E
  216. LDA <Gamepad_Temp,X9 H4 v3 E7 D3 {  N$ }+ s1 F
  217. STA <Gamepad_0_Value,X
    9 j  Z+ Q/ u5 M
  218. GamepadMergeInput;合并手柄输入
    9 Z* P0 V* v- j( v
  219. DEX+ e/ p: z: j! s3 x# l, K  z4 `
  220. BPL GamepadMergeCheck( J" P% G0 E( K+ v2 l; N: x: Q
  221. LDA <Gamepad_Merge& [# E; G' G$ j8 f6 ]
  222. AND #GAMEPAD_MERGE_FLAG
    1 x8 E& @! p2 U- l8 m
  223. BNE GamepadStateProcess; ^/ N0 i# A, P. S
  224. LDA <Gamepad_0_Value% |. B0 C. i' _9 F; Y
  225. ORA <Gamepad_1_Value  C8 C. {. w$ f
  226. STA <Gamepad_0_Value
    8 q& [2 ^" S+ R$ j$ Q
  227. GamepadStateProcess;手柄状态处理0 f' d6 r8 b% K  P
  228. LDX #$01
    / z2 B, l5 U$ ~
  229. GamepadStateSave;手柄状态保存
    - [, {& u# V" _: W$ W
  230. LDA <Gamepad_0_Value,X
    7 ?7 f% v7 J* {7 o4 f% W& M' t
  231. TAY/ F& [& O# D! O+ n
  232. EOR <Gamepad_Temp,X
    * o- ^  r  U1 Y: J
  233. AND <Gamepad_0_Value,X
    1 i2 T" |: k  N) w
  234. STA <Gamepad_Once,X9 y, [7 m( R3 j1 Z4 V- \
  235. STY <Gamepad_Keep,X
    1 G4 N, L9 c: z/ i- N+ z( ^
  236. STY <Gamepad_Temp,X- b1 N. D8 |# Q# q4 m
  237. DEX
    1 r  o- i8 u2 e0 d! C
  238. BPL GamepadStateSave
    6 M) M$ T, y* z
  239. RTS7 B- n; p8 M" R# G. i
  240. + G3 p! A1 I. w1 u
  241. GamepadDatacan;手柄数据扫描
    # p$ L- b3 }& X0 N, Y' @9 P% `5 j
  242. LDX #$01
    ! p; T  N/ r5 P- q9 Y
  243. STX $4016
    & K5 E4 @& U$ X7 [
  244. DEX7 l7 F3 S4 W% S; h1 I
  245. STX $4016
    4 A5 a" R7 e: N4 v1 Y
  246. LDY #$08( b6 S( Q, x- j8 |) k4 ~9 i
  247. GamepadPortScan;手柄端口扫描
    # B7 Q+ E0 b/ k) w% Z% k: V" @
  248. LDA $4016
    ! e* l1 H, }- Z
  249. STA <Gamepad_Port_Value
    , c+ U; K7 w) h3 D
  250. LSR A
    1 D" E2 w$ Y: T2 V
  251. ORA <Gamepad_Port_Value( J  i! _9 B" Q- }! X8 t
  252. LSR A+ o( i6 v6 h) v# ]
  253. ROL <Gamepad_0_Value- t4 q; n1 y4 {) U& B3 e8 L! A
  254. LDA $40173 y& S" T# O! \5 p! r9 B5 u
  255. STA <Gamepad_Port_Value  I" y) D( f1 }' K. w; j7 r1 F, t
  256. LSR A
    " E) ~7 L0 a: g7 u- [; `9 B
  257. ORA <Gamepad_Port_Value
    0 m6 Y3 V( C8 T. X# E
  258. LSR A, u+ }0 x* |' f) t, K0 z; w6 L& J
  259. ROL <Gamepad_1_Value
    9 U7 I: k8 _7 y- g6 p7 o9 o2 g% \
  260. DEY/ ?2 n$ l/ N7 T6 _) a7 Z# k2 ^+ f
  261. BNE GamepadPortScan& n. h1 F* n$ d2 b" K# l! k
  262. RTS
    6 {4 O4 g* e7 `, u

  263. 2 X0 @! L5 h" I6 ~( F2 e! o6 f: f* x
  264. ;==================================================4 E. }" p$ g( Q; R" {; ?9 N; J. I
  265. ;PPU处理
    & T, i& E  m) C
  266. PPU_Process
      m- ~1 j1 V: ]! n
  267. LDA #$003 X2 D! V3 W  L5 x. J' |
  268. STA PPU_MASK
    + W# B4 {, P5 `- o: K5 e+ m
  269. - _# u  \1 y2 q8 }5 u% M+ N
  270. BIT PPU_STATUS. G" N  ?) [8 ^2 z7 Y# p% J0 ?
  271. LDA #$20
    6 L) A: m/ q! _, Y
  272. STA PPU_ADDRESS; e3 j5 r5 @: ^9 Y6 s
  273. LDA #$00
    ( T: K. C; ?) a
  274. STA PPU_ADDRESS
    9 H( u5 |1 u% ?. F4 [0 z

  275. * b/ O5 W# C* s$ h. `
  276. STA PPU_SCROLL
    $ k3 z" {2 J  J: {8 J  u3 _0 h+ Y
  277. STA PPU_SCROLL, ]$ b$ j( c/ n/ q" z
  278. # S- t& x9 y0 U* k9 @1 P  j% e
  279. LDA PPU_Msak_Buf/ F0 ^9 A% ^" y
  280. STA PPU_MASK7 W4 O5 Y2 q/ D2 ^  r
  281. # A" I9 c0 ]9 E) p3 _( I& C1 U
  282. RTS& j. Z( J# ^3 ?% [) E/ n4 g, E

  283. 6 X) W5 p$ c) p3 r" R+ H
  284. ;==============================+ z" ~3 n, s0 ]! W6 u( `
  285. Time_For_Vblank;延时等待
    0 p' }0 C2 @* S' j
  286. LDA PPU_STATUS/ a( ]4 P2 g' F- [$ Z1 ~" S; z
  287. BPL Time_For_Vblank
    8 V4 l' C/ \2 N' r
  288. RTS
      Q, k/ F( z! j5 U% C
  289. ; N: A2 @3 t5 b) G% v# |6 n& p1 D' K
  290. ;==============================( I: B6 L0 m0 b+ q# d
  291. ;初始化MAPPER19! b. m  B( w* w: u% U
  292. Init_Mapper19' x0 v, N8 t2 k
  293. LDA #$00
    2 G+ x" a( P3 d, _
  294. STA M19_CHR_0000
    ) M8 S0 z7 z& s; f2 k: R& }
  295. LDA #$01
    ) v% e( m9 t. l; n
  296. STA M19_CHR_0400
    % B) O# j) g2 w4 V+ h
  297. LDA #$02
    2 F+ Q+ l" K. O
  298. STA M19_CHR_0800
    . t2 V( P) z  L. S+ W' t
  299. LDA #$030 P7 s3 j! w9 \4 N
  300. STA M19_CHR_0C006 E% X- T1 N4 a. \; J) c4 E7 r
  301. LDA #$04! y1 r' y2 ~/ ]0 [3 {+ H9 }1 H
  302. STA M19_CHR_1000( n2 N4 X; U2 _
  303. LDA #$054 C6 k7 J0 ~0 D
  304. STA M19_CHR_14007 z# h; D2 W& ~6 i  W
  305. LDA #$06, q" @# ^* Y# F( n' \0 Q
  306. STA M19_CHR_1800( [# G& |5 F* i7 a6 ~1 l
  307. LDA #$07( Z1 R7 `! U7 c0 H1 u! r* u7 |' e# j
  308. STA M19_CHR_1C00
    ( {4 Q6 Y' Y$ l

  309. ; R# G* G* w' W6 x( F$ \
  310. ;禁用IRQ6 f) @0 o% B$ t9 a0 e
  311. LDA M19_IRQ_COUNT_H9 s2 @, ~, i( I: m
  312. AND #$7F+ ~" J( J2 h" O$ X) x2 V  @: v" N/ s9 {
  313. STA M19_IRQ_COUNT_H  ~; i+ k8 N* S% j; @" f% c

  314. * f. @: W4 n' U4 p: I0 c
  315. ;命名表
    + ~  a7 a8 {& ]8 m
  316. LDA #$E03 x7 W6 p- |$ g" ~1 F, s
  317. STA M19_NT_2000
    , F. R& [; S$ T- _
  318. STA M19_NT_2400
    + D+ R+ N9 ?! x; c; @* D) L
  319. ( b+ _) W) @) i9 E
  320. ;命名表
    . C5 O3 i+ R' u8 M8 |% m5 D5 K5 I
  321. LDA #$E1, B, }. }$ N2 W5 D$ o% J
  322. STA M19_NT_2800! l, c* u( p1 i4 [) w& l$ C* c1 \! b
  323. STA M19_NT_2C00) v6 H( P  k6 Z$ K2 ]6 b" h

  324. " \6 ^4 }/ Q( w' n$ R
  325. RTS! D  s; _: a# o4 [- m

  326. 6 Q( j( R- h7 D
  327. ;==================================================
    , ?$ ~: @: O$ c2 Z( @7 C
  328. ;重置中断处理) j) r  Z' [4 p4 P0 g# e& }
  329. ResetProgram
    2 F, i. c3 }' N! J& ?
  330. SEI
    2 i8 A8 V" Y0 @2 z, ]) E6 s
  331. CLD) s; C' u% W" ~  V* Y# r& i
  332. LDA #$00) X! G$ j1 v/ B* @# e
  333. STA PPU_CTRL
    9 g) P7 S$ [3 d3 L( ]2 l
  334. STA PPU_MASK
    - i+ ^, o/ Z" h4 ?0 b
  335. STA PPU_STATUS7 T* d& `1 k4 f$ A
  336. STA JOY2_FRAME' h* Y4 D# `6 a6 W8 [* j
  337. STA APU_STATUS7 d/ d( [. s" G" H: B

  338. ( r: Z, W5 a5 Q- y+ m. w) U
  339. LDA #$C0
    ; X5 b: }* L+ i/ R
  340. STA JOY2_FRAME* G* m$ h  Q6 X6 \" ^* |9 q

  341. % Z& i# ~7 _% e, ]
  342. ;等待vblank
    1 E' z2 G0 A# T& s
  343. LDX #$02( n, a. C3 _4 e# d0 O, U, `1 d
  344. Vblank_Wait_1
    , T) m6 ]9 v4 s6 D' t$ ^! m& K( P
  345. BIT PPU_STATUS
    3 E* q  m' K! _5 W# g# b
  346. BPL Vblank_Wait_1$ s( a; S# }6 v" H9 x
  347. Vblank_Wait_2# B1 r% @* w( M, }' S
  348. BIT PPU_STATUS& l4 `0 V+ k- C& q; U
  349. BMI Vblank_Wait_2
    5 O2 K' G( @5 Q8 J7 E' F  C
  350. DEX
    ( s; t" u7 }( Z7 Z# N  I: _
  351. BNE Vblank_Wait_1
    5 M. z3 e& m% S0 L# z/ S) N# [2 w/ t
  352. / b/ J- M& H5 H% K5 c" ^
  353. LDX #$FF0 l% w) g  h) E6 p3 R3 j2 ]
  354. TXS
    ( `; |( R$ y4 C3 I$ S0 c- y- u

  355. + v& y! g- m/ K3 B/ i. ]* K
  356. ;初始化MAPPER19% A- r+ m3 l5 H) c8 _& `* N
  357. JSR Init_Mapper19
    . A$ f& `$ @2 ~5 D4 z
  358. ; X1 J9 q% j' ?- S  N
  359. ;==============================% A! o5 j1 g3 V- y+ \" B+ j. y
  360. ;RAM初始化: r& ?1 ~: }6 C) V9 _4 r8 X
  361. Nes_Ram_Init
    7 S2 I- q/ g; F# U
  362. LDY #$00
    & |1 K& O7 F; m% l3 H. m% b( H3 o
  363. LDX #$08" C; y; E+ @' r: l! q: T
  364. LDA #$00
    ! u( K/ H% p9 Z4 E) z8 a- V
  365. STA <$00
    ! B4 u- T0 T; u, r, ^6 w5 o/ T3 y
  366. STA <$01
    0 S) f  ^+ S% a* C. z
  367. Nes_Ram_Init_Write
    9 _( J, g+ y# N% `8 n# G
  368. STA [$00],Y0 z4 S: g- c( I; x% D, P
  369. INY" r$ P5 p, P) D- l  Y
  370. BNE Nes_Ram_Init_Write3 u4 W5 N8 z7 b$ Z8 ^
  371. INC <$01# f! ?2 U# V. E# i  c9 u$ d
  372. DEX
    : h9 z& O' c6 S; J4 k1 Y
  373. BNE Nes_Ram_Init_Write9 G/ M% M" _0 t, n) n8 H/ c

  374. $ R2 O$ r. E6 I- D" @1 V& I2 F0 }
  375. ;初始化命名表5 z, Q( O1 M" T
  376. JSR Init_Name_Table# m: A8 x# u! {% ~7 E/ M+ p" V" {
  377. 7 b3 D2 b6 d2 B
  378. ;初始化调色板
    ! [. v5 L: K+ ?6 B" r& ^" @
  379. JSR Init_Palette9 e" V  c$ x* j- a4 ~- F5 ?

  380. $ A" h; E0 O/ `* |* U
  381. ;初始化命名表属性
    $ O- g- n( A' G) m! a/ n! G
  382. JSR Init_NameTable_Attributes5 I* ~: d6 p+ n
  383. 4 I# j: P9 `3 N* m0 c) X, T
  384. ;初始化精灵内存
    " s' y( k# O+ b. [
  385. JSR Init_OAM_Ram& Q3 z  M8 s# W" r  f9 C

  386. ) _" w7 K1 U: ^/ M7 W  s! ?5 W
  387. ;在屏幕上写点东西
    + W9 ~+ B! `* c4 H7 B- c
  388. JSR Init_Name_Table_Text
    ' y+ \: n) C6 L& B% O0 K* ?

  389. ! ?( F9 n) @4 ?/ Y$ C; I2 E9 l
  390. JSR Time_For_Vblank! f9 b# N/ i; M6 q! I& d
  391. ;开启PPU控制' ?! v3 V; D4 S5 U# @
  392. LDA #$A8( i1 l) f/ Q) p' L
  393. STA PPU_Ctrl_Buf$ i4 [" `! l9 I) R6 i: Y8 m: G$ j: k
  394. STA PPU_CTRL' H0 }8 \* O7 w2 z4 b5 ^
  395. ! d; J/ {2 R; m. P
  396. ;开启PPU显示- }. X# X" }# o/ d9 T
  397. LDA #$1E3 O" R( V* [& t. F
  398. STA PPU_Msak_Buf
    ) i& q' I" d- \
  399. 7 N: L2 t( ^# r! `! ]
  400. CLI
    , |. c( r" O8 N3 P1 J1 K
  401. JMP Loop
    & E. X8 K5 I+ Q% |2 e4 A8 Q

  402. 0 l4 V2 H1 P  ~3 T+ G
  403. ;==============================! T  O) e1 X& _- y# k' K
  404. ;死循环, 等待NMI中断
      J1 Q; U. @: F2 i/ t' ?2 @- D  u6 }" ?
  405. Loop
    2 M1 X' u* {' y( N& F" {
  406. JMP Loop& ~  C7 a3 \3 [) N0 B" c6 K

  407. % k7 }: I. d  d
  408. ;每行扫描线1789772.5Hz / (262 * 59.94) = 113.967
    - F- c( I8 [) R( J8 ^/ @2 [1 t

  409. ) l! b4 l* ?/ V! Z, v5 V/ ^
  410. ;BEGIN_LINE_CYCLES_START = 32768 - ((260 - 240 + 16) * 113.967)
      _& V5 N# y& G& R: h7 ?
  411. BEGIN_LINE_CYCLES_START = 32768 - (4103)
    % K# ]% }. F4 F0 F# J
  412. ;==================================================/ u2 s, z+ w9 {+ s
  413. ;NMI中断处理
    + t* P- e& A" `* l- K$ z( W/ x" e
  414. NmiProgram
    ! Q9 K) u% K: O% m9 r' R
  415. PHA* {# _4 `4 [# M& z( n/ e/ D6 \
  416. TXA
    3 k; Z: j9 p* B6 ^$ ^  B; q
  417. PHA
    ( f2 ^2 r2 d$ I# a' d8 y
  418. TYA
    ! Y/ v+ E6 [9 c3 H- S# B
  419. PHA7 g* M/ n/ [1 M! ^0 S5 t3 a

  420. ' F9 ]$ \# B% C" ]9 \( w% b1 G" L
  421. BIT PPU_STATUS
    1 J" t8 y- g0 [. @. s

  422. " G8 W# a( [/ _
  423. LDA #$00
    9 t. R) M0 r- o' Y" d
  424. STA IRQ_Index! u6 N: h' _% S4 |$ d# k- u

  425. ( l, A# Z2 I( p
  426. ;Mapper 19 的IRQ是基于CPU周期的, 为了IRQ稳定, 首先开启IRQ, 避免PPU处理周期不稳定导致IRQ抖动
    " {" A& w) {) @6 J" _/ U" e  Z5 s
  427. LDA #LOW(BEGIN_LINE_CYCLES_START)
    4 r* y/ C' a+ }- [9 C: {
  428. STA M19_IRQ_COUNT_L3 ~$ `4 Y6 B: f: i- y
  429. LDA #HIGH(BEGIN_LINE_CYCLES_START)
    3 a% t7 J0 s( N9 B2 i2 b
  430. ORA #$80
    0 k* x2 |9 A0 ~6 @* m
  431. STA M19_IRQ_COUNT_H- g7 t  C7 G& i7 }4 v/ N! H
  432. CLI% Z$ @/ h' O7 O3 x7 T, p
  433. ( y! Y4 I( r' k
  434. ;关闭PPU控制" s2 }. N) R9 k) F, H+ a6 K4 g
  435. LDA #$00: w# m; y, h; d5 ]0 @3 X
  436. STA PPU_CTRL
    $ `2 T/ j. }% N8 Q
  437. / e3 p/ k' @5 V1 @& i# }# I; y
  438. ;处理PPU
    ( J8 r+ \, u, `8 l+ y' n3 m
  439. JSR PPU_Process
    8 I0 L. m8 V+ D& E2 n
  440. + t/ d( ?3 S; g' [' ]
  441. ;开启PPU控制$ D' G7 I' O# [, V" P: h# H  A
  442. LDA PPU_Ctrl_Buf
    ! ~) _+ w* E, v2 |
  443. STA PPU_CTRL) m! H4 U7 \6 g: ^8 r2 M

  444. / n! \2 g9 V$ F2 J. z
  445. ;手柄处理
    ! I. ^" s4 @/ Z2 K% T" b' r( I
  446. JSR GamepadProcess
    6 U& T/ N0 B' q4 _5 G5 c
  447. ; z0 }% V" q% L3 z/ G' P$ ?
  448. LDA #$003 H; v! `3 ~/ `6 x- j4 d
  449. STA IRQ_Index. `  z8 [9 l, c- y! c

  450. " @% G4 ^3 ?# U0 ~" h9 V% o
  451. PLA
    7 D2 K2 e" y3 x8 }1 s0 E
  452. TAY
    $ X& N8 ~* v" H) i7 b: ]/ P
  453. PLA
    3 i. ]7 w  w7 w/ l5 k4 m- K
  454. TAX
      e; H5 T0 Y% I. j. }
  455. PLA
    ; |# ?3 u" v; H2 D/ r
  456. RTI
    " f# _2 g4 ~9 o* F
  457. - |# V% i" Z. N9 X8 O0 ]* E1 @3 E
  458. ;每行扫描线113.67
    + D& T7 w! H1 @4 o8 }1 d" D
  459. ;BEGIN_LINE_CYCLES = 32768 - (16 * 113.967)' A  I/ y* v. ~6 F: Z
  460. BEGIN_LINE_CYCLES = 32768 - (1824) + 27 + 7
    7 H5 H$ |( u: r& b% u" ^, I
  461. ;==================================================
    * D5 m; X1 a) K
  462. ;IRQ中断处理1 w% L5 [* ]6 z3 ^# h0 e
  463. IrqProgram  ~- f/ @# s( v7 ^' ~# V# z
  464. PHA
    6 i6 _) i! `* b2 \. y' W* P
  465. TXA
    + _3 [# v7 N0 v2 q. ^) C, R8 z
  466. PHA
    & A) P! ^: T0 r! b
  467. TYA3 p1 [: B# x! L, @7 f
  468. PHA
    0 t$ p6 U  f* [% o

  469. , I4 L1 c: Z5 g$ |( G- D
  470. ;16条扫描线后触发IRQ! U% s) S+ a. S7 R) c
  471. LDA #LOW(BEGIN_LINE_CYCLES)
    ) m% Z4 @, A2 @
  472. STA M19_IRQ_COUNT_L" L: P- \# A- U. Q4 K/ t  U8 V
  473. LDA #HIGH(BEGIN_LINE_CYCLES)
    4 L# a  R, _4 e" q# C# v7 @
  474. ORA #$80
    - z: k" P# d  v/ U+ E3 E7 D: Y9 X
  475. STA M19_IRQ_COUNT_H
    0 z8 Z; ^" v8 b0 R% ?2 }
  476. - n9 i+ T7 u( G4 L! L
  477. LDA <IRQ_Index3 I* U5 _3 @2 x6 ^( q8 O4 t
  478. BNE * + 4
    : H5 ^7 L1 c; v5 Z
  479. INC <PPU_Scroll_H
      j3 J. W. y( A

  480.   X  w8 B+ ?  z8 e7 {' D8 i
  481. ;设置屏幕滚动( t! w0 @4 [$ @2 s' u) X/ P8 F
  482. LDA <IRQ_Index: x+ Y1 Q. f) i' B( P6 X
  483. AND #$01
    4 e: n, \; e( }  C% S' c
  484. BEQ Irq_Scroll_Right
    : m4 X! v$ d. r% [6 u/ a' H/ p
  485. 2 j# M6 k; ^0 Q! I/ O6 t  T
  486. Irq_Scroll_Left
    $ p5 D5 B, N0 s, y$ k% s
  487. BIT PPU_STATUS
    4 p, R: @; Q, H5 V
  488. LDA <PPU_Scroll_H
    * w* o: j$ |" ]0 i+ s4 {* ?2 F
  489. STA PPU_SCROLL8 {- A% ]6 w/ {. A; a8 c
  490. STA PPU_SCROLL5 f3 ~9 d  K5 f: c' |' H
  491. JMP Irq_Scroll_Over& B0 i6 S' @+ y0 ?* A9 @
  492. ; B+ ^+ h9 i) A; c% X" T* {
  493. Irq_Scroll_Right
    # @" O- @, g# l
  494. SEC
    2 J/ R4 O: M- d9 e( j# _, e
  495. SBC <PPU_Scroll_H
    ! B1 b7 l5 O/ |; I5 P+ K1 s& f
  496. STA PPU_SCROLL) Y6 t8 a' B8 l4 U
  497. STA PPU_SCROLL
    ( i) m2 g( d) j; |& ^( k
  498. Irq_Scroll_Over- i0 \6 M; C" ]8 S

  499. / E3 F/ Y, R9 U6 W* M( \# _# V
  500. INC <IRQ_Index
    " S( t. f  c3 q5 b8 ]5 [
  501. 5 u& ]# B1 W) c5 d( D( \' O
  502. LDA <IRQ_Index
    + n3 P" \$ Q4 }0 O' [, ]
  503. CMP #14! c' E- G5 n2 N/ X$ n$ q/ g7 l& F# z
  504. BCC * + 10" R- S) N0 ^" `* A# C7 u
  505. LDA #$00
    $ u# T0 F! j8 L2 N3 Z; u5 ~8 R% L
  506. STA M19_IRQ_COUNT_L
    5 j; w% r, c# L& ?2 v" F' a' f8 W
  507. STA M19_IRQ_COUNT_H; F" V6 l" |& Q: d' O" X
  508. + `1 K- Y, [, ]6 q+ {
  509. IrqProgramEnd$ a7 `8 F! [' w8 `6 d- u
  510. PLA0 C0 G3 P4 G- Y- a7 q# r, m
  511. TAY
    . D' d2 n" _$ n" f# u  D4 ?
  512. PLA
    1 }5 j6 t! d7 o$ ^
  513. TAX- ?4 ^3 i2 c; O8 V
  514. PLA
    : W9 ?% v* y( A" U* a0 s
  515. RTI- c8 m% L" P6 P7 v3 P( t
  516. / h4 u5 J; P- S- s6 V) l. f
  517. ;==================================================$ ~' Z4 y; Z0 P$ B
  518. ;中断表7 J& \7 Y3 X+ H, f; w0 h
  519. .ORG $FFFA- J% l% v( H4 k3 z' Q
  520. .WORD NmiProgram4 Z" J1 ]7 n( A* h9 d- ?
  521. .WORD ResetProgram
    ) L7 w6 @" H, S2 _. o, S6 z5 Y* o
  522. .WORD IrqProgram
复制代码
9 G# K! W/ L' G

本帖子中包含更多资源

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

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

本版积分规则

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

GMT+8, 2026-6-5 22:33

Powered by Discuz! X3.5

© 2001-2026 Discuz! Team.

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