diff --git a/graphics/gr/plasma/Makefile b/graphics/gr/plasma/Makefile index b9dd9c2f..b0fd1fef 100644 --- a/graphics/gr/plasma/Makefile +++ b/graphics/gr/plasma/Makefile @@ -6,10 +6,11 @@ LINKERSCRIPTS = ../../../linker_scripts all: plasma.dsk -plasma.dsk: HELLO PLASMA PLASMA_TINY PLASMA_BOT WIRES WIRES_BOT +plasma.dsk: HELLO PLASMA PLASMA_128 PLASMA_TINY PLASMA_BOT WIRES WIRES_BOT cp empty.dsk plasma.dsk $(DOS33) -y plasma.dsk SAVE A HELLO - $(DOS33) -y plasma.dsk BSAVE -a 0x300 PLASMA + $(DOS33) -y plasma.dsk BSAVE -a 0x70 PLASMA + $(DOS33) -y plasma.dsk BSAVE -a 0x70 PLASMA_128 $(DOS33) -y plasma.dsk BSAVE -a 0xC00 PLASMA_TINY $(DOS33) -y plasma.dsk BSAVE -a 0x36B PLASMA_BOT $(DOS33) -y plasma.dsk BSAVE -a 0xC00 WIRES @@ -23,13 +24,22 @@ HELLO: hello.bas ### PLASMA: plasma.o - ld65 -o PLASMA plasma.o -C $(LINKERSCRIPTS)/apple2_300.inc + ld65 -o PLASMA plasma.o -C ./apple2_70_zp.inc plasma.o: plasma.s ca65 -o plasma.o plasma.s -l plasma.lst ### +PLASMA_128: plasma_128.o + ld65 -o PLASMA_128 plasma_128.o -C ./apple2_70_zp.inc + +plasma_128.o: plasma_128.s + ca65 -o plasma_128.o plasma_128.s -l plasma_128.lst + + +### + PLASMA_BOT: plasma_bot.o ld65 -o PLASMA_BOT plasma_bot.o -C ./apple2_36b.inc @@ -67,4 +77,4 @@ wires_bot.o: wires_bot.s ### clean: - rm -f *~ *.o *.lst PLASMA PLASMA_TINY PLASMA_BOT WIRES WIRES_BOT + rm -f *~ *.o *.lst PLASMA PLASMA_128 PLASMA_TINY PLASMA_BOT WIRES WIRES_BOT diff --git a/graphics/gr/plasma/apple2_70_zp.inc b/graphics/gr/plasma/apple2_70_zp.inc new file mode 100644 index 00000000..9737f2d1 --- /dev/null +++ b/graphics/gr/plasma/apple2_70_zp.inc @@ -0,0 +1,12 @@ +MEMORY { + ZP: start = $70, size = $90, type = rw; + RAM: start = $70, 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 = ro; +} diff --git a/graphics/gr/plasma/plasma.s b/graphics/gr/plasma/plasma.s index b859a671..9c4830a3 100644 --- a/graphics/gr/plasma/plasma.s +++ b/graphics/gr/plasma/plasma.s @@ -18,13 +18,39 @@ ; 141 -- smc DRAW_PAGE ; 139 -- from qkumba, remove php/plp ; 138 -- from qkumba, remove SAVEX +; 133 -- run from zero page +; 132 -- make lookup 8*sin+7 +; 131 -- re-arrange sine table +; 128 -- call into PLOT for MASK seting +; 127 -- base YY<<16 by adding smc, not by shifting +; 125 -- realize that the top byte wraps so no need to and +; 124 -- re-arrange code to make an CLC unnecessary -; goal=135 +; urgh lovebyte wants 124 byte (counts header) -.include "zp.inc" -.include "hardware.inc" +; zero page +GBASL = $26 +GBASH = $27 +MASK = $2E +COLOR = $30 +;CTEMP = $68 +YY = $69 + +; soft-switches +FULLGR = $C052 +PAGE1 = $C054 + +; ROM routines +PLOT1 = $F80E ;; PLOT at (GBASL),Y (need MASK to be $0f or $f0) +GBASCALC= $F847 ;; take Y-coord/2 in A, put address in GBASL/H ( a trashed, C clear) +SETCOL = $F864 ;; COLOR=A*17 +SETGR = $FB40 + + +.zeropage + +.globalzp colorlookup,plot_lookup_smc,draw_page_smc,frame_smc,sinetable -CTEMP = $FC ;================================ ; Clear screen and setup graphics @@ -42,25 +68,27 @@ plasma: ; we only create a 16x16 texture, which we pattern across 40x48 screen + + ; I've tried re-optimizing this about 10 different ways + ; and it never ends up shorter + create_lookup: - ldy #15 -create_yloop: ldx #15 +create_yloop: + ldy #15 create_xloop: - clc - lda #15 ; 8+8 (but 15 works better) - adc sinetable,X - adc sinetable,Y + sec + lda sinetable,X + adc sinetable,Y ; 15+sin(x)+sin(y) lsr lookup_smc: sta lookup ; always starts at $d00 - inc lookup_smc+1 - dex + dey bpl create_xloop - dey + dex bpl create_yloop ; X and Y both $FF @@ -70,34 +98,30 @@ create_lookup_done: forever_loop: cycle_colors: + ; cycle colors + ; instead of advancing entire frame, do slightly slower route + ; instead now and just incrememnting the frame and doing the + ; adjustment at plot time. - ; can't do palette rotate on Apple II so faking it here - ; just incrementing every entry in texture by 1 - - ; X if $FF when arriving here -; ldx #0 - inx ; make X 0 -cycle_loop: - inc lookup,X - inx - bne cycle_loop - - + ; increment frame + inc frame_smc+1 ; set/flip pages ; we want to flip pages and then draw to the offscreen one flip_pages: -; ldx #0 ; x already 0 +; ldy #0 + + iny ; y is $FF, make it 0 lda draw_page_smc+1 ; DRAW_PAGE beq done_page - inx + iny done_page: - ldy PAGE0,X ; set display page to PAGE1 or PAGE2 + ldx PAGE1,Y ; set display page to PAGE1 or PAGE2 eor #$4 ; flip draw page between $400/$800 sta draw_page_smc+1 ; DRAW_PAGE @@ -109,26 +133,13 @@ done_page: plot_frame: ldx #47 ; YY=47 (count backwards) - plot_yloop: - txa ; get (y&0xf)<<4 - pha ; save YY - asl - asl - asl - asl - sta CTEMP ; save for later - - txa ; get Y in accumulator + txa ; get YY into A + pha ; save X for later lsr ; call actually wants Ycoord/2 - - ldy #$0f ; setup mask for odd/even line - bcc plot_mask - ldy #$f0 ; needlessly clever, from monitor rom src -plot_mask: - sty MASK + php ; save C flag for mask handling ; ugh can't use PLOT trick as it always will draw something ; to PAGE1 even if we don't want to @@ -141,34 +152,43 @@ draw_page_smc: adc #0 sta GBASH - + ; increment YY in top nibble of lookup for (yy<<16)+xx + ; clc from above, C always 0 + lda plot_lookup_smc+1 + adc #$10 ; no need to mask as it will oflo and be ignored + sta plot_lookup_smc+1 ;========== ldy #39 ; XX = 39 (countdown) + ; sets MASK by calling into middle of PLOT routine + ; by Y being 39 draw in a spot that gets over-written + + plp + jsr $f806 + plot_xloop: - tya ; get x&0xf + tya ; get XX & 0x0f and #$f - ora CTEMP ; combine with val from earlier - ; get ((y&0xf)*16)+x - tax -plot_lookup: - -; sta plot_lookup_smc+1 - plot_lookup_smc: - lda lookup,X ; load lookup, (y*16)+x -; lda lookup ; load lookup, (y*16)+x + lda lookup,X ; load lookup, (YY*16)+XX + + clc +frame_smc: + adc #$00 ; add in frame and #$f lsr ; we actually only have 8 colors tax + lda colorlookup,X ; lookup color + + sta COLOR ; each nibble should be same jsr PLOT1 ; plot at GBASL,Y (x co-ord goes in Y) @@ -178,29 +198,28 @@ plot_lookup_smc: pla ; restore YY tax - dex bpl plot_yloop bmi forever_loop colorlookup: -bw_color_lookup: + ; blue .byte $55,$22,$66,$77,$ff,$77,$55 ; ,$00 shared w sin table -; pink -;.byte $55,$11,$33,$bb,$ff,$bb,$55 ; ,$00 shared w sin table -; this is actually 8*sin(x) + sinetable: -.byte $00,$03,$05,$07,$08,$07,$05,$03 -.byte $00,$FD,$FB,$F9,$F8,$F9,$FB,$FD +; this is actually (8*sin(x))+7 +; re-arranged so starts with $00 for colorlookup overlap +.byte $00,$FF +HACK: ; use the $0200 here for (HACK),Y addressing? + ; in the end no way to get Y set properly +.byte $00,$02,$04 +.byte $07,$0A,$0C,$0E,$0F,$0E,$0C,$0A +.byte $07,$04,$02 -;colorlookup: -;.byte $00,$00,$05,$05,$07,$07,$0f,$0f -;.byte $07,$07,$06,$06,$02,$02,$05,$05 -;.byte $00,$55,$77,$ff,$77,$66,$22,$55 ; make lookup happen at page boundary -.org $d00 +.org $200 lookup: diff --git a/graphics/gr/plasma/plasma_128.s b/graphics/gr/plasma/plasma_128.s new file mode 100644 index 00000000..063c7db1 --- /dev/null +++ b/graphics/gr/plasma/plasma_128.s @@ -0,0 +1,221 @@ +; do a (hopefully fast) plasma type demo + +; 151 -- original +; 137 -- optimize generation +; 136 -- align lookup table so we can index it easier +; 130 -- optimize indexing of lookup +; 126 -- run loops backaward +; 124 -- notice X already 0 before plot +; 131 -- use GBASCALC. much faster, but 7 bytes larger +; 129 -- run loop backwards +; 128 -- set color ourselves +; 127 -- overlap color lookup with sine table +; 119 -- forgot to comment out unused +; 121 -- make it use full screen (40x48) + +; 149 -- add page flipping +; 144 -- optimize a bit +; 141 -- smc DRAW_PAGE +; 139 -- from qkumba, remove php/plp +; 138 -- from qkumba, remove SAVEX +; 133 -- run from zero page +; 132 -- make lookup 8*sin+7 +; 131 -- re-arrange sine table +; 128 -- call into PLOT for MASK seting + +; urgh lovebyte wants 124 byte (counts header) + +; zero page +GBASL = $26 +GBASH = $27 +MASK = $2E +COLOR = $30 +CTEMP = $68 + +; soft-switches +FULLGR = $C052 +PAGE0 = $C054 + +; ROM routines +PLOT1 = $F80E ;; PLOT at (GBASL),Y (need MASK to be $0f or $f0) +GBASCALC= $F847 ;; take Y-coord/2 in A, put address in GBASL/H ( a trashed, C clear) +SETCOL = $F864 ;; COLOR=A*17 +SETGR = $FB40 + + +.zeropage + +.globalzp sinetable,colorlookup,draw_page_smc + + ;================================ + ; Clear screen and setup graphics + ;================================ +plasma: + + jsr SETGR ; set lo-res 40x40 mode + bit FULLGR ; make it 40x48 + + + +; color = ( 8.0 + 8*sin(x) + 8.0 + 8*sin(y) )/2 +; becomes +; color = ( 16 + (sintable[xx&0xf]) + (sintable[yy&0xf])) / 2; + + ; we only create a 16x16 texture, which we pattern across 40x48 screen + + +create_lookup: + ldy #15 +create_yloop: + ldx #15 +create_xloop: + sec + lda sinetable,X + adc sinetable,Y ; 15+sin(x)+sin(y) + lsr +lookup_smc: + sta lookup ; always starts at $d00 + inc lookup_smc+1 + + dex + bpl create_xloop + + dey + bpl create_yloop + + + ; X and Y both $FF + +create_lookup_done: + +forever_loop: + +cycle_colors: + ; cycle colors + + ; can't do palette rotate on Apple II so faking it here + ; just incrementing every entry in texture by 1 + + ; X if $FF when arriving here +; ldx #0 + inx ; make X 0 +cycle_loop: + inc lookup,X + inx + bne cycle_loop + + + + + ; set/flip pages + ; we want to flip pages and then draw to the offscreen one + +flip_pages: + +; ldx #0 ; x already 0 + + lda draw_page_smc+1 ; DRAW_PAGE + beq done_page + inx +done_page: + ldy PAGE0,X ; set display page to PAGE1 or PAGE2 + + eor #$4 ; flip draw page between $400/$800 + sta draw_page_smc+1 ; DRAW_PAGE + + + ; plot current frame + ; scan whole 40x48 screen and plot each point based on + ; lookup table colors +plot_frame: + + ldx #47 ; YY=47 (count backwards) + +plot_yloop: + + txa ; get (y&0xf)<<4 + pha ; save YY + asl + asl + asl + asl + sta CTEMP ; save for later + + txa ; get Y in accumulator + lsr ; call actually wants Ycoord/2 + + php ; save C flag for mask handling + + ; ugh can't use PLOT trick as it always will draw something + ; to PAGE1 even if we don't want to + + jsr GBASCALC ; point GBASL/H to address in (A is ycoord/2) + ; after, A is GBASL, C is clear + + lda GBASH ; adjust to be PAGE1/PAGE2 ($400 or $800) +draw_page_smc: + adc #0 + sta GBASH + + + + ;========== + + ldy #39 ; XX = 39 (countdown) + + ; sets MASK by calling into middle of PLOT routine + ; by Y being 39 draw in a spot that gets over-written + + plp + jsr $f806 + +plot_xloop: + + tya ; get x&0xf + and #$f + ora CTEMP ; combine with val from earlier + ; get ((y&0xf)*16)+x + + tax + +plot_lookup: +plot_lookup_smc: + lda lookup,X ; load lookup, (y*16)+x + + and #$f + lsr ; we actually only have 8 colors + + tax + lda colorlookup,X ; lookup color + sta COLOR ; each nibble should be same + + jsr PLOT1 ; plot at GBASL,Y (x co-ord goes in Y) + + dey + bpl plot_xloop + + pla ; restore YY + tax + + dex + bpl plot_yloop + bmi forever_loop + +colorlookup: + +; blue +.byte $55,$22,$66,$77,$ff,$77,$55 ; ,$00 shared w sin table + + +sinetable: +; this is actually (8*sin(x))+7 +; re-arranged so starts with $00 for colorlookup overlap +.byte $00,$FF,$00,$02,$04 +.byte $07,$0A,$0C,$0E,$0F,$0E,$0C,$0A +.byte $07,$04,$02 + + +; make lookup happen at page boundary + +.org $d00 +lookup: diff --git a/graphics/gr/sier/Makefile b/graphics/gr/sier/Makefile index 17f2f53a..7682dd82 100644 --- a/graphics/gr/sier/Makefile +++ b/graphics/gr/sier/Makefile @@ -6,11 +6,12 @@ LINKERSCRIPTS = ../../../linker_scripts all: sier.dsk -sier.dsk: HELLO SIER SIER_TINY +sier.dsk: HELLO SIER SIER_TINY SIER_64 cp empty.dsk sier.dsk $(DOS33) -y sier.dsk SAVE A HELLO $(DOS33) -y sier.dsk BSAVE -a 0x36C SIER $(DOS33) -y sier.dsk BSAVE -a 0x300 SIER_TINY + $(DOS33) -y sier.dsk BSAVE -a 0x300 SIER_64 ### @@ -33,8 +34,17 @@ SIER_TINY: sier_tiny.o sier_tiny.o: sier_tiny.s ca65 -o sier_tiny.o sier_tiny.s -l sier_tiny.lst +### + +SIER_64: sier_64.o + ld65 -o SIER_64 sier_64.o -C $(LINKERSCRIPTS)/apple2_300.inc + +sier_64.o: sier_64.s + ca65 -o sier_64.o sier_64.s -l sier_64.lst + + ### clean: - rm -f *~ *.o *.lst HELLO SIER SIER_TINY + rm -f *~ *.o *.lst HELLO SIER SIER_TINY SIER_64 diff --git a/graphics/gr/sier/sier_64.s b/graphics/gr/sier/sier_64.s new file mode 100644 index 00000000..e1320e3c --- /dev/null +++ b/graphics/gr/sier/sier_64.s @@ -0,0 +1,94 @@ +; fake sierpinski + +; scrolling and colors + +; by Vince `deater` Weaver, dSr, Lovebyte 2021 + +; just plot XX AND YY + +; zero page +COLOR = $30 +XX = $66 +YY = $67 +FRAME = $68 +;X2 = $69 + +; soft-switches +FULLGR = $C052 + +; rom routines +PLOT = $F800 ;; PLOT AT Y,A +PLOT1 = $F80E ;; PLOT at (GBASL),Y (need MASK to be $0f or $f0) +SETCOL = $F864 ;; COLOR=A +SETGR = $FB40 + + ;================================ + ; Clear screen and setup graphics + ;================================ +sier: + + jsr SETGR ; set lo-res 40x40 mode + bit FULLGR ; make it 40x48 + + lda #0 + sta FRAME + +sier_loop: + + inc FRAME + + ldx #47 ; YY + +sier_yloop: + + lda #39 + sta XX + + tay + txa + jsr PLOT ; PLOT AT Y,A + ; sets GBASL/GBASH and MASK + +sier_xloop: + + txa + clc + adc FRAME + +; sta X2 +; lda XX +; adc FRAME +; and X2 + + and XX + + bne black +; lda #$11 ; red + lda FRAME + lsr + lsr + lsr + lsr + bne not_zero + lda #3 + +not_zero: + + .byte $2C ; bit trick +black: + lda #$00 +; sta COLOR + jsr SETCOL + + ldy XX + txa + jsr PLOT1 ; PLOT AT (GBASL),Y + + dec XX + bpl sier_xloop + + dex + bpl sier_yloop + +done: + bmi sier_loop diff --git a/graphics/hgr/sprite/apple2_36b.inc b/graphics/hgr/sprite/apple2_36b.inc new file mode 100644 index 00000000..ac221fa9 --- /dev/null +++ b/graphics/hgr/sprite/apple2_36b.inc @@ -0,0 +1,12 @@ +MEMORY { + ZP: start = $00, size = $1A, type = rw; + RAM: start = $36B, size = $8E00, file = %O; +} + +SEGMENTS { +CODE: load = RAM, type = ro, align = $1; +RODATA: load = RAM, type = ro; +DATA: load = RAM, type = rw; +BSS: load = RAM, type = bss, define = yes; +ZEROPAGE: load = ZP, type = zp; +}