Milestone 5 achieved! Mario moves on the screen now in response to the arrow keys, and sets a bunch of variables in response to A/B/Select/Start.
This commit is contained in:
2
Makefile
2
Makefile
@@ -6,7 +6,7 @@ MAIN_SOURCE=nesgame.S
|
|||||||
|
|
||||||
all: nesgame.nes
|
all: nesgame.nes
|
||||||
nesgame.nes : $(SOURCE)
|
nesgame.nes : $(SOURCE)
|
||||||
ophis -o $(MAIN_SOURCE) $<
|
ophis -o $@ $(MAIN_SOURCE)
|
||||||
|
|
||||||
.PHONY: test
|
.PHONY: test
|
||||||
test: nesgame.nes
|
test: nesgame.nes
|
||||||
|
|||||||
8
README
8
README
@@ -6,12 +6,14 @@ Compiles with Ophis (http://michaelcmartin.github.com/Ophis/), tests with fceux
|
|||||||
|
|
||||||
Milestone list:
|
Milestone list:
|
||||||
|
|
||||||
1- (DONE) Boot a ROM that does nothing
|
1- (DONE) Boot a ROM that does nothing
|
||||||
2- (DONE) Single sprite visible on the screen
|
2- (DONE) Single sprite visible on the screen
|
||||||
3- (DONE) Complete complex (multi-part) sprite visible on the screen
|
3- (DONE) Complete complex (multi-part) sprite visible on the screen
|
||||||
3.5 - (DONE) single background tile visible on the screen
|
3.5 - (DONE) single background tile visible on the screen
|
||||||
4- Swap palette of sprite in response to gamepad
|
4- (INVALIDATED) Swap palette of sprite in response to gamepad
|
||||||
5- Move sprite on screen with no animation
|
This milestone got invalidated because my sprite data is in ROM, not in RAM
|
||||||
|
and besides, milestone 5 covers everything this was supposed to anyway
|
||||||
|
5- (DONE) Move sprite on screen with no animation
|
||||||
6- Display a full tile map on the screen
|
6- Display a full tile map on the screen
|
||||||
7- Collide a sprite with the world map
|
7- Collide a sprite with the world map
|
||||||
8- Apply gravity to a sprite and have him stand on the "ground"
|
8- Apply gravity to a sprite and have him stand on the "ground"
|
||||||
|
|||||||
16
defines.S
16
defines.S
@@ -1,16 +0,0 @@
|
|||||||
.alias curSpriteDataRead curSpriteDataLo
|
|
||||||
.alias curSpriteDataWrite curSpriteDataHi
|
|
||||||
|
|
||||||
.macro storeStackReturn ; storeStackReturn
|
|
||||||
PLA
|
|
||||||
STA prevReturnAddrHi
|
|
||||||
PLA
|
|
||||||
STA prevReturnAddrLo
|
|
||||||
.macend
|
|
||||||
|
|
||||||
.macro restoreStackReturn
|
|
||||||
LDA prevReturnAddrLo
|
|
||||||
PHA
|
|
||||||
LDA prevReturnAddrhi
|
|
||||||
PHA
|
|
||||||
.macend
|
|
||||||
@@ -1,5 +1,13 @@
|
|||||||
.alias curSpriteDataRead curSpriteDataLo
|
.alias curSpriteDataRead curSpriteDataLo
|
||||||
.alias curSpriteDataWrite curSpriteDataHi
|
.alias curSpriteDataWrite curSpriteDataHi
|
||||||
|
.alias pada %10000000
|
||||||
|
.alias padb %01000000
|
||||||
|
.alias padselect %00100000
|
||||||
|
.alias padstart %00010000
|
||||||
|
.alias padup %00001000
|
||||||
|
.alias paddown %00000100
|
||||||
|
.alias padleft %00000010
|
||||||
|
.alias padright %00000001
|
||||||
|
|
||||||
.macro storeStackReturn ; storeStackReturn
|
.macro storeStackReturn ; storeStackReturn
|
||||||
PLA
|
PLA
|
||||||
@@ -13,4 +21,4 @@
|
|||||||
PHA
|
PHA
|
||||||
LDA prevReturnAddrhi
|
LDA prevReturnAddrhi
|
||||||
PHA
|
PHA
|
||||||
.macend
|
.macend
|
||||||
|
|||||||
155
nesgame.S
155
nesgame.S
@@ -4,7 +4,7 @@
|
|||||||
;; and how to perform background mirroring
|
;; and how to perform background mirroring
|
||||||
|
|
||||||
;; iNES header block
|
;; iNES header block
|
||||||
|
|
||||||
.byte "NES",$1A
|
.byte "NES",$1A
|
||||||
.byte $01 ;; 1 PRG ROM page (how big is an ophis page?)
|
.byte $01 ;; 1 PRG ROM page (how big is an ophis page?)
|
||||||
.byte $02 ;; 1 CHR (tile/sprite) ROM page (how big is a page?)
|
.byte $02 ;; 1 CHR (tile/sprite) ROM page (how big is a page?)
|
||||||
@@ -14,7 +14,7 @@
|
|||||||
.byte $00,$00,$00,$00 ; Reserved bytes
|
.byte $00,$00,$00,$00 ; Reserved bytes
|
||||||
|
|
||||||
.require "include/defines.S"
|
.require "include/defines.S"
|
||||||
|
|
||||||
.text zp
|
.text zp
|
||||||
.org $0000
|
.org $0000
|
||||||
;; $0000 is reserved for things we use to extend PL/PH for call/return stacks
|
;; $0000 is reserved for things we use to extend PL/PH for call/return stacks
|
||||||
@@ -42,23 +42,22 @@
|
|||||||
.space curSpriteLen 1
|
.space curSpriteLen 1
|
||||||
.space playery 1
|
.space playery 1
|
||||||
.space playerx 1
|
.space playerx 1
|
||||||
.space pad1a 1
|
.space pad1state 1
|
||||||
.space pad1b 1
|
.space pad2state 1
|
||||||
.space pad1select 1
|
.space pad3state 1
|
||||||
.space pad1start 1
|
.space pad4state 1
|
||||||
.space pad1up 1
|
|
||||||
.space pad1down 1
|
|
||||||
.space pad1left 1
|
|
||||||
.space pad1right 1
|
|
||||||
.space pad1areleased 1
|
|
||||||
.space multiSpriteList 16 ; reserve 6 words for the list of multisprites
|
|
||||||
; currently on screen, each one listed as a
|
|
||||||
; WORD address
|
|
||||||
.space tempdivident 1
|
.space tempdivident 1
|
||||||
.space tempdivisor 1
|
.space tempdivisor 1
|
||||||
.space tempdivresult 1
|
.space tempdivresult 1
|
||||||
.space tempdivmodulus 1
|
.space tempdivmodulus 1
|
||||||
|
|
||||||
|
.org $0040
|
||||||
|
.space sprMario2DataHook1 1
|
||||||
|
.space sprMario2DataHook2 1
|
||||||
|
.space sprMario2DataHook3 1
|
||||||
|
.space sprMario2DataHook4 1
|
||||||
|
|
||||||
.text
|
.text
|
||||||
.org $C000 ;; PRG bank code starts at 0xC000
|
.org $C000 ;; PRG bank code starts at 0xC000
|
||||||
|
|
||||||
@@ -82,7 +81,7 @@ START:
|
|||||||
TXS ;; Move the contents of X to the stack pointer
|
TXS ;; Move the contents of X to the stack pointer
|
||||||
INX ;; increment X by 1, which causes overflow, so
|
INX ;; increment X by 1, which causes overflow, so
|
||||||
;; now X is 0
|
;; now X is 0
|
||||||
|
|
||||||
STX $2000 ;; set PPU flag to disable NMI (0x2000 = 0)
|
STX $2000 ;; set PPU flag to disable NMI (0x2000 = 0)
|
||||||
STX $2001 ;; set PPU flag to disable rendering (0x2001=0)
|
STX $2001 ;; set PPU flag to disable rendering (0x2001=0)
|
||||||
STX $4010 ;; disable APU IRQs, no audio
|
STX $4010 ;; disable APU IRQs, no audio
|
||||||
@@ -113,7 +112,7 @@ _START_clearmem:
|
|||||||
;; stack (0100-01FF), the entirety of main RAM
|
;; stack (0100-01FF), the entirety of main RAM
|
||||||
;; (0200-07FF)
|
;; (0200-07FF)
|
||||||
|
|
||||||
LDA #$FE ;; These two are clearing all of the sprite
|
LDA #$FE ;; These two are clearing all of the sprite
|
||||||
STA $0200, x ;; OAM; previous tutorial had this at 0300,
|
STA $0200, x ;; OAM; previous tutorial had this at 0300,
|
||||||
;; which may have been wrong. We don't HAVE
|
;; which may have been wrong. We don't HAVE
|
||||||
;; to reserve this range for OAM; we could
|
;; to reserve this range for OAM; we could
|
||||||
@@ -131,9 +130,9 @@ _START_vblankwait2:
|
|||||||
BPL _START_vblankwait2 ;; once we've gotten 1 vblank,
|
BPL _START_vblankwait2 ;; once we've gotten 1 vblank,
|
||||||
;; cleared mem, and gotten another vblank,
|
;; cleared mem, and gotten another vblank,
|
||||||
;; the PPU is ready. Wait for it.
|
;; the PPU is ready. Wait for it.
|
||||||
JMP main
|
JMP main
|
||||||
|
|
||||||
|
|
||||||
main:
|
main:
|
||||||
;; horray, here is main()
|
;; horray, here is main()
|
||||||
LDA #$00
|
LDA #$00
|
||||||
@@ -144,7 +143,7 @@ main:
|
|||||||
PHA
|
PHA
|
||||||
JSR paletteLoad
|
JSR paletteLoad
|
||||||
;; $2000 is the PPU Control register, controlled by various bitflags.
|
;; $2000 is the PPU Control register, controlled by various bitflags.
|
||||||
;;
|
;;
|
||||||
;; 7654 3210
|
;; 7654 3210
|
||||||
;; |||| ||||
|
;; |||| ||||
|
||||||
;; |||| ||++- Base nametable address
|
;; |||| ||++- Base nametable address
|
||||||
@@ -163,7 +162,7 @@ main:
|
|||||||
|
|
||||||
;; The PPU mask is set at $2001, the 2nd PPU Control register, and it
|
;; The PPU mask is set at $2001, the 2nd PPU Control register, and it
|
||||||
;; sets one config option for every bit of the byte
|
;; sets one config option for every bit of the byte
|
||||||
;;
|
;;
|
||||||
;; 76543210
|
;; 76543210
|
||||||
;; ||||||||
|
;; ||||||||
|
||||||
;; |||||||+- Grayscale (0: normal color; 1: AND all palette entries
|
;; |||||||+- Grayscale (0: normal color; 1: AND all palette entries
|
||||||
@@ -177,7 +176,7 @@ main:
|
|||||||
;; |+------- Intensify greens (and darken other colors)
|
;; |+------- Intensify greens (and darken other colors)
|
||||||
;; +-------- Intensify blues (and darken other colors)
|
;; +-------- Intensify blues (and darken other colors)
|
||||||
|
|
||||||
|
|
||||||
LDA #$80
|
LDA #$80
|
||||||
STA playerx
|
STA playerx
|
||||||
STA playery
|
STA playery
|
||||||
@@ -241,7 +240,7 @@ _bgcall:
|
|||||||
_MAIN_loop:
|
_MAIN_loop:
|
||||||
JMP _MAIN_loop ;; Loop forever
|
JMP _MAIN_loop ;; Loop forever
|
||||||
|
|
||||||
NMI:
|
NMI:
|
||||||
;; We need to copy all our OAM data to put sprites on screen during
|
;; We need to copy all our OAM data to put sprites on screen during
|
||||||
;; vblank. $2003 is the PPU OAM address, so we're going to tell it
|
;; vblank. $2003 is the PPU OAM address, so we're going to tell it
|
||||||
;; to pull OAM from $0200, and do a DMA transfer.
|
;; to pull OAM from $0200, and do a DMA transfer.
|
||||||
@@ -254,6 +253,112 @@ NMI:
|
|||||||
; which takes ~513 cycles. An unrolled
|
; which takes ~513 cycles. An unrolled
|
||||||
; loop to do the same thing would take
|
; loop to do the same thing would take
|
||||||
; 3-4 times as long.
|
; 3-4 times as long.
|
||||||
|
|
||||||
|
_latch1:
|
||||||
|
LDA #$01
|
||||||
|
STA $4016
|
||||||
|
LDA #$00
|
||||||
|
STA $4016
|
||||||
|
LDA #$00
|
||||||
|
STA pad1state
|
||||||
|
|
||||||
|
LDX #$08
|
||||||
|
CLC
|
||||||
|
_readpad1:
|
||||||
|
LDA $4016
|
||||||
|
AND #%00000001
|
||||||
|
ORA pad1state
|
||||||
|
DEX
|
||||||
|
BEQ _storepad1
|
||||||
|
CLC
|
||||||
|
ROL
|
||||||
|
STA pad1state
|
||||||
|
JMP _readpad1
|
||||||
|
_storepad1:
|
||||||
|
STA pad1state
|
||||||
|
|
||||||
|
_checkselect:
|
||||||
|
LDA #padselect
|
||||||
|
AND pad1state
|
||||||
|
BEQ _checkstart
|
||||||
|
LDA sprMario2DataHook1
|
||||||
|
CLC
|
||||||
|
ADC #$01
|
||||||
|
STA sprMario2DataHook1
|
||||||
|
_checkstart:
|
||||||
|
LDA #padstart
|
||||||
|
AND pad1state
|
||||||
|
BEQ _checka
|
||||||
|
LDA sprMario2DataHook2
|
||||||
|
CLC
|
||||||
|
ADC #$01
|
||||||
|
STA sprMario2DataHook2
|
||||||
|
_checka:
|
||||||
|
LDA #pada
|
||||||
|
AND pad1state
|
||||||
|
BEQ _checkb
|
||||||
|
LDA sprMario2DataHook3
|
||||||
|
CLC
|
||||||
|
ADC #$01
|
||||||
|
STA sprMario2DataHook3
|
||||||
|
_checkb:
|
||||||
|
LDA #padb
|
||||||
|
AND pad1state
|
||||||
|
BEQ _checkwalkright
|
||||||
|
LDA sprMario2DataHook4
|
||||||
|
CLC
|
||||||
|
ADC #$01
|
||||||
|
STA sprMario2DataHook4
|
||||||
|
|
||||||
|
_checkwalkright:
|
||||||
|
LDA #%00000001
|
||||||
|
AND pad1state
|
||||||
|
BEQ _checkwalkleft
|
||||||
|
LDA playerx
|
||||||
|
CLC
|
||||||
|
ADC #$01
|
||||||
|
STA playerx
|
||||||
|
_checkwalkleft:
|
||||||
|
LDA #padleft
|
||||||
|
AND pad1state
|
||||||
|
BEQ _checkwalkup
|
||||||
|
LDA playerx
|
||||||
|
SEC
|
||||||
|
SBC #$01
|
||||||
|
STA playerx
|
||||||
|
_checkwalkup:
|
||||||
|
LDA #padup
|
||||||
|
AND pad1state
|
||||||
|
BEQ _checkwalkdown
|
||||||
|
LDA playery
|
||||||
|
SEC
|
||||||
|
SBC #$01
|
||||||
|
STA playery
|
||||||
|
_checkwalkdown:
|
||||||
|
LDA #paddown
|
||||||
|
AND pad1state
|
||||||
|
BEQ _move_mario
|
||||||
|
LDA playery
|
||||||
|
CLC
|
||||||
|
ADC #$01
|
||||||
|
STA playery
|
||||||
|
_move_mario:
|
||||||
|
;; Put mario in as the first multisprite
|
||||||
|
LDA #<sprMarioData
|
||||||
|
PHA
|
||||||
|
LDA #>sprMarioData
|
||||||
|
PHA
|
||||||
|
LDA sprMario
|
||||||
|
PHA
|
||||||
|
;; DO IT
|
||||||
|
LDA #$00
|
||||||
|
STA curSpriteOAMIndexLo
|
||||||
|
LDA #$02
|
||||||
|
STA curSpriteOAMIndexHi
|
||||||
|
JSR oamInsertMultiSprite
|
||||||
|
|
||||||
|
|
||||||
|
_nmi_finish:
|
||||||
LDA #%10010000 ; enable NMI (so we get a function call every
|
LDA #%10010000 ; enable NMI (so we get a function call every
|
||||||
; vblank), and draw sprites from table 0
|
; vblank), and draw sprites from table 0
|
||||||
STA $2000
|
STA $2000
|
||||||
@@ -262,7 +367,7 @@ NMI:
|
|||||||
LDA #$00 ; hey PPU, stop friggin scrolling!
|
LDA #$00 ; hey PPU, stop friggin scrolling!
|
||||||
STA $2005
|
STA $2005
|
||||||
STA $2005
|
STA $2005
|
||||||
RTI ; just return
|
RTI
|
||||||
|
|
||||||
palette:
|
palette:
|
||||||
.byte $22,$29,$1A,$0F,$22,$36,$17,$0F,$22,$30,$21,$0F,$22,$27,$17,$0F ;;background palette
|
.byte $22,$29,$1A,$0F,$22,$36,$17,$0F,$22,$30,$21,$0F,$22,$27,$17,$0F ;;background palette
|
||||||
@@ -345,6 +450,6 @@ sprMario2Data:
|
|||||||
.word 0 ;; If we used an external IRQ vector, we would put it here
|
.word 0 ;; If we used an external IRQ vector, we would put it here
|
||||||
|
|
||||||
;; --- graphics bank
|
;; --- graphics bank
|
||||||
|
|
||||||
.org $0000 ;; CHR data is below PRG data in the memory
|
.org $0000 ;; CHR data is below PRG data in the memory
|
||||||
.incbin "mario.chr" ; include 8kB of graphics from SMB1
|
.incbin "mario.chr" ; include 8kB of graphics from SMB1
|
||||||
|
|||||||
Reference in New Issue
Block a user