hgr: oval: pageflipping

This commit is contained in:
Vince Weaver 2021-10-25 16:58:31 -04:00
parent 9c6e0cb5ce
commit 0527513905
6 changed files with 620 additions and 42 deletions

View File

@ -7,11 +7,15 @@ EMPTYDISK = ../../../empty_disk/empty.dsk
all: plasma_hgr.dsk
plasma_hgr.dsk: HELLO OVAL PURPLE_WAVES
plasma_hgr.dsk: HELLO OVAL PURPLE_WAVES ZEBRA JAWS TWIST OVAL_BOT
cp $(EMPTYDISK) plasma_hgr.dsk
$(DOS33) -y plasma_hgr.dsk SAVE A HELLO
$(DOS33) -y plasma_hgr.dsk BSAVE -a 0xc00 OVAL
$(DOS33) -y plasma_hgr.dsk BSAVE -a 0xc00 PURPLE_WAVES
$(DOS33) -y plasma_hgr.dsk BSAVE -a 0xc00 ZEBRA
$(DOS33) -y plasma_hgr.dsk BSAVE -a 0xc00 JAWS
$(DOS33) -y plasma_hgr.dsk BSAVE -a 0xc00 TWIST
$(DOS33) -y plasma_hgr.dsk BSAVE -a 0x378 OVAL_BOT
###
@ -28,6 +32,41 @@ oval.o: oval.s
###
OVAL_BOT: oval_bot.o
ld65 -o OVAL_BOT oval_bot.o -C $(LINKERSCRIPTS)/apple2_378.inc
oval_bot.o: oval_bot.s
ca65 -o oval_bot.o oval_bot.s -l oval_bot.lst
###
JAWS: jaws.o
ld65 -o JAWS jaws.o -C $(LINKERSCRIPTS)/apple2_c00.inc
jaws.o: jaws.s
ca65 -o jaws.o jaws.s -l jaws.lst
###
TWIST: twist.o
ld65 -o TWIST twist.o -C $(LINKERSCRIPTS)/apple2_c00.inc
twist.o: twist.s
ca65 -o twist.o twist.s -l twist.lst
###
ZEBRA: zebra.o
ld65 -o ZEBRA zebra.o -C $(LINKERSCRIPTS)/apple2_c00.inc
zebra.o: zebra.s
ca65 -o zebra.o zebra.s -l zebra.lst
###
PURPLE_WAVES: purple_waves.o
ld65 -o PURPLE_WAVES purple_waves.o -C $(LINKERSCRIPTS)/apple2_c00.inc
@ -37,5 +76,5 @@ purple_waves.o: purple_waves.s
###
clean:
rm -f *~ *.o *.lst OVAL PURPLE_WAVES
rm -f *~ *.o *.lst OVAL PURPLE_WAVES ZEBRA JAWS TWIST OVAL_BOT

180
graphics/hgr/plasma/jaws.s Normal file
View File

@ -0,0 +1,180 @@
; Jaws -- can remove the sine table to make smaller
; inner loop after lots of ops = 49 cycles (376320) = 2.6fps
; optimized to 38 (256-entry sine table) = (291840) = 3.4fps
; optimized to 37 (row_sum smc) = (284160) = 3.5fps
; zero page
GBASL = $26
GBASH = $27
YY = $69
ROW_SUM = $70
HGR_X = $E0
HGR_XH = $E1
HGR_Y = $E2
HGR_COLOR = $E4
HGR_PAGE = $E6
FRAME = $FC
SUM = $FD
SAVEX = $FE
SAVEY = $FF
; soft-switches
FULLGR = $C052
PAGE1 = $C054
; ROM routines
HGR2 = $F3D8
HPOSN = $F411 ; (Y,X),(A) (values stores in HGRX,XH,Y)
;================================
; Clear screen and setup graphics
;================================
oval:
jsr HGR2 ; set hi-res 140x192, page2, fullscreen
;====================
; create sinetable
ldy #0
sinetable_loop:
tya ; 2
and #$3f ; wrap sine at 63 entries ; 2
cmp #$20
php ; save pos/negative for later
and #$1f
cmp #$10
bcc sin_left
sin_right:
; sec carry should be set?
eor #$FF
adc #$20 ; 32-X
sin_left:
tax
lda sinetable_base,X ; 4+
lsr
lsr
plp
bcc sin_done
sin_negate:
; carry set here
eor #$ff
adc #0
sin_done:
sta sinetable,Y
iny
bne sinetable_loop
; NOTE: making gbash/gbasl table wasn't worth it
;============================
; main loop
;============================
draw_oval:
inc FRAME
ldx #191 ; YY
stx HGR_Y
create_yloop:
lda HGR_Y
; ldx #39 ; X is don't care?
ldy #0
jsr HPOSN ; (Y,X),(A) (values stores in HGRX,XH,Y)
; restore values
ldy #39 ; XX
lda HGR_Y ; YY
calcsine_div2:
lsr ; 2
tax
clc
lda sinetable,X
adc FRAME
sta row_sum_smc+1
ldx HGR_Y ; YY
create_xloop:
;=====================
; critical inner loop
; every cycle here is 40x192 cycles
;=====================
lda sinetable,Y ; 4+
clc ; 2
row_sum_smc:
adc #$dd ; row base value ; 2
lsr ; double colors ; 2
; also puts bit in carry
; which helps make blue
and #$7 ; mask ; 2
tax ; 2
lda colorlookup,X ; lookup in table ; 5
ror_nop_smc:
ror ; $6A/$EA ; 2
; and #$7f ; make all purple
sta (GBASL),Y ; 6
lda ror_nop_smc ; toggle ror/nop ; 4
eor #$80 ; 2
sta ror_nop_smc ; 4
dey ; 2
bpl create_xloop ; 2/3
dec HGR_Y
bne create_yloop
; we skip drawing line 0 as it makes it easier
beq draw_oval
colorlookup:
.byte $11,$55,$5d,$7f,$5d,$55,$11 ; use 00 from sinetable
;.byte $00
sinetable_base = $F5BA
;sinetable_base:
; this is actually (32*sin(x))
.byte $00,$03,$06,$09,$0C,$0F,$11,$14
.byte $16,$18,$1A,$1C,$1D,$1E,$1F,$1F
.byte $20
;,$1F,$1F,$1E,$1D,$1C,$1A,$18
;.byte $16,$14,$11,$0F,$0C,$09,$06,$03
; for bot
jmp oval
sinetable=$6000
gbasl = $6100
gbash = $6200

View File

@ -41,51 +41,24 @@ oval:
;====================
; create sinetable
.if 0
ldy #0
sinetable_loop:
tya ; 2
and #$3f ; wrap sine at 63 entries ; 2
tax ; 2
cmp #$20 ; see if negative ; 2
bcc sin_pos ; 2/3
sin_neg:
lda #0 ; 2
sbc sinetable_base-32,X ; 4+
jmp sin_done ; 3
sin_pos:
; carry already clear
lda sinetable_base,X ; 4+
sin_done:
sta sinetable,Y
iny
bne sinetable_loop
.endif
ldy #0
sinetable_loop:
tya ; 2
and #$3f ; wrap sine at 63 entries ; 2
cmp #$20
php
php ; save pos/negative for later
and #$1f
cmp #$10
bcc sin_blah
bcc sin_left
sin_right:
sec
; sec carry should be set?
eor #$FF
adc #$20 ; 32-X
sin_blah:
sin_left:
tax
lda sinetable_base,X ; 4+
@ -93,16 +66,17 @@ sin_blah:
bcc sin_done
sin_negate:
clc
; carry set here
eor #$ff
adc #1
adc #0
sin_done:
sta sinetable,Y
iny
bne sinetable_loop
; NOTE: making gbash/gbasl table wasn't worth it
;============================
; main loop
@ -116,7 +90,7 @@ draw_oval:
create_yloop:
lda HGR_Y
ldx #39
; ldx #39 ; X is don't care?
ldy #0
jsr HPOSN ; (Y,X),(A) (values stores in HGRX,XH,Y)
@ -151,6 +125,8 @@ row_sum_smc:
adc #$dd ; row base value ; 2
lsr ; double colors ; 2
; also puts bit in carry
; which helps make blue
and #$7 ; mask ; 2
tax ; 2
lda colorlookup,X ; lookup in table ; 5
@ -176,13 +152,12 @@ ror_nop_smc:
colorlookup:
.byte $11,$55,$5d,$7f,$5d,$55,$11 ; use 00 from sinetable
;.byte $00
sinetable_base:
; this is actually (32*sin(x))
.byte $00,$03,$06,$09,$0C,$0F,$11,$14
.byte $16,$18,$1A,$1C,$1D,$1E,$1F,$1F
.byte $20
@ -190,8 +165,8 @@ sinetable_base:
;.byte $16,$14,$11,$0F,$0C,$09,$06,$03
; for bot
jmp oval
sinetable=$6000
gbasl = $6100
gbash = $6200

View File

@ -0,0 +1,193 @@
; Ovals
; inner loop after lots of ops = 49 cycles (376320) = 2.6fps
; optimized to 38 (256-entry sine table) = (291840) = 3.4fps
; optimized to 37 (row_sum smc) = (284160) = 3.5fps
; zero page
GBASL = $26
GBASH = $27
YY = $69
ROW_SUM = $70
HGR_X = $E0
HGR_XH = $E1
HGR_Y = $E2
HGR_COLOR = $E4
HGR_PAGE = $E6
FRAME = $FC
SUM = $FD
SAVEX = $FE
SAVEY = $FF
; soft-switches
FULLGR = $C052
PAGE1 = $C054
; ROM routines
HGR2 = $F3D8
HPOSN = $F411 ; (Y,X),(A) (values stores in HGRX,XH,Y)
;================================
; Clear screen and setup graphics
;================================
oval:
jsr HGR2 ; set hi-res 140x192, page2, fullscreen
;====================
; create sinetable
ldy #0
sinetable_loop:
tya ; 2
and #$3f ; wrap sine at 63 entries ; 2
cmp #$20
php ; save pos/negative for later
and #$1f
cmp #$10
bcc sin_left
sin_right:
; sec carry should be set?
eor #$FF
adc #$20 ; 32-X
sin_left:
tax
lda sinetable_base,X ; 4+
plp
bcc sin_done
sin_negate:
; carry set here
eor #$ff
adc #0
sin_done:
sta sinetable,Y
iny
bne sinetable_loop
; NOTE: making gbash/gbasl table wasn't worth it
;============================
; main loop
;============================
draw_oval:
inc FRAME
lda #191 ; YY
; sta HGR_Y
create_yloop:
; dec HGR_Y
; lda HGR_Y
; ldx #39 ; X is don't care?
ldy #0
jsr HPOSN ; (Y,X),(A) (values stores in HGRX,XH,Y)
; restore values
ldy #39 ; XX
lda HGR_Y ; YY
calcsine_div2:
lsr ; 2
tax
clc
lda sinetable,X
adc FRAME
sta row_sum_smc+1
ldx HGR_Y ; YY
create_xloop:
;=====================
; critical inner loop
; every cycle here is 40x192 cycles
;=====================
lda sinetable,Y ; 4+
clc ; 2
row_sum_smc:
adc #$dd ; row base value ; 2
lsr ; double colors ; 2
; also puts bit in carry
; which helps make blue
and #$7 ; mask ; 2
tax ; 2
lda colorlookup,X ; lookup in table ; 5
ror_nop_smc:
ror ; $6A/$EA ; 2
; and #$7f ; make all purple
sta (GBASL),Y ; 6
lda ror_nop_smc ; toggle ror/nop ; 4
eor #$80 ; 2
sta ror_nop_smc ; 4
dey ; 2
bpl create_xloop ; 2/3
dec HGR_Y
lda HGR_Y
bne create_yloop
; we skip drawing line 0 as it makes it easier
flip_pages:
; Y should be $FF here
iny
lda HGR_PAGE
cmp #$20
beq done_page
iny
done_page:
ldx PAGE1,Y ; set display page to PAGE1 or PAGE2
eor #$60 ; flip draw page between $400/$800
sta HGR_PAGE
bne draw_oval ; bra
colorlookup:
.byte $11,$55,$5d,$7f,$5d,$55,$11 ; use 00 from sinetable
;.byte $00
sinetable_base:
; this is actually (32*sin(x))
.byte $00,$03,$06,$09,$0C,$0F,$11,$14
.byte $16,$18,$1A,$1C,$1D,$1E,$1F,$1F
.byte $20
;,$1F,$1F,$1E,$1D,$1C,$1A,$18
;.byte $16,$14,$11,$0F,$0C,$09,$06,$03
; for bot
; 3F5 - 7d = 378
jmp oval
sinetable=$6000
gbasl = $6100
gbash = $6200

179
graphics/hgr/plasma/zebra.s Normal file
View File

@ -0,0 +1,179 @@
; Ovals
; inner loop after lots of ops = 49 cycles (376320) = 2.6fps
; optimized to 38 (256-entry sine table) = (291840) = 3.4fps
; optimized to 37 (row_sum smc) = (284160) = 3.5fps
; zero page
GBASL = $26
GBASH = $27
YY = $69
ROW_SUM = $70
HGR_X = $E0
HGR_XH = $E1
HGR_Y = $E2
HGR_COLOR = $E4
HGR_PAGE = $E6
FRAME = $FC
SUM = $FD
SAVEX = $FE
SAVEY = $FF
; soft-switches
FULLGR = $C052
PAGE1 = $C054
; ROM routines
HGR2 = $F3D8
HPOSN = $F411 ; (Y,X),(A) (values stores in HGRX,XH,Y)
;================================
; Clear screen and setup graphics
;================================
oval:
jsr HGR2 ; set hi-res 140x192, page2, fullscreen
;====================
; create sinetable
ldy #0
sinetable_loop:
tya ; 2
and #$3f ; wrap sine at 63 entries ; 2
cmp #$20
php ; save pos/negative for later
and #$1f
cmp #$10
bcc sin_left
sin_right:
; sec carry should be set?
eor #$FF
adc #$20 ; 32-X
sin_left:
tax
lda sinetable_base,X ; 4+
plp
bcc sin_done
sin_negate:
; carry set here
eor #$ff
adc #0
sin_done:
sta sinetable,Y
iny
bne sinetable_loop
; NOTE: making gbash/gbasl table wasn't worth it
;============================
; main loop
;============================
draw_oval:
inc FRAME
ldx #191 ; YY
stx HGR_Y
create_yloop:
lda HGR_Y
ldx #39
ldy #0
jsr HPOSN ; (Y,X),(A) (values stores in HGRX,XH,Y)
; restore values
ldy #39 ; XX
lda HGR_Y ; YY
calcsine_div2:
lsr ; 2
tax
clc
lda sinetable,X
adc FRAME
sta row_sum_smc+1
ldx HGR_Y ; YY
create_xloop:
;=====================
; critical inner loop
; every cycle here is 40x192 cycles
;=====================
lda sinetable,Y ; 4+
clc ; 2
row_sum_smc:
adc #$dd ; row base value ; 2
; lsr ; double colors ; 2
and #$fe ; mask ; 2
tax ; 2
lda colorlookup,X ; lookup in table ; 5
ror_nop_smc:
ror ; $6A/$EA ; 2
; and #$7f ; make all purple
sta (GBASL),Y ; 6
lda ror_nop_smc ; toggle ror/nop ; 4
eor #$80 ; 2
sta ror_nop_smc ; 4
dey ; 2
bpl create_xloop ; 2/3
dec HGR_Y
bne create_yloop
; we skip drawing line 0 as it makes it easier
beq draw_oval
colorlookup:
.byte $11,$11,$55,$55,$5d,$5d
.byte $7f,$7f,$5d,$5d,$55,$55
.byte $11,$11,$00 ; use 00 from sinetable
;.byte $00
;.byte $11,$55,$5d,$7f,$5d,$55,$11 ; use 00 from sinetable
;.byte $00
sinetable_base:
; this is actually (32*sin(x))
.byte $00,$03,$06,$09,$0C,$0F,$11,$14
.byte $16,$18,$1A,$1C,$1D,$1E,$1F,$1F
.byte $20
;,$1F,$1F,$1E,$1D,$1C,$1A,$18
;.byte $16,$14,$11,$0F,$0C,$09,$06,$03
; for bot
jmp oval
sinetable=$6000
gbasl = $6100
gbash = $6200

View File

@ -0,0 +1,12 @@
MEMORY {
ZP: start = $00, size = $1A, type = rw;
RAM: start = $378, size = $8E00, file = %O;
}
SEGMENTS {
CODE: load = RAM, type = ro;
RODATA: load = RAM, type = ro;
DATA: load = RAM, type = rw;
BSS: load = RAM, type = bss, define = yes;
ZEROPAGE: load = ZP, type = zp;
}