diff --git a/gr-sim/gr-sim.c b/gr-sim/gr-sim.c index a7a54aac..61abdbfb 100644 --- a/gr-sim/gr-sim.c +++ b/gr-sim/gr-sim.c @@ -595,3 +595,68 @@ int basic_vlin(int y1, int y2, int at) { return 0; } + + +short gr_addr_lookup[48]={ + 0x400,0x480,0x500,0x580,0x600,0x680,0x700,0x780, + 0x428,0x4a8,0x528,0x5a8,0x628,0x6a8,0x728,0x7a8, + 0x450,0x4d0,0x550,0x5d0,0x650,0x6d0,0x750,0x7d0, +}; + +int grsim_put_sprite(unsigned char *sprite_data, int xpos, int ypos) { + + unsigned char i; + unsigned char *ptr; + short address; + + ptr=sprite_data; + x=*ptr; + ptr++; + ram[CV]=*ptr; + ptr++; + + while(1) { + address=gr_addr_lookup[ypos/2]; + address+=xpos; + for(i=0;i0) y-=2; + if (ch=='m') if (y<39) y+=2; + if (ch=='j') if (x>0) x--; + if (ch=='k') if (x<39) x++; + + gr_copy(0x800,0x400); + grsim_put_sprite(test_sprite,x,y); + + grsim_update(); usleep(100000); } diff --git a/tfv/Makefile b/tfv/Makefile index e68266d5..7718061b 100644 --- a/tfv/Makefile +++ b/tfv/Makefile @@ -6,12 +6,12 @@ PNG2GR = ../gr-utils/png2gr all: tfv.dsk tfv.dsk: TITLE.GR TFV ED - $(DOS33) -y tfv.dsk BSAVE -a 0xc00 TFV + $(DOS33) -y tfv.dsk BSAVE -a 0x1000 TFV $(DOS33) -y tfv.dsk BSAVE -a 0x400 TITLE.GR $(DOS33) -y tfv.dsk BSAVE -a 0x900 ED TFV: tfv.o - ld65 -o TFV tfv.o -C ./apple2_c00.inc + ld65 -o TFV tfv.o -C ./apple2_1000.inc tfv.o: tfv.s title.inc ca65 -o tfv.o tfv.s -l tfv.lst @@ -27,3 +27,4 @@ TITLE.GR: title.png clean: rm -f *~ TITLE.GR *.o *.lst ED + diff --git a/tfv/apple2_1000.inc b/tfv/apple2_1000.inc new file mode 100644 index 00000000..e22976de --- /dev/null +++ b/tfv/apple2_1000.inc @@ -0,0 +1,12 @@ +MEMORY { + ZP: start = $00, size = $1A, type = rw; + RAM: start = $1000, 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; +} diff --git a/tfv/tfv.dsk b/tfv/tfv.dsk index 7dbb5d54..4d50fb8f 100644 Binary files a/tfv/tfv.dsk and b/tfv/tfv.dsk differ diff --git a/tfv/tfv.s b/tfv/tfv.s index 7ee52448..c26d4c51 100644 --- a/tfv/tfv.s +++ b/tfv/tfv.s @@ -1,14 +1,22 @@ .define EQU = +KEYPRESS EQU $C000 +KEYRESET EQU $C010 + ;; SOFT SWITCHES -GR EQU $C050 -TEXT EQU $C051 -FULLGR EQU $C052 -TEXTGR EQU $C053 -PAGE0 EQU $C054 -PAGE1 EQU $C055 -LORES EQU $C056 -HIRES EQU $C057 +GR EQU $C050 +TEXT EQU $C051 +FULLGR EQU $C052 +TEXTGR EQU $C053 +PAGE0 EQU $C054 +PAGE1 EQU $C055 +LORES EQU $C056 +HIRES EQU $C057 + +PADDLE_BUTTON0 EQU $C061 +PADDL0 EQU $C064 +PTRIG EQU $C070 + ;; MONITOR ROUTINES HLINE EQU $F819 ;; HLINE Y,$2C at A @@ -38,11 +46,20 @@ H2 EQU $2C V2 EQU $2D MASK EQU $2E COLOR EQU $30 -FIRST EQU $F0 -TEMP EQU $FA -RUN EQU $FA -TEMP2 EQU $FB +FIRST EQU $F0 +LASTKEY EQU $F1 +PADDLE_STATUS EQU $F2 +XPOS EQU $F3 +YPOS EQU $F4 +TEMP EQU $FA +RUN EQU $FA +TEMP2 EQU $FB +TEMPY EQU $FB +INL EQU $FC +INH EQU $FD +OUTL EQU $FE +OUTH EQU $FF ;============================= ; set low-res graphics, page 0 @@ -55,6 +72,10 @@ TEMP2 EQU $FB ;================= jsr CLRTOP + lda #$c + sta BASH + lda #$0 + sta BASL ; load image off-screen 0xc00 lda #>(title_image) sta GBASH @@ -62,14 +83,71 @@ TEMP2 EQU $FB sta GBASL jsr load_rle_gr + jsr gr_copy + + lda #20 + sta YPOS + lda #20 + sta XPOS + +main_loop: + + jsr gr_copy + + jsr put_sprite + + jsr wait_until_keypressed + + lda LASTKEY + + cmp #('Q') + beq exit + + cmp #('I') + bne check_down + dec YPOS + dec YPOS + +check_down: + cmp #('M') + bne check_left + inc YPOS + inc YPOS + +check_left: + cmp #('J') + bne check_right + dec XPOS + +check_right: + cmp #('K') + bne check_done + inc XPOS + +check_done: + jmp main_loop + + + +exit: + lda #$4 sta BASH lda #$0 - sta BASL ; 0x400 is GR page 0 + sta BASL ; restore to 0x400 (page 0) + ; copy to 0x400 (page 0) + + ; call home + jsr HOME + ; Return to BASIC? rts +;===================================================================== +;= ROUTINES +;===================================================================== + ;================= ; load RLE image ;================= @@ -188,4 +266,261 @@ set_gr_page0: bit GR ; set graphics rts + ;========================================================= + ; gr_copy + ;========================================================= + ; for now copy 0xc00 to 0x400 + ; 2 + 8*38 + 4*80*23 + 4*120*26 + 13 = 20,159 = 20ms = 50Hz + ; +gr_copy: + ldx #0 ; set y to zero ; 2 + +gr_copy_loop: + stx TEMP ; save y ; 3 + txa ; move to A ; 2 + asl ; mult by 2 ; 2 + tay ; put into Y ; 2 + lda gr_offsets,Y ; lookup low byte for line addr ; 5 + sta OUTL ; out and in are the same ; 3 + sta INL ; 3 + lda gr_offsets+1,Y ; lookup high byte for line addr ; 5 + sta OUTH ; 3 + adc #$8 ; for now, fixed 0xc ; 2 + sta INH ; 3 + ldx TEMP ; restore y ; 3 + + ldy #0 ; set X counter to 0 ; 2 +gr_copy_line: + lda (INL),Y ; load a byte ; 5 + sta (OUTL),Y ; store a byte ; 6 + iny ; increment pointer ; 2 + + cpx #$4 ; don't want to copy bottom 4*40 ; 2 + bcs gr_copy_above4 ; 3 + +gr_copy_below4: + cpy #120 ; for early ones, copy 120 bytes ; 2 + bne gr_copy_line ; 3 + beq gr_copy_line_done ; 3 + +gr_copy_above4: ; for last four, just copy 80 bytes + cpy #80 ; 2 + bne gr_copy_line ; 3 + +gr_copy_line_done: + inx ; increment y value ; 2 + cpx #8 ; there are 8 of them ; 2 + bne gr_copy_loop ; if not, loop ; 3 + rts ; 6 + + ;========================================================== + ; Wait until keypressed + ;========================================================== + ; + +wait_until_keypressed: + lda KEYPRESS ; check if keypressed + bpl wait_until_keypressed ; if not, loop + jmp figure_out_key + + + ;========================================================== + ; Get Key + ;========================================================== + ; + +get_key: + +check_paddle_button: + + ; check for paddle button + + bit PADDLE_BUTTON0 + bpl no_button + lda #' '+128 + jmp save_key + +no_button: + lda KEYPRESS + bpl no_key + +figure_out_key: + cmp #' '+128 ; the mask destroys space + beq save_key ; so handle it specially + + and #$5f ; mask, to make upper-case +check_right_arrow: + cmp #$15 + bne check_left_arrow + lda #'K' +check_left_arrow: + cmp #$08 + bne check_up_arrow + lda #'J' +check_up_arrow: + cmp #$0B + bne check_down_arrow + lda #'I' +check_down_arrow: + cmp #$0A + bne check_escape + lda #'M' +check_escape: + cmp #$1B + bne save_key + lda #'Q' + jmp save_key + +no_key: + bit PADDLE_STATUS + bpl no_key_store + + ; check for paddle action + ; code from http://web.pdx.edu/~heiss/technotes/aiie/tn.aiie.06.html + + inc PADDLE_STATUS + lda PADDLE_STATUS + and #$03 + beq check_paddles + jmp no_key_store + +check_paddles: + lda PADDLE_STATUS + and #$80 + sta PADDLE_STATUS + + ldx #$0 + LDA PTRIG ;TRIGGER PADDLES + LDY #0 ;INIT COUNTER + NOP ;COMPENSATE FOR 1ST COUNT + NOP +PREAD2: LDA PADDL0,X ;COUNT EVERY 11 uSEC. + BPL RTS2D ;BRANCH WHEN TIMED OUT + INY ;INCREMENT COUNTER + BNE PREAD2 ;CONTINUE COUNTING + DEY ;COUNTER OVERFLOWED +RTS2D: ;RETURN W/VALUE 0-255 + + cpy #96 + bmi paddle_left + cpy #160 + bmi no_key_store + lda #'K' + jmp save_key +paddle_left: + lda #'J' + jmp save_key + +no_key_store: + lda #0 ; no key, so save a zero + +save_key: + sta LASTKEY ; save the key to our buffer + bit KEYRESET ; clear the keyboard buffer + rts + + ;============================================= + ; put_sprite + ;============================================= +put_sprite: + + lda #>tb1_sprite ; hardcoded for tb1 for now + sta INH + lda #