From 51dd5e9a257b9a15d4234c8ad0d17a5a1b5f08df Mon Sep 17 00:00:00 2001 From: Vince Weaver Date: Wed, 25 Jul 2018 11:52:16 -0400 Subject: [PATCH] fancy_lores: loads at least. now to figre out vapor lock --- dither_lores/Makefile | 25 -- fancy_lores/Makefile | 37 ++ .../apple_40_48d.png | Bin {dither_lores => fancy_lores}/apple_40_96.png | Bin {dither_lores => fancy_lores}/apple_orig.jpg | Bin fancy_lores/disp4096.s | 351 ++++++++++++++++++ fancy_lores/fancy_lores_viewer.dsk | Bin 0 -> 143360 bytes {dither_lores => fancy_lores}/genpal.c | 0 fancy_lores/gr_copy.s | 59 +++ .../katahdin_40_48d.png | Bin .../katahdin_40_96.png | Bin .../katahdin_orig.jpg | Bin {dither_lores => fancy_lores}/loadpng.c | 0 {dither_lores => fancy_lores}/loadpng.h | 0 {dither_lores => fancy_lores}/png_to_40x96.c | 14 +- 15 files changed, 454 insertions(+), 32 deletions(-) delete mode 100644 dither_lores/Makefile create mode 100644 fancy_lores/Makefile rename {dither_lores => fancy_lores}/apple_40_48d.png (100%) rename {dither_lores => fancy_lores}/apple_40_96.png (100%) rename {dither_lores => fancy_lores}/apple_orig.jpg (100%) create mode 100644 fancy_lores/disp4096.s create mode 100644 fancy_lores/fancy_lores_viewer.dsk rename {dither_lores => fancy_lores}/genpal.c (100%) create mode 100644 fancy_lores/gr_copy.s rename {dither_lores => fancy_lores}/katahdin_40_48d.png (100%) rename {dither_lores => fancy_lores}/katahdin_40_96.png (100%) rename {dither_lores => fancy_lores}/katahdin_orig.jpg (100%) rename {dither_lores => fancy_lores}/loadpng.c (100%) rename {dither_lores => fancy_lores}/loadpng.h (100%) rename {dither_lores => fancy_lores}/png_to_40x96.c (97%) diff --git a/dither_lores/Makefile b/dither_lores/Makefile deleted file mode 100644 index e8ca51cd..00000000 --- a/dither_lores/Makefile +++ /dev/null @@ -1,25 +0,0 @@ -include ../Makefile.inc - -all: png_to_40x96 katahdin_40_96.inc - - -katahdin_40_96.inc: png_to_40x96 katahdin_40_96.png - ./png_to_40x96 asm katahdin_40_96.png katahdin > katahdin_40_96.inc - -loadpng.o: loadpng.c - $(CC) $(CFLAGS) -c loadpng.c - -png_to_40x96: png_to_40x96.o - $(CC) $(LFLAGS) -lpng -o png_to_40x96 png_to_40x96.o - -png_to_40x96.o: png_to_40x96.c - $(CC) $(CFLAGS) -c png_to_40x96.c - - -install: - cp png_to_40x96 $(INSTALL_LOC) - -clean: - rm -f *~ *.o *.inc png_to_40x96 - - diff --git a/fancy_lores/Makefile b/fancy_lores/Makefile new file mode 100644 index 00000000..03e03e54 --- /dev/null +++ b/fancy_lores/Makefile @@ -0,0 +1,37 @@ +include ../Makefile.inc + +DOS33 = ../dos33fs-utils/dos33 + +all: fancy_lores_viewer.dsk png_to_40x96 katahdin_40_96.inc + +fancy_lores_viewer.dsk: DISP4096 + $(DOS33) -y fancy_lores_viewer.dsk BSAVE -a 0x1000 DISP4096 + +DISP4096: disp4096.o + ld65 -o DISP4096 disp4096.o -C ../linker_scripts/apple2_1000.inc + + +disp4096.o: disp4096.s gr_copy.s \ + katahdin_40_96.inc + ca65 -o disp4096.o disp4096.s -l disp4096.lst + +katahdin_40_96.inc: png_to_40x96 katahdin_40_96.png + ./png_to_40x96 asm katahdin_40_96.png katahdin > katahdin_40_96.inc + +loadpng.o: loadpng.c + $(CC) $(CFLAGS) -c loadpng.c + +png_to_40x96: png_to_40x96.o + $(CC) $(LFLAGS) -lpng -o png_to_40x96 png_to_40x96.o + +png_to_40x96.o: png_to_40x96.c + $(CC) $(CFLAGS) -c png_to_40x96.c + + +install: + cp png_to_40x96 $(INSTALL_LOC) + +clean: + rm -f *~ *.o *.lst *.inc png_to_40x96 DISP4096 + + diff --git a/dither_lores/apple_40_48d.png b/fancy_lores/apple_40_48d.png similarity index 100% rename from dither_lores/apple_40_48d.png rename to fancy_lores/apple_40_48d.png diff --git a/dither_lores/apple_40_96.png b/fancy_lores/apple_40_96.png similarity index 100% rename from dither_lores/apple_40_96.png rename to fancy_lores/apple_40_96.png diff --git a/dither_lores/apple_orig.jpg b/fancy_lores/apple_orig.jpg similarity index 100% rename from dither_lores/apple_orig.jpg rename to fancy_lores/apple_orig.jpg diff --git a/fancy_lores/disp4096.s b/fancy_lores/disp4096.s new file mode 100644 index 00000000..ee2df55f --- /dev/null +++ b/fancy_lores/disp4096.s @@ -0,0 +1,351 @@ +; Display a 40x96 lo-res image + +; Uses the 40x96 page1/page2 every-2-scanline pageflip mode +; as shown in my kfest18 hackfest demo + +; by deater (Vince Weaver) + +; Zero Page +FRAMEBUFFER = $00 ; $00 - $0F +YPOS = $10 +YPOS_SIN = $11 +CH = $24 +CV = $25 +GBASL = $26 +GBASH = $27 +BASL = $28 +BASH = $29 +FRAME = $60 +BLARGH = $69 +DRAW_PAGE = $EE +LASTKEY = $F1 +PADDLE_STATUS = $F2 +TEMP = $FA + +; Soft Switches +KEYPRESS= $C000 +KEYRESET= $C010 +SET_GR = $C050 ; Enable graphics +FULLGR = $C052 ; Full screen, no text +PAGE0 = $C054 ; Page0 +PAGE1 = $C055 ; Page1 +LORES = $C056 ; Enable LORES graphics +PADDLE_BUTTON0 = $C061 +PADDL0 = $C064 +PTRIG = $C070 + +; ROM routines + +TEXT = $FB36 ;; Set text mode +HOME = $FC58 ;; Clear the text screen +WAIT = $FCA8 ;; delay 1/2(26+27A+5A^2) us + + + ;=================== + ; init screen + + jsr TEXT + jsr HOME + + ;=================== + ; init vars + + lda #0 + sta DRAW_PAGE + + ; Clear Page0 + lda #$00 + sta DRAW_PAGE + jsr clear_gr + + ; draw border line + +; lda #$55 +; ldy #38 +; jsr hline + + ; Clear Page1 + lda #$4 + sta DRAW_PAGE + lda #$0 + jsr clear_gr + + + ;================== + ; Draw Blue Border on screen + ;================== + ; F -> 7 -> 6 -> 2 + +; lda #$0 +; sta DRAW_PAGE +; lda #$6f +; ldy #0 +; jsr hline +; lda #$72 +; ldy #38 +; jsr hline + + +; lda #$4 +; sta DRAW_PAGE +; lda #$27 +; ldy #0 +; jsr hline +; lda #$f6 +; ldy #38 +; jsr hline + + ;============================= + ; Load graphic page0 + + lda #$0c + sta BASH + lda #$00 + sta BASL ; load image to page0 $400 + + lda #>(katahdin_low) + sta GBASH + lda #<(katahdin_low) + sta GBASL + jsr load_rle_gr + + lda #0 + sta DRAW_PAGE + + jsr gr_copy_to_current + + ; GR part + bit PAGE0 + bit LORES ; 4 + bit SET_GR ; 4 + bit FULLGR ; 4 + + jsr wait_until_keypressed + + + ;============================= + ; Load graphic page1 + + lda #$0c + sta BASH + lda #$00 + sta BASL ; load image to page0 $400 + + lda #>(katahdin_high) + sta GBASH + lda #<(katahdin_high) + sta GBASL + jsr load_rle_gr + + lda #4 + sta DRAW_PAGE + + jsr gr_copy_to_current + + ; GR part + bit PAGE1 + + jsr wait_until_keypressed + + + + ;===================================================== + ; attempt vapor lock + ; by reading the "floating bus" we can see most recently + ; written value of the display + ; we look for $55 (which is the grey line) + ;===================================================== + ; See: + ; Have an Apple Split by Bob Bishop + ; Softalk, October 1982 + + ; Challenges: each scan line scans 40 bytes. + ; The blanking happens at the *beginning* + ; So 65 bytes are scanned, starting at adress of the line - 25 + + ; the scan takes 8 cycles, look for 4 repeats of the value + ; to avoid false positive found if the horiz blanking is mirroring + ; the line (max 3 repeats in that case) + +vapor_lock_loop: ; first make sure we have all zeroes + LDA #$00 +zxloop: + LDX #$04 +wiloop: + CMP $C051 + BNE zxloop + DEX + BNE wiloop + + LDA #$72 ; now look for our border color (4 times) +zloop: + LDX #$04 +qloop: + CMP $C051 + BNE zloop + DEX + BNE qloop + + ; found first line of low-res grey, need to kill time + ; until we can enter at top of screen + ; so we want roughly 10 lines * 4 = 40*65 = 2600+4550-65 + ; +4550 - 65 (for the scanline we missed) = 7085 - 12 = 7073 + + + ; GR part + bit LORES ; 4 + bit SET_GR ; 4 + bit FULLGR ; 4 + + + ; want 7073 + ; Try X=26 Y=52 cycles=7073 + + lda #0 ; 2 + lda #0 ; 2 + + ldy #52 ; 2 +loopA: + ldx #26 ; 2 +loopB: + dex ; 2 + bne loopB ; 2nt/3 + + dey ; 2 + bne loopA ; 2nt/3 + + jmp display_loop +.align $100 + + + ;================================================ + ; Display Loop + ;================================================ + ; each scan line 65 cycles + ; 1 cycle each byte (40cycles) + 25 for horizontal + ; Total of 12480 cycles to draw screen + ; Vertical blank = 4550 cycles (70 scan lines) + ; Total of 17030 cycles to get back to where was + + ; We want to alternate between page1 and page2 every 65 cycles + ; vblank = 4550 cycles to do scrolling + + + ; 2 + 48*( (4+2+25*(2+3)) + (4+2+23*(2+3)+4+5)) + 9) + ; 48*[(6+125)-1] + [(6+115+10)-1] + +display_loop: + + ldy #48 ; 2 + +outer_loop: + + bit PAGE0 ; 4 + ldx #25 ; 130 cycles with PAGE0 ; 2 +page0_loop: ; delay 126+bit + dex ; 2 + bne page0_loop ; 2/3 + + + bit PAGE1 ; 4 + ldx #23 ; 130 cycles with PAGE1 ; 2 +page1_loop: ; delay 115+(7 loop)+4 (bit)+4(extra) + dex ; 2 + bne page1_loop ; 2/3 + + nop ; 2 + lda DRAW_PAGE ; 3 + + dey ; 2 + bne outer_loop ; 2/3 + + + + ;====================================================== + ; We have 4550 cycles in the vblank, use them wisely + ;====================================================== + ; scroll_the_text should be 4550+1 -2 - 13 -13 = 4523 + ; rasterbars should be 4550+1 -2 - 13 -18 = 4518 + ; do_nothing should be 4550+1 -2 - 13 -19 = 4517 + + jsr do_nothing ; 6 + jmp display_loop ; 3 + + + + ;================================= + ; do nothing + ;================================= + ; and take 4517-6 = 4511 cycles to do it +do_nothing: + ; Try X=7 Y=110 cycles=4511 + + ldy #110 ; 2 +loop1: + ldx #7 ; 2 +loop2: + dex ; 2 + bne loop2 ; 2nt/3 + + dey ; 2 + bne loop1 ; 2nt/3 + + + rts ; 6 + + + + ;================================== + ; HLINE + ;================================== + + ; Color in A + ; Y has which line +hline: + pha ; 3 + ldx gr_offsets,y ; 4+ + stx hline_loop+1 ; 4 + lda gr_offsets+1,y ; 4+ + clc ; 2 + adc DRAW_PAGE ; 3 + sta hline_loop+2 ; 4 + pla ; 4 + ldx #39 ; 2 +hline_loop: + sta $5d0,X ; 38 ; 5 + dex ; 2 + bpl hline_loop ; 2nt/3 + rts ; 6 + + ;========================== + ; Clear gr screen + ;========================== + ; Color in A +clear_gr: + ldy #46 +clear_page_loop: + jsr hline + dey + dey + bpl clear_page_loop + rts + + + + + + + + +gr_offsets: + .word $400,$480,$500,$580,$600,$680,$700,$780 + .word $428,$4a8,$528,$5a8,$628,$6a8,$728,$7a8 + .word $450,$4d0,$550,$5d0,$650,$6d0,$750,$7d0 + + +.include "../asm_routines/gr_unrle.s" +.include "../asm_routines/keypress.s" +.include "gr_copy.s" + +.include "katahdin_40_96.inc" + diff --git a/fancy_lores/fancy_lores_viewer.dsk b/fancy_lores/fancy_lores_viewer.dsk new file mode 100644 index 0000000000000000000000000000000000000000..3469203442d34bf132f44c3e4bf4472408d6aa5d GIT binary patch literal 143360 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 Wjd2tvrhNOF@m1`<@Hc7(vi*OkUqhS# literal 0 HcmV?d00001 diff --git a/dither_lores/genpal.c b/fancy_lores/genpal.c similarity index 100% rename from dither_lores/genpal.c rename to fancy_lores/genpal.c diff --git a/fancy_lores/gr_copy.s b/fancy_lores/gr_copy.s new file mode 100644 index 00000000..e8c2e8e7 --- /dev/null +++ b/fancy_lores/gr_copy.s @@ -0,0 +1,59 @@ + ;========================================================= + ; gr_copy_to_current, 40x48 version + ;========================================================= + ; copy 0xc00 to DRAW_PAGE + ; + ; 45 + 2 + 120*(8*9 + 5) -1 + 6 = 9292 + +gr_copy_to_current: + + lda DRAW_PAGE ; 3 + clc ; 2 + adc #$4 ; 2 + sta gr_copy_line+5 ; 4 + sta gr_copy_line+11 ; 4 + adc #$1 ; 2 + sta gr_copy_line+17 ; 4 + sta gr_copy_line+23 ; 4 + adc #$1 ; 2 + sta gr_copy_line+29 ; 4 + sta gr_copy_line+35 ; 4 + adc #$1 ; 2 + sta gr_copy_line+41 ; 4 + sta gr_copy_line+47 ; 4 + ;=========== + ; 45 + + ldy #119 ; for early ones, copy 120 bytes ; 2 + +gr_copy_line: + lda $C00,Y ; load a byte (self modified) ; 4 + sta $400,Y ; store a byte (self modified) ; 5 + + lda $C80,Y ; load a byte (self modified) ; 4 + sta $480,Y ; store a byte (self modified) ; 5 + + lda $D00,Y ; load a byte (self modified) ; 4 + sta $500,Y ; store a byte (self modified) ; 5 + + lda $D80,Y ; load a byte (self modified) ; 4 + sta $580,Y ; store a byte (self modified) ; 5 + + lda $E00,Y ; load a byte (self modified) ; 4 + sta $600,Y ; store a byte (self modified) ; 5 + + lda $E80,Y ; load a byte (self modified) ; 4 + sta $680,Y ; store a byte (self modified) ; 5 + + lda $F00,Y ; load a byte (self modified) ; 4 + sta $700,Y ; store a byte (self modified) ; 5 + + lda $F80,Y ; load a byte (self modified) ; 4 + sta $780,Y ; store a byte (self modified) ; 5 + + dey ; decrement pointer ; 2 + + + bpl gr_copy_line ; ; 2nt/3 + rts ; 6 + diff --git a/dither_lores/katahdin_40_48d.png b/fancy_lores/katahdin_40_48d.png similarity index 100% rename from dither_lores/katahdin_40_48d.png rename to fancy_lores/katahdin_40_48d.png diff --git a/dither_lores/katahdin_40_96.png b/fancy_lores/katahdin_40_96.png similarity index 100% rename from dither_lores/katahdin_40_96.png rename to fancy_lores/katahdin_40_96.png diff --git a/dither_lores/katahdin_orig.jpg b/fancy_lores/katahdin_orig.jpg similarity index 100% rename from dither_lores/katahdin_orig.jpg rename to fancy_lores/katahdin_orig.jpg diff --git a/dither_lores/loadpng.c b/fancy_lores/loadpng.c similarity index 100% rename from dither_lores/loadpng.c rename to fancy_lores/loadpng.c diff --git a/dither_lores/loadpng.h b/fancy_lores/loadpng.h similarity index 100% rename from dither_lores/loadpng.h rename to fancy_lores/loadpng.h diff --git a/dither_lores/png_to_40x96.c b/fancy_lores/png_to_40x96.c similarity index 97% rename from dither_lores/png_to_40x96.c rename to fancy_lores/png_to_40x96.c index 2015f1d7..ad1a6fb3 100644 --- a/dither_lores/png_to_40x96.c +++ b/fancy_lores/png_to_40x96.c @@ -103,7 +103,7 @@ int loadpng(char *filename, unsigned char **image_ptr, int *xsize, int *ysize, width = png_get_image_width(png_ptr, info_ptr); height = png_get_image_height(png_ptr, info_ptr); *xsize=width; - *ysize=height; + *ysize=height/2; color_type = png_get_color_type(png_ptr, info_ptr); bit_depth = png_get_bit_depth(png_ptr, info_ptr); @@ -137,7 +137,7 @@ int loadpng(char *filename, unsigned char **image_ptr, int *xsize, int *ysize, out_ptr=image; if (color_type==PNG_COLOR_TYPE_RGB_ALPHA) { - for(y=0;y