fn: making progress

This commit is contained in:
Vince Weaver 2023-05-02 00:50:49 -04:00
parent b462b2a3ca
commit b4c8a5ed5e
12 changed files with 437 additions and 82 deletions

View File

@ -34,11 +34,13 @@ sb.o: sb.s zx02_optim.s \
FN: fn.o
ld65 -o FN fn.o -C $(LINKER_SCRIPTS)/apple2_6000.inc
fn.o: fn.s zx02_optim.s \
fn.o: fn.s zx02_optim.s duet.s hgr_sprite_mask.s hgr_tables.s \
zp.inc hardware.inc \
fn_sound/fortnight.ed \
fn_graphics/a2_fortnight.hgr.zx02 \
fn_graphics/a2_fortnight_rat1.hgr.zx02 \
fn_graphics/a2_fortnight_rat2.hgr.zx02
fn_graphics/a2_fortnight_rat2.hgr.zx02 \
fn_graphics/disk_sprites.inc
ca65 -o fn.o fn.s -l fn.lst

View File

@ -1,3 +1,5 @@
; hacked up to switch pages
; ***************************************************************************
; * Copyright (C) 1979-2015 by Paul Lutus *
; * http://arachnoid.com/administration *
@ -33,9 +35,11 @@ MADDRL = $1E
MADDRH = $1F
LOC4E = $4E
COUNT256 = $4F
WHICH_PAGE = $50
play_ed:
LDA #$01 ; 900: A9 01 ; 2 *!*
sta WHICH_PAGE
STA INSTRUMENT1 ; 902: 85 09 ; 3 set default
STA INSTRUMENT2 ; 904: 85 1D ; 3 instruments
PHA ; 906: 48 ; 3 1 on stack
@ -44,13 +48,24 @@ play_ed:
BNE load_triplet ; 909: D0 15 ; 4 *!* start decoding
change_instrmnt:
INY ; 90B: C8 ; 2
LDA (MADDRL),Y ; 90C: B1 1E ; 5 *!* load next byte
bmi switch_page
STA INSTRUMENT1 ; 90E: 85 09 ; 3 save instrument
INY ; 910: C8 ; 2
LDA (MADDRL),Y ; 911: B1 1E ; 5 *!* load next byte
STA INSTRUMENT2 ; 913: 85 1D ; 3 save instrument
jmp triplet_loop
switch_page:
lda WHICH_PAGE
eor #$1
sta WHICH_PAGE
tax
lda PAGE1,X
triplet_loop:
LDA MADDRL ; 915: A5 1E ; 3 *!* increment pointer
CLC ; 917: 18 ; 2 by three
@ -130,8 +145,10 @@ label7:
BIT $C030 ; 96C: 2C 30C0 ; 4 SPEAKER
label9:
STA LOC4E ; 96F: 85 4E ; 3
BIT $C000 ; 971: 2C 00C0 ; 4 KEYBOARD DATA
BMI exit_player ; 974: 30 C0 ; 4 *!* if keypress, exit
DEY ; 976: 88 ; 2
BNE selfmodify2 ; 977: D0 02 ; 4 *!*
BEQ label11 ; 979: F0 06 ; 4 *!*

View File

@ -10,6 +10,11 @@
fortnight_start:
lda #$20
sta HGR_PAGE
jsr hgr_make_tables
;===================
; set graphics mode
;===================
@ -37,6 +42,23 @@ floppy_animation:
jsr full_decomp
lda #10
sta CURSOR_X
lda #10
sta CURSOR_Y
lda #<disk_sprite0
sta INL
lda #>disk_sprite0
sta INH
lda #<disk_mask0
sta MASKL
lda #>disk_mask0
sta MASKH
jsr hgr_draw_sprite
jsr wait_until_keypress
@ -60,15 +82,30 @@ load_rats:
jsr full_decomp
;=============================
; play music and animate rat
;=============================
play_music:
lda #<music
sta MADDRL
lda #>music
sta MADDRH
jsr play_ed
rat_loop:
bit PAGE1
jsr wait_until_keypress
bit PAGE2
; bit PAGE1
; jsr wait_until_keypress
; bit PAGE2
jsr wait_until_keypress
jmp rat_loop
; jmp rat_loop
jmp fortnight_start
wait_until_keypress:
@ -79,6 +116,14 @@ wait_until_keypress:
.include "zx02_optim.s"
.include "hgr_sprite_mask.s"
.include "hgr_tables.s"
.align $100
.include "duet.s"
music:
.incbin "fn_sound/fortnight.ed"
fn_image:
.incbin "fn_graphics/a2_fortnight.hgr.zx02"
@ -87,3 +132,4 @@ rat1_image:
rat2_image:
.incbin "fn_graphics/a2_fortnight_rat2.hgr.zx02"
.include "fn_graphics/disk_sprites.inc"

View File

@ -8,10 +8,35 @@ EMPTY_DISK = ../../../empty_disk/empty.dsk
TOKENIZE = ../../../utils/asoft_basic-utils/tokenize_asoft
PNG2GR = ../../../utils/gr-utils/png2gr
PNG2SPRITES = ../../../utils/gr-utils/png2sprites
HGR_SPRITE = ../../../utils/hgr-utils/hgr_make_sprite
all: a2_fortnight.hgr.zx02 \
a2_fortnight_rat1.hgr.zx02 \
a2_fortnight_rat2.hgr.zx02
a2_fortnight_rat2.hgr.zx02 \
disk_sprites.inc
####
disk_sprites.inc: a2_fortnight_sprites.png
$(HGR_SPRITE) -s -l disk_sprite0 a2_fortnight_sprites.png 14 7 41 34 > disk_sprites.inc
$(HGR_SPRITE) -s -l disk_sprite1 a2_fortnight_sprites.png 14 42 41 69 >> disk_sprites.inc
$(HGR_SPRITE) -s -l disk_sprite2 a2_fortnight_sprites.png 14 77 41 104 >> disk_sprites.inc
$(HGR_SPRITE) -s -l disk_sprite3 a2_fortnight_sprites.png 14 112 41 139 >> disk_sprites.inc
$(HGR_SPRITE) -s -l disk_mask0 a2_fortnight_sprites.png 56 7 83 34 >> disk_sprites.inc
$(HGR_SPRITE) -s -l disk_mask1 a2_fortnight_sprites.png 56 42 83 69 >> disk_sprites.inc
$(HGR_SPRITE) -s -l disk_mask2 a2_fortnight_sprites.png 56 77 83 104 >> disk_sprites.inc
$(HGR_SPRITE) -s -l disk_mask3 a2_fortnight_sprites.png 56 112 83 139 >> disk_sprites.inc
$(HGR_SPRITE) -s -l disk_sprite4 a2_fortnight_sprites.png 98 7 125 34 >> disk_sprites.inc
$(HGR_SPRITE) -s -l disk_sprite5 a2_fortnight_sprites.png 98 42 125 69 >> disk_sprites.inc
$(HGR_SPRITE) -s -l disk_sprite6 a2_fortnight_sprites.png 98 77 125 104 >> disk_sprites.inc
$(HGR_SPRITE) -s -l disk_sprite7 a2_fortnight_sprites.png 98 112 125 139 >> disk_sprites.inc
$(HGR_SPRITE) -s -l disk_mask4 a2_fortnight_sprites.png 140 7 167 34 >> disk_sprites.inc
$(HGR_SPRITE) -s -l disk_mask5 a2_fortnight_sprites.png 140 42 167 69 >> disk_sprites.inc
$(HGR_SPRITE) -s -l disk_mask6 a2_fortnight_sprites.png 140 77 167 104 >> disk_sprites.inc
$(HGR_SPRITE) -s -l disk_mask7 a2_fortnight_sprites.png 140 112 167 139 >> disk_sprites.inc
####
@ -42,5 +67,5 @@ a2_fortnight_rat2.hgr: a2_fortnight_rat2.png
####
clean:
rm -f *~ *.o *.lst
rm -f *~ *.o *.lst disk_sprintes.inc *.zx02 *.hgr

Binary file not shown.

Before

Width:  |  Height:  |  Size: 1.4 KiB

After

Width:  |  Height:  |  Size: 1.4 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 1.4 KiB

View File

@ -0,0 +1,86 @@
;===========================================
; hgr draw sprite (only at 7-bit boundaries)
;===========================================
; SPRITE in INL/INH
; Location at CURSOR_X CURSOR_Y
; xsize, ysize in first two bytes
; sprite AT INL/INH
hgr_draw_sprite:
ldy #0
lda (INL),Y ; load xsize
clc
adc CURSOR_X
sta sprite_width_end_smc+1 ; self modify for end of line
iny ; load ysize
lda (INL),Y
sta sprite_ysize_smc+1 ; self modify
; skip the xsize/ysize and point to sprite
clc
lda INL ; 16-bit add
adc #2
sta sprite_smc1+1
lda INH
adc #0
sta sprite_smc1+2
ldx #0 ; X is pointer offset
stx MASK ; actual row
hgr_sprite_yloop:
lda MASK ; row
clc
adc CURSOR_Y ; add in cursor_y
; calc GBASL/GBASH
tay ; get output ROW into GBASL/H
lda hposn_low,Y
sta GBASL
lda hposn_high,Y
; eor #$00 draws on page2
; eor #$60 draws on page1
hgr_sprite_page_smc:
eor #$00
sta GBASH
ldy CURSOR_X
sprite_inner_loop:
sprite_smc1:
lda $d000 ; get sprite pattern
sta (GBASL),Y ; store out
inx
iny
inc sprite_smc1+1
bne sprite_noflo
inc sprite_smc1+2
sprite_noflo:
sprite_width_end_smc:
cpy #6
bne sprite_inner_loop
inc MASK ; row
lda MASK ; row
sprite_ysize_smc:
cmp #31
bne hgr_sprite_yloop
rts

141
games/sb/hgr_tables.s Normal file
View File

@ -0,0 +1,141 @@
div7_table = $1000
mod7_table = $1100
hposn_high = $1200
hposn_low = $1300
;=====================
; make /7 %7 tables
;=====================
hgr_make_tables:
ldy #0
lda #0
ldx #0
div7_loop:
sta div7_table,Y
inx
cpx #7
bne div7_not7
clc
adc #1
ldx #0
div7_not7:
iny
bne div7_loop
ldy #0
lda #0
mod7_loop:
sta mod7_table,Y
clc
adc #1
cmp #7
bne mod7_not7
lda #0
mod7_not7:
iny
bne mod7_loop
; Hposn table
lda #0
hposn_loop:
ldy #0
ldx #0
pha
jsr hposn ; (Y,X),(A)
pla
tax
lda GBASL
sta hposn_low,X
lda GBASH
sta hposn_high,X
inx
txa
cmp #192
bne hposn_loop
rts
; left masks
; in memory on screen
; x111 1111 1111111 start at 0
; x111 1110 0111111 start at 1
; x111 1100 0011111 start at 2
; ...
; x100 0000 0000001 start at 6
left_masks:
.byte $FF,$FE,$FC,$F8, $F0,$E0,$C0
; right masks
; in memory on screen
; x000 0001 1000000 end at 0
; x000 0011 1100000 end at 1
; x000 0111 1110000 end at 2
; ...
; x011 1111 1111110 end at 5
; x111 1111 1111111 end at 6
right_masks:
.byte $81,$83,$87, $8F,$9F,$BF,$FF
; from the Apple II firmware
hposn:
; sta HGR_Y ; save Y and X positions
; stx HGR_X
; sty HGR_X+1
pha ; Y pos on stack
and #$C0 ; calc base addr for Y-pos
sta GBASL
lsr
lsr
ora GBASL
sta GBASL
pla
sta GBASH
asl
asl
asl
rol GBASH
asl
rol GBASH
asl
ror GBASL
lda GBASH
and #$1F
ora HGR_PAGE ; default is $40 in this game
sta GBASH
; txa
; cpy #0
; beq xpos_lessthan_256
; ldy #35
; adc #4
;label_1:
; iny
;xpos_lessthan_256:
; sbc #7
; bcs label_1
rts

View File

@ -66,4 +66,4 @@ which_ok:
comp_data:
.incbin "graphics/strongbad_sample.hgr.zx02"
.incbin "graphics/czmg4ap_title.hgr.zx02"

View File

@ -161,6 +161,9 @@ DRAW_PAGE = $EF
XPOS = $F0
YPOS = $F1
XMAX = $F2
CURSOR_X = $F3
CURSOR_Y = $F4
HGR_PAGE = $F5
TEMP = $F8
TEMPY = $F9

View File

@ -2,7 +2,7 @@ include ../../Makefile.inc
TOKENIZE = ../../utils/asoft_basic-utils/tokenize_asoft
DOS33 = ../../utils/dos33fs-utils/dos33
TEXT_TO_ED = ./text_to_ed
TEXT_TO_ED = ../../utils/music/text_to_ed
EMPTY_DISK = ../../empty_disk/empty.dsk
all: eduet.dsk
@ -81,17 +81,6 @@ korobeiniki.ed: $(TEXT_TO_ED) korobeiniki.txt
###
text_to_ed: text_to_ed.o notes.o
$(CC) -o text_to_ed text_to_ed.o notes.o $(LFLAGS) -lm
text_to_ed.o: text_to_ed.c notes.h
$(CC) $(CFLAGS) -c text_to_ed.c
notes.o: notes.c notes.h
$(CC) $(CFLAGS) -c notes.c
###
clean:
rm -f *~ *.o *.lst ED text_to_ed
rm -f *~ *.o *.lst ED

View File

@ -26,6 +26,7 @@
/* byte1 = voice1 instrument */
/* byte2 = voice2 instrument */
/* Varies, bigger than 8 seem to make no difference */
/* custom hack, negative means do action */
/* Otherwise, byte0 = duration (20=quarter, 40=half) */
/* byte1 = voice1 note */
@ -101,7 +102,6 @@ static int get_note(char *string, int sp, struct note_type *n, int line) {
int freq;
int ch;
// fprintf(stderr,"VMW: Entering, sp=%d\n",sp);
/* Skip white space */
while((string[sp]==' ' || string[sp]=='\t')) sp++;
@ -111,8 +111,6 @@ static int get_note(char *string, int sp, struct note_type *n, int line) {
/* return early if no change */
ch=string[sp];
// fprintf(stderr,"VMW: %d %d\n",ch,sp);
if (ch=='-') {
if (header_version==0) return sp+6;
else {
@ -198,6 +196,12 @@ static int get_string(char *string, char *key, char *output, int strip_linefeed)
}
static void update_voice(FILE *ed_file,int voice1,int voice2) {
fprintf(ed_file,"%c%c%c",1,voice1,voice2);
}
static void print_help(int just_version, char *exec_name) {
printf("\ntext_to_ed version %s by Vince Weaver <vince@deater.net>\n\n",VERSION);
@ -206,13 +210,14 @@ static void print_help(int just_version, char *exec_name) {
printf("This created Electric Duet files\n\n");
printf("Usage:\n");
printf("\t%s [-h] [-v] [-d] [-o X] [-i X] textfile outbase\n\n",
printf("\t%s [-h] [-v] [-d] [-o X] [-i X] [-l] textfile outbase\n\n",
exec_name);
printf("\t-h: this help message\n");
printf("\t-v: version info\n");
printf("\t-d: print debug messages\n");
printf("\t-o: Offset octave by X\n");
printf("\t-i: set second instrument to X\n");
printf("\t-l: generate lyrics file\n");
exit(0);
}
@ -224,15 +229,17 @@ int main(int argc, char **argv) {
char *result;
char ed_filename[BUFSIZ],lyrics_filename[BUFSIZ],*in_filename;
char temp[BUFSIZ];
FILE *ed_file,*lyrics_file,*in_file=NULL;
FILE *ed_file,*lyrics_file=NULL,*in_file=NULL;
//int attributes=0;
int loop=0,i;
int sp,external_frequency,irq;
struct note_type a,b,c;
int copt;
int generate_lyrics=0;
// Instruments 0=square
int voice1=0,voice2=0;
int newvoice1,newvoice2;
char song_name[BUFSIZ];
char author_name[BUFSIZ];
@ -265,6 +272,10 @@ int main(int argc, char **argv) {
/* instrument to use */
voice1=atoi(optarg);
break;
case 'l':
/* generate lyrics */
generate_lyrics=1;
break;
default:
print_help(0,argv[0]);
break;
@ -303,13 +314,14 @@ int main(int argc, char **argv) {
return -1;
}
lyrics_file=fopen(lyrics_filename,"w");
if (lyrics_file==NULL) {
fprintf(stderr,"Couldn't open %s\n",lyrics_filename);
return -1;
if (generate_lyrics) {
lyrics_file=fopen(lyrics_filename,"w");
if (lyrics_file==NULL) {
fprintf(stderr,"Couldn't open %s\n",lyrics_filename);
return -1;
}
}
/* Get the info for the header */
while(1) {
@ -392,7 +404,7 @@ int main(int argc, char **argv) {
int frame=0,lyric=0;
int lyric_line=1;
fprintf(ed_file,"%c%c%c",1,voice1,voice2);
update_voice(ed_file,voice1,voice2);
offset+=3;
while(1) {
@ -410,6 +422,38 @@ int main(int argc, char **argv) {
if (string[0]=='-') continue;
if (string[0]=='*') continue;
if (string[0]=='@') {
sscanf(string,"@%d %d",&newvoice1,&newvoice2);
/* special case */
if (newvoice1>128) {
update_voice(ed_file,0xff,0xff);
}
else {
voice1=newvoice1;
voice2=newvoice2;
update_voice(ed_file,voice1,voice2);
}
offset+=3;
/* Avoid changing instrument by accident */
/* Also keep lyrics in sync */
if (same_count<2) {
same_count=2;
}
fprintf(ed_file,"%c%c%c",same_count,a_last,b_last);
offset+=3;
if (debug) {
printf("%04X: %x %x %x\n",offset,same_count,a_last,b_last);
}
same_count=0;
continue;
}
sp=0;
/* Skip line number */
@ -420,60 +464,59 @@ int main(int argc, char **argv) {
if (sp!=-1) sp=get_note(string,sp,&c,line);
/* handle lyrics */
if ((sp!=-1) && (string[sp]!='\n') && (string[sp]!=0)) {
fprintf(lyrics_file,"; %d: %s",frame,&string[sp]);
while((string[sp]==' ' || string[sp]=='\t')) sp++;
if (string[sp]!='\n') {
fprintf(lyrics_file,".byte\t$%02X",lyric_line&0xff);
if (generate_lyrics) {
if ((sp!=-1) && (string[sp]!='\n') && (string[sp]!=0)) {
fprintf(lyrics_file,"; %d: %s",frame,&string[sp]);
while((string[sp]==' ' || string[sp]=='\t')) sp++;
if (string[sp]!='\n') {
fprintf(lyrics_file,".byte\t$%02X",lyric_line&0xff);
/* get to first quote */
while(string[sp]!='\"') sp++;
sp++;
/* stop at second quote */
while(string[sp]!='\"') {
if (string[sp]=='\\') {
sp++;
/* Ignore if we have LED panel */
if (string[sp]=='i') {
//printf(",$%02X",10);
}
/* form feed */
else if (string[sp]=='f') {
fprintf(lyrics_file,",$%02X",12);
}
/* Vertical tab */
else if (string[sp]=='v') {
fprintf(lyrics_file,",$%02X",11);
}
else if (string[sp]=='n') {
fprintf(lyrics_file,",$%02X",13|0x80);
}
else if ((string[sp]>='0') &&
(string[sp]<=':')) {
fprintf(lyrics_file,",$%02X",string[sp]-'0');
}
else {
printf("UNKNOWN ESCAPE %d\n",string[sp]);
}
/* get to first quote */
while(string[sp]!='\"') sp++;
sp++;
/* stop at second quote */
while(string[sp]!='\"') {
if (string[sp]=='\\') {
sp++;
/* Ignore if we have LED panel */
if (string[sp]=='i') {
//printf(",$%02X",10);
}
/* form feed */
else if (string[sp]=='f') {
fprintf(lyrics_file,",$%02X",12);
}
/* Vertical tab */
else if (string[sp]=='v') {
fprintf(lyrics_file,",$%02X",11);
}
else if (string[sp]=='n') {
fprintf(lyrics_file,",$%02X",13|0x80);
}
else if ((string[sp]>='0') &&
(string[sp]<=':')) {
fprintf(lyrics_file,",$%02X",string[sp]-'0');
}
else {
printf("UNKNOWN ESCAPE %d\n",string[sp]);
}
sp++;
continue;
}
fprintf(lyrics_file,",$%02X",string[sp]|0x80);
sp++;
continue;
}
fprintf(lyrics_file,",$%02X",string[sp]|0x80);
sp++;
fprintf(lyrics_file,",$00\n");
// fprintf(lyrics_file," %s",&string[sp]);
// printf("%s",&string[sp]);
}
lyric=1;
}
fprintf(lyrics_file,",$00\n");
// fprintf(lyrics_file," %s",&string[sp]);
// printf("%s",&string[sp]);
}
lyric=1;
}
if ((a.ed_freq!=0)||(b.ed_freq!=0)) {
if (debug) {
printf("%d: ",frame);
@ -564,7 +607,10 @@ int main(int argc, char **argv) {
fprintf(ed_file,"%c%c%c",0,0,0); // EOF?
fclose(ed_file);
fclose(lyrics_file);
if (generate_lyrics) {
fclose(lyrics_file);
}
(void) irq;
(void) loop;