[FC][音乐12 IN 1][nes + 源码]
本帖最后由 yandagui 于 2023-7-23 22:29 编辑[音乐12 IN 1]
时间: 2023.07.23
作者: FlameCyclone
收录音乐内容:
1.Raf世界
2.最终任务
3.赤影战士
4.双截龙
5.双截龙2
6.双截龙3
7.洛克人
8.洛克人2
9.洛克人3
10.洛克人4
11.洛克人5
12.洛克人6
操作:
上键: 上一个专辑
下键: 下一个专辑
左键: 上一曲
右键: 下一曲
B/A键: 前10曲/后10曲
选择键: 下一页
开始键: 停止/播放
http://flamecyclone.ysepan.com/
http://2006.emu618.org:6180/data/attachment/album/202307/23/200601ozt0dsquupyhlptg.pnghttp://2006.emu618.org:6180/data/attachment/album/202307/23/200600rpf1glmta3bq13pz.png
http://2006.emu618.org:6180/data/attachment/album/202307/23/200559czmeytdaomzjxxjg.png
;[播放器模板]
;FlameCyclone 20230710
;文件头
;======================================================================
.INESPRG 16 ;16KB PRG 数量
.INESCHR 1 ;8KB CHR 数量
.INESMAP 4 ;mapper 4
.INESMIR 1 ;命名表镜像 0水平 1垂直
;==================================================
SOUND_BAR_SHOW_ENABLE = 1
;==================================================
BANK_DATA_MASK = $1F
CHR_RAM_ENABLE = 0
IRQ_SCANLINE = 136
;==================================================
SOUND_DATA_BANK_00 = $00
SOUND_DATA_BANK_01 = $01
SOUND_DATA_BANK_02 = $02
SOUND_DATA_BANK_03 = $03
SOUND_DATA_BANK_04 = $04
SOUND_DATA_BANK_05 = $05
SOUND_DATA_BANK_06 = $06
SOUND_DATA_BANK_07 = $07
SOUND_DATA_BANK_08 = $08
SOUND_DATA_BANK_09 = $09
SOUND_DATA_BANK_0A = $0A
SOUND_DATA_BANK_0B = $0B
SOUND_DATA_BANK_0C = $0C
SOUND_DATA_BANK_0D = $0D
SOUND_DATA_BANK_0E = $0E
SOUND_DATA_BANK_0F = $0F
SOUND_DATA_BANK_10 = $10
SOUND_DATA_BANK_11 = $11
SOUND_DATA_BANK_12 = $12
SOUND_DATA_BANK_13 = $13
SOUND_DATA_BANK_14 = $14
SOUND_DATA_BANK_15 = $15
SOUND_DATA_BANK_16 = $16
SOUND_DATA_BANK_17 = $17
SOUND_DATA_BANK_18 = $18
SOUND_DATA_BANK_19 = $19
SOUND_DATA_BANK_1A = $1A
SOUND_DATA_BANK_1B = $1B
SOUND_DATA_BANK_1C = $1C
SOUND_DATA_BANK_1D = $1D
SOUND_DATA_BANK_C000 = $1E
SOUND_DATA_BANK_E000 = $1F
;-------------------------------------------------
CHR_DATA_BANK = $20
CHR_DATA_ADDR = $A000
;-------------------------------------------------
PROGRAM_BANK = $00
PROGRAM_ADDR = $8000
;-------------------------------------------------
RESET_BANK = $1F
RESET_ADDR = $FD00
;==================================================
ITEM_MAX_SIZE = 12 ;最大节目数
ITEM_MAX_INDEX =ITEM_MAX_SIZE - 1 ;最大节目索引
PAGE_SIZE = 5 ;每页节目数
;==================================================
.IF ITEM_MAX_SIZE % PAGE_SIZE;不能整除
PAGE_TOTAL_SIZE= ITEM_MAX_SIZE/PAGE_SIZE + 1 ;页码总数
.ELSE
PAGE_TOTAL_SIZE= ITEM_MAX_SIZE/PAGE_SIZE ;页码总数
.ENDIF
PAGE_MAX_INDEX= (PAGE_TOTAL_SIZE - 1) * PAGE_SIZE;最大页索引
;==================================================
ITEM_SHOW_POS = $20A8 ;节目名位置
ARROW_X_OFFSET = (((ITEM_SHOW_POS & $1F) - 1) << 3) - 2
ARROW_Y_OFFSET = (((ITEM_SHOW_POS & $03FF) >> 5) << 3) - 1;
;==================================================
Caption_Text_Pos = $204D ;标题文本位置
Author_Text_Pos = $2324 ;作者文本位置
Date_Text_Pos = $236B ;日期文本位置
;------------------------------
;------------------------------
.IF SOUND_BAR_SHOW_ENABLE
Play_Index_Pos = $2273 ;当前曲目位置
Play_Time_Pos = $22B3 ;播放时间位置
Play_State_Pos = $22F3 ;播放状态位置
.ELSE
Play_Index_Pos = $226C ;当前曲目位置
Play_Time_Pos = $22AC ;播放时间位置
Play_State_Pos = $22EC ;播放状态位置
.ENDIF
;------------------------------
Track_Name_Pos = $222B ;曲目文本位置
;Track_Name_Pos = $00 ;曲目文本位置
Sound_Track_Pos = $2265 ;声道文本位置
Sound_Bar_Pos = $2269 ;音乐条位置
;==================================================
Scroll_X = $00
Scroll_Y = $00
;==================================================
Sound_Ram_Addr_1 = $0100
Sound_Ram_Addr_1_Size= $80
Sound_Ram_Addr_2 = $0090
Sound_Ram_Addr_2_Size= $70
Sound_Ram_Addr_3 = $0700
Sound_Ram_Addr_3_Size= $00
Sound_Ram_Addr_4 = $0400
Sound_Ram_Addr_4_Size= $00
Sound_Ram_Addr_5 = $0500
Sound_Ram_Addr_5_Size= $40
OAM_TEMP_ADDR = $0300
;==================================================
PPU_CTRL = $2000 ;PPU控制寄存器
PPU_MASK = $2001 ;PPU掩码寄存器
PPU_STATUS = $2002 ;PPU状态寄存器:读取后PPU_SCROLL和PPU_ADDRESS被复位,下一个写到PPU_SCROLL的数据是水平的,写到PPU_ADDRESS的数据是高位
PPU_OAM_ADDR = $2003 ;精灵RAM地址:用来设置通过PPU_OAM_DATA访问的256字节精灵RAM地址。每次访问PPU_OAM_DATA后该地址增加1
PPU_OAM_DATA = $2004 ;精灵RAM数据:用来读/写精灵内存。地址通过PPU_OAM_ADDR来设置,每次访问后地址增加1
PPU_SCROLL = $2005 ;屏幕滚动偏移:第一个写的值会进入垂直滚动寄存器(若>239,被忽略)。第二个值出现在水平滚动寄存器
PPU_ADDRESS = $2006 ;VRAM地址:设置PPU_DATA访问的VRAM地址。第一个写地址的高6位。第二个写低8位。每次访问PPU_DATA后地址增加
PPU_DATA = $2007 ;VRAM数据:用来访问VRAM数据,通过PPU_ADDRESS设置的地址在每次访问之后会增加1或32
OAM_DMA = $4014 ;DMA访问精灵RAM:通过写一个值xx到这个端口,引起CPU内存地址为$xx00-$xxFF的区域传送到精灵内存
APU_STATUS = $4015 ;声音通道切换
JOY1_FRAME = $4016 ;手柄1 + 选通
JOY2_FRAME = $4017 ;手柄2 + 选通
;==================================================
MMC3_BANK_CTRL = $8000
MMC3_BANK_DATA = $8001
MMC3_MIRRORING = $A000
MMC3_PRG_RAM_PROTECT = $A001
MMC3_IRQ_LATCH = $C000
MMC3_IRQ_RELOAD = $C001
MMC3_IRQ_DISABLE = $E000
MMC3_IRQ_ENABLE = $E001
;==================================================
PPU_Addr = $0200
Palette_Addr = $02C0
Sound_Bar = PPU_Addr+$E0
;==================================================
Bkg_Palette_Update_Addr = Palette_Addr+$0D
Sprite_Palette_Update_Addr= Palette_Addr+$11
PALETTE_UPDATE_MAX = $2C
PALETTE_UPDATE_MIN = $21
PALETTE_UPDATE_INTERVAL = 60
;==================================================
Sound_Bar_Cnt = PPU_Addr+$F0
PPU_Cur = Sound_Bar_Cnt+$02
PPU_Addr_H = PPU_Cur+$03
PPU_Addr_L = PPU_Addr_H+$04
Screen_Ctrl = PPU_Addr_L+$01
Screen_State = Screen_Ctrl+$01
;==================================================
Use_Ram_Begin = $50
;==================================================
JSR_Addr_Op = Use_Ram_Begin
JSR_Addr_L = JSR_Addr_Op + $01
JSR_Addr_H = JSR_Addr_L + $01
JSR_Addr_Rts = JSR_Addr_H + $01
Data_L = JSR_Addr_Rts + $01
Data_H = Data_L + $01
Data_Cnt = Data_H + $01
Data_Buf = Data_Cnt + $01
Nmi_Time_Count = Data_Buf + $01
Time_Wait_Cnt = Nmi_Time_Count + $01
Palette_Wait_Cnt = Time_Wait_Cnt + $01
;调色板刷新标志
Palette_Update_Flag = Palette_Wait_Cnt + $01
;当前帧文本写入禁用标志
Text_Disable_Flag = Palette_Update_Flag + $01
;==================================================
;当前帧文本写入禁用标志, 防止缓冲过大导致画面跳动
TEXT_DISABLE_BAR = %00000001 ;音乐条
TEXT_DISABLE_TIME = %00000010 ;播放时间
TEXT_DISABLE_ITEM = %00000100 ;播放时间
TEXT_DISABLE_RAM = %00001000 ;播放时间
;==================================================
Key_Keep = Text_Disable_Flag + 1
Key_Once = Key_Keep + $01
Key_Kemp = Key_Once + $01
Key_Temp = Key_Kemp + $01
Key_Getv = Key_Temp + $01
;==================================================
Music_Item_Cur = Key_Getv + $01 ;当前音乐集
Music_Item_Last = Music_Item_Cur + $01
Music_Total = Music_Item_Last + $01 ;当前音乐集
Music_Cur = Music_Total + $01;当前曲目
Music_Last = Music_Cur + ITEM_MAX_SIZE ;上一个曲目
Music_Stop_State = Music_Last + $01 ;播放停止状态
;==================================================
HEX_Data = Music_Stop_State + $01
DEC_H = HEX_Data + $01
DEC_T = DEC_H + $01
DEC_L = DEC_T + $01
;==================================================
Time_S = DEC_L + $01
Time_M = Time_S + $01
Time_H = Time_M + $02
Time_Cnt = Time_H + $03
;==================================================
Music_Bank_8000 = Time_Cnt + 1
Music_Bank_A000 = Music_Bank_8000 + 1
;==================================================
Scroll_H = Music_Bank_A000 + 1
Scroll_V = Scroll_H + 1
IRQ_Process_Index = Scroll_V + 1
;--------------------------------------------------
Page_Cur = IRQ_Process_Index + $01
Page_Cur_Index = Page_Cur + $01
Page_Cur_Cnt = Page_Cur_Index + $01
Page_Last = Page_Cur_Cnt + $01
Page_Last_Index = Page_Last + $01
Page_Last_Cnt = Page_Last_Index + $01
Use_Ram_End = Page_Last_Cnt + $01
;======================================================================
;音乐数据块
.IF SOUND_BAR_SHOW_ENABLE
.BANK SOUND_DATA_BANK_00 & BANK_DATA_MASK
.ORG $9000
.INCBIN "sound_bank/fc music(mapper 4)/rockman/rockman_1_music_data_0_bar.bank"
.BANK SOUND_DATA_BANK_01 & BANK_DATA_MASK
.INCBIN "sound_bank/fc music(mapper 4)/rockman/rockman_1_music_data_1.bank"
.BANK SOUND_DATA_BANK_02 & BANK_DATA_MASK
.INCBIN "sound_bank/fc music(mapper 4)/rockman/rockman_2_music_data_0_bar.bank"
.BANK SOUND_DATA_BANK_03 & BANK_DATA_MASK
.INCBIN "sound_bank/fc music(mapper 4)/rockman/rockman_2_music_data_1.bank"
.BANK SOUND_DATA_BANK_04 & BANK_DATA_MASK
.INCBIN "sound_bank/fc music(mapper 4)/rockman/rockman_4_music_data_0_bar.bank"
.BANK SOUND_DATA_BANK_05 & BANK_DATA_MASK
.INCBIN "sound_bank/fc music(mapper 4)/rockman/rockman_4_music_data_1.bank"
.BANK SOUND_DATA_BANK_06 & BANK_DATA_MASK
.INCBIN "sound_bank/fc music(mapper 4)/rockman/rockman_4_music_data_2.bank"
.BANK SOUND_DATA_BANK_07 & BANK_DATA_MASK
.INCBIN "sound_bank/fc music(mapper 4)/rockman/rockman_5_music_data_0_bar.bank"
.BANK SOUND_DATA_BANK_08 & BANK_DATA_MASK
.INCBIN "sound_bank/fc music(mapper 4)/rockman/rockman_5_music_data_1.bank"
.BANK SOUND_DATA_BANK_09 & BANK_DATA_MASK
.INCBIN "sound_bank/fc music(mapper 4)/rockman/rockman_5_music_data_2.bank"
.BANK SOUND_DATA_BANK_0A & BANK_DATA_MASK
.INCBIN "sound_bank/fc music(mapper 4)/rockman/rockman_6_music_data_0_bar.bank"
.BANK SOUND_DATA_BANK_0B & BANK_DATA_MASK
.INCBIN "sound_bank/fc music(mapper 4)/rockman/rockman_6_music_data_1.bank"
.BANK SOUND_DATA_BANK_0C & BANK_DATA_MASK
.INCBIN "sound_bank/fc music(mapper 4)/rockman/rockman_6_music_data_2.bank"
.BANK SOUND_DATA_BANK_0D & BANK_DATA_MASK
.INCBIN "sound_bank/fc music(mapper 4)/rockman/rockman_3_music_data_0_bar.bank"
.BANK SOUND_DATA_BANK_0E & BANK_DATA_MASK
.INCBIN "sound_bank/fc music(mapper 4)/rockman/rockman_3_music_data_1.bank"
.BANK SOUND_DATA_BANK_0F & BANK_DATA_MASK
.INCBIN "sound_bank/fc music(mapper 4)/rockman/rockman_3_music_data_2.bank"
.BANK SOUND_DATA_BANK_10 & BANK_DATA_MASK
.INCBIN "sound_bank/fc music(mapper 4)/raf world/raf_music_data_8000_bar.bank"
.BANK SOUND_DATA_BANK_11 & BANK_DATA_MASK
.INCBIN "sound_bank/fc music(mapper 4)/raf world/raf_music_data_A000.bank"
.BANK SOUND_DATA_BANK_12 & BANK_DATA_MASK
.INCBIN "sound_bank/fc music(mapper 4)/final mission/final_mission_music_data_8000_bar.bank"
.BANK SOUND_DATA_BANK_13 & BANK_DATA_MASK
.INCBIN "sound_bank/fc music(mapper 4)/final mission/final_mission_music_data_A000.bank"
.BANK SOUND_DATA_BANK_14 & BANK_DATA_MASK
.INCBIN "sound_bank/fc music(mapper 4)/kage/kage_music_data_8000.bank"
.BANK SOUND_DATA_BANK_15 & BANK_DATA_MASK
.INCBIN "sound_bank/fc music(mapper 4)/kage/kage_music_data_A000_bar.bank"
.BANK SOUND_DATA_BANK_16 & BANK_DATA_MASK
.INCBIN "sound_bank/fc music(mapper 4)/double dragon/dd1_music_data_0_bar.bank"
.BANK SOUND_DATA_BANK_17 & BANK_DATA_MASK
.INCBIN "sound_bank/fc music(mapper 4)/double dragon/dd1_music_data_1.bank"
.BANK SOUND_DATA_BANK_18 & BANK_DATA_MASK
.INCBIN "sound_bank/fc music(mapper 4)/double dragon/dd2_music_data_0_bar.bank"
.BANK SOUND_DATA_BANK_19 & BANK_DATA_MASK
.INCBIN "sound_bank/fc music(mapper 4)/double dragon/dd2_music_data_1.bank"
.BANK SOUND_DATA_BANK_1A & BANK_DATA_MASK
.INCBIN "sound_bank/fc music(mapper 4)/double dragon/dd3_music_data_0_bar.bank"
.BANK SOUND_DATA_BANK_1B & BANK_DATA_MASK
.INCBIN "sound_bank/fc music(mapper 4)/double dragon/dd3_music_data_1.bank"
.BANK SOUND_DATA_BANK_C000 & BANK_DATA_MASK
.INCBIN "sound_bank/fc music(mapper 4)/raf world/raf_music_data_C000_dmc.bank"
.BANK SOUND_DATA_BANK_C000 & BANK_DATA_MASK
.ORG $D400
.INCBIN "sound_bank/fc music(mapper 4)/final mission/final_mission_music_data_C000_dmc.bank"
.BANK SOUND_DATA_BANK_C000 & BANK_DATA_MASK
.ORG $D800
.INCBIN "sound_bank/fc music(mapper 4)/kage/kage_music_data_E000_dmc.bank"
.ELSE
.BANK SOUND_DATA_BANK_00 & BANK_DATA_MASK
.ORG $9000
.INCBIN "sound_bank/fc music(mapper 4)/rockman/rockman_1_music_data_0.bank"
.BANK SOUND_DATA_BANK_01 & BANK_DATA_MASK
.INCBIN "sound_bank/fc music(mapper 4)/rockman/rockman_1_music_data_1.bank"
.BANK SOUND_DATA_BANK_02 & BANK_DATA_MASK
.INCBIN "sound_bank/fc music(mapper 4)/rockman/rockman_2_music_data_0.bank"
.BANK SOUND_DATA_BANK_03 & BANK_DATA_MASK
.INCBIN "sound_bank/fc music(mapper 4)/rockman/rockman_2_music_data_1.bank"
.BANK SOUND_DATA_BANK_04 & BANK_DATA_MASK
.INCBIN "sound_bank/fc music(mapper 4)/rockman/rockman_4_music_data_0.bank"
.BANK SOUND_DATA_BANK_05 & BANK_DATA_MASK
.INCBIN "sound_bank/fc music(mapper 4)/rockman/rockman_4_music_data_1.bank"
.BANK SOUND_DATA_BANK_06 & BANK_DATA_MASK
.INCBIN "sound_bank/fc music(mapper 4)/rockman/rockman_4_music_data_2.bank"
.BANK SOUND_DATA_BANK_07 & BANK_DATA_MASK
.INCBIN "sound_bank/fc music(mapper 4)/rockman/rockman_5_music_data_0.bank"
.BANK SOUND_DATA_BANK_08 & BANK_DATA_MASK
.INCBIN "sound_bank/fc music(mapper 4)/rockman/rockman_5_music_data_1.bank"
.BANK SOUND_DATA_BANK_09 & BANK_DATA_MASK
.INCBIN "sound_bank/fc music(mapper 4)/rockman/rockman_5_music_data_2.bank"
.BANK SOUND_DATA_BANK_0A & BANK_DATA_MASK
.INCBIN "sound_bank/fc music(mapper 4)/rockman/rockman_6_music_data_0.bank"
.BANK SOUND_DATA_BANK_0B & BANK_DATA_MASK
.INCBIN "sound_bank/fc music(mapper 4)/rockman/rockman_6_music_data_1.bank"
.BANK SOUND_DATA_BANK_0C & BANK_DATA_MASK
.INCBIN "sound_bank/fc music(mapper 4)/rockman/rockman_6_music_data_2.bank"
.BANK SOUND_DATA_BANK_0D & BANK_DATA_MASK
.INCBIN "sound_bank/fc music(mapper 4)/rockman/rockman_3_music_data_0.bank"
.BANK SOUND_DATA_BANK_0E & BANK_DATA_MASK
.INCBIN "sound_bank/fc music(mapper 4)/rockman/rockman_3_music_data_1.bank"
.BANK SOUND_DATA_BANK_0F & BANK_DATA_MASK
.INCBIN "sound_bank/fc music(mapper 4)/rockman/rockman_3_music_data_2.bank"
.BANK SOUND_DATA_BANK_10 & BANK_DATA_MASK
.INCBIN "sound_bank/fc music(mapper 4)/raf world/raf_music_data_8000.bank"
.BANK SOUND_DATA_BANK_11 & BANK_DATA_MASK
.INCBIN "sound_bank/fc music(mapper 4)/raf world/raf_music_data_A000.bank"
.BANK SOUND_DATA_BANK_12 & BANK_DATA_MASK
.INCBIN "sound_bank/fc music(mapper 4)/final mission/final_mission_music_data_8000.bank"
.BANK SOUND_DATA_BANK_13 & BANK_DATA_MASK
.INCBIN "sound_bank/fc music(mapper 4)/final mission/final_mission_music_data_A000.bank"
.BANK SOUND_DATA_BANK_14 & BANK_DATA_MASK
.INCBIN "sound_bank/fc music(mapper 4)/kage/kage_music_data_8000.bank"
.BANK SOUND_DATA_BANK_15 & BANK_DATA_MASK
.INCBIN "sound_bank/fc music(mapper 4)/kage/kage_music_data_A000.bank"
.BANK SOUND_DATA_BANK_16 & BANK_DATA_MASK
.INCBIN "sound_bank/fc music(mapper 4)/double dragon/dd1_music_data_0.bank"
.BANK SOUND_DATA_BANK_17 & BANK_DATA_MASK
.INCBIN "sound_bank/fc music(mapper 4)/double dragon/dd1_music_data_1.bank"
.BANK SOUND_DATA_BANK_18 & BANK_DATA_MASK
.INCBIN "sound_bank/fc music(mapper 4)/double dragon/dd2_music_data_0.bank"
.BANK SOUND_DATA_BANK_19 & BANK_DATA_MASK
.INCBIN "sound_bank/fc music(mapper 4)/double dragon/dd2_music_data_1.bank"
.BANK SOUND_DATA_BANK_1A & BANK_DATA_MASK
.INCBIN "sound_bank/fc music(mapper 4)/double dragon/dd3_music_data_0.bank"
.BANK SOUND_DATA_BANK_1B & BANK_DATA_MASK
.INCBIN "sound_bank/fc music(mapper 4)/double dragon/dd3_music_data_1.bank"
.BANK SOUND_DATA_BANK_C000 & BANK_DATA_MASK
.INCBIN "sound_bank/fc music(mapper 4)/raf world/raf_music_data_C000_dmc.bank"
.BANK SOUND_DATA_BANK_C000 & BANK_DATA_MASK
.ORG $D400
.INCBIN "sound_bank/fc music(mapper 4)/final mission/final_mission_music_data_C000_dmc.bank"
.BANK SOUND_DATA_BANK_C000 & BANK_DATA_MASK
.ORG $D800
.INCBIN "sound_bank/fc music(mapper 4)/kage/kage_music_data_E000_dmc.bank"
.ENDIF
;CHR图形数据
;======================================================================
.BANK CHR_DATA_BANK
.INCBIN "chr_bank/chr_data.chr"
;======================================================================
.BANK PROGRAM_BANK & BANK_DATA_MASK
.ORG PROGRAM_ADDR
;==================================================
NmiProcess
;关闭屏幕控制
LDA #$00
STA PPU_CTRL
;没播放音乐就不需要触发IRQ
LDA <Music_Stop_State
BNE NmiNormal
;重置IRQ索引
LDA #$00
STA <IRQ_Process_Index
;时间秒数为空则跳过
LDA <Time_H
ORA <Time_M
ORA <Time_S
BEQ EnableFirstIrq
INC <Scroll_H
EnableFirstIrq
;80条扫描线后触发IRQ
LDA #IRQ_SCANLINE
STA MMC3_IRQ_LATCH
STA MMC3_IRQ_RELOAD
STA MMC3_IRQ_ENABLE
CLI
NmiNormal
;处理PPU图像
JSR PPU_Proc
;写入精灵, 会占用516个CPU周期, 约4.53扫描线, 写入会导致1像素抖动(PPU处理徐优化)
LDA PPU_STATUS
;LDA #$00
;STA PPU_OAM_ADDR
LDA #OAM_TEMP_ADDR / $0100
STA OAM_DMA
;启用NMI中断
LDA Screen_Ctrl
STA PPU_CTRL
LDA <Text_Disable_Flag
AND #TEXT_DISABLE_RAM
BNE Nmi_Sound_Play
;处理手柄输入
JSR Key_Proc
;切换音乐(手柄触发)
LDA <Time_Wait_Cnt
BNE Nmi_Cursor_Arrow
JSR Change_Select_Item
Nmi_Cursor_Arrow
;处理光标箭头
JSR Show_Arrow
;更新调色板
JSR Update_Palette_Data
;显示时间(缓冲)
JSR Time_Show
;音乐显示(缓冲)
.IF SOUND_BAR_SHOW_ENABLE
JSR Music_Vision
.ENDIF
Nmi_Sound_Play
;播放声音
LDA <Music_Stop_State
BNE Nmi_Time_Wait_Set
JSR Sound_Play_Proc
;播放计时
JSR Time_Count
Nmi_Time_Wait_Set
LDA <Time_Wait_Cnt
BEQ NmiNormalProcessEnd
DEC <Time_Wait_Cnt
NmiNormalProcessEnd
INC <Nmi_Time_Count
RTS
;==================================================
Init_MMC3
;==============================
;禁用IRQ
STA MMC3_IRQ_DISABLE
;水平镜像
LDA #$01
STA MMC3_MIRRORING
;初始化图形bank
JSR Init_MMC3_Chr_Bank
RTS
;==================================================
ProgramBegin;主程序
LDA #$00
STA PPU_CTRL
LDA #$00
STA PPU_STATUS
STA PPU_MASK
STA JOY2_FRAME
STA PPU_SCROLL
STA PPU_SCROLL
;==================================================
LDX #$FF
TXS
JSR Init_MMC3
LDX #$02
Check1
BIT PPU_STATUS
BPL Check1
Check2
BIT PPU_STATUS
BMI Check2
LDA #$0F
STA APU_STATUS
LDA #$C0
STA JOY2_FRAME
LDA PPU_STATUS
LDA #$10
TAX
Check3
STA PPU_ADDRESS
STA PPU_ADDRESS
EOR #$00
DEX
BNE Check3
;==============================
;调色板清空
LDA PPU_STATUS
LDA #$3F
STA PPU_ADDRESS
LDA #$00
STA PPU_ADDRESS
LDA #$0F
Palette_Clear
STA PPU_DATA
INX
CPX #$20
BCC Palette_Clear
LDA #$00
STA APU_STATUS
;==============================
;RAM初始化
RAM_Clear_All
LDY #$00
LDX #$08
LDA #$00
STA <$00
STA <$01
RAM_Clear_All_Start
STA [$00],Y
INY
BNE RAM_Clear_All_Start
INC <$01
DEX
BNE RAM_Clear_All_Start
JSR VramClear
JSR VramInit
JSR OAM_Ram_Init
JSR Init_Palette_Addr
LDA #$FF
STA Use_Ram_End
;==============================
;初始化背景调色板
JSR Set_Palette_Color
JSR Set_NameTable_Attributes
LDA #$00
STA PPU_OAM_ADDR
LDA #OAM_TEMP_ADDR / $0100
STA OAM_DMA
JSR Sound_Reset_Proc
JSR Set_Sound_Total
Init_Start_Music
LDX #$00
Init_Start_Music_Write
LDA Sound_Start_Port,X
STA <Music_Cur,X
INX
CPX #ITEM_MAX_SIZE
BCC Init_Start_Music_Write
JSR Show_Music_Text
.IF SOUND_BAR_SHOW_ENABLE
JSR Sound_Bar_Text_Set
.ENDIF
.IF Track_Name_Pos
JSR Show_Track_Info
.ENDIF
JSR PPU_Proc
;==================================================
;音乐bank初始化
JSR Init_Sound_Bank
JSR Music_Show
JSR Time_Show
JSR Music_State_Show
JSR Time_Delay
LDA #$01
STA <Music_Stop_State
LDA #$88
STA Screen_Ctrl
STA PPU_CTRL
JSR Show_Page_Text
LDA #$10
STA <Time_Wait_Cnt
Wait_Time_Over
LDA <Time_Wait_Cnt
BNE Wait_Time_Over
JSR Show_Arrow
LDA #OAM_TEMP_ADDR / $0100
STA OAM_DMA
LDA #$1E
STA Screen_State
LDX <Music_Item_Cur
LDA <Music_Cur,X
JSR Sound_Init_Proc
CLI
JMP MainLoop
;==============================
Time_Delay;延时等待
LDA PPU_STATUS
BPL Time_Delay
RTS
;==============================
OAM_Ram_Init;初始化精灵内存
LDX #$00
OAM_Ram_Init_Write
LDA #$F8
STA OAM_TEMP_ADDR,X
INX
LDA #$F8
STA OAM_TEMP_ADDR,X
INX
LDA #$00
STA OAM_TEMP_ADDR,X
INX
LDA #$F8
STA OAM_TEMP_ADDR,X
INX
BNE OAM_Ram_Init_Write
RTS
;==============================
VramClear;初始化图形内存
LDA #$20
STA PPU_ADDRESS
LDA #$00
STA PPU_ADDRESS
LDA #$00
LDY #$00
LDX #$10
VramClearWrite
STA PPU_DATA
INY
BNE VramClearWrite
DEX
BNE VramClearWrite
RTS
;==================================================
;设置MMC3图像bank
Init_MMC3_Chr_Bank
LDX #$05
Init_MMC3_Chr_Bank_Write
STX MMC3_BANK_CTRL
LDA MMC3_Chr_Bank_Data,X
STA MMC3_BANK_DATA
DEX
BPL Init_MMC3_Chr_Bank_Write
RTS
;--------------------------------------------------
MMC3_Chr_Bank_Data
.DB $00,$02,$04,$05,$06,$07
;==============================
VramInit;初始化图形内存
.IF CHR_RAM_ENABLE
LDA #CHR_DATA_BANK
JSR Switch_Bank_A000
LDA #LOW(CHR_DATA_ADDR)
STA <Data_L
LDA #HIGH(CHR_DATA_ADDR)
STA <Data_H
LDY #$00
LDX #$20
LDA #$00
STA PPU_ADDRESS
STA PPU_ADDRESS
VramInitWrite
LDA ,Y
STA PPU_DATA
INY
BNE VramInitWrite
INC <Data_H
DEX
BNE VramInitWrite
.ENDIF
RTS
;==============================
;音乐切换
Music_Play_Change
LDA <Key_Once
AND #$FF
BEQ Music_Play_Change_Check
;禁用音乐条刷新
LDA <Text_Disable_Flag
ORA #TEXT_DISABLE_BAR | TEXT_DISABLE_TIME
STA <Text_Disable_Flag
Music_Play_Change_Check
Music_arrow
LDA <Key_Once
AND #$0F
BEQ Music_Play_Change_End
JSR Music_Track_Change
JSR Sound_Reset_Proc
JSR Music_Show
Music_Play_Change_End
RTS
;==============================
;音乐曲目切换
Music_Track_Change
LDX <Music_Item_Cur
LDA <Music_Cur,X
STA <Music_Last
Music_Decrease
LDA <Key_Once
AND #$42
BEQ Music_Increase
LDA <Music_Cur,X
BEQ Music_Increase
DEC <Music_Cur,X
Music_Increase
LDA <Key_Once
AND #$81
BEQ Music_Decrease_10
JSR Set_Sound_Total
LDA <Music_Cur,X
CMP Music_Total
BCS * + 4
INC <Music_Cur,X
Music_Decrease_10
LDA <Key_Once
CMP #$04
BNE Music_Increase_10
LDA <Music_Cur,X
CMP #10
BCC Music_Start_Song_Min
LDA <Music_Cur,X
SEC
SBC #10
STA <Music_Cur,X
LDA #$00
BEQ Music_Increase_10
Music_Start_Song_Min
LDA #$00
STA <Music_Cur,X
Music_Increase_10
LDA <Key_Once
CMP #$08
BNE Music_Track_Change_End
LDA <Music_Cur,X
CLC
ADC #10
CMP Music_Total
BCS Music_Start_Song_Max
STA <Music_Cur,X
LDA #00
BEQ Music_Track_Change_End
Music_Start_Song_Max
LDA Music_Total
STA <Music_Cur,X
Music_Track_Change_End
RTS
;==============================
;按键处理
Key_Proc
JSR Key_Scan
LDA <Key_Keep
STA <Key_Temp
JSR Key_Scan
LDA <Key_Keep
CMP <Key_Temp
BEQ Key_Get_Once
LDA <Key_Kemp
STA <Key_Keep
Key_Get_Once
TAY
EOR Key_Kemp
AND <Key_Keep
STA <Key_Once
STY <Key_Kemp
RTS
;------------------------------
;按键扫描
Key_Scan
LDX #$01
STX JOY1_FRAME
DEX
STX JOY1_FRAME
LDX #$08
Key_Value
LDA JOY1_FRAME
STA <Key_Getv
LSR A
ORA <Key_Getv
LSR A
ROL <Key_Keep
DEX
BNE Key_Value
RTS
;==============================
.IF SOUND_BAR_SHOW_ENABLE
;音乐条显示
Music_Vision
LDA <Text_Disable_Flag
AND #TEXT_DISABLE_ITEM
BNE Music_Vision_End
AND #TEXT_DISABLE_BAR
BNE Music_Vision_Set
LDX PPU_Cur
JSR Music_Animation
STX PPU_Cur
Music_Vision_Set
LDA <Text_Disable_Flag
AND #TEXT_DISABLE_BAR ^ $FF
STA <Text_Disable_Flag
Music_Vision_End
RTS
;------------------------------
;音乐条显示处理
Music_Animation
LDA #PPU_MODE_CNT_LINE
STA PPU_Addr,X
INX
LDA #HIGH(Sound_Bar_Pos)
STA PPU_Addr,X
INX
LDA #LOW(Sound_Bar_Pos)
STA PPU_Addr,X
INX
LDA #$08
STA PPU_Addr,X
INX
LDA Sound_Bar
JSR Volume_Convert
JSR Volume_Set_Cnt
LDA Sound_Bar+$4
JSR Volume_Convert
JSR Volume_Set_Cnt
LDA Sound_Bar+$8
JSR Volume_Convert
JSR Volume_Set_Cnt
LDA Sound_Bar+$C
JSR Volume_Convert
JSR Volume_Set_Cnt
LDY #$10
LDA APU_STATUS
AND #$10
BNE Volume_Count
LDY #$00
BEQ Volume_Count
;------------------------------
;音乐条处理
Volume_Convert
AND #$0F
TAY
Volume_Count
LDA #$08
STA Sound_Bar_Cnt
Volume_FILL
DEY
BEQ Volume_Half
BMI Volume_Empty
DEY
Volume_Full
LDA #$16
BNE Volume_PPU
Volume_Half
LDA #$15
BNE Volume_PPU
Volume_Empty
LDA #$14
Volume_PPU
STA PPU_Addr,X
INX
DEC Sound_Bar_Cnt
BNE Volume_FILL
RTS
Volume_Set_Cnt
LDA #PPU_MODE_CNT_LINE_NEXT
STA PPU_Addr,X
INX
LDA #$08
STA PPU_Addr,X
INX
RTS
.ENDIF
;==============================
PPU_MODE_CNT_LINE = $FA ;行计数写入
PPU_MODE_CNT_LINE_NEXT = $FB ;转下行计数模式
PPU_MODE_CNT_CLEAR = $FC ;行计数清除
;------------------------------
;PPU处理
PPU_Proc
LDX PPU_Cur
LDA #$00
STA PPU_Cur
STA PPU_Addr,X
LDA PPU_Addr
BNE PPU_Proc_Beg
PPU_Proc_Ret
RTS
;------------------------------
PPU_Mode_Return_Cnt;转下行模式
INX
LDA PPU_Addr_L
CLC
ADC #$20
STA PPU_Addr_L
BCC PPU_Mode_Return_Cnt_End
INC PPU_Addr_H
PPU_Mode_Return_Cnt_End
LDA PPU_Addr_H
STA PPU_ADDRESS
LDA PPU_Addr_L
STA PPU_ADDRESS
LDA PPU_Addr,X
TAY
PPU_Mode_Return_Cnt_Write
INX
LDA PPU_Addr,X
STA PPU_DATA
DEY
BNE PPU_Mode_Return_Cnt_Write
JMP PPU_Proc_End
;------------------------------
PPU_Proc_Beg;处理开始
LDX #$00
STX PPU_MASK
;------------------------------
PPU_Mode_Select;模式选择
LDA PPU_Addr,X
CMP #PPU_MODE_CNT_CLEAR
BEQ PPU_Proc_Clear
CMP #PPU_MODE_CNT_LINE
BEQ PPU_Proc_Cnt_Line
CMP #PPU_MODE_CNT_LINE_NEXT
BEQ PPU_Mode_Return_Cnt
JMP PPU_Proc_End_Write
;------------------------------
PPU_Proc_End;单行写入结束
INX
LDA PPU_Addr,X
BNE PPU_Mode_Select
STA PPU_Addr
JSR Update_Palette_Color
PPU_Proc_End_Write
LDA #$00
STA PPU_ADDRESS
STA PPU_ADDRESS
LDA <Text_Disable_Flag
AND #(TEXT_DISABLE_BAR | TEXT_DISABLE_TIME | TEXT_DISABLE_RAM) ^ $FF
STA <Text_Disable_Flag
LDA #Scroll_X
STA PPU_SCROLL
LDA #Scroll_Y
STA PPU_SCROLL
LDA Screen_State
STA PPU_MASK
RTS
PPU_Proc_Clear
INX
LDA PPU_Addr,X
STA PPU_ADDRESS
INX
LDA PPU_Addr,X
STA PPU_ADDRESS
INX
LDY PPU_Addr,X
LDA #$00
PPU_Proc_Clear_Write
STA PPU_DATA
DEY
BNE PPU_Proc_Clear_Write
JMP PPU_Proc_End
PPU_Proc_Cnt_Line
INX
LDA PPU_Addr,X
STA PPU_Addr_H
STA PPU_ADDRESS
INX
LDA PPU_Addr,X
STA PPU_Addr_L
STA PPU_ADDRESS
INX
LDY PPU_Addr,X
PPU_Proc_Cnt_Line_Write
INX
LDA PPU_Addr,X
STA PPU_DATA
DEY
BNE PPU_Proc_Cnt_Line_Write
JMP PPU_Proc_End
;==============================
HEX_To_Dec;十六进制转十进制
STA <HEX_Data
PHA
TXA
PHA
LDX #$00
LDA #$00
HEX_Cln
STA <DEC_H,X
INX
CPX #$03
BCC HEX_Cln
LDA <HEX_Data
;------------------------------
HEX_100
CMP #100
BCC HEX_10
SEC
SBC #100
INC <DEC_H
BNE HEX_100
;------------------------------
HEX_10
CMP #10
BCC HEX_1
SEC
SBC #10
INC <DEC_T
BNE HEX_10
;------------------------------
HEX_1
STA <DEC_L
PLA
TAX
PLA
RTS
;==============================
;音乐曲目显示
Music_Show
LDX <Music_Item_Cur
LDA <Music_Cur,X
CLC
ADC #$01
JSR HEX_To_Dec
LDX PPU_Cur
LDA #PPU_MODE_CNT_LINE
STA PPU_Addr,X
INX
LDA #HIGH(Play_Index_Pos)
STA PPU_Addr,X
INX
LDA #LOW(Play_Index_Pos)
STA PPU_Addr,X
INX
LDA #$07
BNE Music_Show_Length
Music_Show_Length
STA PPU_Addr,X
INX
LDA <DEC_H
ORA #'0'
STA PPU_Addr,X
INX
LDA <DEC_T
ORA #'0'
STA PPU_Addr,X
INX
LDA <DEC_L
ORA #'0'
STA PPU_Addr,X
INX
LDA #'/'
STA PPU_Addr,X
INX
Music_Show_Total
LDA Music_Total
CLC
ADC #$01
JSR HEX_To_Dec
LDA <DEC_H
ORA #'0'
STA PPU_Addr,X
INX
LDA <DEC_T
ORA #'0'
STA PPU_Addr,X
INX
LDA <DEC_L
ORA #'0'
STA PPU_Addr,X
INX
STX PPU_Cur
Music_Show_End
RTS
;==============================
Time_Show;播放时间显示
LDA <Text_Disable_Flag
AND #TEXT_DISABLE_ITEM
BNE Time_Show_End
AND #TEXT_DISABLE_TIME
BNE Time_Show_Enable
LDX PPU_Cur
LDA #PPU_MODE_CNT_LINE
STA PPU_Addr,X
INX
LDA #HIGH(Play_Time_Pos)
STA PPU_Addr,X
INX
LDA #LOW(Play_Time_Pos)
STA PPU_Addr,X
INX
LDA #$08
STA PPU_Addr,X
INX
Time_Show_H
LDA <Time_H
JSR HEX_To_Dec
JSR Time_Digit
LDA #':'
STA PPU_Addr,X
INX
Time_Show_M
LDA <Time_M
JSR HEX_To_Dec
JSR Time_Digit
LDA #':'
STA PPU_Addr,X
INX
Time_Show_S
LDA <Time_S
JSR HEX_To_Dec
JSR Time_Digit
STX PPU_Cur
Time_Show_Enable
LDA <Text_Disable_Flag
AND #TEXT_DISABLE_TIME ^ $FF
STA <Text_Disable_Flag
Time_Show_End
RTS
Time_Digit
LDA <DEC_T
ORA #'0'
STA PPU_Addr,X
INX
LDA <DEC_L
ORA #'0'
STA PPU_Addr,X
INX
RTS
;==============================
Time_Count;计时
LDA <Music_Stop_State
ORA <Time_Wait_Cnt
BNE Time_Count_End
INC <Time_Cnt
LDA <Time_Cnt
CMP #60
BCC Time_Count_End
LDA #00
STA <Time_Cnt
INC <Time_S
Time_S_Cnt
LDA <Time_S
CMP #60
BCC Time_Count_End
LDA #00
STA <Time_S
INC <Time_M
Time_M_Cnt
LDA <Time_M
CMP #60
BCC Time_Count_End
LDA #00
STA <Time_M
INC <Time_H
Time_H_Cnt
LDA <Time_H
CMP #24
BCC Time_Count_End
LDA #00
STA <Time_H
Time_Count_End
RTS
;==============================
Time_ReSet;播放时间重置
LDA #$00
STA <Time_S
STA <Time_M
STA <Time_H
STA <Time_Cnt
RTS
;==============================
Music_Bar_ReSet;音乐条重置
LDA #$00
LDX #$00
Music_Bar_ReSet_Set
STA Sound_Bar,X
INX
CPX #$10
BCC Music_Bar_ReSet_Set
RTS
;==============================
PPU_Data;PPU数据写入
STY <Data_L
STX <Data_H
LDY #$FF
LDX PPU_Cur
DEX
PPU_Data_Beg
INX
INY
LDA ,Y
STA PPU_Addr,X
BNE PPU_Data_Beg
STX PPU_Cur
PPU_Data_End
RTS
;==============================
Music_State_Show;播放状态显示
LDA <Music_Stop_State
BEQ Music_State_Show_Play
Music_State_Show_Stop
LDY #LOW(Music_State_Stop)
LDX #HIGH(Music_State_Stop)
JSR PPU_Data
RTS
Music_State_Show_Play
LDY #LOW(Music_State_Play)
LDX #HIGH(Music_State_Play)
JSR PPU_Data
RTS
.IF SOUND_BAR_SHOW_ENABLE
;==============================
Sound_Bar_Text_Set;标题与音乐条初始化
LDY #LOW(Sound_Bar_Text_Data)
LDX #HIGH(Sound_Bar_Text_Data)
JSR PPU_Data
RTS
.ENDIF
;==============================
Set_NameTable_Attributes;设置命名表属性
BIT PPU_STATUS
LDA #$23
STA PPU_ADDRESS
LDA #$C0
STA PPU_ADDRESS
LDX #$00
Set_NameTable_Attributes_Write
LDA Palette_Attributes,X
STA PPU_DATA
INX
CPX #$40
BCC Set_NameTable_Attributes_Write
RTS
;==============================
Set_Palette_Color;设置调色板数据
BIT PPU_STATUS
LDA #$3F
STA PPU_ADDRESS
LDA #$00
STA PPU_ADDRESS
LDX #$00
Set_Palette_Color_Write
LDA Palette_Data,X
STA PPU_DATA
INX
CPX #$20
BCC Set_Palette_Color_Write
RTS
;==============================
Init_Palette_Addr;初始化调色板数据
LDX #$00
Init_Palette_Addr_Write
LDA Palette_Data,X
STA Palette_Addr,X
INX
CPX #$20
BCC Init_Palette_Addr_Write
RTS
;==============================
Update_Palette_Color;更新调色板颜色
LDA <Palette_Update_Flag
BEQ Update_Palette_Color_End
LDA #$3F
STA PPU_ADDRESS
LDA #$0C
STA PPU_ADDRESS
LDX #$0C
Update_Palette_Color_Write
LDA Palette_Addr,X
STA PPU_DATA
INX
CPX #$14
BCC Update_Palette_Color_Write
LDA #$00
STA <Palette_Update_Flag
Update_Palette_Color_End
RTS
Update_Sprite_Palette_Data
.DB $21
.DB $21
.DB $11
.DB $01
.DB $01
.DB $11
.DB $21
.DB $21
.DB $11
.DB $01
.DB $11
.DB $21
.DB $21
.DB $11
.DB $01
.DB $11
;==============================
Update_Palette_Data;更新调色板数据
LDA Nmi_Time_Count
AND #$08
CMP #$08
BNE Update_Bkg_Palette_Data
Update_Sprite_Palette_Data_Set
LDA Nmi_Time_Count
LSR A
LSR A
LSR A
LSR A
AND #$0F
TAX
LDA Update_Sprite_Palette_Data,X
STA Sprite_Palette_Update_Addr
LDA #$01
STA <Palette_Update_Flag
Update_Bkg_Palette_Data
LDA <Text_Disable_Flag
AND #TEXT_DISABLE_RAM
BNE Update_Palette_Data_End
LDA <Music_Stop_State
BNE Update_Palette_Data_End
Update_Palette_Data_Check
LDA Palette_Wait_Cnt
BPL Update_Palette_Data_Check_Over
LDA #PALETTE_UPDATE_INTERVAL
STA Palette_Wait_Cnt
Update_Palette_Data_Check_Over
DEC Palette_Wait_Cnt
BNE Update_Palette_Data_End
LDA <Text_Disable_Flag
ORA #TEXT_DISABLE_BAR | TEXT_DISABLE_TIME
STA Text_Disable_Flag
INC Palette_Update_Flag
LDA #PALETTE_UPDATE_INTERVAL
STA Palette_Wait_Cnt
LDA Bkg_Palette_Update_Addr
CMP #PALETTE_UPDATE_MAX
BNE Update_Bkg_Palette_Data_Set
LDA #PALETTE_UPDATE_MIN - 1
STA Bkg_Palette_Update_Addr
Update_Bkg_Palette_Data_Set
INC Bkg_Palette_Update_Addr
Update_Palette_Data_End
RTS
;==============================
Show_Music_Text;显示静态文本
LDX #$00
Show_Music_Text_Set
LDA Static_Text_Data,X
STA <Data_L
INX
LDA Static_Text_Data,X
STA <Data_H
INX
LDY #$00
LDA ,Y
STA <Data_Cnt
DEX
DEX
LDA Static_Text_Pos,X
STA PPU_ADDRESS
INX
LDA #$20
SEC
SBC <Data_Cnt
LSR A
STA <Data_Buf
LDA Static_Text_Pos,X
AND #$E0
CLC
ADC <Data_Buf
STA PPU_ADDRESS
INX
Show_Music_Text_Set_Write
INY
LDA ,Y
STA PPU_DATA
DEC <Data_Cnt
BNE Show_Music_Text_Set_Write
CPX #Static_Text_Pos_End - Static_Text_Pos
BCC Show_Music_Text_Set
RTS
;==============================
.IF Track_Name_Pos;显示曲目信息
Clear_Track_Info
PHA
LDX <Music_Item_Cur
LDA Track_Name_Addr_Flag,X
BEQ Clear_Track_Info_End_Ex
PLA
LDX PPU_Cur
PHA
LDA #PPU_MODE_CNT_CLEAR
STA PPU_Addr,X
INX
PLA
JSR Show_Get_Track_Name_Center_Pos
STX PPU_Cur
Clear_Track_Info_End
RTS
Clear_Track_Info_End_Ex
PLA
RTS
Write_Track_Info
PHA
LDX <Music_Item_Cur
LDA Track_Name_Addr_Flag,X
BEQ Write_Track_Info_End_Ex
PLA
PHA
LDX PPU_Cur
LDA #PPU_MODE_CNT_LINE
STA PPU_Addr,X
INX
PLA
JSR Show_Get_Track_Name_Center_Pos
Write_Track_Info_Data
INY
LDA ,Y
STA PPU_Addr,X
INX
DEC <Data_Cnt
BNE Write_Track_Info_Data
STX PPU_Cur
Write_Track_Info_End
RTS
Write_Track_Info_End_Ex
PLA
RTS
Show_Track_Info
Show_Track_Info_Clear
LDA <Music_Last
JSR Clear_Track_Info
LDX <Music_Item_Cur
LDA <Music_Cur,X
JSR Write_Track_Info
RTS
;==============================
Show_Get_Track_Name_Center_Pos;获取中间位置
;取出集合名索引
PHA
LDA <Music_Item_Cur
ASL A
TAY
LDA Track_Name_Addr_Port,Y
PHA
INY
LDA Track_Name_Addr_Port,Y
STA <Data_H
PLA
STA <Data_L
PLA
ASL A
TAY
LDA ,Y
PHA
INY
LDA ,Y
STA Data_H
PLA
STA Data_L
LDY #$00
LDA ,Y
STA <Data_Cnt
LDA #$20
SEC
SBC <Data_Cnt
LSR A
STA <Data_Buf
LDA #HIGH(Track_Name_Pos)
STA PPU_Addr,X
INX
LDA #LOW(Track_Name_Pos)
AND #$E0
CLC
ADC <Data_Buf
STA PPU_Addr,X
INX
LDA <Data_Cnt
STA PPU_Addr,X
INX
Show_Get_Pos_Center_End
RTS
.ENDIF
;==============================
;音乐端口清除
Sound_Data_Clear
JSR Sound_Port_Clear
JSR Sound_Ram_Clear
RTS
;==============================
;音乐端口清除
Sound_Port_Clear
LDA #$00
STA APU_STATUS
LDX #$00
Sound_Port_Clear_Write
STA $4000,X
INX
CPX #$14
BCC Sound_Port_Clear_Write
RTS
;==============================
Sound_Ram_Clear;RAM清除
LDX #$00
LDA #$00
Sound_Ram_Clear_1
STA Sound_Ram_Addr_1,X
INX
CPX #Sound_Ram_Addr_1_Size
BNE Sound_Ram_Clear_1
LDX #$00
Sound_Ram_Clear_2
STA Sound_Ram_Addr_2,X
INX
CPX #Sound_Ram_Addr_2_Size
BNE Sound_Ram_Clear_2
LDX #$00
Sound_Ram_Clear_3
STA Sound_Ram_Addr_3,X
INX
CPX #Sound_Ram_Addr_3_Size
BNE Sound_Ram_Clear_3
LDX #$00
Sound_Ram_Clear_4
STA Sound_Ram_Addr_4,X
INX
CPX #Sound_Ram_Addr_4_Size
BNE Sound_Ram_Clear_4
Sound_Ram_Clear_5
STA Sound_Ram_Addr_5,X
INX
CPX #Sound_Ram_Addr_5_Size
BNE Sound_Ram_Clear_5
RTS
Get_Music_Collection_Name
PHA
LDA <Music_Item_Cur
ASL A
TAY
LDA Music_Collection_Name,Y
STA <Data_L
INY
LDA Music_Collection_Name,Y
STA <Data_H
PLA
RTS
Set_Sound_Total
LDY <Music_Item_Cur
LDA Sound_Total_Port,Y
SEC
SBC #$01
STA <Music_Total
RTS
Get_Sound_Start
LDY <Music_Item_Cur
LDA Sound_Start_Port,Y
RTS
Set_Sound_Init_Port
PHA
LDA #$20
STA <JSR_Addr_Op
LDA <Music_Item_Cur
ASL A
TAY
LDA Sound_Init_Port,Y
STA <JSR_Addr_L
INY
LDA Sound_Init_Port,Y
STA <JSR_Addr_H
LDA #$60
STA <JSR_Addr_Rts
PLA
RTS
Set_Sound_Play_Port
PHA
LDA #$20
STA <JSR_Addr_Op
LDA <Music_Item_Cur
ASL A
TAY
LDA Sound_Play_Port,Y
STA <JSR_Addr_L
INY
LDA Sound_Play_Port,Y
STA <JSR_Addr_H
LDA #$60
STA <JSR_Addr_Rts
PLA
RTS
Set_Sound_Reset_Port
PHA
LDA #$20
STA <JSR_Addr_Op
LDA <Music_Item_Cur
ASL A
TAY
LDA Sound_Reset_Port,Y
STA <JSR_Addr_L
INY
LDA Sound_Reset_Port,Y
STA <JSR_Addr_H
LDA #$60
STA <JSR_Addr_Rts
PLA
RTS
;初始化音乐bank
Init_Sound_Bank
LDY <Music_Item_Cur
LDA Sound_Bank_8000,Y
STA <Music_Bank_8000
LDY <Music_Item_Cur
LDA Sound_Bank_A000,Y
STA <Music_Bank_A000
RTS
;==================================================
Sound_State_Reset;音乐状态重置
JSR Music_Bar_ReSet ;重置音乐条
JSR Time_ReSet ;重置播放时间
LDA #$00
STA <Music_Stop_State
JSR Music_State_Show ;显示播放状态
.IF Track_Name_Pos
JSR Show_Track_Info ;音乐曲目名显示
.ENDIF
RTS
;==================================================
Sound_Init_Proc;音乐初始化处理
PHA
JSR Set_Sound_Init_Port ;设置音乐初始化地址
LDA #$00
STA <Scroll_H ;重设水平滚动
LDA #$0F
STA APU_STATUS
PLA
JSR Sound_Init ;音乐初始化
JSR Sound_State_Reset ;重置音乐播放状态
RTS
;==================================================
Sound_Play_Proc;音乐播放处理
JSR Set_Sound_Play_Port ;设置音乐播放地址
JSR Sound_Play ;音乐播放
RTS
;==================================================
Sound_Reset_Proc;音乐重置处理
JSR Set_Sound_Reset_Port ;设置音乐重置地址
LDA <JSR_Addr_L
ORA <JSR_Addr_H
BEQ Sound_Reset_Proc_Default
JSR Sound_Reset ;执行音乐重置
JMP Sound_Reset_Proc_Init_Sound
Sound_Reset_Proc_Default ;默认音乐重置处理
;清理内存很耗费cpu周期, 这里禁用一下NMI中断
LDA #$00
STA PPU_CTRL
JSR Sound_Data_Clear
Sound_Reset_Proc_Default_Wait
LDA PPU_STATUS
BPL Sound_Reset_Proc_Default_Wait
LDA #$00
STA PPU_ADDRESS
STA PPU_ADDRESS
STA PPU_SCROLL
STA PPU_SCROLL
;恢复PPU控制
LDA Screen_Ctrl
STA PPU_CTRL
Sound_Reset_Proc_Init_Sound
LDA <Music_Stop_State
BNE Sound_Reset_Proc_End
LDX <Music_Item_Cur
LDA <Music_Cur,X
JSR Sound_Init_Proc
Sound_Reset_Proc_End
RTS
;==================================================
Clear_Item_Text;清除页项目
LDX PPU_Cur
LDA #PPU_MODE_CNT_CLEAR
STA PPU_Addr,X
INX
LDA <Page_Last
SEC
SBC <Page_Last_Index
ASL A
TAY
LDA Item_Pos_Data,Y
PHA
INY
LDA Item_Pos_Data,Y
STA PPU_Addr,X
INX
PLA
STA PPU_Addr,X
INX
LDA <Page_Last
ASL A
TAY
LDA Music_Collection_Name,Y
STA <Data_L
INY
LDA Music_Collection_Name,Y
STA <Data_H
LDY #$00
LDA ,Y
STA PPU_Addr,X
INX
Clear_Item_Text_End
STX PPU_Cur
RTS
;==================================================
Show_Item_Text;显示页项目
LDX PPU_Cur
LDA #PPU_MODE_CNT_LINE
STA PPU_Addr,X
INX
LDA Page_Cur
SEC
SBC <Page_Cur_Index
ASL A
TAY
LDA Item_Pos_Data,Y
PHA
INY
LDA Item_Pos_Data,Y
STA PPU_Addr,X
INX
PLA
STA PPU_Addr,X
INX
LDA Page_Cur
ASL A
TAY
LDA Music_Collection_Name,Y
STA <Data_L
INY
LDA Music_Collection_Name,Y
STA <Data_H
LDY #$00
LDA ,Y
STA PPU_Addr,X
STA Data_Cnt
INX
INY
Show_Item_Text_Write
LDA ,Y
STA PPU_Addr,X
INY
INX
DEC Data_Cnt
BNE Show_Item_Text_Write
Show_Item_Text_End
STX PPU_Cur
RTS
;==================================================
Get_Page_Start_Index;获取当前页号起始与条目数量
STA <Data_Buf
LDA #$00
Get_Page_Index_Calc
CLC
ADC #PAGE_SIZE
CMP <Data_Buf
BCC Get_Page_Index_Calc
BEQ Get_Page_Index_Calc_End
SEC
SBC #PAGE_SIZE
Get_Page_Index_Calc_End
STA <Data_Buf
Get_Page_Index_Cnt
LDA #PAGE_SIZE
STA Data_Cnt
LDA <Data_Buf
CLC
ADC #PAGE_SIZE
CMP #ITEM_MAX_SIZE
BCC Get_Page_Index_Cnt_End
LDA #ITEM_MAX_SIZE
SEC
SBC <Data_Buf
STA <Data_Cnt
Get_Page_Index_Cnt_End
RTS
;==================================================
Get_Last_Page_Start_Index
LDA <Music_Item_Last
JSR Get_Page_Start_Index
LDA Data_Buf
STA Page_Last
STA Page_Last_Index
LDA Data_Cnt
STA Page_Last_Cnt
RTS
;==================================================
Get_Cur_Page_Start_Index
LDA <Music_Item_Cur
JSR Get_Page_Start_Index
LDA Data_Buf
STA Page_Cur
STA Page_Cur_Index
LDA Data_Cnt
STA Page_Cur_Cnt
RTS
;==================================================
Show_Page_Text;显示页文本
LDA <Text_Disable_Flag
ORA #TEXT_DISABLE_BAR | TEXT_DISABLE_TIME | TEXT_DISABLE_ITEM
STA <Text_Disable_Flag
JSR Get_Last_Page_Start_Index
JSR Get_Cur_Page_Start_Index
Show_Page_Text_Set
Clear_Page_Last_Item;清理上一页
LDA Page_Last_Cnt
BEQ Clear_Page_Last_Item_End
JSR Clear_Item_Text
INC Page_Last
DEC Page_Last_Cnt
Clear_Page_Last_Item_End
Show_Page_Cur_Item;显示当前页
LDA Page_Cur_Cnt
BEQ Show_Page_Cur_Item_End
JSR Show_Item_Text
INC Page_Cur
DEC Page_Cur_Cnt
Show_Page_Cur_Item_End
INC <Time_Wait_Cnt
Show_Page_Text_Set_Wait;等待NMI完成PPU操作
LDA <Time_Wait_Cnt
BNE Show_Page_Text_Set_Wait
LDA Page_Last_Cnt
ORA Page_Cur_Cnt
BNE Show_Page_Text_Set
LDA <Text_Disable_Flag
AND #TEXT_DISABLE_ITEM ^ $FF
STA <Text_Disable_Flag
RTS
;==================================================
Last_Item;上一项
JSR Clear_Last_Track_Name
JSR Disable_Text_Draw
LDA <Music_Item_Cur
STA <Music_Item_Last
JSR Get_Last_Page_Start_Index
LDA #$00
STA Data_Buf
LDA <Page_Last
CMP <Music_Item_Cur
BNE Last_Item_Begin
LDA #$01
STA Data_Buf
Last_Item_Begin
LDA <Music_Item_Cur
BNE Last_Item_Set
LDA #ITEM_MAX_INDEX + 1
STA <Music_Item_Cur
Last_Item_Set
DEC <Music_Item_Cur
LDA <Music_Item_Cur
JSR Reset_Current_Music
Last_Item_Play
LDA Data_Buf
BEQ Last_Item_End
JSR Show_Page_Text
Last_Item_End
RTS
;==================================================
Next_Item;下一项
JSR Clear_Last_Track_Name
JSR Disable_Text_Draw
LDA <Music_Item_Cur
STA <Music_Item_Last
JSR Get_Last_Page_Start_Index
LDA #$00
STA Data_Buf
LDA <Page_Last
CLC
ADC <Page_Last_Cnt
SEC
SBC #$01
CMP <Music_Item_Cur
BNE Next_Item_Begin
LDA #$01
STA Data_Buf
Next_Item_Begin
LDA <Music_Item_Cur
CMP #ITEM_MAX_INDEX
BCC Next_Item_Set
LDA #$FF
STA <Music_Item_Cur
Next_Item_Set
INC <Music_Item_Cur
LDA <Music_Item_Cur
LDA <Music_Item_Cur
JSR Reset_Current_Music
Next_Item_Play
LDA Data_Buf
BEQ Next_Item_End
JSR Show_Page_Text
Next_Item_End
RTS
;==================================================
Last_Page;上一页
RTS
;==================================================
Next_Page;下一页
LDA #PAGE_MAX_INDEX
CMP #$01
BEQ Next_Page_End
LDA <Music_Item_Cur
STA <Music_Item_Last
JSR Get_Last_Page_Start_Index
LDA <Page_Last_Index
CMP #PAGE_MAX_INDEX
BCS Next_Page_In_End_Page
Next_Page_Not_End_Page;不是在最后一页
LDA <Music_Item_Cur
CLC
ADC #PAGE_SIZE
CMP #ITEM_MAX_SIZE
BCC Next_Page_Not_End_Page_Less
LDA <Music_Item_Cur
SEC
SBC <Page_Last_Index
CLC
ADC #PAGE_MAX_INDEX
CMP #ITEM_MAX_SIZE
BCC Next_Page_Not_End_Page_Less
LDA #ITEM_MAX_INDEX
Next_Page_Not_End_Page_Less
STA <Music_Item_Cur
JMP Next_Page_Reset
Next_Page_In_End_Page;在最后一页
LDA <Music_Item_Cur
SEC
SBC <Page_Last_Index
STA <Music_Item_Cur
Next_Page_Reset
LDA <Music_Item_Cur
JSR Reset_Current_Music
JSR Show_Page_Text
Next_Page_End
RTS
;==================================================
Disable_Text_Draw;禁用音乐条刷新
LDA <Text_Disable_Flag
ORA #TEXT_DISABLE_BAR | TEXT_DISABLE_TIME
STA <Text_Disable_Flag
RTS
;==================================================
Clear_Last_Track_Name;清除上次曲目名
LDX <Music_Item_Cur
LDA <Music_Cur,X
.IF Track_Name_Pos
JSR Clear_Track_Info
.ENDIF
RTS
;==================================================
Reset_Current_Music;重设当前曲目
;写入当前总曲目
JSR Set_Sound_Total
LDX <Music_Item_Cur
LDA #$00
STA <Music_Last
JSR Sound_Reset_Proc
JSR Music_Show
RTS
;==================================================
Music_Song_Stop;音乐停止
LDA #$01
STA <Music_Stop_State
JSR Music_Bar_ReSet
JSR Time_ReSet
JSR Sound_Data_Clear
JSR Music_State_Show
RTS
;==================================================
Music_Song_Play;音乐播放
LDA #$00
STA <Music_Stop_State
LDX <Music_Item_Cur
LDA <Music_Cur,X
JSR Sound_Init_Proc
RTS
;==================================================
Music_Song_Last_10;上10曲
JSR Clear_Last_Track_Name
JSR Disable_Text_Draw
LDX <Music_Item_Cur
JSR Set_Sound_Total
LDA <Music_Cur,X
SEC
SBC #10
BCS Music_Song_Last_10_Set
LDA #$00
Music_Song_Last_10_Set
STA <Music_Cur,X
JSR Sound_Reset_Proc
JSR Music_Show
Music_Song_Last_10_End
RTS
;==================================================
Music_Song_Next_10;下10曲
JSR Clear_Last_Track_Name
JSR Disable_Text_Draw
LDX <Music_Item_Cur
JSR Set_Sound_Total
LDA <Music_Cur,X
CLC
ADC #10
CMP Music_Total
BCC Music_Song_Next_10_Set
LDA Music_Total
Music_Song_Next_10_Set
STA <Music_Cur,X
JSR Sound_Reset_Proc
JSR Music_Show
Music_Song_Next_10_End
RTS
;==================================================
Music_Song_Last;上一曲
JSR Clear_Last_Track_Name
JSR Disable_Text_Draw
LDX <Music_Item_Cur
JSR Set_Sound_Total
LDA <Music_Cur,X
BEQ Music_Song_Last_Set
DEC <Music_Cur,X
Music_Song_Last_Set
JSR Sound_Reset_Proc
JSR Music_Show
Music_Song_Last_End
RTS
;==================================================
Music_Song_Next;下一曲
JSR Clear_Last_Track_Name
JSR Disable_Text_Draw
LDX <Music_Item_Cur
JSR Set_Sound_Total
LDA <Music_Cur,X
CMP Music_Total
BCS Music_Song_Next_Set
INC <Music_Cur,X
Music_Song_Next_Set
JSR Sound_Reset_Proc
JSR Music_Show
Music_Song_Next_End
RTS
;==================================================
Change_Select_Item;改变当前选择项
;--------------------------------------------------
Change_Select_Stop_Play_Item;停止/播放
LDA <Key_Once
CMP #$10
BNE Change_Select_Last_Item
LDA <Music_Stop_State
BNE Change_Select_Play
JSR Music_Song_Stop
LDA <Music_Stop_State
RTS
Change_Select_Play
JSR Music_Song_Play
RTS
;--------------------------------------------------
Change_Select_Last_Item;上一个专辑
LDA <Text_Disable_Flag
AND #TEXT_DISABLE_ITEM
BNE Change_Select_Item_End
LDA <Key_Once
CMP #$08
BNE Change_Select_Next_Item
JSR Last_Item
;--------------------------------------------------
Change_Select_Next_Item;下一个专辑
LDA <Key_Once
CMP #$04
BNE Change_Select_Last_10
JSR Next_Item
LDA <Music_Item_Cur
JSR Get_Page_Start_Index
;--------------------------------------------------
Change_Select_Last_10;前10曲
LDA <Key_Once
CMP #$40
BNE Change_Select_Next_10
JSR Music_Song_Last_10
;--------------------------------------------------
Change_Select_Next_10;后10曲
LDA <Key_Once
CMP #$80
BNE Change_Select_Last
JSR Music_Song_Next_10
;--------------------------------------------------
Change_Select_Last;上一曲
LDA <Key_Once
CMP #$02
BNE Change_Select_Next
JSR Music_Song_Last
;--------------------------------------------------
Change_Select_Next;下一曲
LDA <Key_Once
CMP #$01
BNE Change_Page_Next
JSR Music_Song_Next
;--------------------------------------------------
Change_Page_Next;下一页
LDA <Key_Once
CMP #$20
BNE Change_Select_Item_End
JSR Next_Page
;--------------------------------------------------
Change_Select_Item_End
RTS
;==================================================
Show_Arrow;显示箭头光标
LDA <Music_Item_Cur
JSR Get_Page_Start_Index
LDA #$00
STA PPU_OAM_ADDR
LDA <Music_Item_Cur
SEC
SBC <Data_Buf
ASL A
ASL A
ASL A
ASL A
CLC
ADC #ARROW_Y_OFFSET
STA OAM_TEMP_ADDR + $00
;STA PPU_OAM_DATA
LDA #$1F
STA OAM_TEMP_ADDR + $01
;STA PPU_OAM_DATA
LDA #$00
STA OAM_TEMP_ADDR + $02
;STA PPU_OAM_DATA
LDA #ARROW_X_OFFSET
STA OAM_TEMP_ADDR + $03
;STA PPU_OAM_DATA
RTS
;--------------------------------------------------
;命名表数据
Palette_Attributes
.IF SOUND_BAR_SHOW_ENABLE
.DB $00,$00,$00,$00,$00,$00,$00,$00,$55,$55,$55,$55,$55,$55,$55,$55
.DB $55,$55,$55,$55,$55,$55,$55,$55,$55,$55,$55,$55,$55,$55,$55,$55
.DB $55,$F5,$F5,$F5,$F5,$F5,$F5,$55,$55,$FF,$FF,$FF,$FF,$FF,$FF,$75
.DB $A5,$A5,$A5,$A5,$A5,$A5,$A5,$A5,$AA,$AA,$AA,$AA,$AA,$AA,$AA,$AA
.ELSE
.DB $00,$00,$00,$00,$00,$00,$00,$00,$55,$55,$55,$55,$55,$55,$55,$55
.DB $55,$55,$55,$55,$55,$55,$55,$55,$55,$55,$55,$55,$55,$55,$55,$55
.DB $55,$F5,$F5,$F5,$F5,$F5,$F5,$55,$55,$FF,$FF,$FF,$FF,$FF,$FF,$75
.DB $A5,$A5,$A5,$A5,$A5,$A5,$A5,$A5,$AA,$AA,$AA,$AA,$AA,$AA,$AA,$AA
.ENDIF
;--------------------------------------------------
;调色板数据
Palette_Data
.DB $0F,$27,$20,$0F,$0F,$23,$20,$0F,$0F,$21,$20,$0F,$0F,$24,$20,$0F
.DB $0F,$21,$24,$25,$0F,$24,$20,$0F,$0F,$24,$20,$0F,$0F,$24,$20,$0F
;--------------------------------------------------
Static_Text_Data
.WORD Static_Text_Caption_Data
.WORD Static_Text_Author_Data
.WORD Static_Text_Date_Data
Static_Text_Data_End
;--------------------------------------------------
Static_Text_Pos
.DB HIGH(Caption_Text_Pos),LOW(Caption_Text_Pos)
.DB HIGH(Author_Text_Pos),LOW(Author_Text_Pos)
.DB HIGH(Date_Text_Pos),LOW(Date_Text_Pos)
Static_Text_Pos_End
;--------------------------------------------------
Music_State_Stop
.IF SOUND_BAR_SHOW_ENABLE
.DB PPU_MODE_CNT_LINE,HIGH(Play_State_Pos),LOW(Play_State_Pos),$07,"STOPPED",$00
ELSE
.DB PPU_MODE_CNT_LINE,HIGH(Play_State_Pos),LOW(Play_State_Pos),$07,"STOPPED",$00
.ENDIF
Music_State_Play
.DB PPU_MODE_CNT_LINE,HIGH(Play_State_Pos),LOW(Play_State_Pos),$07,"PLAYING",$00
;--------------------------------------------------
Sound_Bar_Text_Data;声音类型文本
.DB PPU_MODE_CNT_LINE,HIGH(Sound_Track_Pos),LOW(Sound_Track_Pos),$04,"SQ1-"
.DB PPU_MODE_CNT_LINE_NEXT,$04,"SQ2-"
.DB PPU_MODE_CNT_LINE_NEXT,$04,"TRI-"
.DB PPU_MODE_CNT_LINE_NEXT,$04,"NOI-"
.DB PPU_MODE_CNT_LINE_NEXT,$04,"DMC-",$00
.IF Track_Name_Pos
;--------------------------------------------------
Track_Name_Addr_00;曲目名地址索引
.WORD Trackr_00_01
Trackr_00_01 .DB 15,"RAF WORLD BGM 1"
Trackr_00_02 .DB 15,"RAF WORLD BGM 2"
;--------------------------------------------------
Track_Name_Addr_01;曲目名地址索引
.WORD Trackr_01_01
;==================================================
Trackr_01_01 .DB 19,"FINAL MISSION BGM 1"
Trackr_01_02 .DB 19,"FINAL MISSION BGM 2"
;==================================================
Track_Name_Addr_Port ;曲目名地址间接索引
.WORD Track_Name_Addr_00
.WORD Track_Name_Addr_01
.WORD Track_Name_Addr_01
.ENDIF
;--------------------------------------------------
Static_Text_Caption_Data;静态文本数据
.DB 16
.DB "FC MUSIC 12 IN 1"
Static_Text_Author_Data
.DB 25
.DB "EXTRACTED BY FLAMECYCLONE"
Static_Text_Date_Data
.DB 10
.DB "2023.07.23"
;==================================================
Music_Collection_Name ;专辑名间接索引
.DW Music_Collection_Name_00
.DW Music_Collection_Name_01
.DW Music_Collection_Name_02
.DW Music_Collection_Name_03
.DW Music_Collection_Name_04
.DW Music_Collection_Name_05
.DW Music_Collection_Name_06
.DW Music_Collection_Name_07
.DW Music_Collection_Name_08
.DW Music_Collection_Name_09
.DW Music_Collection_Name_10
.DW Music_Collection_Name_11
;==================================================
Music_Collection_Name_00 ;专辑名文本数据
.DB 11,"1.RAF WORLD"
Music_Collection_Name_01
.DB 15,"2.FINAL MISSION"
Music_Collection_Name_02
.DB 06,"3.KAGE"
Music_Collection_Name_03
.DB 16,"4.DOUBLE DRAGON"
Music_Collection_Name_04
.DB 17,"5.DOUBLE DRAGON 2"
Music_Collection_Name_05
.DB 17,"6.DOUBLE DRAGON 3"
Music_Collection_Name_06
.DB 09,"7.ROCKMAN"
Music_Collection_Name_07
.DB 12,"8.ROCKMAN 2"
Music_Collection_Name_08
.DB 12,"9.ROCKMAN 3"
Music_Collection_Name_09
.DB 12,"10.ROCKMAN 4"
Music_Collection_Name_10
.DB 12,"11.ROCKMAN 5"
Music_Collection_Name_11
.DB 12,"12.ROCKMAN 6"
;==================================================
Track_Name_Addr_Flag ;显示曲目名标记
.DB 0,0,0,0,0,0,0,0,0,0,0,0
;==================================================
Item_Pos_Data ;光标箭头位置
.WORD ITEM_SHOW_POS
.WORD ITEM_SHOW_POS + $0040
.WORD ITEM_SHOW_POS + $0080
.WORD ITEM_SHOW_POS + $00C0
.WORD ITEM_SHOW_POS + $0100
.WORD ITEM_SHOW_POS + $0140
;==================================================
Sound_Init_Port ;音乐初始化入口地址
.DW $BFC8
.DW $D7F0
.DW $9FC0
.DW $BF70
.DW $8003
.DW $BF30
.DW $9003
.DW $8003
.DW $8003
.DW $8003
.DW $8003
.DW $8003
;==================================================
Sound_Play_Port ;音乐播放入口地址
.DW $8000
.DW $8001
.DW $A000
.DW $8003
.DW $8000
.DW $8003
.DW $9000
.DW $8000
.DW $8000
.DW $8000
.DW $8000
.DW $8000
;==================================================
Sound_Reset_Port ;音乐重置入口地址
.DW $0000
.DW $0000
.DW $0000
.DW $0000
.DW $0000
.DW $0000
.DW $0000
.DW $0000
.DW $0000
.DW $0000
.DW $0000
.DW $0000
;==================================================
Sound_Total_Port ;曲目总数
.DB 38
.DB 33
.DB 49
.DB 41
.DB 83
.DB 70
.DB 50
.DB 67
.DB 57
.DB 71
.DB 76
.DB 102
;==================================================
Sound_Start_Port ;起始播放曲目
.DB 00
.DB 00
.DB 00
.DB 00
.DB 00
.DB 00
.DB 00
.DB 00
.DB 00
.DB 00
.DB 00
.DB 00
;==================================================
Sound_Bank_8000 ;专辑bank_8000
.DB $10
.DB $12
.DB $14
.DB $16
.DB $18
.DB $1A
.DB $00
.DB $02
.DB $0D
.DB $04
.DB $07
.DB $0A
;==================================================
Sound_Bank_A000 ;专辑bank_A000
.DB $11
.DB $13
.DB $15
.DB $17
.DB $19
.DB $1B
.DB $01
.DB $03
.DB $0E
.DB $05
.DB $08
.DB $0B
;==================================================
.BANK RESET_BANK & BANK_DATA_MASK
.ORG RESET_ADDR
;==================================================
Switch_Bank_8000;切换bank到8000-9FFF
PHA
LDA #$06
STA MMC3_BANK_CTRL
PLA
STA MMC3_BANK_DATA
RTS
;==================================================
Switch_Bank_A000;切换bank到A000-BFFF
PHA
LDA #$07
STA MMC3_BANK_CTRL
PLA
STA MMC3_BANK_DATA
RTS
;==================================================
Switch_Main_Bank;切到主程序bank
LDA #PROGRAM_BANK & BANK_DATA_MASK
JSR Switch_Bank_8000 ;设置$8000地址bank
RTS
;==================================================
Sound_Reset;音乐重设(如果有的话)
JSR Switch_Music_Bank;切换到音乐bank
JSR JSR_Addr_Op ;执行音乐重置
JSR Switch_Main_Bank ;切回主程序
RTS
;==================================================
Switch_Music_Bank;切换音乐bank
JSR Init_Sound_Bank ;拿到音乐bank号
LDA <Music_Bank_8000
JSR Switch_Bank_8000 ;设置$8000地址bank
LDA <Music_Bank_A000
JSR Switch_Bank_A000 ;设置$A000地址bank
RTS
;==================================================
Sound_Init;音乐初始化
PHA
JSR Switch_Music_Bank;切换到音乐bank
PLA
JSR JSR_Addr_Op ;执行音乐初始化
JSR Switch_Main_Bank ;切回主程序
RTS
;==================================================
Sound_Play;音乐播放
JSR Switch_Music_Bank;切换到音乐bank
JSR JSR_Addr_Op ;执行音乐播放
JSR Switch_Main_Bank ;切回主程序
RTS
;==================================================
MainLoop;死循环
JMP MainLoop
IRQ_SUBPROCESS_JMP = 0
.IF IRQ_SUBPROCESS_JMP
;==================================================
IRQ_Process_0;IRQ处理过程0
;15条扫描线后触发IRQ
LDA #15
STA MMC3_IRQ_LATCH
;设置屏幕滚动
LDA <Scroll_H
STA PPU_SCROLL
STA PPU_SCROLL
IRQ_Process_0_End
INC <IRQ_Process_Index
JMP IrqProgramEnd
;==================================================
IRQ_Process_1;IRQ处理过程1
LDA #55
STA MMC3_IRQ_LATCH
;设置屏幕滚动
LDA #$00
STA PPU_SCROLL
STA PPU_SCROLL
INC <IRQ_Process_Index
JMP IrqProgramEnd
;==================================================
IRQ_Process_2;IRQ处理过程2
LDA #15
STA MMC3_IRQ_LATCH
;设置屏幕滚动
LDA #$00
SEC
SBC <Scroll_H
STA PPU_SCROLL
STA PPU_SCROLL
INC <IRQ_Process_Index
JMP IrqProgramEnd
;==================================================
IRQ_Process_3;IRQ处理过程3
;设置屏幕滚动
LDA <Scroll_H
STA PPU_SCROLL
STA PPU_SCROLL
;禁用IRQ
STA MMC3_IRQ_DISABLE
JMP IrqProgramEnd
IrqProcessAddr
.DW IRQ_Process_0,IRQ_Process_1,IRQ_Process_2,IRQ_Process_3
.ENDIF
;==================================================
;IRQ滚动模式常量
IRQ_SCROLL_MODE_ZERO = 0 ;不滚动
IRQ_SCROLL_MODE_LEFT = 1 ;向左滚动
IRQ_SCROLL_MODE_RIGHT = 2 ;向右滚动
;IRQ扫描线数据
IRQ_Scanline_Data
.DB 8
.DB 54
.DB 8
.DB 00 ;关闭IRQ
;IRQ滚动控制模式
IRQ_Scanline_Mode
.DB IRQ_SCROLL_MODE_ZERO
.DB IRQ_SCROLL_MODE_ZERO
.DB IRQ_SCROLL_MODE_RIGHT
.DB IRQ_SCROLL_MODE_LEFT
;==================================================
;IRQ处理
IRQ_Process
LDX <IRQ_Process_Index
LDA IRQ_Scanline_Data,X
BNE IRQ_Process_Latch
IRQ_Process_Disable;禁用IRQ
STA MMC3_IRQ_DISABLE
STA IRQ_Process_Index
BEQ IRQ_Process_Scroll
IRQ_Process_Latch;设置下次 IRQ 触发扫描线
STA MMC3_IRQ_LATCH
INC <IRQ_Process_Index
IRQ_Process_Scroll;IRQ滚动控制
LDA IRQ_Scanline_Mode,X
CMP #IRQ_SCROLL_MODE_LEFT
BEQ IRQ_Process_Scroll_Left
CMP #IRQ_SCROLL_MODE_RIGHT
BEQ IRQ_Process_Scroll_Right
IRQ_Process_Scroll_Zero;不滚动
LDA #$00
STA PPU_SCROLL
STA PPU_SCROLL
RTS
IRQ_Process_Scroll_Left;向左滚动
LDA <Scroll_H
STA PPU_SCROLL
STA PPU_SCROLL
RTS
IRQ_Process_Scroll_Right;向右滚动
LDA #$00
SEC
SBC <Scroll_H
STA PPU_SCROLL
STA PPU_SCROLL
RTS
;==================================================
NmiProgram;Nmi中断处理
PHA
TXA
PHA
TYA
PHA
;读取清除Vblank标志, 防止重复进入
BIT PPU_STATUS
;切换主程序bank
JSR Switch_Main_Bank
;Nmi处理
JSR NmiProcess
Nmi_Proc_End
PLA
TAY
PLA
TAX
PLA
RTI
;==================================================
ResetProgram;重置中断处理
SEI
CLD
LDA #$00
STA PPU_CTRL
STA PPU_MASK
;切换主程序bank
JSR Switch_Main_Bank
;程序处理开始
JMP ProgramBegin
;==================================================
IrqProgram;Irq中断处理
PHA
TXA
PHA
TYA
PHA
;关闭IRQ
STA MMC3_IRQ_DISABLE
;允许下个IRQ触发
STA MMC3_IRQ_ENABLE
.IF IRQ_SUBPROCESS_JMP
;执行IRQ过程
LDA <Data_L
PHA
LDA <Data_H
PHA
LDA <IRQ_Process_Index
ASL A
TAY
LDA IrqProcessAddr,Y
STA <Data_L
INY
LDA IrqProcessAddr,Y
STA <Data_H
JMP
.ELSE
JSR IRQ_Process
.ENDIF
IrqProgramEnd
.IF IRQ_SUBPROCESS_JMP
PLA
STA <Data_H
PLA
STA <Data_L
.ENDIF
PLA
TAY
PLA
TAX
PLA
RTI
.ORG $FFFA
.WORD NmiProgram
.WORD ResetProgram
.WORD IrqProgram
.BANK RESET_BANK & BANK_DATA_MASK
.IF SOUND_BAR_SHOW_ENABLE
.ORG $FE00
PHA
STY $07BA
LDA #$8D
STA $07BC
TYA
CLC
ADC #LOW(Sound_Bar)
STA $07BD
LDA #HIGH(Sound_Bar)
STA $07BE
LDA #$60
STA $07BF
PLA
RTS
.ORG $FE20
STA $07BA
CLC
ADC #LOW(Sound_Bar)
STA $07BD
LDA #$8D
STA $07BC
LDA #HIGH(Sound_Bar)
STA $07BE
LDA #$60
STA $07BF
RTS
.ORG $FE40
PHA
STY $07F1
LDA #$8D
STA $07F3
TYA
CLC
ADC #LOW(Sound_Bar)
STA $07F4
LDA #HIGH(Sound_Bar)
STA $07F5
LDA #$60
STA $07F6
PLA
RTS
.ORG $FE60
STA $07F1
CLC
ADC #LOW(Sound_Bar)
STA $07F4
LDA #$8D
STA $07F3
LDA #HIGH(Sound_Bar)
STA $07F5
LDA #$60
STA $07F6
RTS
.ORG $FF40
STA $4000
STA Sound_Bar + $00
RTS
.ORG $FF48
STA $4004
STA Sound_Bar + $04
RTS
.ORG $FF50
STA $4008
STA Sound_Bar + $08
RTS
.ORG $FF58
STA $400C
STA Sound_Bar + $0C
RTS
.ORG $FF60
STX $4000
STX Sound_Bar + $00
RTS
.ORG $FF68
STX $4004
STX Sound_Bar + $04
RTS
.ORG $FF70
STX $4008
STX Sound_Bar + $08
RTS
.ORG $FF78
STX $400C
STX Sound_Bar + $0C
RTS
.ORG $FF80
STY $4000
STY Sound_Bar + $00
RTS
.ORG $FF88
STY $4004
STY Sound_Bar + $04
RTS
.ORG $FF90
STY $4008
STY Sound_Bar + $08
RTS
.ORG $FF98
STY $400C
STY Sound_Bar + $0C
RTS
.ORG $FFA0
STA $4000,X
STA Sound_Bar + $00,X
RTS
.ORG $FFA8
STA $4000,Y
STA Sound_Bar + $00,Y
RTS
.ORG $FFB0
STA $4004,X
STA Sound_Bar + $04,X
RTS
.ORG $FFB8
STA $4004,Y
STA Sound_Bar + $04,Y
RTS
.ORG $FFC0
STA $4008,X
STA Sound_Bar + $08,X
RTS
.ORG $FFC8
STA $4008,Y
STA Sound_Bar + $08,Y
RTS
.ORG $FFD0
STA $400C,X
STA Sound_Bar + $0C,X
RTS
.ORG $FFD8
STA $400C,Y
STA Sound_Bar + $0C,Y
RTS
.ENDIF
**** Hidden Message ***** 非常支持您
页:
[1]