ecs: updated unit tests

This commit is contained in:
Steven Hugg 2022-02-27 19:46:26 -06:00
parent e09f115084
commit 0fc860f524
25 changed files with 5113 additions and 2085 deletions

148
test/ecs/bigdemo.ecs Normal file
View File

@ -0,0 +1,148 @@
//#resource "vcs-ca65.h"
import "vcslib.ecs"
import "sprites.ecs"
import "kernel2.ecs"
import "score.ecs"
demo Main
using FrameLoop, Kernel2Sprite
using Joystick, MoveJoyX, MoveJoyY
using SetXPos, SetHorizPos
using SpriteShuffler, SpriteHider
using Kernel6Digit
using JoyButton, BCDMath
entity Score [BCDScore6, PFColor, BGColor]
const pfcolor = $3c
const bgcolor = $02
end
entity Kernel [KernelSection, BGColor]
const lines = 168
const bgcolor = 0xa0
end
entity Weird [Bitmap,Colormap]
decode vcs_sprite
---
.x...... 12
.xx..... 14
.xxx.... 16
.xxxx... 18
.xxxxx.. 1a
.xxxxxx. 1c
.xxx.xxx 1e
.x.x.x.x 18
---
end
entity Cool [Bitmap,Colormap]
decode vcs_sprite
---
...xx... 48
..xxxx.. 4a
.xxxxxx. 4c
xxxxxxxx 4e
x..xx..x 4e
x.xxx.xx 4e
xxxxxxxx 4e
xxxxxxxx 4e
xxxxxxxx 4e
xx....xx 4e
xxxxxxxx 4e
.xxxxxx. 4c
..xxxx.. 4a
---
end
entity Cool2 [Bitmap,Colormap]
decode vcs_sprite
---
...xx... 48
..xxxx.. 4a
.xxxxxx. 4c
xxxxxxxx 8e
x..xx..x ce
x..xx..x ce
xxxxxxxx ce
xxxxxxxx 4e
xxxxxxxx 4e
xx.xx.xx 4e
xxx..xxx 4e
.xxxxxx. 4c
..xxxx.. 4a
---
end
entity Bitmap1 [Bitmap]
const bitmapdata = [1, 1, 3, 7, 15, 31, 63, 255]
const height = 8
end
entity Bitmap2 [Bitmap]
const bitmapdata = [$18,$3e,$ff,$ff,$ff,$ff,$3e,$18]
const height = 8
end
entity Colormap1 [Colormap]
const colormapdata = [6, 3, 6, 9, 12, 14, 31, 63]
end
entity Sprite0 [Sprite,HasBitmap,HasColormap,HasXpos,HasYpos,Player]
var xpos = 50
var ypos = 150
var bitmap = #Cool
var colormap = #Cool
const plyrflags = 0
end
entity Sprite1 [Sprite,HasBitmap,HasColormap,HasXpos,HasYpos,Player]
var xpos = 100
var ypos = 60
var bitmap = #Cool2
var colormap = #Cool2
const plyrflags = 3
end
entity Sprite2 [Sprite,HasBitmap,HasColormap,HasXpos,HasYpos]
var xpos = 80
var ypos = 90
var bitmap = #Weird
var colormap = #Weird
const plyrflags = 0
end
entity Sprite3 [Sprite,HasBitmap,HasColormap,HasXpos,HasYpos]
var xpos = 40
var ypos = 150
var bitmap = #Weird
var colormap = #Weird
const plyrflags = 0
end
entity Slot0 [SpriteSlot]
var sprite = #Sprite0
end
entity Slot1 [SpriteSlot]
var sprite = #Sprite1
end
entity Slot2 [SpriteSlot]
var sprite = #Sprite2
end
entity Slot3 [SpriteSlot]
var sprite = #Sprite3
end
system Enemies
on postframe do foreach [Sprite,HasYpos,-Player]
---
inc {{set ypos}}
; inc {{set ypos}}
---
end
end demo

885
test/ecs/bigdemo.txt Normal file
View File

@ -0,0 +1,885 @@
EVENT__start = 1
EVENT__postframe = 1
EVENT__preframe = 1
EVENT__kernel = 1
EVENT__scanline = 1
EVENT__joyleft = 1
EVENT__joyright = 1
EVENT__joyup = 1
EVENT__joydown = 1
EVENT__prekernel = 1
EVENT__SetHorizPos = 1
EVENT__AddBCD4 = 1
EVENT__AddBCD2 = 1
EVENT__SubBCD2 = 1
.scope Main
.zeropage
Sprite_bitmap_b0:
.res 1
.res 1
.res 1
.res 1
HasColormap_colormap_b0:
.res 1
.res 1
.res 1
.res 1
HasXpos_xpos_b0:
.res 1
.res 1
.res 1
.res 1
HasYpos_ypos_b0:
.res 1
.res 1
.res 1
.res 1
SpriteSlot_sprite_b0:
.res 1
.res 1
.res 1
.res 1
BCDScore6_digits_b0:
.res 1
BCDScore6_digits_b8:
.res 1
BCDScore6_digits_b16:
.res 1
TEMP:
Kernel2Sprite__2__tmp:
Joystick__3__tmp:
SpriteHider__9__tmp:
.res 1
SpriteShuffler__8__tmp:
.res 1
.res 1
.res 1
.res 1
.res 1
.res 1
.res 1
.res 1
.res 1
.res 1
.res 1
.res 1
Kernel6Digit__10__tmp:
.res 1
.res 1
.res 1
.res 1
.res 1
.res 1
.res 1
.res 1
.res 1
.res 1
.res 1
.res 1
.res 1
.res 1
.res 1
.code
PFColor_pfcolor_b0:
.byte 60
BGColor_bgcolor_b0:
.byte 2
.byte 160
KernelSection_lines_b0:
.byte 168
Bitmap_bitmapdata_b0:
.byte <(Bitmap_bitmapdata_e2_b0+31)
.byte <(Bitmap_bitmapdata_e3_b0+31)
.byte <(Bitmap_bitmapdata_e4_b0+31)
.byte <(Bitmap_bitmapdata_e5_b0+31)
.byte <(Bitmap_bitmapdata_e6_b0+31)
Bitmap_bitmapdata_b8:
.byte >(Bitmap_bitmapdata_e2_b0+31)
.byte >(Bitmap_bitmapdata_e3_b0+31)
.byte >(Bitmap_bitmapdata_e4_b0+31)
.byte >(Bitmap_bitmapdata_e5_b0+31)
.byte >(Bitmap_bitmapdata_e6_b0+31)
Bitmap_bitmapdata_e2_b0:
.byte 85
.byte 119
.byte 126
.byte 124
.byte 120
.byte 112
.byte 96
.byte 64
Bitmap_height_b0:
.byte 7
.byte 12
.byte 12
.byte 8
.byte 8
Colormap_colormapdata_b0:
.byte <(Colormap_colormapdata_e2_b0+31)
.byte <(Colormap_colormapdata_e3_b0+31)
.byte <(Colormap_colormapdata_e4_b0+31)
.res 1
.res 1
.byte <(Colormap_colormapdata_e7_b0+31)
Colormap_colormapdata_b8:
.byte >(Colormap_colormapdata_e2_b0+31)
.byte >(Colormap_colormapdata_e3_b0+31)
.byte >(Colormap_colormapdata_e4_b0+31)
.res 1
.res 1
.byte >(Colormap_colormapdata_e7_b0+31)
Colormap_colormapdata_e2_b0:
.byte 24
.byte 30
.byte 28
.byte 26
.byte 24
.byte 22
.byte 20
.byte 18
Bitmap_bitmapdata_e3_b0:
.byte 60
.byte 126
.byte 255
.byte 195
.byte 255
.byte 255
.byte 255
.byte 187
.byte 153
.byte 255
.byte 126
.byte 60
.byte 24
Colormap_colormapdata_e3_b0:
.byte 74
.byte 76
.byte 78
.byte 78
.byte 78
.byte 78
.byte 78
.byte 78
.byte 78
.byte 78
.byte 76
.byte 74
.byte 72
Bitmap_bitmapdata_e4_b0:
.byte 60
.byte 126
.byte 231
.byte 219
.byte 255
.byte 255
.byte 255
.byte 153
.byte 153
.byte 255
.byte 126
.byte 60
.byte 24
Colormap_colormapdata_e4_b0:
.byte 74
.byte 76
.byte 78
.byte 78
.byte 78
.byte 78
.byte 206
.byte 206
.byte 206
.byte 142
.byte 76
.byte 74
.byte 72
Bitmap_bitmapdata_e5_b0:
.byte 1
.byte 1
.byte 3
.byte 7
.byte 15
.byte 31
.byte 63
.byte 255
Bitmap_bitmapdata_e6_b0:
.byte 24
.byte 62
.byte 255
.byte 255
.byte 255
.byte 255
.byte 62
.byte 24
Colormap_colormapdata_e7_b0:
.byte 6
.byte 3
.byte 6
.byte 9
.byte 12
.byte 14
.byte 31
.byte 63
Sprite_plyrflags_b0:
.byte 0
.byte 3
.byte 0
.byte 0
Main__INITDATA:
.byte 1
.byte 2
.byte 0
.byte 0
.byte 1
.byte 2
.byte 0
.byte 0
.byte 50
.byte 100
.byte 80
.byte 40
.byte 150
.byte 60
.byte 90
.byte 150
.byte 0
.byte 1
.byte 2
.byte 3
.byte 0
.byte 0
.byte 0
__Start:
;;; start action Init__main_init__1
.include "vcs-ca65.h"
.macpack longbranch
.define PAL 0
__NMI:
__Reset:
__BRK:
CLEAN_START
ldy #23
: lda Main__INITDATA-1,y
sta Sprite_bitmap_b0-1,y
dey
bne :-
;;; start action FrameLoop__start__3
FrameLoop__start__4__NextFrame:
FRAME_END
FRAME_START
;;; start action Kernel2Sprite__preframe__5
; TODOO: can store KLINES in memory?
.define KLINES #168
.define KPAD 32
; set height to zero in case no sprites
lda #0
sta Kernel2Sprite__2__tmp+8
sta Kernel2Sprite__2__tmp+9
;;; end action Kernel2Sprite__preframe__5
;;; start action Kernel2Sprite__preframe__8
ldy #0
Kernel2Sprite__preframe__9____each:
ldx SpriteSlot_sprite_b0,y
; set player object flags
lda Sprite_plyrflags_b0,x
sta NUSIZ0,y
sta REFP0,y
; calculate screen height - ypos
lda KLINES
clc
adc KPAD
sec
sbc HasYpos_ypos_b0,x
sta Kernel2Sprite__2__tmp+11
; calculate bitmap pointer
stx Kernel2Sprite__2__tmp+12 ; save X (Sprite index)
lda Sprite_bitmap_b0,x ; deref bitmap
tax
lda Bitmap_bitmapdata_b0,x
sec
sbc Kernel2Sprite__2__tmp+11
sta Kernel2Sprite__2__tmp+0,y ; Y = sprite slot index
lda Bitmap_bitmapdata_b8,x
sbc #0
sta Kernel2Sprite__2__tmp+2,y
; get bitmap height
lda Bitmap_height_b0,x
sta Kernel2Sprite__2__tmp+8,y
; calculate colormap pointer
ldx Kernel2Sprite__2__tmp+12 ; restore X
lda HasColormap_colormap_b0,x ; deref colormap
tax
lda Colormap_colormapdata_b0,x
sec
sbc Kernel2Sprite__2__tmp+11
sta Kernel2Sprite__2__tmp+4,y
lda Colormap_colormapdata_b8,x
sbc #0
sta Kernel2Sprite__2__tmp+6,y
; save ypos
ldx Kernel2Sprite__2__tmp+12 ; restore X
lda HasYpos_ypos_b0,x
sta Kernel2Sprite__2__tmp+10,y
iny
cpy #2
jne Kernel2Sprite__preframe__9____each
Kernel2Sprite__preframe__9____exit:
;;; end action Kernel2Sprite__preframe__8
;;; start action Kernel2Sprite__preframe__11
; shuffle pointers into (MSB, LSB) byte order
; L0 L1 H0 H1 -> L0 H0 L1 H1
lda Kernel2Sprite__2__tmp+1
ldy Kernel2Sprite__2__tmp+2
sty Kernel2Sprite__2__tmp+1
sta Kernel2Sprite__2__tmp+2
lda Kernel2Sprite__2__tmp+5
ldy Kernel2Sprite__2__tmp+6
sty Kernel2Sprite__2__tmp+5
sta Kernel2Sprite__2__tmp+6
;;; end action Kernel2Sprite__preframe__11
;;; start action Kernel2Sprite__preframe__13
lda #160
sta COLUBK
;;; end action Kernel2Sprite__preframe__13
;;; start action Kernel2Sprite__preframe__16
;;; end action Kernel2Sprite__preframe__16
;;; start action SetXPos__preframe__17
ldy #0
SetXPos__preframe__18____each:
ldx SpriteSlot_sprite_b0,y
lda HasXpos_xpos_b0,x
jsr SetHorizPos__SetHorizPos__20
iny
cpy #2
jne SetXPos__preframe__18____each
SetXPos__preframe__18____exit:
;;; end action SetXPos__preframe__17
;;; start action SetXPos__preframe__22
;;; end action SetXPos__preframe__22
;;; start action Kernel6Digit__preframe__23
Digit0 = Kernel6Digit__10__tmp+0
Digit1 = Kernel6Digit__10__tmp+2
Digit2 = Kernel6Digit__10__tmp+4
Digit3 = Kernel6Digit__10__tmp+6
Digit4 = Kernel6Digit__10__tmp+8
Digit5 = Kernel6Digit__10__tmp+10
Kernel6Digit__preframe__25__BCD0 = Kernel6Digit__10__tmp+12
Kernel6Digit__preframe__25__BCD1 = Kernel6Digit__10__tmp+13
Kernel6Digit__preframe__25__BCD2 = Kernel6Digit__10__tmp+14
lda BCDScore6_digits_b0
sta Kernel6Digit__preframe__25__BCD0
lda BCDScore6_digits_b8
sta Kernel6Digit__preframe__25__BCD1
lda BCDScore6_digits_b16
sta Kernel6Digit__preframe__25__BCD2
ldx #0 ; leftmost bitmap
ldy #2 ; start from most-sigificant BCD value
Kernel6Digit__preframe__25__Loop:
lda Kernel6Digit__preframe__25__BCD0,y ; get BCD value
and #$f0 ; isolate high nibble (* 16)
lsr ; shift right 1 bit (* 8)
clc
adc #<FontTable
sta Digit0,x ; store pointer lo byte
lda #>FontTable
adc #0
sta Digit0+1,x ; store pointer hi byte
inx
inx ; next bitmap pointer
lda Kernel6Digit__preframe__25__BCD0,y ; get BCD value (again)
and #$f ; isolate low nibble
asl
asl
asl ; * 8
clc
adc #<FontTable
sta Digit0,x ; store pointer lo byte
lda #>FontTable
adc #0
sta Digit0+1,x ; store pointer hi byte
inx
inx ; next bitmap pointer
dey ; next BCD value
bpl Kernel6Digit__preframe__25__Loop ; repeat until < 0
;;; end action Kernel6Digit__preframe__23
;;; start action SetXPos__prekernel__26
sta WSYNC
sta HMOVE
SLEEPR 24
sta HMCLR
;;; end action SetXPos__prekernel__26
KERNEL_START
;;; start action Kernel2Sprite__kernel__28
ldy #0
sty VDELP0
iny
sty VDELP1
;;; end action Kernel2Sprite__kernel__28
jsr Kernel2Sprite__kernel__31
;;; start action Kernel2Sprite__kernel__40
lda #0
sta GRP0
sta GRP1
sta GRP0
sta GRP1
;;; end action Kernel2Sprite__kernel__40
;;; start action Kernel6Digit__kernel__42
lda #60
sta COLUP0
sta COLUP1
lda #3
sta NUSIZ0
sta NUSIZ1
; set horizontal position of player objects
sta WSYNC
sta HMCLR
SLEEPR 24
sta RESP0
sta RESP1
lda #$10
sta HMP1
sta WSYNC
sta HMOVE
SLEEPR 24 ; wait 24 cycles between write to HMOVE and HMxxx
sta HMCLR
lda #1
sta VDELP0
sta VDELP1
;;; end action Kernel6Digit__kernel__42
jsr Kernel6Digit__kernel__45
KERNEL_END
;;; start action FrameLoop__postframe__48
lsr SWCHB ; test Game Reset switch
bcs FrameLoop__postframe__49__NoStart
FrameLoop__postframe__49__NoStart:
;;; end action FrameLoop__postframe__48
;;; start action Joystick__postframe__50
; 2 control inputs share a single byte, 4 bits each
lda SWCHA
sta Joystick__3__tmp+0
;;; end action Joystick__postframe__50
;;; start action Joystick__postframe__52
ldx #0
Joystick__postframe__53____each:
asl Joystick__3__tmp+0
.ifdef EVENT__joyright
bcs Joystick__postframe__54__SkipMoveRight
;;; start action MoveJoyX__joyright__55
lda HasXpos_xpos_b0,x
clc
adc #1
cmp #150
bcs MoveJoyX__joyright__57__nomove
sta HasXpos_xpos_b0,x
MoveJoyX__joyright__57__nomove:
;;; end action MoveJoyX__joyright__55
Joystick__postframe__54__SkipMoveRight:
.endif
asl Joystick__3__tmp+0
.ifdef EVENT__joyleft
bcs Joystick__postframe__54__SkipMoveLeft
;;; start action MoveJoyX__joyleft__58
lda HasXpos_xpos_b0,x
sec
sbc #1
bcc MoveJoyX__joyleft__60__nomove
sta HasXpos_xpos_b0,x
MoveJoyX__joyleft__60__nomove:
;;; end action MoveJoyX__joyleft__58
Joystick__postframe__54__SkipMoveLeft:
.endif
asl Joystick__3__tmp+0
.ifdef EVENT__joydown
bcs Joystick__postframe__54__SkipMoveDown
;;; start action MoveJoyY__joydown__61
lda HasYpos_ypos_b0,x
clc
adc #1
cmp #220
bcs MoveJoyY__joydown__63__nomove
sta HasYpos_ypos_b0,x
MoveJoyY__joydown__63__nomove:
;;; end action MoveJoyY__joydown__61
Joystick__postframe__54__SkipMoveDown:
.endif
asl Joystick__3__tmp+0
.ifdef EVENT__joyup
bcs Joystick__postframe__54__SkipMoveUp
;;; start action MoveJoyY__joyup__64
lda HasYpos_ypos_b0,x
sec
sbc #1
bcc MoveJoyY__joyup__66__nomove
sta HasYpos_ypos_b0,x
MoveJoyY__joyup__66__nomove:
;;; end action MoveJoyY__joyup__64
Joystick__postframe__54__SkipMoveUp:
.endif
inx
cpx #2
jne Joystick__postframe__53____each
Joystick__postframe__53____exit:
;;; end action Joystick__postframe__52
;;; start action SpriteShuffler__postframe__67
; load two sprite slots at left side of array
lda SpriteSlot_sprite_b0
sta SpriteShuffler__8__tmp+0
lda SpriteSlot_sprite_b0+1
sta SpriteShuffler__8__tmp+1
; move two slots to the left
ldx #0
SpriteShuffler__postframe__69__loop:
lda SpriteSlot_sprite_b0+2,x
sta SpriteSlot_sprite_b0,x
inx
cpx #4-2
bne SpriteShuffler__postframe__69__loop
; store two sprite slots at right side of array
lda SpriteShuffler__8__tmp+0
sta SpriteSlot_sprite_b0+4-2
lda SpriteShuffler__8__tmp+1
sta SpriteSlot_sprite_b0+4-1
;;; end action SpriteShuffler__postframe__67
;;; start action SpriteHider__postframe__70
lda #4-1
sta SpriteHider__9__tmp+0
;;; end action SpriteHider__postframe__70
;;; start action SpriteHider__postframe__73
ldy #0
SpriteHider__postframe__74____each:
ldx SpriteSlot_sprite_b0,y
lda HasYpos_ypos_b0,x
cmp #192
bcc SpriteHider__postframe__75__skip
; swap this sprite slot with slot at end of array
lda SpriteSlot_sprite_b0,y
pha
ldx SpriteHider__9__tmp+0 ; clobbers X, but no longer used
lda SpriteSlot_sprite_b0,x
sta SpriteSlot_sprite_b0,y
pla
sta SpriteSlot_sprite_b0,x
dec SpriteHider__9__tmp+0
SpriteHider__postframe__75__skip:
iny
cpy #2
jne SpriteHider__postframe__74____each
SpriteHider__postframe__74____exit:
;;; end action SpriteHider__postframe__73
;;; start action JoyButton__postframe__76
ldx #0
JoyButton__postframe__77____each:
lda INPT4,x ;read button input
bmi JoyButton__postframe__78__NotPressed
JoyButton__postframe__78__NotPressed:
inx
cpx #2
jne JoyButton__postframe__77____each
JoyButton__postframe__77____exit:
;;; end action JoyButton__postframe__76
;;; start action Enemies__postframe__79
ldx #0
Enemies__postframe__80____each:
inc HasYpos_ypos_b0+2,x
; inc HasYpos_ypos_b0+2,x
inx
cpx #2
jne Enemies__postframe__80____each
Enemies__postframe__80____exit:
;;; end action Enemies__postframe__79
jmp FrameLoop__start__4__NextFrame ; loop to next frame
;;; end action FrameLoop__start__3
; start main routine
.segment "VECTORS"
ZeroByte: .byte $00
Return: .byte $60
VecNMI:
VecReset: .word __Reset
VecBRK: .word __BRK
.code
;;; end action Init__main_init__1
.rodata
__ALIGNORIGIN:
.rodata
SetHorizPos__SetHorizPos__20:
; SetHorizPos routine
; A = X coordinate
; Y = player number (0 or 1)
sec ; set carry flag
sta WSYNC ; start a new line
:
sbc #15 ; subtract 15
bcs :- ; branch until negative
eor #7 ; calculate fine offset
asl
asl
asl
asl
sta HMP0,y ; set fine offset
sta RESP0,y ; fix coarse position
sta WSYNC ; won't overrun if X < 150
rts
.assert >(SetHorizPos__SetHorizPos__20) = >(*), error, "SetHorizPos__SetHorizPos__20 crosses a page boundary!"
.assert (* - SetHorizPos__SetHorizPos__20) <= 22, error, .sprintf("SetHorizPos__SetHorizPos__20 does not fit in 22 bytes, it took %d!", (* - SetHorizPos__SetHorizPos__20))
.rodata
Kernel2Sprite__kernel__31:
ldy #168
Kernel2Sprite__kernel__33__LVScan:
;;; start action Kernel2Sprite__scanline__34
; draw player 0
lda Kernel2Sprite__2__tmp+8 ; height
dcp Kernel2Sprite__2__tmp+10 ; ypos
bcs Kernel2Sprite__scanline__35__DoDraw1
lda #0
.byte $2C
Kernel2Sprite__scanline__35__DoDraw1:
lda (Kernel2Sprite__2__tmp+0),y
; .if 0 = 0 ; TODO: configurable?
sta WSYNC
; .endif
sta GRP0
lda (Kernel2Sprite__2__tmp+4),y
sta COLUP0
; draw player 1
lda Kernel2Sprite__2__tmp+9 ; height
dcp Kernel2Sprite__2__tmp+11 ; ypos
bcs Kernel2Sprite__scanline__35__DoDraw2
lda #0
.byte $2C
Kernel2Sprite__scanline__35__DoDraw2:
lda (Kernel2Sprite__2__tmp+2),y
sta GRP1
lda (Kernel2Sprite__2__tmp+6),y
sta COLUP1
;;; end action Kernel2Sprite__scanline__34
;;; start action Kernel2Sprite__scanline__36
;;; end action Kernel2Sprite__scanline__36
dey ; next scanline
;;; start action Kernel2Sprite__scanline__37
; draw player 0
lda Kernel2Sprite__2__tmp+8 ; height
dcp Kernel2Sprite__2__tmp+10 ; ypos
bcs Kernel2Sprite__scanline__38__DoDraw1
lda #0
.byte $2C
Kernel2Sprite__scanline__38__DoDraw1:
lda (Kernel2Sprite__2__tmp+0),y
; .if 1 = 0 ; TODO: configurable?
sta WSYNC
; .endif
sta GRP0
lda (Kernel2Sprite__2__tmp+4),y
sta COLUP0
; draw player 1
lda Kernel2Sprite__2__tmp+9 ; height
dcp Kernel2Sprite__2__tmp+11 ; ypos
bcs Kernel2Sprite__scanline__38__DoDraw2
lda #0
.byte $2C
Kernel2Sprite__scanline__38__DoDraw2:
lda (Kernel2Sprite__2__tmp+2),y
sta GRP1
lda (Kernel2Sprite__2__tmp+6),y
sta COLUP1
;;; end action Kernel2Sprite__scanline__37
;;; start action Kernel2Sprite__scanline__39
;;; end action Kernel2Sprite__scanline__39
dey ; next scanline
bne Kernel2Sprite__kernel__33__LVScan ; repeat until out of lines
rts
.assert >(Kernel2Sprite__kernel__31) = >(*), error, "Kernel2Sprite__kernel__31 crosses a page boundary!"
.if <(* - __ALIGNORIGIN) > 256-72
.align $100
.endif
.rodata
Kernel6Digit__kernel__45:
; Display the resulting 48x8 bitmap
; using the Digit0-5 pointers.
Kernel6Digit__kernel__47__LoopCount = Kernel6Digit__10__tmp+12
Kernel6Digit__kernel__47__Temp = Kernel6Digit__10__tmp+13
lda #2
sta WSYNC
sta COLUBK
lda #7
sta Kernel6Digit__kernel__47__LoopCount
SLEEPR 20 ; TODO?
:
ldy Kernel6Digit__kernel__47__LoopCount ; counts backwards
lda (Digit0),y ; load B0 (1st sprite byte)
sta GRP0 ; B0 -> [GRP0]
lda (Digit1),y ; load B1 -> A
sta GRP1 ; B1 -> [GRP1], B0 -> GRP0
sta WSYNC ; sync to next scanline
lda (Digit2),y ; load B2 -> A
sta GRP0 ; B2 -> [GRP0], B1 -> GRP1
lda (Digit5),y ; load B5 -> A
sta Kernel6Digit__kernel__47__Temp ; B5 -> temp
lda (Digit4),y ; load B4
tax ; -> X
lda (Digit3),y ; load B3 -> A
ldy Kernel6Digit__kernel__47__Temp ; load B5 -> Y
sta GRP1 ; B3 -> [GRP1]; B2 -> GRP0
stx GRP0 ; B4 -> [GRP0]; B3 -> GRP1
sty GRP1 ; B5 -> [GRP1]; B4 -> GRP0
sta GRP0 ; ?? -> [GRP0]; B5 -> GRP1
dec Kernel6Digit__kernel__47__LoopCount ; go to next line
bpl :- ; repeat until < 0
lda #0 ; clear the sprite registers
sta WSYNC
sta GRP0
sta GRP1
sta GRP0
sta GRP1
sta COLUBK
rts
.assert >(Kernel6Digit__kernel__45) = >(*), error, "Kernel6Digit__kernel__45 crosses a page boundary!"
.assert (* - Kernel6Digit__kernel__45) <= 72, error, .sprintf("Kernel6Digit__kernel__45 does not fit in 72 bytes, it took %d!", (* - Kernel6Digit__kernel__45))
FontTable:
;;; start action FontTable__FontTable__82
; Font table for digits 0-9 (8x8 pixels)
;;{w:8,h:8,count:10,brev:1,flip:1};;
.byte $00,$3c,$66,$66,$76,$6e,$66,$3c,$00,$7e,$18,$18,$18,$38,$18,$18
.byte $00,$7e,$60,$30,$0c,$06,$66,$3c,$00,$3c,$66,$06,$1c,$06,$66,$3c
.byte $00,$06,$06,$7f,$66,$1e,$0e,$06,$00,$3c,$66,$06,$06,$7c,$60,$7e
.byte $00,$3c,$66,$66,$7c,$60,$66,$3c,$00,$18,$18,$18,$18,$0c,$66,$7e
.byte $00,$3c,$66,$66,$3c,$66,$66,$3c,$00,$3c,$66,$06,$3e,$66,$66,$3c
;;; end action FontTable__FontTable__82
.endscope
Main__Start = Main::__Start

685
test/ecs/jumper.ecs Normal file
View File

@ -0,0 +1,685 @@
//#resource "vcs-ca65.h"
import "vcslib.ecs"
import "sprites.ecs"
import "score.ecs"
import "sound.ecs"
import "velocity.ecs"
import "kernel2.ecs"
import "random.ecs"
import "versatile.ecs"
import "music.ecs"
// TODO: not yet used
component Activity
activity: enum [Standing,Walking,Jumping]
end
component Enemy
end
component Gravity
end
component Jumper
end
system MoveJoyVel
// dampen velocity
on frame8 do with [HasXpos]
---
lda {{<xvel}}
lsr
clc
adc #4
sta {{<xvel}}
---
// move left and right
on joyleft do with [HasXpos]
---
lda {{<xvel}}
sec
sbc #1
cmp #2
bcc @nomove
sta {{<xvel}}
@nomove:
---
on joyright do with [HasXpos]
---
lda {{<xvel}}
clc
adc #1
cmp #14
bcs @nomove
sta {{<xvel}}
@nomove:
---
end
system Gravity
on frame8 do foreach [Gravity]
---
lda {{get bitmap}}
cmp #{{&DudeStanding1}}-{{&Blank}}+1
bcc @skip
lda {{<yvel}}
cmp #14
bcs @nofall
clc
adc #2
bne @done
@nofall:
lda #15
@done:
sta {{<yvel}}
@skip:
---
on xmoved do with [TinyVelY]
---
lda {{<yvel}}
cmp #7
bcc @nodown
{{!checkplatform}}
@nodown:
---
on ymoved do with [TinyVelY]
---
lda {{<yvel}}
cmp #7
bcc @nodown
{{!checkplatform}}
@nodown:
---
on joybutton do with [Player]
---
; TODO
lda {{get bitmap}}
cmp #{{&DudeStanding1}}-{{&Blank}}+1
bcs @nojump
lda #0
sta {{get yvel}}
lda #{{&DudeJumping1}}-{{&Blank}}
sta {{set bitmap}}
{{!playsound 0 1 5}}
@nojump:
---
end
system PlatformJumper
on platformstopped do with [Jumper]
---
lda {{<ypos}}
and #$fe
sta {{<ypos}}
---
on platformstopped do if [Player]
---
lda {{<yvel}}
cmp #8
beq @skip
lda #8
sta {{<yvel}}
lda #{{&DudeStanding1}}-{{&Blank}}
sta {{set bitmap}}
{{!playsound 0 2 5}}
@skip:
---
on platformnotstopped do if [Player]
---
lda #{{&DudeJumping1}}-{{&Blank}}
sta {{set bitmap}}
---
end
resource PFCollideMask ---
.byte $10,$20,$40,$80 ; PF0
.byte $80,$40,$20,$10,$08,$04,$02,$01 ; PF1
.byte $01,$02,$04,$08,$10,$20,$40,$80 ; PF2
.byte $80,$40,$20,$10,$08,$04,$02,$01 ; PF2
.byte $01,$02,$04,$08,$10,$20,$40,$80 ; PF1
.byte $80,$40,$20,$10 ; PF0
---
resource PFCollideReg ---
.byte $d,$d,$d,$d
.byte $e,$e,$e,$e,$e,$e,$e,$e
.byte $f,$f,$f,$f,$f,$f,$f,$f
.byte $f,$f,$f,$f,$f,$f,$f,$f
.byte $e,$e,$e,$e,$e,$e,$e,$e
.byte $d,$d,$d,$d
---
system EnemyMotion
on stopped do if [Enemy]
---
lda #5
sta {{<yvel}}
---
on frame16 do foreach [Enemy]
---
lda {{<xvel}}
adc {{<Les.xpos}}
and #15
sta {{<xvel}}
---
end
system EnemyCollider
on preframe do once
---
sta CXCLR
---
on postframe do once
---
lda CXPPMM
bpl @nocollide
{{!enemyspawn}}
@nocollide:
---
on enemyspawn do once
---
{{!nextrand8}}
and #$e0
clc
adc {{get Les.xpos}}
and #$7f
clc
adc #10
sta {{set Rock.xpos}}
{{!nextrand8}}
and #$20
clc
adc {{get Les.ypos}}
and #$7f
clc
adc #24
sta {{set Rock.ypos}}
; TODO:
;inc {{set Rock.bitmap}}
---
end
system EnemyDifficulty
locals 1
on preframe do foreach [Enemy]
---
{{!nextrand8}}
lsr
lsr
cmp {{get PlayerScore.digits}}
bcs @nomove
; run away from player
lda {{get xpos}}
cmp #2
bcc @nox
cmp #140
bcs @nox
sec
sbc {{get Les.xpos}}
bcc @xdec
inc {{set xpos}}
inc {{set xpos}}
@xdec:
dec {{set xpos}}
@nox:
; move Y a bit
lda {{get ypos}}
cmp #40
bcc @nomove
cmp #170
bcs @nomove
sec
sbc {{get Les.ypos}}
bcc @ydec
inc {{set ypos}}
inc {{set ypos}}
@ydec:
dec {{set ypos}}
@nomove:
---
end
//
scope Main
using FrameLoop, ResetConsole
using Kernel2Digit, BCDMath
using Kernel2Sprite
using SetXPos, SetHorizPos
using TinyMover
using Gravity
using VersatilePlayfield
using PlatformJumper
using FrameCounter
entity FrameCount [FrameCount]
end
// TODO: this has to be after FrameCounter
// for velocity damping to work correctly
// but "after" keyword might be better
using Joystick, JoyButton, MoveJoyVel with [Player]
using EnemyCollider
using EnemyDifficulty
entity Level1 [VersatilePlayfield]
decode vcs_versatile
---
.................... .. .. ..
.................... .. .. 01
.................... e8 .. ..
.................... .. .. ..
.................... .. .. ..
.................... .. .. ..
.................... .. .. ..
.................... .. .. ..
.................... .. .. ..
.................... .. .. ..
.................... .. .. ..
.................... .. .. ..
.................... .. .. ..
.................... .. .. ..
.................... .. .. ..
.................... .. .. ..
.................... .. .. ..
.................... .. .. ..
.................... .. .. ..
.................... .. .. ..
.................... .. .. ..
.................... .. .. ..
.................... .. .. ..
.................... .. .. ..
.................... .. .. ..
............xxx..... .. .. ..
.............x...... .. .. ..
.................... .. .. ..
.................... .. .. ..
.................... .. .. ..
.................... .. .. ..
.................... .. .. ..
.................... .. .. ..
.................... .. .. ..
.................... .. .. ..
.........xxx........ .. .. ..
..........xx........ .. .. ..
...........x........ .. .. ..
.................... .. .. ..
.................... 18 .. ..
.................... .. .. ..
xxxx................ .. .. ..
xxx................. .. .. ..
xx.................. .. .. ..
x................... .. .. ..
.................... .. .. ..
.................... 28 .. ..
.................... .. .. ..
....xxxxxx.......... .. .. ..
......xxxx.......... .. .. ..
........x........... .. .. ..
.................... .. .. ..
............xxx..... .. .. ..
.............xx..xxx .. .. ..
..............x...xx .. .. ..
..................xx .. .. ..
...................x .. .. ..
...................x .. .. ..
.................... .. .. ..
.................... 38 .. ..
.....xxxx........... .. .. ..
......xxx........... .. .. ..
.......xx........... .. .. ..
........x........... .. .. ..
.................... .. .. ..
.................... 48 .. ..
............xxx..... .. .. ..
.............xx..... .. .. ..
..............x..... .. .. ..
.................... .. .. ..
.................... 58 .. ..
..................xx .. .. ..
.................xxx .. .. ..
................xxxx .. .. ..
..................xx .. .. ..
...................x .. .. ..
.................... .. .. ..
.................... .. 82 ..
.................... .. .. ..
.................... .. 84 ..
.................... .. .. ..
.................... .. 86 ..
.................... .. .. ..
.................... 68 .. ..
............xxxxxx.. .. .. ..
............xxxxxx.. .. .. ..
--- end
entity Blank [Bitmap,Colormap]
decode vcs_sprite
---
........ 00
---
end
entity DudeStanding1 [Bitmap,Colormap,Activity]
const activity = Standing
decode vcs_sprite
---
..xxx... f8
.xxxxx.. f8
x.xxxx.. f8
.xxx.x.. f8
x.xxxxx. f8
x.xxxx.. f8
..xx.... f8
..xxxx.. f8
...xxx.. f8
...xx... f8
...xx... f8
..xxx... 38
..xxx... 48
.x.xxx.. 58
x..xxx.. 68
x..xx.x. 78
x..xx..x 88
...xxx.. 98
..xxxx.. 98
..x..x.. 98
..x..xx. 98
.xx...x. 98
.x....x. 98
.x....x. f8
xx....xx f8
---
end
entity DudeJumping1 [Bitmap,Colormap,Activity]
const activity = Jumping
const colormapdata = DudeStanding1.colormapdata
decode vcs_bitmap
---
x.xxx...
.xxxxx..
x.xxxx..
.xxx.x..
..xxxxx.
..xxxx..
..xx....
..xxx...
...xxx..
...xx...
x..xx...
x.xxx..x
x.xxx.x.
.x.xxx..
...xx...
...xx...
...xx...
...xxx..
..xxxx..
.xx..xx.
.x....x.
.x....x.
.x....x.
.x....x.
xx....xx
---
end
entity Coin1 [Bitmap,Colormap]
decode vcs_sprite
---
00001000 ca
01001001 dc
00100010 ee
00000000 0e
00011110 0e
00100011 ee
01000101 ee
10001001 ee
11111001 ee
11101001 ee
11011001 ee
11111001 dc
11111001 ca
11011010 ca
10111100 ca
01111000 ca
---
end
entity Coin2 [Bitmap,Colormap]
decode vcs_sprite
---
..xxxx.. ca
.xxxxxx. dc
xxxxxxxx ee
x..xx..x 0e
xx.xx.xx 0e
xxxxxxxx ee
xxxxxxxx ee
.xx..xx. ee
.xxxxxx. ee
.xx..xx. ee
..xxxx.. dc
...xx... ca
........ ca
---
end
entity Empty [Sprite,HasBitmap,HasColormap]
const bitmap = #Blank
const colormap = #Blank
end
entity Les [Sprite,HasBitmap,HasColormap,HasXpos,HasYpos,TinyVelX,TinyVelY,Player,Jumper,Gravity]
var xpos = 73
var ypos = 90
var bitmap = #DudeJumping1
const colormap = #DudeStanding1
var plyrflags = $00
var xvel = 8
var yvel = 7
end
entity Rock [Sprite,HasBitmap,HasColormap,HasXpos,HasYpos,Enemy]
var bitmap = #Coin1
const colormap = #Coin1
var xpos = 73
var ypos = 140
end
entity PlayerScore [BCDScore2]
var scorecolor = $ca
end
entity TimerScore [BCDScore2]
var scorecolor = $0e
var digits = $00
end
entity Kernel [KernelSection, BGColor]
const lines = 174
var bgcolor = $80
end
entity Slot0 [SpriteSlot]
var sprite = #Les
end
entity Slot1 [SpriteSlot]
var sprite = #Rock
end
// SOUNDS
using SoundEngine
entity SFXNull [SoundEffect]
const duration = 0
const sounddata = [0]
end
entity SFXJump [SoundEffect]
const duration = 14
const sounddata = [
$81,$83,$85,
$10,$11,$12,$13,$14,$15,$16,$17,$18,$19,
$a8]
end
entity SFXBounce [SoundEffect]
const duration = 10
const sounddata = [
$02,$03,$04,$08,$10,$20,$40,$20,$10,
$a4]
end
entity SFXScore [SoundEffect]
const duration = 11
const sounddata = [
$02,$03,$04,$08,$10,$20,$10,$20,$10,$08,
$a2]
end
entity SFXScore2 [SoundEffect]
const duration = 11
const sounddata = [
$02,$03,$04,$08,$10,$20,$10,$20,$10,$08,
$a8]
end
// TODO: make sfx have priority over music?
entity SFX1 [SoundChannel] end
entity SFX2 [SoundChannel] end
// MUSIC
using MusicPlayer
entity MusicPlayer [MusicPlayer]
const volume = 10
const tempo = 31
end
entity Music1 [MusicChannel] end
entity Music2 [MusicChannel] end
//
using Random
system GameManager
// start the game? set timer to 99
on joybutton do select [#TimerScore]
---
lda {{<digits}}
bne @skip
lda #$99
sta {{<digits}}
@skip:
---
// decrease the timer every 16 frames
on frame16 do foreach [#TimerScore]
---
lda {{<digits}}
beq @done
{{!SubBCD2 1}}
lda {{<digits}}
bne @done
{{!timerexpired}}
@done:
---
// add score for each new spawn
on enemyspawn do begin
foreach [#PlayerScore]
---
{{!AddBCD2 1}}
{{!playsound 1 3 10}}
---
// add timer for each new spawn
foreach [#TimerScore]
---
{{!AddBCD2 10}}
---
end
// subtract one when player wraps around vertically
on ymoved do begin
---
lda {{<yvel}}
cmp #7
bcc @nowrap
lda {{<ypos}}
cmp #2
bcs @nowrap
{{!playerwrapped}}
inc {{set ypos}}
@nowrap:
---
end
// TODO: doesn't work yet
on playerwrapped do with [#PlayerScore]
---
{{!SubBCD2 1}}
---
// each frame, game is either running or stopped
on preframe do once
---
lda {{<TimerScore.digits}}
bne @gameon
{{!gamestopped}}
jmp @done
@gameon:
{{!gamerunning}}
@done:
---
// stop everything when game is stopped
// TODO: if "Sprite" it overwrites array elements
on gamestopped do foreach [TinyVelX,TinyVelY]
// on gamestopped do foreach [Sprite]
---
lda #8
sta {{set xvel}}
sta {{set yvel}}
---
// set colors when game is stopped
on gamestopped do once
---
lda #$4c
sta {{set TimerScore.scorecolor}}
lda #$02
sta {{set Kernel.bgcolor}}
---
// set colors when game is running
on gamerunning do once
---
lda #$0a
sta {{set TimerScore.scorecolor}}
lda #$80
sta {{set Kernel.bgcolor}}
; blink when timer is close to zero
lda {{get TimerScore.digits}}
cmp #$20
bcs @nocolor
lda {{get FrameCount:frame}}
lsr
lsr
and #$07
ora #$40
sta {{set Kernel.bgcolor}}
@nocolor:
---
// play music when timer expires
on timerexpired do once
---
;{{^SampleMusic}}
{{!playmusic SampleMusic}}
---
on xxx_preframeloop do once
---
;{{^IntroMusic}}
{{!playmusic IntroMusic}}
---
end
entity [Random8]
end
end
// TODO: use byte array too?
resource IntroMusic ---
.byte $27,$90,$2c,$8f,$2f,$8f,$33,$8f,$38,$8f,$3b,$8f,$20,$23,$88,$3a,$83,$38,$82,$37,$83,$38,$20,$ff
---

1
test/ecs/jumper.txt Normal file
View File

@ -0,0 +1 @@
Error: ENOENT: no such file or directory, open './test/ecs/velocity.ecs'

147
test/ecs/kernel1.ecs Normal file
View File

@ -0,0 +1,147 @@
//#resource "vcs-ca65.h"
import "vcslib.ecs"
import "sprites.ecs"
system Kernel1Sprite
locals 7
on kernelsetup do with [Sprite]
---
; set player object flags
lda {{<plyrflags}}
sta NUSIZ0
sta REFP0
---
on kernelsetup do with
[Sprite,HasBitmap,HasColormap,HasYpos]
---
; calculate screen height - ypos
lda {{<lines}}
clc
adc #32
sec
sbc {{<ypos}}
sta {{$5}}
; calculate bitmap pointer
stx {{$6}} ; save X (Sprite index)
lda {{<bitmap}} ; deref bitmap
tax
lda {{<Bitmap:bitmapdata}},x
sec
sbc {{$5}}
sta {{$0}} ; Y = sprite slot index
lda {{>Bitmap:bitmapdata}},x
sbc #0
sta {{$1}}
; get bitmap height
lda {{<Bitmap:height}},x
sta {{$4}}
; calculate colormap pointer
ldx {{$6}} ; restore X
lda {{<colormap}} ; deref colormap
tax
lda {{<Colormap:colormapdata}},x
sec
sbc {{$5}}
sta {{$2}}
lda {{>Colormap:colormapdata}},x
sbc #0
sta {{$3}}
; save ypos
ldx {{$6}} ; restore X
lda {{<ypos}}
sta {{$5}}
@nosprite:
---
// TODO: what if > 1 player? or missile?
on kernelsetup do with [Sprite,HasXpos]
---
ldy #0
lda {{<xpos}}
{{!SetHorizPos}}
sta HMOVE
---
on prescanline do once
---
; draw player 0
lda {{$4}} ; height
dcp {{$5}} ; ypos
bcs @DoDraw1
lda #0
.byte $2C
@DoDraw1:
lda ({{$0}}),y
---
on scanline do once
---
sta GRP0
lda ({{$2}}),y
sta COLUP0
---
on kerneldone do once
---
lda #0
sta GRP0
sta GRP1
sta GRP0
sta GRP1
---
end
system KernelMissile
locals 1
// TODO: unroll loops
on preframe do foreach [Missile,HasYpos] limit 1
---
lda {{<ypos}}
sta {{$0}}
---
on scanline do foreach [Missile,HasYpos] limit 1
---
dec {{$0}}
php
pla
sta ENAM0+{{const index}}-2
---
on kerneldone do foreach [Missile,HasYpos] limit 1
---
; skip 3 lines each kernel section
lda #0
sta ENAM0+{{const index}}-2
dec {{$0}}
dec {{$0}}
dec {{$0}}
---
end
system KernelCollide
locals 1
on preframe do once
---
lda #$ff
sta {{$0}} ; object index if collision
---
on kernelsetup do once
---
sta CXCLR ; clear collision flags
---
on kerneldone do with [Sprite]
---
lda CXM1P
bpl @nocollide ; missile 1 <-> player 0?
stx {{$0}} ; save object index
@nocollide:
---
// TODO: somehow avoid select? pass arg to explode?
on postframe do select [Sprite]
---
ldx {{$0}} ; get object index
bmi @noexplode ; was there collision?
{{!explode}}
@noexplode:
---
end

231
test/ecs/kernel2.ecs Normal file
View File

@ -0,0 +1,231 @@
//#resource "vcs-ca65.h"
import "vcslib.ecs"
import "sprites.ecs"
system Kernel2Sprite
locals 13
on preframe do with [KernelSection]
---
; TODOO: can store KLINES in memory?
.define KLINES {{<lines}}
.define KPAD 32
; set height to zero in case no sprites
lda #0
sta {{$8}}
sta {{$9}}
---
on preframe do join
[SpriteSlot] with
[Sprite] limit 2
---
; set player object flags
lda {{<plyrflags}}
sta NUSIZ0,y
sta REFP0,y
; calculate screen height - ypos
lda KLINES
clc
adc KPAD
sec
sbc {{<ypos}}
sta {{$11}}
; calculate bitmap pointer
stx {{$12}} ; save X (Sprite index)
lda {{<bitmap}} ; deref bitmap
tax
lda {{<Bitmap:bitmapdata}},x
sec
sbc {{$11}}
sta {{$0}},y ; Y = sprite slot index
lda {{>Bitmap:bitmapdata}},x
sbc #0
sta {{$2}},y
; get bitmap height
lda {{<Bitmap:height}},x
sta {{$8}},y
; calculate colormap pointer
ldx {{$12}} ; restore X
lda {{<colormap}} ; deref colormap
tax
lda {{<Colormap:colormapdata}},x
sec
sbc {{$11}}
sta {{$4}},y
lda {{>Colormap:colormapdata}},x
sbc #0
sta {{$6}},y
; save ypos
ldx {{$12}} ; restore X
lda {{<ypos}}
sta {{$10}},y
---
on preframe do once
---
; shuffle pointers into (MSB, LSB) byte order
; L0 L1 H0 H1 -> L0 H0 L1 H1
lda {{$1}}
ldy {{$2}}
sty {{$1}}
sta {{$2}}
lda {{$5}}
ldy {{$6}}
sty {{$5}}
sta {{$6}}
---
on preframe do if [KernelSection,BGColor]
---
lda {{<bgcolor}}
sta COLUBK
---
on preframe do if [Missile,HasYpos]
---
lda KLINES
sec
sbc {{<ypos}}
sta {{$12}}
---
on kernel do with [KernelSection]
---
ldy #0
sty VDELP0
iny
sty VDELP1
---
on kernel do critical with [KernelSection]
---
ldy {{<lines}}
@LVScan:
{{!scanline 0}}
dey ; next scanline
{{!scanline 1}}
dey ; next scanline
bne @LVScan ; repeat until out of lines
---
on scanline do once
---
; draw player 0
lda {{$8}} ; height
dcp {{$10}} ; ypos
bcs @DoDraw1
lda #0
.byte $2C
@DoDraw1:
lda ({{$0}}),y
; .if {{#0}} = 0 ; TODO: configurable?
sta WSYNC
; .endif
sta GRP0
lda ({{$4}}),y
sta COLUP0
; draw player 1
lda {{$9}} ; height
dcp {{$11}} ; ypos
bcs @DoDraw2
lda #0
.byte $2C
@DoDraw2:
lda ({{$2}}),y
sta GRP1
lda ({{$6}}),y
sta COLUP1
---
on kernel do once
---
lda #0
sta GRP0
sta GRP1
sta GRP0
sta GRP1
---
on scanline do if [Missile,HasYpos]
---
cpy {{$12}}
php
pla
sta ENAM0
---
end
///
demo Main
using FrameLoop, Kernel2Sprite
using Joystick, MoveJoyX, MoveJoyY
using SetXPos, SetHorizPos
using SpriteShuffler, SpriteHider
entity Kernel [KernelSection, BGColor]
const lines = 192
const bgcolor = 0xa2
end
entity Bitmap1 [Bitmap]
const bitmapdata = [1, 1, 3, 7, 15, 31, 63, 127, 0]
const height = 8
end
entity Bitmap2 [Bitmap]
const bitmapdata = [$18,$3e,$ff,$ff,$ff,$ff,$3e,$18, 0]
const height = 8
end
entity Colormap1 [Colormap]
const colormapdata = [2, 4, 6, 8, 10, 12, 14, 14, 14]
end
entity Sprite0 [Sprite,HasBitmap,HasColormap,HasXpos,HasYpos,Player]
init xpos = 50
init ypos = 150
init bitmap = #Bitmap2
init colormap = #Colormap1
const plyrflags = 0
end
entity Sprite1 [Sprite,HasBitmap,HasColormap,HasXpos,HasYpos,Player]
init xpos = 100
init ypos = 60
init bitmap = #Bitmap1
init colormap = #Colormap1
const plyrflags = 3
end
entity Sprite2 [Sprite,HasBitmap,HasColormap,HasXpos,HasYpos,Player]
init xpos = 80
init ypos = 90
init bitmap = #Bitmap2
init colormap = #Colormap1
const plyrflags = 2
end
entity Sprite3 [Sprite,HasBitmap,HasColormap,HasXpos,HasYpos,Player]
init xpos = 40
init ypos = 150
init bitmap = #Bitmap1
init colormap = #Colormap1
const plyrflags = 0
end
/*
entity [Missile,HasXpos,HasYpos]
init xpos = 70
init ypos = 70
end
*/
entity Slot0 [SpriteSlot]
init sprite = #Sprite0
end
entity Slot1 [SpriteSlot]
init sprite = #Sprite1
end
entity Slot2 [SpriteSlot]
init sprite = #Sprite2
end
entity Slot3 [SpriteSlot]
init sprite = #Sprite3
end
end demo

587
test/ecs/kernel2.txt Normal file
View File

@ -0,0 +1,587 @@
EVENT__start = 1
EVENT__postframe = 1
EVENT__preframe = 1
EVENT__kernel = 1
EVENT__scanline = 1
EVENT__joyleft = 1
EVENT__joyright = 1
EVENT__joyup = 1
EVENT__joydown = 1
EVENT__prekernel = 1
EVENT__SetHorizPos = 1
.scope Main
.zeropage
Sprite_bitmap_b0:
.res 1
.res 1
.res 1
.res 1
HasColormap_colormap_b0:
.res 1
.res 1
.res 1
.res 1
HasXpos_xpos_b0:
.res 1
.res 1
.res 1
.res 1
HasYpos_ypos_b0:
.res 1
.res 1
.res 1
.res 1
SpriteSlot_sprite_b0:
.res 1
.res 1
.res 1
.res 1
TEMP:
Kernel2Sprite__2__tmp:
Joystick__3__tmp:
SpriteHider__9__tmp:
.res 1
SpriteShuffler__8__tmp:
.res 1
.res 1
.res 1
.res 1
.res 1
.res 1
.res 1
.res 1
.res 1
.res 1
.res 1
.res 1
.code
KernelSection_lines_b0:
.byte 192
BGColor_bgcolor_b0:
.byte 162
Bitmap_bitmapdata_b0:
.byte <(Bitmap_bitmapdata_e1_b0+31)
.byte <(Bitmap_bitmapdata_e2_b0+31)
Bitmap_bitmapdata_b8:
.byte >(Bitmap_bitmapdata_e1_b0+31)
.byte >(Bitmap_bitmapdata_e2_b0+31)
Bitmap_bitmapdata_e1_b0:
.byte 1
.byte 1
.byte 3
.byte 7
.byte 15
.byte 31
.byte 63
.byte 127
.byte 0
Bitmap_height_b0:
.byte 8
.byte 8
Bitmap_bitmapdata_e2_b0:
.byte 24
.byte 62
.byte 255
.byte 255
.byte 255
.byte 255
.byte 62
.byte 24
.byte 0
Colormap_colormapdata_b0:
.byte <(Colormap_colormapdata_e3_b0+31)
Colormap_colormapdata_b8:
.byte >(Colormap_colormapdata_e3_b0+31)
Colormap_colormapdata_e3_b0:
.byte 2
.byte 4
.byte 6
.byte 8
.byte 10
.byte 12
.byte 14
.byte 14
.byte 14
Sprite_plyrflags_b0:
.byte 0
.byte 3
.byte 2
.byte 0
Main__INITDATA:
.byte 1
.byte 0
.byte 1
.byte 0
.byte 0
.byte 0
.byte 0
.byte 0
.byte 50
.byte 100
.byte 80
.byte 40
.byte 150
.byte 60
.byte 90
.byte 150
.byte 0
.byte 1
.byte 2
.byte 3
__Start:
;;; start action Init__main_init__1
.include "vcs-ca65.h"
.macpack longbranch
.define PAL 0
__NMI:
__Reset:
__BRK:
CLEAN_START
ldy #20
: lda Main__INITDATA-1,y
sta Sprite_bitmap_b0-1,y
dey
bne :-
;;; start action FrameLoop__start__3
FrameLoop__start__4__NextFrame:
FRAME_END
FRAME_START
;;; start action Kernel2Sprite__preframe__5
; TODOO: can store KLINES in memory?
.define KLINES #192
.define KPAD 32
; set height to zero in case no sprites
lda #0
sta Kernel2Sprite__2__tmp+8
sta Kernel2Sprite__2__tmp+9
;;; end action Kernel2Sprite__preframe__5
;;; start action Kernel2Sprite__preframe__8
ldy #0
Kernel2Sprite__preframe__9____each:
ldx SpriteSlot_sprite_b0,y
; set player object flags
lda Sprite_plyrflags_b0,x
sta NUSIZ0,y
sta REFP0,y
; calculate screen height - ypos
lda KLINES
clc
adc KPAD
sec
sbc HasYpos_ypos_b0,x
sta Kernel2Sprite__2__tmp+11
; calculate bitmap pointer
stx Kernel2Sprite__2__tmp+12 ; save X (Sprite index)
lda Sprite_bitmap_b0,x ; deref bitmap
tax
lda Bitmap_bitmapdata_b0,x
sec
sbc Kernel2Sprite__2__tmp+11
sta Kernel2Sprite__2__tmp+0,y ; Y = sprite slot index
lda Bitmap_bitmapdata_b8,x
sbc #0
sta Kernel2Sprite__2__tmp+2,y
; get bitmap height
lda Bitmap_height_b0,x
sta Kernel2Sprite__2__tmp+8,y
; calculate colormap pointer
ldx Kernel2Sprite__2__tmp+12 ; restore X
lda HasColormap_colormap_b0,x ; deref colormap
tax
lda Colormap_colormapdata_b0,x
sec
sbc Kernel2Sprite__2__tmp+11
sta Kernel2Sprite__2__tmp+4,y
lda Colormap_colormapdata_b8,x
sbc #0
sta Kernel2Sprite__2__tmp+6,y
; save ypos
ldx Kernel2Sprite__2__tmp+12 ; restore X
lda HasYpos_ypos_b0,x
sta Kernel2Sprite__2__tmp+10,y
iny
cpy #2
jne Kernel2Sprite__preframe__9____each
Kernel2Sprite__preframe__9____exit:
;;; end action Kernel2Sprite__preframe__8
;;; start action Kernel2Sprite__preframe__11
; shuffle pointers into (MSB, LSB) byte order
; L0 L1 H0 H1 -> L0 H0 L1 H1
lda Kernel2Sprite__2__tmp+1
ldy Kernel2Sprite__2__tmp+2
sty Kernel2Sprite__2__tmp+1
sta Kernel2Sprite__2__tmp+2
lda Kernel2Sprite__2__tmp+5
ldy Kernel2Sprite__2__tmp+6
sty Kernel2Sprite__2__tmp+5
sta Kernel2Sprite__2__tmp+6
;;; end action Kernel2Sprite__preframe__11
;;; start action Kernel2Sprite__preframe__13
lda #162
sta COLUBK
;;; end action Kernel2Sprite__preframe__13
;;; start action Kernel2Sprite__preframe__16
;;; end action Kernel2Sprite__preframe__16
;;; start action SetXPos__preframe__17
ldy #0
SetXPos__preframe__18____each:
ldx SpriteSlot_sprite_b0,y
lda HasXpos_xpos_b0,x
jsr SetHorizPos__SetHorizPos__20
iny
cpy #2
jne SetXPos__preframe__18____each
SetXPos__preframe__18____exit:
;;; end action SetXPos__preframe__17
;;; start action SetXPos__preframe__22
;;; end action SetXPos__preframe__22
;;; start action SetXPos__prekernel__23
sta WSYNC
sta HMOVE
SLEEPR 24
sta HMCLR
;;; end action SetXPos__prekernel__23
KERNEL_START
;;; start action Kernel2Sprite__kernel__25
ldy #0
sty VDELP0
iny
sty VDELP1
;;; end action Kernel2Sprite__kernel__25
jsr Kernel2Sprite__kernel__28
;;; start action Kernel2Sprite__kernel__37
lda #0
sta GRP0
sta GRP1
sta GRP0
sta GRP1
;;; end action Kernel2Sprite__kernel__37
KERNEL_END
;;; start action FrameLoop__postframe__39
lsr SWCHB ; test Game Reset switch
bcs FrameLoop__postframe__40__NoStart
FrameLoop__postframe__40__NoStart:
;;; end action FrameLoop__postframe__39
;;; start action Joystick__postframe__41
; 2 control inputs share a single byte, 4 bits each
lda SWCHA
sta Joystick__3__tmp+0
;;; end action Joystick__postframe__41
;;; start action Joystick__postframe__43
ldx #0
Joystick__postframe__44____each:
asl Joystick__3__tmp+0
.ifdef EVENT__joyright
bcs Joystick__postframe__45__SkipMoveRight
;;; start action MoveJoyX__joyright__46
lda HasXpos_xpos_b0,x
clc
adc #1
cmp #150
bcs MoveJoyX__joyright__48__nomove
sta HasXpos_xpos_b0,x
MoveJoyX__joyright__48__nomove:
;;; end action MoveJoyX__joyright__46
Joystick__postframe__45__SkipMoveRight:
.endif
asl Joystick__3__tmp+0
.ifdef EVENT__joyleft
bcs Joystick__postframe__45__SkipMoveLeft
;;; start action MoveJoyX__joyleft__49
lda HasXpos_xpos_b0,x
sec
sbc #1
bcc MoveJoyX__joyleft__51__nomove
sta HasXpos_xpos_b0,x
MoveJoyX__joyleft__51__nomove:
;;; end action MoveJoyX__joyleft__49
Joystick__postframe__45__SkipMoveLeft:
.endif
asl Joystick__3__tmp+0
.ifdef EVENT__joydown
bcs Joystick__postframe__45__SkipMoveDown
;;; start action MoveJoyY__joydown__52
lda HasYpos_ypos_b0,x
clc
adc #1
cmp #220
bcs MoveJoyY__joydown__54__nomove
sta HasYpos_ypos_b0,x
MoveJoyY__joydown__54__nomove:
;;; end action MoveJoyY__joydown__52
Joystick__postframe__45__SkipMoveDown:
.endif
asl Joystick__3__tmp+0
.ifdef EVENT__joyup
bcs Joystick__postframe__45__SkipMoveUp
;;; start action MoveJoyY__joyup__55
lda HasYpos_ypos_b0,x
sec
sbc #1
bcc MoveJoyY__joyup__57__nomove
sta HasYpos_ypos_b0,x
MoveJoyY__joyup__57__nomove:
;;; end action MoveJoyY__joyup__55
Joystick__postframe__45__SkipMoveUp:
.endif
inx
cpx #2
jne Joystick__postframe__44____each
Joystick__postframe__44____exit:
;;; end action Joystick__postframe__43
;;; start action SpriteShuffler__postframe__58
; load two sprite slots at left side of array
lda SpriteSlot_sprite_b0
sta SpriteShuffler__8__tmp+0
lda SpriteSlot_sprite_b0+1
sta SpriteShuffler__8__tmp+1
; move two slots to the left
ldx #0
SpriteShuffler__postframe__60__loop:
lda SpriteSlot_sprite_b0+2,x
sta SpriteSlot_sprite_b0,x
inx
cpx #4-2
bne SpriteShuffler__postframe__60__loop
; store two sprite slots at right side of array
lda SpriteShuffler__8__tmp+0
sta SpriteSlot_sprite_b0+4-2
lda SpriteShuffler__8__tmp+1
sta SpriteSlot_sprite_b0+4-1
;;; end action SpriteShuffler__postframe__58
;;; start action SpriteHider__postframe__61
lda #4-1
sta SpriteHider__9__tmp+0
;;; end action SpriteHider__postframe__61
;;; start action SpriteHider__postframe__64
ldy #0
SpriteHider__postframe__65____each:
ldx SpriteSlot_sprite_b0,y
lda HasYpos_ypos_b0,x
cmp #192
bcc SpriteHider__postframe__66__skip
; swap this sprite slot with slot at end of array
lda SpriteSlot_sprite_b0,y
pha
ldx SpriteHider__9__tmp+0 ; clobbers X, but no longer used
lda SpriteSlot_sprite_b0,x
sta SpriteSlot_sprite_b0,y
pla
sta SpriteSlot_sprite_b0,x
dec SpriteHider__9__tmp+0
SpriteHider__postframe__66__skip:
iny
cpy #2
jne SpriteHider__postframe__65____each
SpriteHider__postframe__65____exit:
;;; end action SpriteHider__postframe__64
jmp FrameLoop__start__4__NextFrame ; loop to next frame
;;; end action FrameLoop__start__3
; start main routine
.segment "VECTORS"
ZeroByte: .byte $00
Return: .byte $60
VecNMI:
VecReset: .word __Reset
VecBRK: .word __BRK
.code
;;; end action Init__main_init__1
.rodata
__ALIGNORIGIN:
.rodata
SetHorizPos__SetHorizPos__20:
; SetHorizPos routine
; A = X coordinate
; Y = player number (0 or 1)
sec ; set carry flag
sta WSYNC ; start a new line
:
sbc #15 ; subtract 15
bcs :- ; branch until negative
eor #7 ; calculate fine offset
asl
asl
asl
asl
sta HMP0,y ; set fine offset
sta RESP0,y ; fix coarse position
sta WSYNC ; won't overrun if X < 150
rts
.assert >(SetHorizPos__SetHorizPos__20) = >(*), error, "SetHorizPos__SetHorizPos__20 crosses a page boundary!"
.assert (* - SetHorizPos__SetHorizPos__20) <= 22, error, .sprintf("SetHorizPos__SetHorizPos__20 does not fit in 22 bytes, it took %d!", (* - SetHorizPos__SetHorizPos__20))
.rodata
Kernel2Sprite__kernel__28:
ldy #192
Kernel2Sprite__kernel__30__LVScan:
;;; start action Kernel2Sprite__scanline__31
; draw player 0
lda Kernel2Sprite__2__tmp+8 ; height
dcp Kernel2Sprite__2__tmp+10 ; ypos
bcs Kernel2Sprite__scanline__32__DoDraw1
lda #0
.byte $2C
Kernel2Sprite__scanline__32__DoDraw1:
lda (Kernel2Sprite__2__tmp+0),y
; .if 0 = 0 ; TODO: configurable?
sta WSYNC
; .endif
sta GRP0
lda (Kernel2Sprite__2__tmp+4),y
sta COLUP0
; draw player 1
lda Kernel2Sprite__2__tmp+9 ; height
dcp Kernel2Sprite__2__tmp+11 ; ypos
bcs Kernel2Sprite__scanline__32__DoDraw2
lda #0
.byte $2C
Kernel2Sprite__scanline__32__DoDraw2:
lda (Kernel2Sprite__2__tmp+2),y
sta GRP1
lda (Kernel2Sprite__2__tmp+6),y
sta COLUP1
;;; end action Kernel2Sprite__scanline__31
;;; start action Kernel2Sprite__scanline__33
;;; end action Kernel2Sprite__scanline__33
dey ; next scanline
;;; start action Kernel2Sprite__scanline__34
; draw player 0
lda Kernel2Sprite__2__tmp+8 ; height
dcp Kernel2Sprite__2__tmp+10 ; ypos
bcs Kernel2Sprite__scanline__35__DoDraw1
lda #0
.byte $2C
Kernel2Sprite__scanline__35__DoDraw1:
lda (Kernel2Sprite__2__tmp+0),y
; .if 1 = 0 ; TODO: configurable?
sta WSYNC
; .endif
sta GRP0
lda (Kernel2Sprite__2__tmp+4),y
sta COLUP0
; draw player 1
lda Kernel2Sprite__2__tmp+9 ; height
dcp Kernel2Sprite__2__tmp+11 ; ypos
bcs Kernel2Sprite__scanline__35__DoDraw2
lda #0
.byte $2C
Kernel2Sprite__scanline__35__DoDraw2:
lda (Kernel2Sprite__2__tmp+2),y
sta GRP1
lda (Kernel2Sprite__2__tmp+6),y
sta COLUP1
;;; end action Kernel2Sprite__scanline__34
;;; start action Kernel2Sprite__scanline__36
;;; end action Kernel2Sprite__scanline__36
dey ; next scanline
bne Kernel2Sprite__kernel__30__LVScan ; repeat until out of lines
rts
.assert >(Kernel2Sprite__kernel__28) = >(*), error, "Kernel2Sprite__kernel__28 crosses a page boundary!"
.endscope
Main__Start = Main::__Start

189
test/ecs/music.ecs Normal file
View File

@ -0,0 +1,189 @@
//#resource "vcs-ca65.h"
import "vcslib.ecs"
component Song
songdata: array of 0..255
end
// TODO: merge with SoundChannel
component MusicChannel
duration: 0..255
note: 0..255
duty: 0..255
end
component MusicPlayer
timer: 0..255 default 255
channel: [MusicChannel]
songptr: 0..65535
volume: 0..15 default 15
tempo: 0..255 default 7
end
// Table of AUDF base values for each note
resource FREQZ ---
.byte 30, 30, 30, 30, 30, 28, 26, 25, 23, 22, 21, 19, 18, 17, 16, 15, 14, 13, 12, 12, 11, 10, 10, 9, 8, 8, 7, 7, 6, 6, 5, 5, 30, 29, 27, 25, 24, 22, 21, 20, 19, 18, 16, 15, 15, 14, 13, 12, 11, 11, 10, 31, 29, 27, 25, 24, 23, 21, 20, 19, 18, 16, 15, 15
---
// Table of duty-cycle bits for each note
resource DUTYZ ---
.byte 247, 247, 247, 247, 1, 73, 219, 1, 219, 73, 0, 219, 181, 85, 85, 85, 181, 219, 247, 1, 73, 181, 0, 73, 219, 17, 219, 17, 219, 73, 247, 85, 247, 1, 85, 247, 73, 247, 181, 17, 1, 0, 247, 247, 0, 1, 17, 73, 181, 0, 17, 0, 1, 85, 247, 73, 0, 181, 73, 1, 0, 247, 247, 0
---
// Table of AUDC values for each note
resource TONEZ ---
.byte 0, 0, 0, 0, 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, 12, 12, 12, 12, 12, 12, 12, 12, 12, 12, 12, 12, 12, 12, 12, 12, 12, 12, 12, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4
---
system MusicPlayer
on preframe do once
---
{{!musicpulse}} ; update song
{{!musicframe}} ; update registers
---
on prekernel do once
---
{{!musicframe}} ; update registers
---
on postkernel do once
---
{{!musicframe}} ; update registers
---
on postframe do once
---
{{!musicframe}} ; update registers
---
// TODO: unroll?
on musicframe do foreach [MusicChannel]
---
; Update channel pitch in AUDF0
; 8-bit rotation of duty cycle bits
lda {{get duration}}
beq :++
lda {{set duty}}
asl
bcc :+
ora #1
: sta {{set duty}}
lda {{get note}}
beq :+
; If next bit is set, add 1 to AUDF0
adc #0
sta AUDF0,x
:
---
on musicpulse do foreach [MusicChannel]
---
; Decrement the volumes for each channel
; Also decrement next-note timer, fetch next note
lda {{get duration}}
beq :+
lsr
sta AUDV0,x
dec {{set duration}}
:
---
on musicpulse do with [MusicPlayer]
---
lda {{get timer}}
bmi @Done
beq @NextData
dec {{set timer}}
jmp @Done
; Timer ran out, so fetch next note
@NextData:
ldx #0
lda ({{get songptr}},x)
bmi @LoadDuration
; < $80, play next note
ldx {{get channel}} ; next channel
tay
{{!musicnote}}
inx
txa
and #1
sta {{set channel}} ; inc next channel
jmp @IncDataPtr
; >= $80, load next duration
@LoadDuration:
cmp #$ff ; $ff = end of song
bne @NoResetTrack
sta {{set timer}}
{{!musicdone}}
jmp @Done
@NoResetTrack:
and #$7f
; asl
sta {{set timer}} ; store duration * 2
@IncDataPtr:
; increment song pointer
inc {{set songptr 0}}
bne @Done
inc {{set songptr 8}}
@Done:
---
// TODO: should use "with"?
on musicnote do select all [MusicChannel]
---
; Play a note
; X = channel (0,1)
; Y = note index (0-63)
lda {{^FREQZ}},y
sta {{base note}},x
lda {{^DUTYZ}},y
sta {{base duty}},x
lda {{^TONEZ}},y
sta AUDC0,x
; TODO: consts?
lda {{get MusicPlayer:tempo}}
sta {{base duration}},x
lda {{get MusicPlayer:volume}}
sta AUDV0,x
---
on playmusic do foreach [MusicPlayer] limit 1
---
lda #<{{arg 0}}
sta {{set songptr 0}}
lda #>{{arg 0}}
sta {{set songptr 8}}
lda #0
sta {{set timer}}
---
on stopmusic do foreach [MusicPlayer] limit 1
---
lda #$ff
sta {{set timer}}
---
end
///
demo music
using FrameLoop
using MusicPlayer
entity [MusicChannel] end
entity [MusicChannel] end
entity MusicPlayer [MusicPlayer]
const volume = 10
const tempo = 31
end
system music
on musicdone do with [MusicPlayer]
---
; TODO: nested exprs
; {{!playmusic ^SampleMusic}}
;{{^SampleMusic}}
{{!playmusic SampleMusic}}
---
on preframeloop do once
---
{{!musicdone}}
---
end
end demo
resource SampleMusic ---
.byte $35,$41,$8a,$37,$43,$8a,$33,$3f,$8a,$30,$3c,$94,$3e,$32,$8a,$3a,$2e,$94,$35,$29,$8a,$37,$2b,$8a,$33,$27,$8a,$30,$24,$94,$32,$26,$8a,$2e,$22,$94,$29,$1d,$8a,$2b,$1f,$8a,$27,$1b,$8a,$24,$18,$94,$1a,$26,$8a,$18,$24,$8a,$17,$23,$8a,$16,$22,$a8,$3a,$35,$ff
---

333
test/ecs/music.txt Normal file
View File

@ -0,0 +1,333 @@
EVENT__start = 1
EVENT__postframe = 1
EVENT__preframe = 1
EVENT__prekernel = 1
EVENT__postkernel = 1
EVENT__musicframe = 1
EVENT__musicpulse = 1
EVENT__musicnote = 1
EVENT__playmusic = 1
EVENT__stopmusic = 1
EVENT__musicdone = 1
EVENT__preframeloop = 1
.scope music
.zeropage
MusicPlayer_timer_b0:
.res 1
MusicChannel_duration_b0:
.res 1
.res 1
MusicChannel_note_b0:
.res 1
.res 1
MusicChannel_duty_b0:
.res 1
.res 1
MusicPlayer_channel_b0:
.res 1
MusicPlayer_songptr_b0:
.res 1
MusicPlayer_songptr_b8:
.res 1
.code
MusicPlayer_volume_b0:
.byte 10
MusicPlayer_tempo_b0:
.byte 31
music__INITDATA:
.byte 255
.byte 0
.byte 0
.byte 0
.byte 0
.byte 0
.byte 0
.byte 0
.byte 0
.byte 0
__Start:
;;; start action Init__main_init__1
.include "vcs-ca65.h"
.macpack longbranch
.define PAL 0
__NMI:
__Reset:
__BRK:
CLEAN_START
ldy #10
: lda music__INITDATA-1,y
sta MusicPlayer_timer_b0-1,y
dey
bne :-
;;; start action FrameLoop__start__3
;;; start action music__preframeloop__5
;;; start action music__musicdone__7
; TODO: nested exprs
;
jsr MusicPlayer__playmusic__10
;SampleMusic
jsr MusicPlayer__playmusic__13
;;; end action music__musicdone__7
;;; end action music__preframeloop__5
FrameLoop__start__4__NextFrame:
FRAME_END
FRAME_START
;;; start action MusicPlayer__preframe__16
;;; start action MusicPlayer__musicpulse__18
ldx #0
MusicPlayer__musicpulse__19____each:
; Decrement the volumes for each channel
; Also decrement next-note timer, fetch next note
lda MusicChannel_duration_b0,x
beq :+
lsr
sta AUDV0,x
dec MusicChannel_duration_b0,x
:
inx
cpx #2
jne MusicPlayer__musicpulse__19____each
MusicPlayer__musicpulse__19____exit:
;;; end action MusicPlayer__musicpulse__18
;;; start action MusicPlayer__musicpulse__21
lda MusicPlayer_timer_b0
bmi MusicPlayer__musicpulse__23__Done
beq MusicPlayer__musicpulse__23__NextData
dec MusicPlayer_timer_b0
jmp MusicPlayer__musicpulse__23__Done
; Timer ran out, so fetch next note
MusicPlayer__musicpulse__23__NextData:
ldx #0
lda (MusicPlayer_songptr_b0,x)
bmi MusicPlayer__musicpulse__23__LoadDuration
; < $80, play next note
ldx MusicPlayer_channel_b0 ; next channel
tay
;;; start action MusicPlayer__musicnote__24
; Play a note
; X = channel (0,1)
; Y = note index (0-63)
lda FREQZ,y
sta MusicChannel_note_b0,x
lda DUTYZ,y
sta MusicChannel_duty_b0,x
lda TONEZ,y
sta AUDC0,x
; TODO: consts?
lda MusicPlayer_tempo_b0
sta MusicChannel_duration_b0,x
lda MusicPlayer_volume_b0
sta AUDV0,x
;;; end action MusicPlayer__musicnote__24
inx
txa
and #1
sta MusicPlayer_channel_b0 ; inc next channel
jmp MusicPlayer__musicpulse__23__IncDataPtr
; >= $80, load next duration
MusicPlayer__musicpulse__23__LoadDuration:
cmp #$ff ; $ff = end of song
bne MusicPlayer__musicpulse__23__NoResetTrack
sta MusicPlayer_timer_b0
;;; start action music__musicdone__27
; TODO: nested exprs
;
jsr MusicPlayer__playmusic__10
;SampleMusic
jsr MusicPlayer__playmusic__13
;;; end action music__musicdone__27
jmp MusicPlayer__musicpulse__23__Done
MusicPlayer__musicpulse__23__NoResetTrack:
and #$7f
; asl
sta MusicPlayer_timer_b0 ; store duration * 2
MusicPlayer__musicpulse__23__IncDataPtr:
; increment song pointer
inc MusicPlayer_songptr_b0
bne MusicPlayer__musicpulse__23__Done
inc MusicPlayer_songptr_b8
MusicPlayer__musicpulse__23__Done:
;;; end action MusicPlayer__musicpulse__21
; update song
jsr MusicPlayer__musicframe__36
; update registers
;;; end action MusicPlayer__preframe__16
;;; start action MusicPlayer__prekernel__39
jsr MusicPlayer__musicframe__36
; update registers
;;; end action MusicPlayer__prekernel__39
KERNEL_START
KERNEL_END
;;; start action MusicPlayer__postkernel__44
jsr MusicPlayer__musicframe__36
; update registers
;;; end action MusicPlayer__postkernel__44
;;; start action FrameLoop__postframe__49
lsr SWCHB ; test Game Reset switch
bcs FrameLoop__postframe__50__NoStart
FrameLoop__postframe__50__NoStart:
;;; end action FrameLoop__postframe__49
;;; start action MusicPlayer__postframe__51
jsr MusicPlayer__musicframe__36
; update registers
;;; end action MusicPlayer__postframe__51
jmp FrameLoop__start__4__NextFrame ; loop to next frame
;;; end action FrameLoop__start__3
; start main routine
.segment "VECTORS"
ZeroByte: .byte $00
Return: .byte $60
VecNMI:
VecReset: .word __Reset
VecBRK: .word __BRK
.code
;;; end action Init__main_init__1
.rodata
__ALIGNORIGIN:
.rodata
MusicPlayer__playmusic__10:
lda #<^SampleMusic
sta MusicPlayer_songptr_b0
lda #>^SampleMusic
sta MusicPlayer_songptr_b8
lda #0
sta MusicPlayer_timer_b0
rts
.rodata
MusicPlayer__playmusic__13:
lda #<SampleMusic
sta MusicPlayer_songptr_b0
lda #>SampleMusic
sta MusicPlayer_songptr_b8
lda #0
sta MusicPlayer_timer_b0
rts
.rodata
MusicPlayer__musicframe__36:
ldx #0
MusicPlayer__musicframe__37____each:
; Update channel pitch in AUDF0
; 8-bit rotation of duty cycle bits
lda MusicChannel_duration_b0,x
beq :++
lda MusicChannel_duty_b0,x
asl
bcc :+
ora #1
: sta MusicChannel_duty_b0,x
lda MusicChannel_note_b0,x
beq :+
; If next bit is set, add 1 to AUDF0
adc #0
sta AUDF0,x
:
inx
cpx #2
jne MusicPlayer__musicframe__37____each
MusicPlayer__musicframe__37____exit:
rts
SampleMusic:
;;; start action SampleMusic__SampleMusic__56
.byte $35,$41,$8a,$37,$43,$8a,$33,$3f,$8a,$30,$3c,$94,$3e,$32,$8a,$3a,$2e,$94,$35,$29,$8a,$37,$2b,$8a,$33,$27,$8a,$30,$24,$94,$32,$26,$8a,$2e,$22,$94,$29,$1d,$8a,$2b,$1f,$8a,$27,$1b,$8a,$24,$18,$94,$1a,$26,$8a,$18,$24,$8a,$17,$23,$8a,$16,$22,$a8,$3a,$35,$ff
;;; end action SampleMusic__SampleMusic__56
FREQZ:
;;; start action FREQZ__FREQZ__58
.byte 30, 30, 30, 30, 30, 28, 26, 25, 23, 22, 21, 19, 18, 17, 16, 15, 14, 13, 12, 12, 11, 10, 10, 9, 8, 8, 7, 7, 6, 6, 5, 5, 30, 29, 27, 25, 24, 22, 21, 20, 19, 18, 16, 15, 15, 14, 13, 12, 11, 11, 10, 31, 29, 27, 25, 24, 23, 21, 20, 19, 18, 16, 15, 15
;;; end action FREQZ__FREQZ__58
DUTYZ:
;;; start action DUTYZ__DUTYZ__60
.byte 247, 247, 247, 247, 1, 73, 219, 1, 219, 73, 0, 219, 181, 85, 85, 85, 181, 219, 247, 1, 73, 181, 0, 73, 219, 17, 219, 17, 219, 73, 247, 85, 247, 1, 85, 247, 73, 247, 181, 17, 1, 0, 247, 247, 0, 1, 17, 73, 181, 0, 17, 0, 1, 85, 247, 73, 0, 181, 73, 1, 0, 247, 247, 0
;;; end action DUTYZ__DUTYZ__60
TONEZ:
;;; start action TONEZ__TONEZ__62
.byte 0, 0, 0, 0, 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, 12, 12, 12, 12, 12, 12, 12, 12, 12, 12, 12, 12, 12, 12, 12, 12, 12, 12, 12, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4
;;; end action TONEZ__TONEZ__62
.endscope
music__Start = music::__Start

35
test/ecs/random.ecs Normal file
View File

@ -0,0 +1,35 @@
component Random8
seed: 0..255 default 1 // TODO: default = 1, or seed?
end
system Random
on nextrand8 do foreach [Random8]
---
lda {{<seed}}
lsr
bcc :+
eor #$d4
:
sta {{<seed}}
---
on prevrand8 do foreach [Random8]
---
lda {{<seed}}
asl
bcc :+
eor #$a9
:
sta {{<seed}}
---
/* add entropy via joystick inputs */
on preframe do foreach [Random8]
---
lda {{<seed}}
eor SWCHA
beq :+
sta {{<seed}}
:
---
end

View File

@ -4,7 +4,8 @@
import "vcslib.ecs"
component BCDScore2
digits: 0..0xff
digits: 0..$ff
scorecolor: 0..$ff
end
component BCDScore4
@ -89,7 +90,9 @@ Digit5 = {{$10}}
sta VDELP0
sta VDELP1
---
on kernel do with [BCDScore6,BGColor]
on kernel do
critical fit 72
with [BCDScore6,BGColor]
---
; Display the resulting 48x8 bitmap
; using the Digit0-5 pointers.
@ -102,7 +105,7 @@ Digit5 = {{$10}}
lda #7
sta @LoopCount
SLEEPR 20 ; TODO?
@BigLoop:
:
ldy @LoopCount ; counts backwards
lda (Digit0),y ; load B0 (1st sprite byte)
sta GRP0 ; B0 -> [GRP0]
@ -122,7 +125,7 @@ Digit5 = {{$10}}
sty GRP1 ; B5 -> [GRP1]; B4 -> GRP0
sta GRP0 ; ?? -> [GRP0]; B5 -> GRP1
dec @LoopCount ; go to next line
bpl @BigLoop ; repeat until < 0
bpl :- ; repeat until < 0
lda #0 ; clear the sprite registers
sta WSYNC
@ -147,18 +150,26 @@ resource FontTable ---
system Kernel2Digit
locals 3
on kernel do select [BCDScore2,PFColor]
on preframe do once
---
lda #0
sta {{$1}}
sta {{$2}}
---
on kernel do select [BCDScore2]
---
lda #$02
sta CTRLPF
; TODO: should be constants
; and it's wrong, too!
lda {{<PFColor:pfcolor}}+0
lda {{<BCDScore2:scorecolor}}+0
sta COLUP0
lda {{<PFColor:pfcolor}}+1
lda {{<BCDScore2:scorecolor}}+1
sta COLUP1
---
on kernel do select [BCDScore2]
on kernel do
critical fit 98
select [BCDScore2]
---
lda #7
sta {{$0}}
@ -166,11 +177,15 @@ system Kernel2Digit
ldx #0
sta WSYNC
{{!compute2digit 0}}
.if {{%ecount}}>1
inx
{{!compute2digit 1}}
.else
{{!compute2digit 0}}
.endif
; playfield
dec {{$0}}
bpl @Loop
jpl @Loop
; dex
; stx PF1
---
@ -242,12 +257,15 @@ resource FontTablePFFancy ---
system BCDMath
locals 1
on AddBCD4 do with [BCDScore6]
on AddBCD4 do once
---
.ifnblank {{arg 0}}
lda #<{{arg 0}}
ldy #>{{arg 0}}
.endif
---
on AddBCD4 do with [BCDScore6]
---
; Adds value to 6-BCD-digit score.
; A = 1st BCD digit
; Y = 2nd BCD digit
@ -262,14 +280,54 @@ system BCDMath
adc #0
sta {{set digits 16}}
cld ; exit BCD mode
---
on AddBCD2 do once
---
.ifnblank {{arg 0}}
lda #<{{arg 0}}
.endif
---
on SubBCD2 do once
---
.ifnblank {{arg 0}}
lda #<{{arg 0}}
.endif
---
on AddBCD2 do with [BCDScore2]
---
sed ; enter BCD mode
clc ; clear carry
adc {{get digits}}
sta {{set digits}}
cld ; exit BCD mode
bcc :+
lda #$99
sta {{set digits}}
:
---
on SubBCD2 do with [BCDScore2]
---
; TODO?
tay
lda {{get digits}}
sty {{set digits}}
sed ; enter BCD mode
sec ; set carry
sbc {{get digits}}
sta {{set digits}}
cld ; exit BCD mode
bcs :+
lda #0
sta {{set digits}}
:
---
end
demo Main
using FrameLoop
using Kernel6Digit, FontTable
using Kernel2Digit, FontTablePF
using Kernel6Digit
using Kernel2Digit
using JoyButton, BCDMath
entity [Player,BCDScore6,PFColor,BGColor]
@ -278,13 +336,13 @@ demo Main
init bgcolor = $02
end
entity [BCDScore2,PFColor]
entity [BCDScore2]
init digits = 0x24
init pfcolor = $ce
init scorecolor = $ce
end
entity [BCDScore2,PFColor]
entity [BCDScore2]
init digits = 0x56
init pfcolor = $3e
init scorecolor = $3e
end
system IncScore

View File

@ -1,12 +1,12 @@
EVENT__start = 1
EVENT__postframe = 1
EVENT__preframe = 1
EVENT__kernel = 1
EVENT__FontTable = 1
EVENT__compute2digit = 1
EVENT__fetchdigit = 1
EVENT__FontTablePF = 1
EVENT__postframe = 1
EVENT__AddBCD4 = 1
EVENT__AddBCD2 = 1
EVENT__SubBCD2 = 1
EVENT__joybutton = 1
.scope Main
.zeropage
@ -18,13 +18,14 @@ BCDScore6_digits_b16:
.res 1
PFColor_pfcolor_b0:
.res 1
.res 1
.res 1
BGColor_bgcolor_b0:
.res 1
BCDScore2_digits_b0:
.res 1
.res 1
BCDScore2_scorecolor_b0:
.res 1
.res 1
TEMP:
Kernel6Digit__2__tmp:
.res 1
@ -42,7 +43,7 @@ Kernel6Digit__2__tmp:
.res 1
.res 1
.res 1
Kernel2Digit__4__tmp:
Kernel2Digit__3__tmp:
.res 1
.res 1
.res 1
@ -52,11 +53,11 @@ Main__INITDATA:
.byte 52
.byte 18
.byte 60
.byte 206
.byte 62
.byte 2
.byte 36
.byte 86
.byte 206
.byte 62
__Start:
;;; start action Init__main_init__1
@ -77,7 +78,10 @@ __BRK:
;;; start action FrameLoop__start__3
FrameLoop__start__4__NextFrame:
FRAME_END
FRAME_START
;;; start action Kernel6Digit__preframe__5
@ -130,9 +134,18 @@ Kernel6Digit__preframe__7__Loop:
;;; end action Kernel6Digit__preframe__5
;;; start action Kernel2Digit__preframe__8
lda #0
sta Kernel2Digit__3__tmp+1
sta Kernel2Digit__3__tmp+2
;;; end action Kernel2Digit__preframe__8
KERNEL_START
;;; start action Kernel6Digit__kernel__8
;;; start action Kernel6Digit__kernel__10
lda PFColor_pfcolor_b0
sta COLUP0
@ -156,190 +169,56 @@ Kernel6Digit__preframe__7__Loop:
sta VDELP0
sta VDELP1
;;; end action Kernel6Digit__kernel__8
;;; end action Kernel6Digit__kernel__10
;;; start action Kernel6Digit__kernel__11
jsr Kernel6Digit__kernel__13
; Display the resulting 48x8 bitmap
; using the Digit0-5 pointers.
Kernel6Digit__kernel__13__LoopCount = Kernel6Digit__2__tmp+12
Kernel6Digit__kernel__13__Temp = Kernel6Digit__2__tmp+13
lda BGColor_bgcolor_b0
sta WSYNC
sta COLUBK
lda #7
sta Kernel6Digit__kernel__13__LoopCount
SLEEPR 20 ; TODO?
Kernel6Digit__kernel__13__BigLoop:
ldy Kernel6Digit__kernel__13__LoopCount ; counts backwards
lda (Digit0),y ; load B0 (1st sprite byte)
sta GRP0 ; B0 -> [GRP0]
lda (Digit1),y ; load B1 -> A
sta GRP1 ; B1 -> [GRP1], B0 -> GRP0
sta WSYNC ; sync to next scanline
lda (Digit2),y ; load B2 -> A
sta GRP0 ; B2 -> [GRP0], B1 -> GRP1
lda (Digit5),y ; load B5 -> A
sta Kernel6Digit__kernel__13__Temp ; B5 -> temp
lda (Digit4),y ; load B4
tax ; -> X
lda (Digit3),y ; load B3 -> A
ldy Kernel6Digit__kernel__13__Temp ; load B5 -> Y
sta GRP1 ; B3 -> [GRP1]; B2 -> GRP0
stx GRP0 ; B4 -> [GRP0]; B3 -> GRP1
sty GRP1 ; B5 -> [GRP1]; B4 -> GRP0
sta GRP0 ; ?? -> [GRP0]; B5 -> GRP1
dec Kernel6Digit__kernel__13__LoopCount ; go to next line
bpl Kernel6Digit__kernel__13__BigLoop ; repeat until < 0
lda #0 ; clear the sprite registers
sta WSYNC
sta GRP0
sta GRP1
sta GRP0
sta GRP1
sta COLUBK
;;; end action Kernel6Digit__kernel__11
;;; start action Kernel2Digit__kernel__14
;;; start action Kernel2Digit__kernel__16
lda #$02
sta CTRLPF
; TODO: should be constants
; and it's wrong, too!
lda PFColor_pfcolor_b0+0
lda BCDScore2_scorecolor_b0+0
sta COLUP0
lda PFColor_pfcolor_b0+1
lda BCDScore2_scorecolor_b0+1
sta COLUP1
;;; end action Kernel2Digit__kernel__14
;;; end action Kernel2Digit__kernel__16
;;; start action Kernel2Digit__kernel__17
lda #7
sta Kernel2Digit__4__tmp+0
Kernel2Digit__kernel__19__Loop:
ldx #0
sta WSYNC
;;; start action Kernel2Digit__compute2digit__20
lda Kernel2Digit__4__tmp+1 ; load 1st pf
sta PF1 ; store 1st pf
; first digit
lda BCDScore2_digits_b0 + 0
pha
and #$0f
asl
asl
asl
;;; start action Kernel2Digit__fetchdigit__22
adc Kernel2Digit__4__tmp+0
tay
; TODO: select your own?
lda FontTablePF,y
;;; end action Kernel2Digit__fetchdigit__22
and #$0f
ldy Kernel2Digit__4__tmp+2 ; load 2nd pf
sta Kernel2Digit__4__tmp+1 + 0
; second digit
pla
and #$f0
lsr
sty PF1 ; store 2nd pf
;;; start action Kernel2Digit__fetchdigit__24
adc Kernel2Digit__4__tmp+0
tay
; TODO: select your own?
lda FontTablePF,y
;;; end action Kernel2Digit__fetchdigit__24
and #$f0
ora Kernel2Digit__4__tmp+1 + 0
sta Kernel2Digit__4__tmp+1 + 0
;;; end action Kernel2Digit__compute2digit__20
inx
;;; start action Kernel2Digit__compute2digit__26
lda Kernel2Digit__4__tmp+1 ; load 1st pf
sta PF1 ; store 1st pf
; first digit
lda BCDScore2_digits_b0 + 1
pha
and #$0f
asl
asl
asl
;;; start action Kernel2Digit__fetchdigit__28
adc Kernel2Digit__4__tmp+0
tay
; TODO: select your own?
lda FontTablePF,y
;;; end action Kernel2Digit__fetchdigit__28
and #$0f
ldy Kernel2Digit__4__tmp+2 ; load 2nd pf
sta Kernel2Digit__4__tmp+1 + 1
; second digit
pla
and #$f0
lsr
sty PF1 ; store 2nd pf
;;; start action Kernel2Digit__fetchdigit__30
adc Kernel2Digit__4__tmp+0
tay
; TODO: select your own?
lda FontTablePF,y
;;; end action Kernel2Digit__fetchdigit__30
and #$f0
ora Kernel2Digit__4__tmp+1 + 1
sta Kernel2Digit__4__tmp+1 + 1
;;; end action Kernel2Digit__compute2digit__26
; playfield
dec Kernel2Digit__4__tmp+0
bpl Kernel2Digit__kernel__19__Loop
; dex
; stx PF1
;;; end action Kernel2Digit__kernel__17
jsr Kernel2Digit__kernel__19
KERNEL_END
;;; start action JoyButton__postframe__32
;;; start action FrameLoop__postframe__40
lsr SWCHB ; test Game Reset switch
bcs FrameLoop__postframe__41__NoStart
FrameLoop__postframe__41__NoStart:
;;; end action FrameLoop__postframe__40
;;; start action JoyButton__postframe__42
lda INPT4 ;read button input
bmi JoyButton__postframe__34__NotPressed
bmi JoyButton__postframe__44__NotPressed
;;; start action IncScore__joybutton__35
;;; start action IncScore__joybutton__45
;;; start action BCDMath__AddBCD4__38
;;; start action BCDMath__AddBCD4__48
.ifnblank $0210
lda #<$0210
ldy #>$0210
.endif
;;; end action BCDMath__AddBCD4__48
;;; start action BCDMath__AddBCD4__50
; Adds value to 6-BCD-digit score.
; A = 1st BCD digit
; Y = 2nd BCD digit
@ -355,32 +234,247 @@ Kernel2Digit__kernel__19__Loop:
sta BCDScore6_digits_b16
cld ; exit BCD mode
;;; end action BCDMath__AddBCD4__38
;;; end action BCDMath__AddBCD4__50
;;; end action IncScore__joybutton__35
;;; end action IncScore__joybutton__45
JoyButton__postframe__34__NotPressed:
JoyButton__postframe__44__NotPressed:
;;; end action JoyButton__postframe__32
;;; end action JoyButton__postframe__42
FRAME_END
jmp FrameLoop__start__4__NextFrame ; loop to next frame
;;; end action FrameLoop__start__3
; start main routine
.segment "VECTORS"
Return: .word $6060
ZeroByte: .byte $00
Return: .byte $60
VecNMI:
VecReset: .word Main::__Reset
VecBRK: .word Main::__BRK
VecReset: .word __Reset
VecBRK: .word __BRK
.code
;;; end action Init__main_init__1
.rodata
__ALIGNORIGIN:
.rodata
Kernel6Digit__kernel__13:
; Display the resulting 48x8 bitmap
; using the Digit0-5 pointers.
Kernel6Digit__kernel__15__LoopCount = Kernel6Digit__2__tmp+12
Kernel6Digit__kernel__15__Temp = Kernel6Digit__2__tmp+13
lda BGColor_bgcolor_b0
sta WSYNC
sta COLUBK
lda #7
sta Kernel6Digit__kernel__15__LoopCount
SLEEPR 20 ; TODO?
:
ldy Kernel6Digit__kernel__15__LoopCount ; counts backwards
lda (Digit0),y ; load B0 (1st sprite byte)
sta GRP0 ; B0 -> [GRP0]
lda (Digit1),y ; load B1 -> A
sta GRP1 ; B1 -> [GRP1], B0 -> GRP0
sta WSYNC ; sync to next scanline
lda (Digit2),y ; load B2 -> A
sta GRP0 ; B2 -> [GRP0], B1 -> GRP1
lda (Digit5),y ; load B5 -> A
sta Kernel6Digit__kernel__15__Temp ; B5 -> temp
lda (Digit4),y ; load B4
tax ; -> X
lda (Digit3),y ; load B3 -> A
ldy Kernel6Digit__kernel__15__Temp ; load B5 -> Y
sta GRP1 ; B3 -> [GRP1]; B2 -> GRP0
stx GRP0 ; B4 -> [GRP0]; B3 -> GRP1
sty GRP1 ; B5 -> [GRP1]; B4 -> GRP0
sta GRP0 ; ?? -> [GRP0]; B5 -> GRP1
dec Kernel6Digit__kernel__15__LoopCount ; go to next line
bpl :- ; repeat until < 0
lda #0 ; clear the sprite registers
sta WSYNC
sta GRP0
sta GRP1
sta GRP0
sta GRP1
sta COLUBK
rts
.assert >(Kernel6Digit__kernel__13) = >(*), error, "Kernel6Digit__kernel__13 crosses a page boundary!"
.assert (* - Kernel6Digit__kernel__13) <= 72, error, .sprintf("Kernel6Digit__kernel__13 does not fit in 72 bytes, it took %d!", (* - Kernel6Digit__kernel__13))
.if <(* - __ALIGNORIGIN) > 256-98
.align $100
.endif
.rodata
Kernel2Digit__kernel__19:
lda #7
sta Kernel2Digit__3__tmp+0
Kernel2Digit__kernel__21__Loop:
ldx #0
sta WSYNC
;;; start action Kernel2Digit__compute2digit__22
lda Kernel2Digit__3__tmp+1 ; load 1st pf
sta PF1 ; store 1st pf
; first digit
lda BCDScore2_digits_b0 + 0
pha
and #$0f
asl
asl
asl
;;; start action Kernel2Digit__fetchdigit__24
adc Kernel2Digit__3__tmp+0
tay
; TODO: select your own?
lda FontTablePF,y
;;; end action Kernel2Digit__fetchdigit__24
and #$0f
ldy Kernel2Digit__3__tmp+2 ; load 2nd pf
sta Kernel2Digit__3__tmp+1 + 0
; second digit
pla
and #$f0
lsr
sty PF1 ; store 2nd pf
;;; start action Kernel2Digit__fetchdigit__26
adc Kernel2Digit__3__tmp+0
tay
; TODO: select your own?
lda FontTablePF,y
;;; end action Kernel2Digit__fetchdigit__26
and #$f0
ora Kernel2Digit__3__tmp+1 + 0
sta Kernel2Digit__3__tmp+1 + 0
;;; end action Kernel2Digit__compute2digit__22
.if 2>1
inx
;;; start action Kernel2Digit__compute2digit__28
lda Kernel2Digit__3__tmp+1 ; load 1st pf
sta PF1 ; store 1st pf
; first digit
lda BCDScore2_digits_b0 + 1
pha
and #$0f
asl
asl
asl
;;; start action Kernel2Digit__fetchdigit__30
adc Kernel2Digit__3__tmp+0
tay
; TODO: select your own?
lda FontTablePF,y
;;; end action Kernel2Digit__fetchdigit__30
and #$0f
ldy Kernel2Digit__3__tmp+2 ; load 2nd pf
sta Kernel2Digit__3__tmp+1 + 1
; second digit
pla
and #$f0
lsr
sty PF1 ; store 2nd pf
;;; start action Kernel2Digit__fetchdigit__32
adc Kernel2Digit__3__tmp+0
tay
; TODO: select your own?
lda FontTablePF,y
;;; end action Kernel2Digit__fetchdigit__32
and #$f0
ora Kernel2Digit__3__tmp+1 + 1
sta Kernel2Digit__3__tmp+1 + 1
;;; end action Kernel2Digit__compute2digit__28
.else
;;; start action Kernel2Digit__compute2digit__34
lda Kernel2Digit__3__tmp+1 ; load 1st pf
sta PF1 ; store 1st pf
; first digit
lda BCDScore2_digits_b0 + 0
pha
and #$0f
asl
asl
asl
;;; start action Kernel2Digit__fetchdigit__36
adc Kernel2Digit__3__tmp+0
tay
; TODO: select your own?
lda FontTablePF,y
;;; end action Kernel2Digit__fetchdigit__36
and #$0f
ldy Kernel2Digit__3__tmp+2 ; load 2nd pf
sta Kernel2Digit__3__tmp+1 + 0
; second digit
pla
and #$f0
lsr
sty PF1 ; store 2nd pf
;;; start action Kernel2Digit__fetchdigit__38
adc Kernel2Digit__3__tmp+0
tay
; TODO: select your own?
lda FontTablePF,y
;;; end action Kernel2Digit__fetchdigit__38
and #$f0
ora Kernel2Digit__3__tmp+1 + 0
sta Kernel2Digit__3__tmp+1 + 0
;;; end action Kernel2Digit__compute2digit__34
.endif
; playfield
dec Kernel2Digit__3__tmp+0
jpl Kernel2Digit__kernel__21__Loop
; dex
; stx PF1
rts
.assert >(Kernel2Digit__kernel__19) = >(*), error, "Kernel2Digit__kernel__19 crosses a page boundary!"
.assert (* - Kernel2Digit__kernel__19) <= 98, error, .sprintf("Kernel2Digit__kernel__19 does not fit in 98 bytes, it took %d!", (* - Kernel2Digit__kernel__19))
FontTable:
;;; start action FontTable__FontTable__41
;;; start action FontTable__FontTable__53
; Font table for digits 0-9 (8x8 pixels)
;;{w:8,h:8,count:10,brev:1,flip:1};;
@ -390,11 +484,11 @@ FontTable:
.byte $00,$3c,$66,$66,$7c,$60,$66,$3c,$00,$18,$18,$18,$18,$0c,$66,$7e
.byte $00,$3c,$66,$66,$3c,$66,$66,$3c,$00,$3c,$66,$06,$3e,$66,$66,$3c
;;; end action FontTable__FontTable__41
;;; end action FontTable__FontTable__53
FontTablePF:
;;; start action FontTablePF__FontTablePF__43
;;; start action FontTablePF__FontTablePF__55
; Font table for digits 0-9 (4x8 pixels)
;;{w:8,h:8,count:10,brev:1,flip:1};;
@ -410,7 +504,7 @@ FontTablePF:
.byte $00,$00,$EE,$22,$EE,$AA,$EE,$00
;;
;;; end action FontTablePF__FontTablePF__43
;;; end action FontTablePF__FontTablePF__55
.endscope
Main__Start = Main::__Start

105
test/ecs/sound.ecs Normal file
View File

@ -0,0 +1,105 @@
//#resource "vcs-ca65.h"
import "vcslib.ecs"
component SoundEffect
duration: 0..255
sounddata: array of 0..255
end
component SoundChannel
sfx: [SoundEffect]
timer: 0..255
end
// TODO
component SoundPriority
priority: 0..15
end
system SoundEngine
locals 3
on preframe do
join [SoundChannel]
with [SoundEffect]
---
lda {{base timer}},y
jeq @nosound
sec
sbc #1
sta {{base timer}},y
pha
lda {{<sounddata}}
sta {{$0}}
lda {{>sounddata}}
sta {{$1}} ; save pointer to sound data
sty {{$2}} ; save Y (sound channel #)
pla
tay
lda ({{$0}}),y ; get sound data
bpl @setfreq ; hi bit clear = just freq
ldy {{$2}}
lsr ; right shift (/ 2)
bcs @setvol ; lo bit set = volume
sta AUDC0,y ; lo bit clear = control
lsr ; also set freq (/ 2)
@setfreq:
ldy {{$2}}
sta AUDF0,y ; set frequency
jmp @done
@nosound:
lda #0
@setvol:
sta AUDV0,y ; set volume
@done:
---
// TODO: need to pass sound entity as arg
on playsound do select [SoundChannel]
---
; arg 0 = sound channel
ldy #{{arg 0}}
; arg 1 = sound effect #
lda #{{arg 1}}
sta {{base sfx}},y
tax
---
// TODO: shouldn't need to split up like this...
on playsound do select [SoundEffect]
---
lda {{base duration}},x
---
on playsound do select [SoundChannel]
---
sta {{base timer}},y
; arg 2 = base volume
lda #{{arg 2}}
sta AUDV0,y
---
end
// TODO: default entities?
demo SoundDemo
using FrameLoop, SoundEngine
entity SFXScore [SoundEffect]
const duration = 11
const sounddata = [
$02,$03,$04,$08,$10,$20,$10,$20,$10,$08,
$a8]
end
// TODO: make sfx have priority?
entity SFX1 [SoundChannel] end
entity SFX2 [SoundChannel] end
system Test
on preframeloop do once
---
{{!playsound 0 0 15}}
---
end
end demo

174
test/ecs/sound.txt Normal file
View File

@ -0,0 +1,174 @@
EVENT__start = 1
EVENT__postframe = 1
EVENT__preframe = 1
EVENT__playsound = 1
EVENT__preframeloop = 1
.scope SoundDemo
.zeropage
SoundChannel_sfx_b0:
.res 1
.res 1
SoundChannel_timer_b0:
.res 1
.res 1
TEMP:
SoundEngine__2__tmp:
.res 1
.res 1
.res 1
.code
SoundEffect_duration_b0:
.byte 11
SoundEffect_sounddata_b0:
.byte <SoundEffect_sounddata_e0_b0
SoundEffect_sounddata_b8:
.byte >SoundEffect_sounddata_e0_b0
SoundEffect_sounddata_e0_b0:
.byte 2
.byte 3
.byte 4
.byte 8
.byte 16
.byte 32
.byte 16
.byte 32
.byte 16
.byte 8
.byte 168
SoundDemo__INITDATA:
.byte 0
.byte 0
.byte 0
.byte 0
__Start:
;;; start action Init__main_init__1
.include "vcs-ca65.h"
.macpack longbranch
.define PAL 0
__NMI:
__Reset:
__BRK:
CLEAN_START
ldy #4
: lda SoundDemo__INITDATA-1,y
sta SoundChannel_sfx_b0-1,y
dey
bne :-
;;; start action FrameLoop__start__3
;;; start action Test__preframeloop__5
;;; start action SoundEngine__playsound__7
; arg 0 = sound channel
ldy #0
; arg 1 = sound effect #
lda #0
sta SoundChannel_sfx_b0,y
tax
;;; end action SoundEngine__playsound__7
;;; start action SoundEngine__playsound__10
lda SoundEffect_duration_b0,x
;;; end action SoundEngine__playsound__10
;;; start action SoundEngine__playsound__13
sta SoundChannel_timer_b0,y
; arg 2 = base volume
lda #15
sta AUDV0,y
;;; end action SoundEngine__playsound__13
;;; end action Test__preframeloop__5
FrameLoop__start__4__NextFrame:
FRAME_END
FRAME_START
;;; start action SoundEngine__preframe__16
ldy #0
SoundEngine__preframe__17____each:
ldx SoundChannel_sfx_b0,y
lda SoundChannel_timer_b0,y
jeq SoundEngine__preframe__18__nosound
sec
sbc #1
sta SoundChannel_timer_b0,y
pha
lda SoundEffect_sounddata_b0,x
sta SoundEngine__2__tmp+0
lda SoundEffect_sounddata_b8,x
sta SoundEngine__2__tmp+1 ; save pointer to sound data
sty SoundEngine__2__tmp+2 ; save Y (sound channel #)
pla
tay
lda (SoundEngine__2__tmp+0),y ; get sound data
bpl SoundEngine__preframe__18__setfreq ; hi bit clear = just freq
ldy SoundEngine__2__tmp+2
lsr ; right shift (/ 2)
bcs SoundEngine__preframe__18__setvol ; lo bit set = volume
sta AUDC0,y ; lo bit clear = control
lsr ; also set freq (/ 2)
SoundEngine__preframe__18__setfreq:
ldy SoundEngine__2__tmp+2
sta AUDF0,y ; set frequency
jmp SoundEngine__preframe__18__done
SoundEngine__preframe__18__nosound:
lda #0
SoundEngine__preframe__18__setvol:
sta AUDV0,y ; set volume
SoundEngine__preframe__18__done:
iny
cpy #2
jne SoundEngine__preframe__17____each
SoundEngine__preframe__17____exit:
;;; end action SoundEngine__preframe__16
KERNEL_START
KERNEL_END
;;; start action FrameLoop__postframe__19
lsr SWCHB ; test Game Reset switch
bcs FrameLoop__postframe__20__NoStart
FrameLoop__postframe__20__NoStart:
;;; end action FrameLoop__postframe__19
jmp FrameLoop__start__4__NextFrame ; loop to next frame
;;; end action FrameLoop__start__3
; start main routine
.segment "VECTORS"
ZeroByte: .byte $00
Return: .byte $60
VecNMI:
VecReset: .word __Reset
VecBRK: .word __BRK
.code
;;; end action Init__main_init__1
.endscope
SoundDemo__Start = SoundDemo::__Start

View File

@ -8,8 +8,8 @@ component Bitmap
height: 0..255
end
// TODO: remove?
component HasBitmap
bitmap: [Bitmap]
end
component Colormap
@ -21,6 +21,7 @@ component HasColormap
end
component Sprite
bitmap: [Bitmap]
plyrflags: 0..63
end
@ -32,218 +33,12 @@ component HasYpos
ypos: 0..255
end
component SpriteSlot
sprite: [Sprite,HasBitmap,HasColormap,HasYpos]
end
component Missile
index: 2..3
end
system Kernel2Sprite
locals 13
on preframe do with [KernelSection]
---
.define KLINES {{<lines}}
.define KPAD 32
; set height to zero in case no sprites
lda #0
sta {{$8}}
sta {{$9}}
; set temp value so we don't read bitmap from h/w registers
lda #$F0
sta {{$2}}
sta {{$3}}
sta {{$6}}
sta {{$7}}
---
on preframe do join
[SpriteSlot] with
[Sprite,HasBitmap,HasColormap,HasYpos] limit 2
---
; flags set according to sprite slot value
; skip sprite if negative
jmi @nosprite
; set player object flags
lda {{<plyrflags}}
sta NUSIZ0,y
sta REFP0,y
; calculate screen height - ypos
lda KLINES+KPAD
sec
sbc {{<ypos}}
sta {{$11}}
; calculate bitmap pointer
stx {{$12}} ; save X (Sprite index)
lda {{<bitmap}} ; deref bitmap
tax
lda {{<Bitmap:bitmapdata}},x
sec
sbc {{$11}}
sta {{$0}},y ; Y = sprite slot index
lda {{>Bitmap:bitmapdata}},x
sbc #0
sta {{$2}},y
; get bitmap height
lda {{<Bitmap:height}},x
sta {{$8}},y
; calculate colormap pointer
ldx {{$12}} ; restore X
lda {{<colormap}} ; deref colormap
tax
lda {{<Colormap:colormapdata}},x
sec
sbc {{$11}}
sta {{$4}},y
lda {{>Colormap:colormapdata}},x
sbc #0
sta {{$6}},y
; save ypos
ldx {{$12}} ; restore X
lda {{<ypos}}
sta {{$10}},y
@nosprite:
---
on preframe do once
---
; shuffle pointers into (MSB, LSB) byte order
; L0 L1 H0 H1 -> L0 H0 L1 H1
lda {{$1}}
ldy {{$2}}
sty {{$1}}
sta {{$2}}
lda {{$5}}
ldy {{$6}}
sty {{$5}}
sta {{$6}}
---
on preframe do if [BGColor]
---
lda {{<bgcolor}}
sta COLUBK
---
on preframe do if [Missile,HasYpos]
---
lda KLINES
sec
sbc {{<ypos}}
sta {{$12}}
---
on kernel do with [KernelSection]
---
ldy #0
sty VDELP0
iny
sta VDELP1
---
on kernel do with [KernelSection]
---
ldy {{<lines}}
@LVScan:
{{!scanline 0}}
dey ; next scanline
{{!scanline 1}}
dey ; next scanline
bne @LVScan ; repeat until out of lines
---
on scanline do once
---
; draw player 0
lda {{$8}} ; height
dcp {{$10}} ; ypos
bcs @DoDraw1
lda #0
.byte $2C
@DoDraw1:
lda ({{$0}}),y
.if {{#0}} = 0
sta WSYNC
.endif
sta GRP0
lda ({{$4}}),y
sta COLUP0
; draw player 1
lda {{$9}} ; height
dcp {{$11}} ; ypos
bcs @DoDraw2
lda #0
.byte $2C
@DoDraw2:
lda ({{$2}}),y
sta GRP1
lda ({{$6}}),y
sta COLUP1
---
on kernel do once
---
lda #0
sta GRP0
sta GRP1
sta GRP0
sta GRP1
---
on scanline do if [Missile,HasYpos]
---
cpy {{$12}}
php
pla
sta ENAM0
---
end
system VersatilePlayfield
locals 2
on preframe do with [VersatilePlayfield]
---
lda {{<data}}
sta {{$0}}
lda {{>data}}
sta {{$1}}
---
on scanline do once
---
.if {{arg 0}} = 0
lda ({{local 0}}),y
tax
.endif
---
on scanline do once
---
.if {{arg 0}} = 1
lda ({{local 0}}),y
sta $00,x
.endif
---
on postframe do once
---
lda #0
sta PF0
sta PF1
sta PF2
---
end
system SetXPos
on preframe do once
---
sta HMCLR
---
on preframe do join [SpriteSlot] with [HasXpos]
limit 2
---
lda {{<xpos}}
{{!SetHorizPos}}
---
on preframe do if [Missile,HasXpos]
---
lda {{<xpos}}
ldx #2
{{!SetHorizPos}}
---
on preframe do once
---
sta WSYNC
sta HMOVE
---
component SpriteSlot
sprite: [Sprite] // TODO: HasBitmap?
end
system JoyFaceDirection
@ -266,7 +61,7 @@ system MoveJoyX
---
lda {{<xpos}}
sec
sbc #1
sbc #1
bcc @nomove
sta {{<xpos}}
@nomove:
@ -276,7 +71,7 @@ system MoveJoyX
lda {{<xpos}}
clc
adc #1
cmp #152
cmp #150
bcs @nomove
sta {{<xpos}}
@nomove:
@ -305,6 +100,28 @@ system MoveJoyY
---
end
system SetXPos
on preframe do join [SpriteSlot] with [Sprite]
limit 2
---
lda {{<xpos}}
{{!SetHorizPos}}
---
on preframe do foreach [Missile,HasXpos]
---
lda {{<xpos}}
ldy {{<index}}
{{!SetHorizPos}}
---
on prekernel do once
---
sta WSYNC
sta HMOVE
SLEEPR 24
sta HMCLR
---
end
system SpriteShuffler
locals 2
on postframe do select [SpriteSlot]
@ -358,84 +175,3 @@ system SpriteHider
---
end
///
demo Main
using FrameLoop, Kernel2Sprite
using Joystick, MoveJoyX, MoveJoyY
using SetXPos, SetHorizPos
using SpriteShuffler, SpriteHider
entity Kernel [KernelSection, BGColor]
const lines = 192
const bgcolor = 0xa2
end
entity Bitmap1 [Bitmap]
const bitmapdata = [1, 1, 3, 7, 15, 31, 63, 127]
const height = 8
end
entity Bitmap2 [Bitmap]
const bitmapdata = [$18,$3e,$ff,$ff,$ff,$ff,$3e,$18]
const height = 8
end
entity Colormap1 [Colormap]
const colormapdata = [6, 3, 6, 9, 12, 14, 31, 63]
end
entity Sprite0 [Sprite,HasBitmap,HasColormap,HasXpos,HasYpos,Player]
init xpos = 50
init ypos = 150
init bitmap = #Bitmap2
init colormap = #Colormap1
const plyrflags = 0
end
entity Sprite1 [Sprite,HasBitmap,HasColormap,HasXpos,HasYpos,Player]
init xpos = 100
init ypos = 60
init bitmap = #Bitmap1
init colormap = #Colormap1
const plyrflags = 3
end
entity Sprite2 [Sprite,HasBitmap,HasColormap,HasXpos,HasYpos,Player]
init xpos = 80
init ypos = 90
init bitmap = #Bitmap2
init colormap = #Colormap1
const plyrflags = 2
end
entity Sprite3 [Sprite,HasBitmap,HasColormap,HasXpos,HasYpos,Player]
init xpos = 40
init ypos = 150
init bitmap = #Bitmap1
init colormap = #Colormap1
const plyrflags = 0
end
/*
entity [Missile,HasXpos,HasYpos]
init xpos = 70
init ypos = 70
end
*/
entity Slot0 [SpriteSlot]
init sprite = #Sprite0
end
entity Slot1 [SpriteSlot]
init sprite = #Sprite1
end
entity Slot2 [SpriteSlot]
init sprite = #Sprite2
end
entity Slot3 [SpriteSlot]
init sprite = #Sprite3
end
end demo

View File

@ -1,561 +0,0 @@
EVENT__start = 1
EVENT__preframe = 1
EVENT__kernel = 1
EVENT__scanline = 1
EVENT__postframe = 1
EVENT__joyleft = 1
EVENT__joyright = 1
EVENT__joyup = 1
EVENT__joydown = 1
EVENT__SetHorizPos = 1
.scope Main
.zeropage
HasBitmap_bitmap_b0:
.res 1
.res 1
.res 1
.res 1
HasColormap_colormap_b0:
.res 1
.res 1
.res 1
.res 1
HasXpos_xpos_b0:
.res 1
.res 1
.res 1
.res 1
HasYpos_ypos_b0:
.res 1
.res 1
.res 1
.res 1
SpriteSlot_sprite_b0:
.res 1
.res 1
.res 1
.res 1
TEMP:
Kernel2Sprite__2__tmp:
Joystick__3__tmp:
SpriteHider__9__tmp:
.res 1
SpriteShuffler__8__tmp:
.res 1
.res 1
.res 1
.res 1
.res 1
.res 1
.res 1
.res 1
.res 1
.res 1
.res 1
.res 1
.code
KernelSection_lines_b0:
.byte 192
BGColor_bgcolor_b0:
.byte 162
Bitmap_bitmapdata_b0:
.byte <(Bitmap_bitmapdata_e1_b0+31)
.byte <(Bitmap_bitmapdata_e2_b0+31)
Bitmap_bitmapdata_b8:
.byte >(Bitmap_bitmapdata_e1_b0+31)
.byte >(Bitmap_bitmapdata_e2_b0+31)
Bitmap_bitmapdata_e1_b0:
.byte 1
.byte 1
.byte 3
.byte 7
.byte 15
.byte 31
.byte 63
.byte 127
Bitmap_height_b0:
.byte 8
.byte 8
Bitmap_bitmapdata_e2_b0:
.byte 24
.byte 62
.byte 255
.byte 255
.byte 255
.byte 255
.byte 62
.byte 24
Colormap_colormapdata_b0:
.byte <(Colormap_colormapdata_e3_b0+31)
Colormap_colormapdata_b8:
.byte >(Colormap_colormapdata_e3_b0+31)
Colormap_colormapdata_e3_b0:
.byte 6
.byte 3
.byte 6
.byte 9
.byte 12
.byte 14
.byte 31
.byte 63
Sprite_plyrflags_b0:
.byte 0
.byte 3
.byte 2
.byte 0
Main__INITDATA:
.byte 1
.byte 0
.byte 1
.byte 0
.byte 0
.byte 0
.byte 0
.byte 0
.byte 50
.byte 100
.byte 80
.byte 40
.byte 150
.byte 60
.byte 90
.byte 150
.byte 0
.byte 1
.byte 2
.byte 3
__Start:
;;; start action Init__main_init__1
.include "vcs-ca65.h"
.macpack longbranch
.define PAL 0
__NMI:
__Reset:
__BRK:
CLEAN_START
ldy #20
: lda Main__INITDATA-1,y
sta HasBitmap_bitmap_b0-1,y
dey
bne :-
;;; start action FrameLoop__start__3
FrameLoop__start__4__NextFrame:
FRAME_START
;;; start action Kernel2Sprite__preframe__5
.define KLINES #192
.define KPAD 32
; set height to zero in case no sprites
lda #0
sta Kernel2Sprite__2__tmp+8
sta Kernel2Sprite__2__tmp+9
; set temp value so we don't read bitmap from h/w registers
lda #$F0
sta Kernel2Sprite__2__tmp+2
sta Kernel2Sprite__2__tmp+3
sta Kernel2Sprite__2__tmp+6
sta Kernel2Sprite__2__tmp+7
;;; end action Kernel2Sprite__preframe__5
;;; start action Kernel2Sprite__preframe__8
ldy #0
Kernel2Sprite__preframe__9____each:
ldx SpriteSlot_sprite_b0,y
; flags set according to sprite slot value
; skip sprite if negative
jmi Kernel2Sprite__preframe__10__nosprite
; set player object flags
lda Sprite_plyrflags_b0,x
sta NUSIZ0,y
sta REFP0,y
; calculate screen height - ypos
lda KLINES+KPAD
sec
sbc HasYpos_ypos_b0,x
sta Kernel2Sprite__2__tmp+11
; calculate bitmap pointer
stx Kernel2Sprite__2__tmp+12 ; save X (Sprite index)
lda HasBitmap_bitmap_b0,x ; deref bitmap
tax
lda Bitmap_bitmapdata_b0,x
sec
sbc Kernel2Sprite__2__tmp+11
sta Kernel2Sprite__2__tmp+0,y ; Y = sprite slot index
lda Bitmap_bitmapdata_b8,x
sbc #0
sta Kernel2Sprite__2__tmp+2,y
; get bitmap height
lda Bitmap_height_b0,x
sta Kernel2Sprite__2__tmp+8,y
; calculate colormap pointer
ldx Kernel2Sprite__2__tmp+12 ; restore X
lda HasColormap_colormap_b0,x ; deref colormap
tax
lda Colormap_colormapdata_b0,x
sec
sbc Kernel2Sprite__2__tmp+11
sta Kernel2Sprite__2__tmp+4,y
lda Colormap_colormapdata_b8,x
sbc #0
sta Kernel2Sprite__2__tmp+6,y
; save ypos
ldx Kernel2Sprite__2__tmp+12 ; restore X
lda HasYpos_ypos_b0,x
sta Kernel2Sprite__2__tmp+10,y
Kernel2Sprite__preframe__10__nosprite:
iny
cpy #2
jne Kernel2Sprite__preframe__9____each
Kernel2Sprite__preframe__9____exit:
;;; end action Kernel2Sprite__preframe__8
;;; start action Kernel2Sprite__preframe__11
; shuffle pointers into (MSB, LSB) byte order
; L0 L1 H0 H1 -> L0 H0 L1 H1
lda Kernel2Sprite__2__tmp+1
ldy Kernel2Sprite__2__tmp+2
sty Kernel2Sprite__2__tmp+1
sta Kernel2Sprite__2__tmp+2
lda Kernel2Sprite__2__tmp+5
ldy Kernel2Sprite__2__tmp+6
sty Kernel2Sprite__2__tmp+5
sta Kernel2Sprite__2__tmp+6
;;; end action Kernel2Sprite__preframe__11
;;; start action Kernel2Sprite__preframe__13
lda #162
sta COLUBK
;;; end action Kernel2Sprite__preframe__13
;;; start action Kernel2Sprite__preframe__16
;;; end action Kernel2Sprite__preframe__16
;;; start action SetXPos__preframe__17
sta HMCLR
;;; end action SetXPos__preframe__17
;;; start action SetXPos__preframe__19
ldy #0
SetXPos__preframe__20____each:
ldx SpriteSlot_sprite_b0,y
lda HasXpos_xpos_b0,x
;;; start action SetHorizPos__SetHorizPos__22
; SetHorizPos routine
; A = X coordinate
; Y = player number (0 or 1)
sta WSYNC ; start a new line
sec ; set carry flag
nop
SetHorizPos__SetHorizPos__23__DivideLoop:
sbc #15 ; subtract 15
bcs SetHorizPos__SetHorizPos__23__DivideLoop ; branch until negative
eor #7 ; calculate fine offset
asl
asl
asl
asl
sta RESP0,y ; fix coarse position
sta HMP0,y ; set fine offset
;;; end action SetHorizPos__SetHorizPos__22
iny
cpy #2
jne SetXPos__preframe__20____each
SetXPos__preframe__20____exit:
;;; end action SetXPos__preframe__19
;;; start action SetXPos__preframe__24
;;; end action SetXPos__preframe__24
;;; start action SetXPos__preframe__25
sta WSYNC
sta HMOVE
;;; end action SetXPos__preframe__25
KERNEL_START
;;; start action Kernel2Sprite__kernel__27
ldy #0
sty VDELP0
iny
sta VDELP1
;;; end action Kernel2Sprite__kernel__27
;;; start action Kernel2Sprite__kernel__30
ldy #192
Kernel2Sprite__kernel__32__LVScan:
;;; start action Kernel2Sprite__scanline__33
; draw player 0
lda Kernel2Sprite__2__tmp+8 ; height
dcp Kernel2Sprite__2__tmp+10 ; ypos
bcs Kernel2Sprite__scanline__34__DoDraw1
lda #0
.byte $2C
Kernel2Sprite__scanline__34__DoDraw1:
lda (Kernel2Sprite__2__tmp+0),y
.if 0 = 0
sta WSYNC
.endif
sta GRP0
lda (Kernel2Sprite__2__tmp+4),y
sta COLUP0
; draw player 1
lda Kernel2Sprite__2__tmp+9 ; height
dcp Kernel2Sprite__2__tmp+11 ; ypos
bcs Kernel2Sprite__scanline__34__DoDraw2
lda #0
.byte $2C
Kernel2Sprite__scanline__34__DoDraw2:
lda (Kernel2Sprite__2__tmp+2),y
sta GRP1
lda (Kernel2Sprite__2__tmp+6),y
sta COLUP1
;;; end action Kernel2Sprite__scanline__33
;;; start action Kernel2Sprite__scanline__35
;;; end action Kernel2Sprite__scanline__35
dey ; next scanline
;;; start action Kernel2Sprite__scanline__36
; draw player 0
lda Kernel2Sprite__2__tmp+8 ; height
dcp Kernel2Sprite__2__tmp+10 ; ypos
bcs Kernel2Sprite__scanline__37__DoDraw1
lda #0
.byte $2C
Kernel2Sprite__scanline__37__DoDraw1:
lda (Kernel2Sprite__2__tmp+0),y
.if 1 = 0
sta WSYNC
.endif
sta GRP0
lda (Kernel2Sprite__2__tmp+4),y
sta COLUP0
; draw player 1
lda Kernel2Sprite__2__tmp+9 ; height
dcp Kernel2Sprite__2__tmp+11 ; ypos
bcs Kernel2Sprite__scanline__37__DoDraw2
lda #0
.byte $2C
Kernel2Sprite__scanline__37__DoDraw2:
lda (Kernel2Sprite__2__tmp+2),y
sta GRP1
lda (Kernel2Sprite__2__tmp+6),y
sta COLUP1
;;; end action Kernel2Sprite__scanline__36
;;; start action Kernel2Sprite__scanline__38
;;; end action Kernel2Sprite__scanline__38
dey ; next scanline
bne Kernel2Sprite__kernel__32__LVScan ; repeat until out of lines
;;; end action Kernel2Sprite__kernel__30
;;; start action Kernel2Sprite__kernel__39
lda #0
sta GRP0
sta GRP1
sta GRP0
sta GRP1
;;; end action Kernel2Sprite__kernel__39
KERNEL_END
;;; start action Joystick__postframe__41
; 2 control inputs share a single byte, 4 bits each
lda SWCHA
sta Joystick__3__tmp+0
;;; end action Joystick__postframe__41
;;; start action Joystick__postframe__43
ldx #0
Joystick__postframe__44____each:
asl Joystick__3__tmp+0
bcs Joystick__postframe__45__SkipMoveRight
;;; start action MoveJoyX__joyright__46
lda HasXpos_xpos_b0,x
clc
adc #1
cmp #152
bcs MoveJoyX__joyright__48__nomove
sta HasXpos_xpos_b0,x
MoveJoyX__joyright__48__nomove:
;;; end action MoveJoyX__joyright__46
Joystick__postframe__45__SkipMoveRight:
asl Joystick__3__tmp+0
bcs Joystick__postframe__45__SkipMoveLeft
;;; start action MoveJoyX__joyleft__49
lda HasXpos_xpos_b0,x
sec
sbc #1
bcc MoveJoyX__joyleft__51__nomove
sta HasXpos_xpos_b0,x
MoveJoyX__joyleft__51__nomove:
;;; end action MoveJoyX__joyleft__49
Joystick__postframe__45__SkipMoveLeft:
asl Joystick__3__tmp+0
bcs Joystick__postframe__45__SkipMoveDown
;;; start action MoveJoyY__joydown__52
lda HasYpos_ypos_b0,x
clc
adc #1
cmp #220
bcs MoveJoyY__joydown__54__nomove
sta HasYpos_ypos_b0,x
MoveJoyY__joydown__54__nomove:
;;; end action MoveJoyY__joydown__52
Joystick__postframe__45__SkipMoveDown:
asl Joystick__3__tmp+0
bcs Joystick__postframe__45__SkipMoveUp
;;; start action MoveJoyY__joyup__55
lda HasYpos_ypos_b0,x
sec
sbc #1
bcc MoveJoyY__joyup__57__nomove
sta HasYpos_ypos_b0,x
MoveJoyY__joyup__57__nomove:
;;; end action MoveJoyY__joyup__55
Joystick__postframe__45__SkipMoveUp:
inx
cpx #4
jne Joystick__postframe__44____each
Joystick__postframe__44____exit:
;;; end action Joystick__postframe__43
;;; start action SpriteShuffler__postframe__58
; load two sprite slots at left side of array
lda SpriteSlot_sprite_b0
sta SpriteShuffler__8__tmp+0
lda SpriteSlot_sprite_b0+1
sta SpriteShuffler__8__tmp+1
; move two slots to the left
ldx #0
SpriteShuffler__postframe__60__loop:
lda SpriteSlot_sprite_b0+2,x
sta SpriteSlot_sprite_b0,x
inx
cpx #4-2
bne SpriteShuffler__postframe__60__loop
; store two sprite slots at right side of array
lda SpriteShuffler__8__tmp+0
sta SpriteSlot_sprite_b0+4-2
lda SpriteShuffler__8__tmp+1
sta SpriteSlot_sprite_b0+4-1
;;; end action SpriteShuffler__postframe__58
;;; start action SpriteHider__postframe__61
lda #4-1
sta SpriteHider__9__tmp+0
;;; end action SpriteHider__postframe__61
;;; start action SpriteHider__postframe__64
ldy #0
SpriteHider__postframe__65____each:
ldx SpriteSlot_sprite_b0,y
lda HasYpos_ypos_b0,x
cmp #192
bcc SpriteHider__postframe__66__skip
; swap this sprite slot with slot at end of array
lda SpriteSlot_sprite_b0,y
pha
ldx SpriteHider__9__tmp+0 ; clobbers X, but no longer used
lda SpriteSlot_sprite_b0,x
sta SpriteSlot_sprite_b0,y
pla
sta SpriteSlot_sprite_b0,x
dec SpriteHider__9__tmp+0
SpriteHider__postframe__66__skip:
iny
cpy #2
jne SpriteHider__postframe__65____each
SpriteHider__postframe__65____exit:
;;; end action SpriteHider__postframe__64
FRAME_END
jmp FrameLoop__start__4__NextFrame ; loop to next frame
;;; end action FrameLoop__start__3
; start main routine
.segment "VECTORS"
Return: .word $6060
VecNMI:
VecReset: .word Main::__Reset
VecBRK: .word Main::__BRK
;;; end action Init__main_init__1
.endscope
Main__Start = Main::__Start

View File

@ -1,515 +1 @@
EVENT__start = 1
EVENT__preframe = 1
EVENT__kernel = 1
EVENT__scanline1 = 1
EVENT__postframe = 1
EVENT__joyleft = 1
EVENT__joyright = 1
EVENT__joyup = 1
EVENT__joydown = 1
EVENT__SetHorizPos = 1
.scope Main
.zeropage
HasBitmap_bitmap_b0:
.res 1
.res 1
.res 1
.res 1
HasXpos_xpos_b0:
.res 1
.res 1
.res 1
.res 1
HasYpos_ypos_b0:
.res 1
.res 1
.res 1
.res 1
SpriteSlot_sprite_b0:
.res 1
.res 1
.res 1
.res 1
HasColormap_colormap_b0:
.res 1
.res 1
.res 1
.res 1
TEMP:
Kernel2Sprite__2__tmp:
Joystick__3__tmp:
SpriteHider__9__tmp:
.res 1
SpriteShuffler__8__tmp:
.res 1
.res 1
.res 1
.res 1
.res 1
.res 1
.res 1
.res 1
.res 1
.res 1
.res 1
.res 1
.code
KernelSection_lines_b0:
.byte 192
BGColor_bgcolor_b0:
.byte 162
Bitmap_bitmapdata_b0:
.byte <(Bitmap_bitmapdata_e1_b0+31)
.byte <(Bitmap_bitmapdata_e2_b0+31)
Bitmap_bitmapdata_b8:
.byte >(Bitmap_bitmapdata_e1_b0+31)
.byte >(Bitmap_bitmapdata_e2_b0+31)
Bitmap_bitmapdata_e1_b0:
.byte 1
.byte 1
.byte 3
.byte 7
.byte 15
.byte 31
.byte 63
.byte 127
Bitmap_height_b0:
.byte 8
.byte 8
Bitmap_bitmapdata_e2_b0:
.byte 24
.byte 62
.byte 255
.byte 255
.byte 255
.byte 255
.byte 62
.byte 24
Colormap_colormapdata_b0:
.byte <(Colormap_colormapdata_e3_b0+31)
Colormap_colormapdata_b8:
.byte >(Colormap_colormapdata_e3_b0+31)
Colormap_colormapdata_e3_b0:
.byte 6
.byte 3
.byte 6
.byte 9
.byte 12
.byte 14
.byte 31
.byte 63
Sprite_plyrflags_b0:
.byte 0
.byte 3
.byte 0
.byte 0
Main__INITDATA:
.byte 1
.byte 0
.byte 1
.byte 0
.byte 50
.byte 100
.byte 80
.byte 40
.byte 150
.byte 60
.byte 90
.byte 150
.byte 0
.byte 1
.byte 2
.byte 3
.byte 0
.byte 0
.byte 0
.byte 0
__Start:
;;; start action Init__main_init__1
.include "vcs-ca65.h"
.macpack longbranch
.define PAL 0
__NMI:
__Reset:
__BRK:
CLEAN_START
ldy #20
: lda Main__INITDATA-1,y
sta HasBitmap_bitmap_b0-1,y
dey
bne :-
;;; start action FrameLoop__start__3
FrameLoop__start__4__NextFrame:
FRAME_START
;;; start action Kernel2Sprite__preframe__5
.define KLINES #192
.define KPAD 32
;;; end action Kernel2Sprite__preframe__5
;;; start action Kernel2Sprite__preframe__8
ldy #0
Kernel2Sprite__preframe__9____each:
ldx SpriteSlot_sprite_b0,y
; set player object flags
lda Sprite_plyrflags_b0,x
sta NUSIZ0,y
sta REFP0,y
; calculate screen height - ypos
lda KLINES+KPAD
sec
sbc HasYpos_ypos_b0,x
sta Kernel2Sprite__2__tmp+11
; calculate bitmap pointer
stx Kernel2Sprite__2__tmp+12 ; save X (Sprite index)
lda HasBitmap_bitmap_b0,x ; deref bitmap
tax
lda Bitmap_bitmapdata_b0,x
sec
sbc Kernel2Sprite__2__tmp+11
sta Kernel2Sprite__2__tmp+0,y ; Y = sprite slot index
lda Bitmap_bitmapdata_b8,x
sbc #0
sta Kernel2Sprite__2__tmp+2,y
; get bitmap height
lda Bitmap_height_b0,x
sta Kernel2Sprite__2__tmp+8,y
; calculate colormap pointer
ldx Kernel2Sprite__2__tmp+12 ; restore X
lda HasColormap_colormap_b0,x ; deref colormap
tax
lda Colormap_colormapdata_b0,x
sec
sbc Kernel2Sprite__2__tmp+11
sta Kernel2Sprite__2__tmp+4,y
lda Colormap_colormapdata_b8,x
sbc #0
sta Kernel2Sprite__2__tmp+6,y
; save ypos
ldx Kernel2Sprite__2__tmp+12 ; restore X
lda HasYpos_ypos_b0,x
sta Kernel2Sprite__2__tmp+10,y
iny
cpy #2
jne Kernel2Sprite__preframe__9____each
Kernel2Sprite__preframe__9____exit:
;;; end action Kernel2Sprite__preframe__8
;;; start action Kernel2Sprite__preframe__11
; L0 L1 H0 H1 -> L0 H0 L1 H1
lda Kernel2Sprite__2__tmp+1
ldy Kernel2Sprite__2__tmp+2
sty Kernel2Sprite__2__tmp+1
sta Kernel2Sprite__2__tmp+2
lda Kernel2Sprite__2__tmp+5
ldy Kernel2Sprite__2__tmp+6
sty Kernel2Sprite__2__tmp+5
sta Kernel2Sprite__2__tmp+6
;;; end action Kernel2Sprite__preframe__11
;;; start action Kernel2Sprite__preframe__13
lda #162
sta COLUBK
;;; end action Kernel2Sprite__preframe__13
;;; start action Kernel2Sprite__preframe__16
;;; end action Kernel2Sprite__preframe__16
;;; start action SetXPos__preframe__17
sta HMCLR
;;; end action SetXPos__preframe__17
;;; start action SetXPos__preframe__19
ldy #0
SetXPos__preframe__20____each:
ldx SpriteSlot_sprite_b0,y
lda HasXpos_xpos_b0,x
;;; start action SetHorizPos__SetHorizPos__22
; SetHorizPos routine
; A = X coordinate
; Y = player number (0 or 1)
sta WSYNC ; start a new line
sec ; set carry flag
nop
SetHorizPos__SetHorizPos__23__DivideLoop:
sbc #15 ; subtract 15
bcs SetHorizPos__SetHorizPos__23__DivideLoop ; branch until negative
eor #7 ; calculate fine offset
asl
asl
asl
asl
sta RESP0,y ; fix coarse position
sta HMP0,y ; set fine offset
;;; end action SetHorizPos__SetHorizPos__22
iny
cpy #2
jne SetXPos__preframe__20____each
SetXPos__preframe__20____exit:
;;; end action SetXPos__preframe__19
;;; start action SetXPos__preframe__24
;;; end action SetXPos__preframe__24
;;; start action SetXPos__preframe__25
sta WSYNC
sta HMOVE
;;; end action SetXPos__preframe__25
KERNEL_START
;;; start action Kernel2Sprite__kernel__27
ldy #0
sty VDELP0
iny
sta VDELP1
;;; end action Kernel2Sprite__kernel__27
;;; start action Kernel2Sprite__kernel__30
; define macro for each line
.macro Kernel2Sprite__kernel__32__DrawLine do_wsync
.local DoDraw1
.local DoDraw2
; draw player 0
lda Kernel2Sprite__2__tmp+8 ; height
dcp Kernel2Sprite__2__tmp+10 ; ypos
bcs DoDraw1
lda #0
.byte $2C
DoDraw1:
lda (Kernel2Sprite__2__tmp+0),y
.if do_wsync
sta WSYNC
.endif
sta GRP0
lda (Kernel2Sprite__2__tmp+4),y
sta COLUP0
; draw player 1
lda Kernel2Sprite__2__tmp+9 ; height
dcp Kernel2Sprite__2__tmp+11 ; ypos
bcs DoDraw2
lda #0
.byte $2C
DoDraw2:
lda (Kernel2Sprite__2__tmp+2),y
sta GRP1
lda (Kernel2Sprite__2__tmp+6),y
sta COLUP1
.endmacro
ldy #192
Kernel2Sprite__kernel__32__LVScan:
;;; start action Kernel2Sprite__scanline1__33
;;; end action Kernel2Sprite__scanline1__33
Kernel2Sprite__kernel__32__DrawLine 1 ; macro: draw scanline w/ WSYNC
dey ; next scanline
Kernel2Sprite__kernel__32__DrawLine 0 ; macro: draw scanline no WSYNC
dey ; next scanline
bne Kernel2Sprite__kernel__32__LVScan ; repeat until out of lines
;;; end action Kernel2Sprite__kernel__30
;;; start action Kernel2Sprite__kernel__34
lda #0
sta GRP0
sta GRP1
sta GRP0
sta GRP1
;;; end action Kernel2Sprite__kernel__34
KERNEL_END
;;; start action Joystick__postframe__37
; 2 control inputs share a single byte, 4 bits each
lda SWCHA
sta Joystick__3__tmp+0
;;; end action Joystick__postframe__37
;;; start action Joystick__postframe__39
ldx #0
Joystick__postframe__40____each:
asl Joystick__3__tmp+0
bcs Joystick__postframe__41__SkipMoveRight
;;; start action MoveJoyX__joyright__42
lda HasXpos_xpos_b0,x
clc
adc #1
cmp #152
bcs MoveJoyX__joyright__44__nomove
sta HasXpos_xpos_b0,x
MoveJoyX__joyright__44__nomove:
;;; end action MoveJoyX__joyright__42
Joystick__postframe__41__SkipMoveRight:
asl Joystick__3__tmp+0
bcs Joystick__postframe__41__SkipMoveLeft
;;; start action MoveJoyX__joyleft__45
lda HasXpos_xpos_b0,x
sec
sbc #1
bcc MoveJoyX__joyleft__47__nomove
sta HasXpos_xpos_b0,x
MoveJoyX__joyleft__47__nomove:
;;; end action MoveJoyX__joyleft__45
Joystick__postframe__41__SkipMoveLeft:
asl Joystick__3__tmp+0
bcs Joystick__postframe__41__SkipMoveDown
;;; start action MoveJoyY__joydown__48
lda HasYpos_ypos_b0,x
clc
adc #1
cmp #220
bcs MoveJoyY__joydown__50__nomove
sta HasYpos_ypos_b0,x
MoveJoyY__joydown__50__nomove:
;;; end action MoveJoyY__joydown__48
Joystick__postframe__41__SkipMoveDown:
asl Joystick__3__tmp+0
bcs Joystick__postframe__41__SkipMoveUp
;;; start action MoveJoyY__joyup__51
lda HasYpos_ypos_b0,x
sec
sbc #1
bcc MoveJoyY__joyup__53__nomove
sta HasYpos_ypos_b0,x
MoveJoyY__joyup__53__nomove:
;;; end action MoveJoyY__joyup__51
Joystick__postframe__41__SkipMoveUp:
inx
cpx #4
jne Joystick__postframe__40____each
Joystick__postframe__40____exit:
;;; end action Joystick__postframe__39
;;; start action SpriteShuffler__postframe__54
; load two sprite slots at left side of array
lda SpriteSlot_sprite_b0
sta SpriteShuffler__8__tmp+0
lda SpriteSlot_sprite_b0+1
sta SpriteShuffler__8__tmp+1
; move two slots to the left
ldx #0
SpriteShuffler__postframe__56__loop:
lda SpriteSlot_sprite_b0+2,x
sta SpriteSlot_sprite_b0,x
inx
cpx #4-2
bne SpriteShuffler__postframe__56__loop
; store two sprite slots at right side of array
lda SpriteShuffler__8__tmp+0
sta SpriteSlot_sprite_b0+4-2
lda SpriteShuffler__8__tmp+1
sta SpriteSlot_sprite_b0+4-1
;;; end action SpriteShuffler__postframe__54
;;; start action SpriteHider__postframe__57
lda #4-1
sta SpriteHider__9__tmp+0
;;; end action SpriteHider__postframe__57
;;; start action SpriteHider__postframe__60
ldy #0
SpriteHider__postframe__61____each:
ldx SpriteSlot_sprite_b0,y
lda HasYpos_ypos_b0,x
cmp #192
bcc SpriteHider__postframe__62__skip
; swap this sprite slot with slot at end of array
lda SpriteSlot_sprite_b0,y
pha
ldx SpriteHider__9__tmp+0 ; clobbers X, but no longer used
lda SpriteSlot_sprite_b0,x
sta SpriteSlot_sprite_b0,y
pla
sta SpriteSlot_sprite_b0,x
dec SpriteHider__9__tmp+0
SpriteHider__postframe__62__skip:
iny
cpy #2
jne SpriteHider__postframe__61____each
SpriteHider__postframe__61____exit:
;;; end action SpriteHider__postframe__60
FRAME_END
jmp FrameLoop__start__4__NextFrame ; loop to next frame
;;; end action FrameLoop__start__3
; start main routine
.segment "VECTORS"
Return: .word $6060
VecNMI:
VecReset: .word Main::__Reset
VecBRK: .word Main::__BRK
;;; end action Init__main_init__1
.endscope
Main__Start = Main::__Start
185:I couldn't find a component named "VersatilePlayfield".

View File

@ -3,6 +3,8 @@
import "vcslib.ecs"
import "sprites.ecs"
import "kernel2.ecs"
import "versatile.ecs"
// https://csanyk.com/2014/02/topology-metropolis-superman-atari-2600/
@ -116,23 +118,24 @@ end
system RoomShuffle
on postframe do select [Location,Sprite]
---
ldy {{%ecount}}
ldy #{{%ecount}}-1
ldx {{<Slot1.sprite}}
bmi @empty ; empty slot, load 1st entry
beq @empty ; empty slot, load 1st entry
@loop:
inx
cpx {{%ecount}}
cpx #{{%ecount}}+1
bcc @norecycle
; TODO: need to get index of specific entity
@empty:
ldx #1 ; skip null sprite and super dude?
ldx #2 ; skip null sprite and player
@norecycle:
lda {{<Location:room}},x
; TODO: should automatically index
lda {{<Location:room}}-1,x
cmp {{<Superdude.room}}
beq @exit
dey
bne @loop
ldx #$ff
ldx #0 ; null sprite
@exit:
stx {{<Slot1.sprite}}
---
@ -152,14 +155,14 @@ using SetXPos, SetHorizPos
//using SpriteShuffler, SpriteHider
entity Kernel [KernelSection, BGColor]
const lines = 192
const lines = 190
const bgcolor = 0xa2
end
entity NullShape [Bitmap,Colormap]
entity Blank [Bitmap,Colormap]
decode vcs_sprite
---
........ 00
........ 00
---
end
@ -452,14 +455,10 @@ x.x.x.x.x.x.x.x.x.x. .. 06 ..
---
end
/*
entity NullSprite [Location,Sprite,HasBitmap,HasColormap,HasXpos,HasYpos,Player]
var ypos = 224
const bitmap = #BexButhor1
const colormap = #BexButhor1
const plyrflags = $00
entity NullSprite [Sprite]
const bitmap = #Blank
//var plyrflags = $00
end
*/
entity Superdude [Location,Sprite,HasBitmap,HasColormap,HasXpos,HasYpos,Player,Moving]
var room = #OutsideDailyPlanet
@ -470,11 +469,11 @@ x.x.x.x.x.x.x.x.x.x. .. 06 ..
var plyrflags = $05
const speed = 2
end
entity BexButhor [Location,Sprite,HasXpos,HasYpos,HasBitmap,HasColormap,Enemy,Moving]
var room = #OutsideDailyPlanet
var xpos = 100
var ypos = 30
var xpos = 70
var ypos = 70
const bitmap = #BexButhor1
const colormap = #BexButhor1
var plyrflags = $00
@ -491,6 +490,7 @@ x.x.x.x.x.x.x.x.x.x. .. 06 ..
const speed = 1
end
/*
entity KBexButhor [Location,Sprite,HasXpos,HasYpos,HasBitmap,HasColormap,Enemy,Moving]
var room = #InsideDailyPlanet
var xpos = 50
@ -499,27 +499,16 @@ x.x.x.x.x.x.x.x.x.x. .. 06 ..
const colormap = #BexButhor1
var plyrflags = $00
const speed = 1
end
end*/
entity Slot0 [SpriteSlot]
var sprite = #Superdude
end
entity Slot1 [SpriteSlot]
var sprite = 0 // $ff
var sprite = #NullSprite
end
using VersatilePlayfield with #Superdude.room
end
/*
InsideDailyPlanetDS
.word SubwayGraphics
.byte WHITE - 2
.byte BLUE + 10
.byte <GreenSubwayDS ; pointer to north room
.byte <BlueSubwayDS ; pointer to east room
.byte <YellowSubwayDS ; pointer to south room
.byte <PinkSubwayDS ; pointer to west room
*/

View File

@ -1,8 +1,8 @@
EVENT__start = 1
EVENT__postframe = 1
EVENT__preframe = 1
EVENT__kernel = 1
EVENT__scanline = 1
EVENT__postframe = 1
EVENT__joyleft = 1
EVENT__joyright = 1
EVENT__gowest = 1
@ -11,29 +11,28 @@ EVENT__gonorth = 1
EVENT__gosouth = 1
EVENT__joyup = 1
EVENT__joydown = 1
EVENT__prekernel = 1
EVENT__SetHorizPos = 1
EVENT__checkplatform = 1
.scope Main
.zeropage
Location_room_b0:
.res 1
.res 1
.res 1
.res 1
Sprite_plyrflags_b0:
.res 1
.res 1
.res 1
.res 1
Location_room_b0:
.res 1
.res 1
.res 1
HasXpos_xpos_b0:
.res 1
.res 1
.res 1
.res 1
HasYpos_ypos_b0:
.res 1
.res 1
.res 1
.res 1
SpriteSlot_sprite_b0:
.res 1
.res 1
@ -62,7 +61,7 @@ VersatilePlayfield__10__tmp:
.res 1
.code
KernelSection_lines_b0:
.byte 192
.byte 190
BGColor_bgcolor_b0:
.byte 162
Bitmap_bitmapdata_b0:
@ -603,39 +602,34 @@ VersatilePlayfield_data_e6_b0:
.byte 10
.byte 112
.byte 9
HasBitmap_bitmap_b0:
Sprite_bitmap_b0:
.byte 0
.byte 1
.byte 2
.byte 2
.byte 2
HasColormap_colormap_b0:
.byte 1
.byte 2
.byte 2
.byte 2
Moving_speed_b0:
.byte 2
.byte 1
.byte 1
.byte 1
Main__INITDATA:
.byte 2
.byte 2
.byte 2
.byte 1
.byte 0
.byte 5
.byte 0
.byte 0
.byte 0
.byte 2
.byte 2
.byte 2
.byte 40
.byte 70
.byte 100
.byte 100
.byte 50
.byte 30
.byte 30
.byte 70
.byte 60
.byte 90
.byte 0
.byte 1
.byte 0
.byte 0
.byte 0
@ -652,31 +646,29 @@ __Reset:
__BRK:
CLEAN_START
ldy #21
ldy #18
: lda Main__INITDATA-1,y
sta Location_room_b0-1,y
sta Sprite_plyrflags_b0-1,y
dey
bne :-
;;; start action FrameLoop__start__3
FrameLoop__start__4__NextFrame:
FRAME_END
FRAME_START
;;; start action Kernel2Sprite__preframe__5
.define KLINES #192
; TODOO: can store KLINES in memory?
.define KLINES #190
.define KPAD 32
; set height to zero in case no sprites
lda #0
sta Kernel2Sprite__2__tmp+8
sta Kernel2Sprite__2__tmp+9
; set temp value so we don't read bitmap from h/w registers
lda #$F0
sta Kernel2Sprite__2__tmp+2
sta Kernel2Sprite__2__tmp+3
sta Kernel2Sprite__2__tmp+6
sta Kernel2Sprite__2__tmp+7
;;; end action Kernel2Sprite__preframe__5
@ -686,21 +678,20 @@ FrameLoop__start__4__NextFrame:
Kernel2Sprite__preframe__9____each:
ldx SpriteSlot_sprite_b0,y
; flags set according to sprite slot value
; skip sprite if negative
jmi Kernel2Sprite__preframe__10__nosprite
; set player object flags
lda Sprite_plyrflags_b0,x
sta NUSIZ0,y
sta REFP0,y
; calculate screen height - ypos
lda KLINES+KPAD
lda KLINES
clc
adc KPAD
sec
sbc HasYpos_ypos_b0,x
sbc HasYpos_ypos_b0-1,x
sta Kernel2Sprite__2__tmp+11
; calculate bitmap pointer
stx Kernel2Sprite__2__tmp+12 ; save X (Sprite index)
lda HasBitmap_bitmap_b0,x ; deref bitmap
lda Sprite_bitmap_b0,x ; deref bitmap
tax
lda Bitmap_bitmapdata_b0,x
sec
@ -714,7 +705,7 @@ Kernel2Sprite__preframe__9____each:
sta Kernel2Sprite__2__tmp+8,y
; calculate colormap pointer
ldx Kernel2Sprite__2__tmp+12 ; restore X
lda HasColormap_colormap_b0,x ; deref colormap
lda HasColormap_colormap_b0-1,x ; deref colormap
tax
lda Colormap_colormapdata_b0,x
sec
@ -725,9 +716,8 @@ Kernel2Sprite__preframe__9____each:
sta Kernel2Sprite__2__tmp+6,y
; save ypos
ldx Kernel2Sprite__2__tmp+12 ; restore X
lda HasYpos_ypos_b0,x
lda HasYpos_ypos_b0-1,x
sta Kernel2Sprite__2__tmp+10,y
Kernel2Sprite__preframe__10__nosprite:
iny
cpy #2
@ -764,59 +754,27 @@ Kernel2Sprite__preframe__9____exit:
;;; start action SetXPos__preframe__17
sta HMCLR
;;; end action SetXPos__preframe__17
;;; start action SetXPos__preframe__19
ldy #0
SetXPos__preframe__20____each:
SetXPos__preframe__18____each:
ldx SpriteSlot_sprite_b0,y
lda HasXpos_xpos_b0,x
lda HasXpos_xpos_b0-1,x
;;; start action SetHorizPos__SetHorizPos__22
; SetHorizPos routine
; A = X coordinate
; Y = player number (0 or 1)
sta WSYNC ; start a new line
sec ; set carry flag
nop
SetHorizPos__SetHorizPos__23__DivideLoop:
sbc #15 ; subtract 15
bcs SetHorizPos__SetHorizPos__23__DivideLoop ; branch until negative
eor #7 ; calculate fine offset
asl
asl
asl
asl
sta RESP0,y ; fix coarse position
sta HMP0,y ; set fine offset
;;; end action SetHorizPos__SetHorizPos__22
jsr SetHorizPos__SetHorizPos__20
iny
cpy #2
jne SetXPos__preframe__20____each
SetXPos__preframe__20____exit:
jne SetXPos__preframe__18____each
SetXPos__preframe__18____exit:
;;; end action SetXPos__preframe__19
;;; end action SetXPos__preframe__17
;;; start action SetXPos__preframe__24
;;; start action SetXPos__preframe__22
;;; end action SetXPos__preframe__24
;;; end action SetXPos__preframe__22
;;; start action SetXPos__preframe__25
sta WSYNC
sta HMOVE
;;; end action SetXPos__preframe__25
;;; start action VersatilePlayfield__preframe__27
;;; start action VersatilePlayfield__preframe__23
ldx Location_room_b0+0
@ -826,136 +784,32 @@ SetXPos__preframe__20____exit:
sta VersatilePlayfield__10__tmp+1
;;; end action VersatilePlayfield__preframe__27
;;; end action VersatilePlayfield__preframe__23
;;; start action SetXPos__prekernel__26
sta WSYNC
sta HMOVE
SLEEPR 24
sta HMCLR
;;; end action SetXPos__prekernel__26
KERNEL_START
;;; start action Kernel2Sprite__kernel__30
;;; start action Kernel2Sprite__kernel__28
ldy #0
sty VDELP0
iny
sta VDELP1
sty VDELP1
;;; end action Kernel2Sprite__kernel__30
;;; end action Kernel2Sprite__kernel__28
;;; start action Kernel2Sprite__kernel__33
ldy #192
Kernel2Sprite__kernel__35__LVScan:
;;; start action Kernel2Sprite__scanline__36
jsr Kernel2Sprite__kernel__31
; draw player 0
lda Kernel2Sprite__2__tmp+8 ; height
dcp Kernel2Sprite__2__tmp+10 ; ypos
bcs Kernel2Sprite__scanline__37__DoDraw1
lda #0
.byte $2C
Kernel2Sprite__scanline__37__DoDraw1:
lda (Kernel2Sprite__2__tmp+0),y
.if 0 = 0
sta WSYNC
.endif
sta GRP0
lda (Kernel2Sprite__2__tmp+4),y
sta COLUP0
; draw player 1
lda Kernel2Sprite__2__tmp+9 ; height
dcp Kernel2Sprite__2__tmp+11 ; ypos
bcs Kernel2Sprite__scanline__37__DoDraw2
lda #0
.byte $2C
Kernel2Sprite__scanline__37__DoDraw2:
lda (Kernel2Sprite__2__tmp+2),y
sta GRP1
lda (Kernel2Sprite__2__tmp+6),y
sta COLUP1
;;; end action Kernel2Sprite__scanline__36
;;; start action Kernel2Sprite__scanline__38
;;; end action Kernel2Sprite__scanline__38
;;; start action VersatilePlayfield__scanline__39
.if 0 = 0
lda (VersatilePlayfield__10__tmp+0),y
tax
.endif
;;; end action VersatilePlayfield__scanline__39
;;; start action VersatilePlayfield__scanline__41
.if 0 = 1
lda (VersatilePlayfield__10__tmp+0),y
sta $00,x
.endif
;;; end action VersatilePlayfield__scanline__41
dey ; next scanline
;;; start action Kernel2Sprite__scanline__43
; draw player 0
lda Kernel2Sprite__2__tmp+8 ; height
dcp Kernel2Sprite__2__tmp+10 ; ypos
bcs Kernel2Sprite__scanline__44__DoDraw1
lda #0
.byte $2C
Kernel2Sprite__scanline__44__DoDraw1:
lda (Kernel2Sprite__2__tmp+0),y
.if 1 = 0
sta WSYNC
.endif
sta GRP0
lda (Kernel2Sprite__2__tmp+4),y
sta COLUP0
; draw player 1
lda Kernel2Sprite__2__tmp+9 ; height
dcp Kernel2Sprite__2__tmp+11 ; ypos
bcs Kernel2Sprite__scanline__44__DoDraw2
lda #0
.byte $2C
Kernel2Sprite__scanline__44__DoDraw2:
lda (Kernel2Sprite__2__tmp+2),y
sta GRP1
lda (Kernel2Sprite__2__tmp+6),y
sta COLUP1
;;; end action Kernel2Sprite__scanline__43
;;; start action Kernel2Sprite__scanline__45
;;; end action Kernel2Sprite__scanline__45
;;; start action VersatilePlayfield__scanline__46
.if 1 = 0
lda (VersatilePlayfield__10__tmp+0),y
tax
.endif
;;; end action VersatilePlayfield__scanline__46
;;; start action VersatilePlayfield__scanline__48
.if 1 = 1
lda (VersatilePlayfield__10__tmp+0),y
sta $00,x
.endif
;;; end action VersatilePlayfield__scanline__48
dey ; next scanline
bne Kernel2Sprite__kernel__35__LVScan ; repeat until out of lines
;;; end action Kernel2Sprite__kernel__33
;;; start action Kernel2Sprite__kernel__50
;;; start action Kernel2Sprite__kernel__48
lda #0
sta GRP0
@ -963,10 +817,20 @@ Kernel2Sprite__scanline__44__DoDraw2:
sta GRP0
sta GRP1
;;; end action Kernel2Sprite__kernel__50
;;; end action Kernel2Sprite__kernel__48
KERNEL_END
;;; start action FrameLoop__postframe__50
lsr SWCHB ; test Game Reset switch
bcs FrameLoop__postframe__51__NoStart
FrameLoop__postframe__51__NoStart:
;;; end action FrameLoop__postframe__50
;;; start action Joystick__postframe__52
; 2 control inputs share a single byte, 4 bits each
@ -978,13 +842,14 @@ Kernel2Sprite__scanline__44__DoDraw2:
;;; start action Joystick__postframe__54
asl Joystick__3__tmp+0
.ifdef EVENT__joyright
bcs Joystick__postframe__56__SkipMoveRight
;;; start action JoyFaceDirection__joyright__57
lda Sprite_plyrflags_b0
lda Sprite_plyrflags_b0+1
and #$f7
sta Sprite_plyrflags_b0
sta Sprite_plyrflags_b0+1
;;; end action JoyFaceDirection__joyright__57
@ -1011,14 +876,16 @@ SuperFly__joyright__62__nomove:
;;; end action SuperFly__joyright__60
Joystick__postframe__56__SkipMoveRight:
.endif
asl Joystick__3__tmp+0
.ifdef EVENT__joyleft
bcs Joystick__postframe__56__SkipMoveLeft
;;; start action JoyFaceDirection__joyleft__66
lda Sprite_plyrflags_b0
lda Sprite_plyrflags_b0+1
ora #$08
sta Sprite_plyrflags_b0
sta Sprite_plyrflags_b0+1
;;; end action JoyFaceDirection__joyleft__66
@ -1044,7 +911,9 @@ SuperFly__joyleft__71__nomove:
;;; end action SuperFly__joyleft__69
Joystick__postframe__56__SkipMoveLeft:
.endif
asl Joystick__3__tmp+0
.ifdef EVENT__joydown
bcs Joystick__postframe__56__SkipMoveDown
;;; start action SuperFly__joydown__75
@ -1070,7 +939,9 @@ SuperFly__joydown__77__nomove:
;;; end action SuperFly__joydown__75
Joystick__postframe__56__SkipMoveDown:
.endif
asl Joystick__3__tmp+0
.ifdef EVENT__joyup
bcs Joystick__postframe__56__SkipMoveUp
;;; start action SuperFly__joyup__81
@ -1095,6 +966,7 @@ SuperFly__joyup__83__nomove:
;;; end action SuperFly__joyup__81
Joystick__postframe__56__SkipMoveUp:
.endif
;;; end action Joystick__postframe__54
@ -1106,9 +978,9 @@ BadMove__postframe__88____each:
;;; start action JoyFaceDirection__joyright__90
lda Sprite_plyrflags_b0+1,x
lda Sprite_plyrflags_b0+2,x
and #$f7
sta Sprite_plyrflags_b0+1,x
sta Sprite_plyrflags_b0+2,x
;;; end action JoyFaceDirection__joyright__90
@ -1136,7 +1008,7 @@ SuperFly__joyright__95__nomove:
inx
cpx #3
cpx #2
jne BadMove__postframe__88____each
BadMove__postframe__88____exit:
@ -1144,23 +1016,24 @@ BadMove__postframe__88____exit:
;;; start action RoomShuffle__postframe__99
ldy 4
ldy #3-1
ldx SpriteSlot_sprite_b0+1
bmi RoomShuffle__postframe__101__empty ; empty slot, load 1st entry
beq RoomShuffle__postframe__101__empty ; empty slot, load 1st entry
RoomShuffle__postframe__101__loop:
inx
cpx 4
cpx #3+1
bcc RoomShuffle__postframe__101__norecycle
; TODO: need to get index of specific entity
RoomShuffle__postframe__101__empty:
ldx #1 ; skip null sprite and super dude?
ldx #2 ; skip null sprite and player
RoomShuffle__postframe__101__norecycle:
lda Location_room_b0,x
; TODO: should automatically index
lda Location_room_b0-1,x
cmp Location_room_b0
beq RoomShuffle__postframe__101__exit
dey
bne RoomShuffle__postframe__101__loop
ldx #$ff
ldx #0 ; null sprite
RoomShuffle__postframe__101__exit:
stx SpriteSlot_sprite_b0+1
@ -1175,19 +1048,163 @@ RoomShuffle__postframe__101__exit:
;;; end action VersatilePlayfield__postframe__102
FRAME_END
jmp FrameLoop__start__4__NextFrame ; loop to next frame
;;; end action FrameLoop__start__3
; start main routine
.segment "VECTORS"
Return: .word $6060
ZeroByte: .byte $00
Return: .byte $60
VecNMI:
VecReset: .word Main::__Reset
VecBRK: .word Main::__BRK
VecReset: .word __Reset
VecBRK: .word __BRK
.code
;;; end action Init__main_init__1
.rodata
__ALIGNORIGIN:
.rodata
SetHorizPos__SetHorizPos__20:
; SetHorizPos routine
; A = X coordinate
; Y = player number (0 or 1)
sec ; set carry flag
sta WSYNC ; start a new line
:
sbc #15 ; subtract 15
bcs :- ; branch until negative
eor #7 ; calculate fine offset
asl
asl
asl
asl
sta HMP0,y ; set fine offset
sta RESP0,y ; fix coarse position
sta WSYNC ; won't overrun if X < 150
rts
.assert >(SetHorizPos__SetHorizPos__20) = >(*), error, "SetHorizPos__SetHorizPos__20 crosses a page boundary!"
.assert (* - SetHorizPos__SetHorizPos__20) <= 22, error, .sprintf("SetHorizPos__SetHorizPos__20 does not fit in 22 bytes, it took %d!", (* - SetHorizPos__SetHorizPos__20))
.rodata
Kernel2Sprite__kernel__31:
ldy #190
Kernel2Sprite__kernel__33__LVScan:
;;; start action Kernel2Sprite__scanline__34
; draw player 0
lda Kernel2Sprite__2__tmp+8 ; height
dcp Kernel2Sprite__2__tmp+10 ; ypos
bcs Kernel2Sprite__scanline__35__DoDraw1
lda #0
.byte $2C
Kernel2Sprite__scanline__35__DoDraw1:
lda (Kernel2Sprite__2__tmp+0),y
; .if 0 = 0 ; TODO: configurable?
sta WSYNC
; .endif
sta GRP0
lda (Kernel2Sprite__2__tmp+4),y
sta COLUP0
; draw player 1
lda Kernel2Sprite__2__tmp+9 ; height
dcp Kernel2Sprite__2__tmp+11 ; ypos
bcs Kernel2Sprite__scanline__35__DoDraw2
lda #0
.byte $2C
Kernel2Sprite__scanline__35__DoDraw2:
lda (Kernel2Sprite__2__tmp+2),y
sta GRP1
lda (Kernel2Sprite__2__tmp+6),y
sta COLUP1
;;; end action Kernel2Sprite__scanline__34
;;; start action Kernel2Sprite__scanline__36
;;; end action Kernel2Sprite__scanline__36
;;; start action VersatilePlayfield__scanline__37
.if 0 = 0
lda (VersatilePlayfield__10__tmp+0),y
tax
.endif
;;; end action VersatilePlayfield__scanline__37
;;; start action VersatilePlayfield__scanline__39
.if 0 = 1
lda (VersatilePlayfield__10__tmp+0),y
sta $00,x
.endif
;;; end action VersatilePlayfield__scanline__39
dey ; next scanline
;;; start action Kernel2Sprite__scanline__41
; draw player 0
lda Kernel2Sprite__2__tmp+8 ; height
dcp Kernel2Sprite__2__tmp+10 ; ypos
bcs Kernel2Sprite__scanline__42__DoDraw1
lda #0
.byte $2C
Kernel2Sprite__scanline__42__DoDraw1:
lda (Kernel2Sprite__2__tmp+0),y
; .if 1 = 0 ; TODO: configurable?
sta WSYNC
; .endif
sta GRP0
lda (Kernel2Sprite__2__tmp+4),y
sta COLUP0
; draw player 1
lda Kernel2Sprite__2__tmp+9 ; height
dcp Kernel2Sprite__2__tmp+11 ; ypos
bcs Kernel2Sprite__scanline__42__DoDraw2
lda #0
.byte $2C
Kernel2Sprite__scanline__42__DoDraw2:
lda (Kernel2Sprite__2__tmp+2),y
sta GRP1
lda (Kernel2Sprite__2__tmp+6),y
sta COLUP1
;;; end action Kernel2Sprite__scanline__41
;;; start action Kernel2Sprite__scanline__43
;;; end action Kernel2Sprite__scanline__43
;;; start action VersatilePlayfield__scanline__44
.if 1 = 0
lda (VersatilePlayfield__10__tmp+0),y
tax
.endif
;;; end action VersatilePlayfield__scanline__44
;;; start action VersatilePlayfield__scanline__46
.if 1 = 1
lda (VersatilePlayfield__10__tmp+0),y
sta $00,x
.endif
;;; end action VersatilePlayfield__scanline__46
dey ; next scanline
bne Kernel2Sprite__kernel__33__LVScan ; repeat until out of lines
rts
.assert >(Kernel2Sprite__kernel__31) = >(*), error, "Kernel2Sprite__kernel__31 crosses a page boundary!"
.endscope
Main__Start = Main::__Start

View File

@ -18,6 +18,9 @@ system Kernel48Pixel
on kernelsetup do if [Bitmap48] ---
lda {{<height}}
sta {{$0}} ; scanline counter
---
// TODO: should factor out this code, but doesnt
on kernelsetup do if [Bitmap48] ---
lda #$22
sta COLUP0 ; show how players alternate
lda #$12
@ -44,13 +47,14 @@ system Kernel48Pixel
sta COLUP0
sta COLUP1
---
on kerneldraw do critical fit 63 if [Bitmap48]
on kerneldraw do critical fit 63
if [Bitmap48]
---
txa
pha
@Loop:
:
ldy {{$0}} ; counts backwards
sta WSYNC ; sync to next scanline
{{!wsync}} ; sync to next scanline
lda {{data bitmap0}},y ; load B0 (1st sprite byte)
sta GRP0 ; B0 -> [GRP0]
lda {{data bitmap1}},y ; load B1 -> A
@ -67,7 +71,7 @@ system Kernel48Pixel
sty GRP1 ; B5 -> [GRP1]; B4 -> GRP0
sta GRP0 ; ?? -> [GRP0]; B5 -> GRP1
dec {{$0}} ; go to next line
bpl @Loop ; repeat until < 0
bpl :- ; repeat until < 0
pla
tax
---
@ -77,7 +81,9 @@ demo TitleDemo
scope Title
using FrameLoop, Kernel48Pixel, StaticKernel
using FrameLoop, StandardKernel
using Kernel48Pixel with [#Name]
using Kernel48Pixel with [#Copyright]
using JoyButton
entity [Player]
@ -91,7 +97,7 @@ demo TitleDemo
end
entity [KernelSection, BGColor]
const lines = 60
const lines = 30
const bgcolor = $a0
end
@ -101,7 +107,7 @@ demo TitleDemo
end
// convert -size 48x -gravity center label:"6502\nECS" pbm: | pnmtopnm -plain
entity [KernelSection, BGColor, PFColor, Bitmap48]
entity Name [KernelSection, BGColor, PFColor, Bitmap48]
const lines = 2
const bgcolor = 0xa4
const pfcolor = 0xfc
@ -147,11 +153,43 @@ demo TitleDemo
---
end
entity Copyright [KernelSection, BGColor, PFColor, Bitmap48]
const lines = 2
const bgcolor = 0xa4
const pfcolor = 0x8c
decode vcs_bitmap48 ---
000000000000000000000000000000100000000100000100
000000000000000000000000000000000000000100000100
000111000111001111010001101110100011010111101110
001001001001001101111001001100100100110110100100
001001001000101000101001001000100100110100010100
011000011000101000101001001000101100010100010100
011000011000101000101010001000101100010100010100
011001001000101000100110001000100100110100010100
001001001001001001000110001000100100110100010110
000110000111001111000110001000100011110100010000
000000000000001000000100000000000000010000000000
000000000000001000000100000000000100100000000000
000000000000001000001000000000000111100000000000
000000000000000000000000000000000000000000000000
000000000000001110001110001110001110000000000000
000000000000010011011010010011010011000000000000
000000000000010001010011010011010001000000000000
000000000000000001110001000001000001000000000000
000000000000000011110001000011000011000000000000
000000000000000110110001000110000110000000000000
000000000000001100110001001100001000000000000000
000000000000010000010001010000010000000000000000
000000000000010000010010010000010000000000000000
000000000000111111001110111111111111000000000000
000000000000000000000000000000000000000000000000
---
end
entity [KernelSection, BGColor]
const lines = 10
const bgcolor = $a2
end
entity [KernelSection, BGColor]
const lines = 10
const bgcolor = $a0
@ -161,21 +199,21 @@ demo TitleDemo
scope Title2
using FrameLoop, Kernel48Pixel, StaticKernel
using FrameLoop, Kernel48Pixel, StandardKernel
entity [KernelSection, BGColor]
const lines = 60
var lines = 60
var bgcolor = 0x10
end
entity [KernelSection, BGColor]
const lines = 10
var lines = 30
var bgcolor = 0x30
end
// convert -size 48x -gravity center label:"6502\nECS" pbm: | pnmtopnm -plain
entity [KernelSection, BGColor, PFColor, Bitmap48]
const lines = 2
var lines = 2
var pfcolor = 0xec
var bgcolor = 0x30
decode vcs_bitmap48 ---
@ -227,12 +265,12 @@ demo TitleDemo
end
entity [KernelSection, BGColor]
const lines = 10
var lines = 20
var bgcolor = 0x30
end
entity [KernelSection, BGColor]
const lines = 10
var lines = 20
var bgcolor = 0x50
end
@ -242,7 +280,14 @@ system Colors
inc {{set pfcolor}}
bne :+
inc {{set bgcolor}}
inc {{set bgcolor}}
:
---
on postframe do foreach [KernelSection]
---
dec {{set lines}}
bne :+
lda #1
sta {{set lines}}
:
---
end
@ -252,7 +297,7 @@ end
system Demo
on start do once
---
jmp Title__Start
{{start Title}}
---
end

File diff suppressed because it is too large Load Diff

View File

@ -13,10 +13,12 @@ __BRK:
CLEAN_START
{{!start}} ; start main routine
.segment "VECTORS"
Return: .word $6060
ZeroByte: .byte $00
Return: .byte $60
VecNMI:
VecReset: .word Main::__Reset
VecBRK: .word Main::__BRK
VecReset: .word __Reset
VecBRK: .word __BRK
.code
---
end
@ -24,13 +26,17 @@ component Player
end
component KernelSection
lines: 1..255
lines: 1..255 default 1
end
component BGColor
bgcolor: 0..255
end
component FGColor
fgcolor: 0..255
end
component PFColor
pfcolor: 0..255
end
@ -44,32 +50,28 @@ component AsymPlayfield
pfright: 0..0xffffff
end
component VersatilePlayfield
data: array of 0..255 baseoffset -1
end
system FrameLoop
on start do once
---
{{emit preframeloop}}
@NextFrame:
FRAME_END
{{emit prevsync}}
FRAME_START
{{emit preframe}}
{{emit prekernel}}
KERNEL_START
{{emit kernel}}
KERNEL_END
{{emit postkernel}}
{{emit postframe}}
FRAME_END
{{emit nextframe}}
jmp @NextFrame ; loop to next frame
---
end
system ResetSwitch
on nextframe do once
on postframe do once
---
lsr SWCHB ; test Game Reset switch
bcs @NoStart
{{!resetswitch}}
{{emit resetswitch}}
@NoStart:
---
end
@ -99,58 +101,71 @@ system Joystick
lda SWCHA
sta {{$0}}
---
on postframe do foreach [Player]
on postframe do foreach [Player] limit 2
---
asl {{$0}}
.ifdef EVENT__joyright
bcs @SkipMoveRight
{{!joyright}}
@SkipMoveRight:
.endif
asl {{$0}}
.ifdef EVENT__joyleft
bcs @SkipMoveLeft
{{!joyleft}}
@SkipMoveLeft:
.endif
asl {{$0}}
.ifdef EVENT__joydown
bcs @SkipMoveDown
{{!joydown}}
@SkipMoveDown:
.endif
asl {{$0}}
.ifdef EVENT__joyup
bcs @SkipMoveUp
{{!joyup}}
@SkipMoveUp:
.endif
---
end
system SetHorizPos
on SetHorizPos do once
on SetHorizPos do critical fit 22 once
---
; SetHorizPos routine
; A = X coordinate
; Y = player number (0 or 1)
sta WSYNC ; start a new line
sec ; set carry flag
nop
@DivideLoop:
sec ; set carry flag
sta WSYNC ; start a new line
:
sbc #15 ; subtract 15
bcs @DivideLoop ; branch until negative
bcs :- ; branch until negative
eor #7 ; calculate fine offset
asl
asl
asl
asl
sta RESP0,y ; fix coarse position
sta HMP0,y ; set fine offset
sta RESP0,y ; fix coarse position
sta WSYNC ; won't overrun if X < 150
---
end
system StaticKernel
system StandardKernel
on wsync do once
---
sta WSYNC
---
on preframe do foreach [KernelSection] limit 1
---
{{!wsync}}
{{!kernelsetup}}
---
on kernel do foreach [KernelSection]
---
sta WSYNC
{{!wsync}}
{{!kernelsetup}}
{{!kerneldraw}}
{{!kerneldone}}
@ -159,7 +174,8 @@ system StaticKernel
---
ldy {{<lines}}
@loop:
sta WSYNC
{{!prescanline}}
{{!wsync}}
{{!scanline}}
dey
bne @loop
@ -185,11 +201,92 @@ system StaticKernel
---
end
component SimpleCollidable
lastx: 0..255
lasty: 0..255
end
system SimpleCollision
on postframe do with [SimpleCollidable]
---
lda CXP0FB
bpl @nocollide
lda {{<lastx}}
sta {{<xpos}}
lda {{<lasty}}
sta {{<ypos}}
@nocollide:
---
on ymoved do with [SimpleCollidable]
---
lda {{<xpos}}
sta {{<lastx}}
lda {{<ypos}}
sta {{<lasty}}
---
end
component FrameCount
frame: 0..255
end
system FrameCounter
on postframe do with [FrameCount]
---
inc {{set frame}}
.ifdef EVENT__frame256
jne @noframe256
{{emit frame256}}
@noframe256:
.endif
---
// TODO: only .if responds to events
on postframe do with [FrameCount]
---
jmp @go
.ifdef EVENT__frame4
@frame4:
{{emit frame4}}
jmp @done
.endif
.ifdef EVENT__frame8
@frame8:
{{emit frame8}}
jmp @done
.endif
.ifdef EVENT__frame16
@frame16:
{{emit frame16}}
jmp @done
.endif
@go:
lda {{get frame}}
.ifdef EVENT__frame16
and #15
jeq @frame16
.endif
.ifdef EVENT__frame8
and #7
cmp #3
jeq @frame8
.endif
.ifdef EVENT__frame4
and #3
cmp #1
jeq @frame4
.endif
@done:
---
end
///
demo Main
using FrameLoop, ResetSwitch, ResetConsole
using StaticKernel, JoyButton
using FrameLoop, ResetConsole
using StandardKernel, JoyButton
entity [Player]
end
entity [KernelSection,BGColor]
@ -218,7 +315,7 @@ demo Main
const bgcolor = $14
const pf = 0x112244
end
entity [KernelSection,BGColor,PFColor,Playfield]
entity Trees2 [KernelSection,BGColor,PFColor,Playfield]
const lines = 50
const bgcolor = $16
const pf = 0x124
@ -236,5 +333,6 @@ demo Main
inc {{set Trees.pfcolor}}
---
end
end demo

View File

@ -1,11 +1,11 @@
EVENT__start = 1
EVENT__nextframe = 1
EVENT__postframe = 1
EVENT__resetswitch = 1
EVENT__wsync = 1
EVENT__preframe = 1
EVENT__kernel = 1
EVENT__kerneldraw = 1
EVENT__kernelsetup = 1
EVENT__postframe = 1
EVENT__joybutton = 1
.scope Main
.zeropage
@ -13,7 +13,7 @@ PFColor_pfcolor_b0:
.res 1
.res 1
TEMP:
Local__6__tmp:
Local__5__tmp:
.res 1
.code
KernelSection_lines_b0:
@ -72,67 +72,84 @@ __BRK:
;;; start action FrameLoop__start__3
FrameLoop__start__4__NextFrame:
FRAME_END
FRAME_START
;;; start action StaticKernel__preframe__5
;;; start action StandardKernel__preframe__5
;;; start action StaticKernel__kernelsetup__8
;;; start action StandardKernel__wsync__8
sta WSYNC
;;; end action StandardKernel__wsync__8
;;; start action StandardKernel__kernelsetup__10
lda #24
sta COLUBK
;;; end action StaticKernel__kernelsetup__8
;;; end action StandardKernel__kernelsetup__10
;;; start action StaticKernel__kernelsetup__11
;;; start action StandardKernel__kernelsetup__13
;;; end action StaticKernel__kernelsetup__11
;;; end action StandardKernel__kernelsetup__13
;;; start action StaticKernel__kernelsetup__12
;;; start action StandardKernel__kernelsetup__14
;;; end action StaticKernel__kernelsetup__12
;;; end action StandardKernel__kernelsetup__14
;;; end action StaticKernel__preframe__5
;;; end action StandardKernel__preframe__5
KERNEL_START
;;; start action StaticKernel__kernel__13
;;; start action StandardKernel__kernel__15
ldx #0
StaticKernel__kernel__14____each:
StandardKernel__kernel__16____each:
;;; start action StandardKernel__wsync__18
sta WSYNC
;;; end action StandardKernel__wsync__18
;;; start action StaticKernel__kernelsetup__16
;;; start action StandardKernel__kernelsetup__20
lda BGColor_bgcolor_b0,x
sta COLUBK
;;; end action StaticKernel__kernelsetup__16
;;; end action StandardKernel__kernelsetup__20
;;; start action StaticKernel__kernelsetup__19
;;; start action StandardKernel__kernelsetup__23
cpx #5+2
jcs StaticKernel__kernelsetup__20____skipxhi
jcs StandardKernel__kernelsetup__24____skipxhi
cpx #5
jcc StaticKernel__kernelsetup__20____skipxlo
jcc StandardKernel__kernelsetup__24____skipxlo
lda PFColor_pfcolor_b0-5,x
sta COLUPF
StaticKernel__kernelsetup__20____skipxlo:
StandardKernel__kernelsetup__24____skipxlo:
StaticKernel__kernelsetup__20____skipxhi:
StandardKernel__kernelsetup__24____skipxhi:
;;; end action StaticKernel__kernelsetup__19
;;; end action StandardKernel__kernelsetup__23
;;; start action StaticKernel__kernelsetup__22
;;; start action StandardKernel__kernelsetup__26
cpx #4
jcc StaticKernel__kernelsetup__23____skipxlo
jcc StandardKernel__kernelsetup__27____skipxlo
lda Playfield_pf_b0-4,x
sta PF0
@ -141,55 +158,45 @@ StaticKernel__kernelsetup__20____skipxhi:
lda Playfield_pf_b16-4,x
sta PF2
StaticKernel__kernelsetup__23____skipxlo:
StandardKernel__kernelsetup__27____skipxlo:
;;; end action StaticKernel__kernelsetup__22
;;; end action StandardKernel__kernelsetup__26
;;; start action StaticKernel__kerneldraw__25
;;; start action StandardKernel__kerneldraw__29
ldy KernelSection_lines_b0,x
StaticKernel__kerneldraw__27__loop:
StandardKernel__kerneldraw__31__loop:
;;; start action StandardKernel__wsync__32
sta WSYNC
;;; end action StandardKernel__wsync__32
dey
bne StaticKernel__kerneldraw__27__loop
bne StandardKernel__kerneldraw__31__loop
;;; end action StaticKernel__kerneldraw__25
;;; end action StandardKernel__kerneldraw__29
inx
cpx #8
jne StaticKernel__kernel__14____each
StaticKernel__kernel__14____exit:
jne StandardKernel__kernel__16____each
StandardKernel__kernel__16____exit:
;;; end action StaticKernel__kernel__13
;;; end action StandardKernel__kernel__15
KERNEL_END
;;; start action JoyButton__postframe__28
lda INPT4 ;read button input
bmi JoyButton__postframe__30__NotPressed
;;; start action Local__joybutton__31
inc Local__6__tmp+0
inc PFColor_pfcolor_b0
;;; end action Local__joybutton__31
JoyButton__postframe__30__NotPressed:
;;; end action JoyButton__postframe__28
FRAME_END
;;; start action ResetSwitch__nextframe__34
;;; start action FrameLoop__postframe__34
lsr SWCHB ; test Game Reset switch
bcs ResetSwitch__nextframe__35__NoStart
bcs FrameLoop__postframe__35__NoStart
;;; start action ResetConsole__resetswitch__36
@ -197,19 +204,37 @@ JoyButton__postframe__30__NotPressed:
;;; end action ResetConsole__resetswitch__36
ResetSwitch__nextframe__35__NoStart:
FrameLoop__postframe__35__NoStart:
;;; end action ResetSwitch__nextframe__34
;;; end action FrameLoop__postframe__34
;;; start action JoyButton__postframe__38
lda INPT4 ;read button input
bmi JoyButton__postframe__40__NotPressed
;;; start action Local__joybutton__41
inc Local__5__tmp+0
inc PFColor_pfcolor_b0
;;; end action Local__joybutton__41
JoyButton__postframe__40__NotPressed:
;;; end action JoyButton__postframe__38
jmp FrameLoop__start__4__NextFrame ; loop to next frame
;;; end action FrameLoop__start__3
; start main routine
.segment "VECTORS"
Return: .word $6060
ZeroByte: .byte $00
Return: .byte $60
VecNMI:
VecReset: .word Main::__Reset
VecBRK: .word Main::__BRK
VecReset: .word __Reset
VecBRK: .word __BRK
.code
;;; end action Init__main_init__1

69
test/ecs/versatile.ecs Normal file
View File

@ -0,0 +1,69 @@
component VersatilePlayfield
data: array of 0..255 baseoffset -1
end
system VersatilePlayfield
locals 2
on preframe do with [VersatilePlayfield]
---
lda {{<data}}
sta {{$0}}
lda {{>data}}
sta {{$1}}
---
on scanline do once
---
.if {{arg 0}} = 0
lda ({{local 0}}),y
tax
.endif
---
on scanline do once
---
.if {{arg 0}} = 1
lda ({{local 0}}),y
sta $00,x
.endif
---
on postframe do once
---
lda #0
sta PF0
sta PF1
sta PF2
---
on checkplatform do with [HasXpos,HasYpos]
---
lda {{<xpos}}
clc
adc #6
lsr
lsr
tay
lda {{^PFCollideMask}},y
pha
lda {{^PFCollideReg}},y
pha
lda #176 ; TODO: adjust for kernel size
sec
sbc {{<ypos}}
and #$fe
tay
; TODO: use system local pointer
pla
cmp ({{$0}}),y ; match register?
bne @nostop1
dey
pla
and ({{$0}}),y ; mask bitmap?
beq @nostop
{{!platformstopped}}
jmp @done
@nostop1:
pla
@nostop:
{{!platformnotstopped}}
@done:
---
end

1
test/ecs/versatile.txt Normal file
View File

@ -0,0 +1 @@
36:I couldn't find a component named "HasXpos".