dos33fsprogs/fireworks/fw.s

555 lines
7.6 KiB
ArmAsm
Raw Normal View History

2018-09-05 19:04:31 +00:00
;=======================================================================
; Based on BASIC program posted by FozzTexx, originally written in 1987
;=======================================================================
2018-09-05 20:07:34 +00:00
; Constants
NUMSTARS = 16
2018-09-05 20:48:54 +00:00
YSIZE = 160
2018-09-05 20:07:34 +00:00
XSIZE = 280
MARGIN = 24
; Zero page addresses
2018-09-06 03:04:25 +00:00
OFFSET = $EF
2018-09-05 20:07:34 +00:00
COLOR_GROUP = $F0
X_VELOCITY = $F1
Y_VELOCITY_H = $F2
Y_VELOCITY_L = $F3
MAX_STEPS = $F4
2018-09-06 03:04:25 +00:00
XPOS_H = $F5
2018-09-05 20:07:34 +00:00
XPOS_L = $F6
YPOS_H = $F7
YPOS_L = $F8
PEAK = $F9
CURRENT_STEP = $FA
Y_OLD = $FB
Y_OLDER = $FC
X_OLD = $FD
X_OLDER = $FE
2018-09-05 20:27:42 +00:00
TEMPY = $FF
2018-09-05 19:04:31 +00:00
draw_fireworks:
jsr HOME ; clear screen
jsr HGR ; set high-res, clear screen, page0
jsr draw_stars ; draw the stars
2018-09-05 20:07:34 +00:00
launch_firework:
jsr random16
lda SEEDL
and #$4
sta COLOR_GROUP ; HGR color group (0 PG or 4 BO)
jsr random16
lda SEEDL
and #$3
clc
adc #$1
sta X_VELOCITY ; x velocity = 1..4
jsr random16
lda SEEDL
and #$3
clc
adc #$2
eor #$ff
sta Y_VELOCITY_H ; y velocity = -3..-6
lda #0
sta Y_VELOCITY_L ; it's 8:8 fixed point
jsr random16
lda SEEDL
and #$1f
clc
adc #33
sta MAX_STEPS ; 33..64
; launch from the two hills
jsr random16
lda SEEDL
and #$3f
sta XPOS_L
jsr random16
lda SEEDL
and #$1
2018-09-05 20:48:54 +00:00
beq right_hill
left_hill:
2018-09-05 20:07:34 +00:00
lda XPOS_L
clc
adc #24
sta XPOS_L ; 24-88 (64)
jmp done_hill
2018-09-05 20:48:54 +00:00
right_hill:
2018-09-05 20:07:34 +00:00
lda XPOS_L
clc
adc #191
sta XPOS_L ; 191-255 (64)
2018-09-05 20:48:54 +00:00
lda X_VELOCITY
eor #$ff
sta X_VELOCITY
inc X_VELOCITY ; aim toward middle
2018-09-05 20:07:34 +00:00
done_hill:
lda #YSIZE
sta YPOS_H
lda #0 ; fixed point 8:8
sta YPOS_L ; start at ground
lda YPOS_H
sta PEAK ; peak starts at ground
;===============
; Draw rocket
;===============
lda #1
sta CURRENT_STEP
draw_rocket_loop:
lda Y_OLD
sta Y_OLDER
lda YPOS_H
sta Y_OLD
lda X_OLD
sta X_OLDER
lda XPOS_L
sta X_OLD
; Move rocket
lda XPOS_L
clc
adc X_VELOCITY
sta XPOS_L ; adjust xpos
; 16 bit add
clc
lda YPOS_L
adc Y_VELOCITY_L
sta YPOS_L
lda YPOS_H
adc Y_VELOCITY_H
sta YPOS_H ; adjust ypos
2018-09-05 19:04:31 +00:00
2018-09-05 20:27:42 +00:00
; adjust Y velocity, slow it down
clc
lda Y_VELOCITY_L
adc #$20 ; $20 = 0.125
sta Y_VELOCITY_L
lda Y_VELOCITY_H
adc #0
sta Y_VELOCITY_H
; if we went higher, adjust peak
lda YPOS_H
cmp PEAK
bmi no_peak
sta PEAK
no_peak:
;========================================
; Check if out of bounds and stop moving
;========================================
lda XPOS_L ; if (xpos_l<=margin) too far left
cmp #MARGIN
bcc done_moving
; Due to 256 wraparound, the above will catch this case???
; cmp #XSIZE-MARGIN ; if (xpos_l>=(xsize-margin)) too far right
; bcs done_moving
lda YPOS_H ; if (ypos_h<=margin) too far up
cmp #MARGIN
bcc done_moving
;======================
; if falling downward
;======================
lda Y_VELOCITY_H
bmi going_up ; if (y_velocity_h>0)
; if too close to ground, explode
lda YPOS_H ; if (ypos_h>=ysize-margin)
cmp #(YSIZE-MARGIN)
bcs done_moving
; if fallen a bit past peak, explode
sec ; if (ypos_h>ysize-(ysize-peak)/2)
lda #YSIZE
sbc PEAK
2018-09-05 20:48:54 +00:00
lsr
2018-09-05 20:27:42 +00:00
eor #$FF
clc
adc #1
clc
adc #YSIZE
cmp YPOS_H
2018-09-05 20:48:54 +00:00
bcc done_moving
2018-09-05 20:27:42 +00:00
going_up:
jmp done_bounds_checking
done_moving:
lda MAX_STEPS
sta CURRENT_STEP
2018-09-05 19:04:31 +00:00
2018-09-05 20:27:42 +00:00
done_bounds_checking:
2018-09-05 20:07:34 +00:00
;==========================
; if not done, draw rocket
;==========================
lda CURRENT_STEP
cmp MAX_STEPS
beq erase_rocket
draw_rocket:
; set hcolor to proper white (3 or 7)
clc
lda COLOR_GROUP
adc #3
tax
lda COLORTBL,X ; get color from table
sta HGR_COLOR
; HPLOT X,Y: X= (y,x), Y=a
ldx X_OLD
lda Y_OLD
ldy #0
jsr HPLOT0 ; hplot(x_old,y_old);
2018-09-05 20:48:54 +00:00
; HPLOT to X,Y X=(x,a), y=Y
lda XPOS_L
ldx #0
ldy YPOS_H
jsr HGLIN ; hplot_to(xpos_l,ypos_h);
2018-09-05 20:07:34 +00:00
erase_rocket:
; erase with proper color black (0 or 4)
ldx COLOR_GROUP
lda COLORTBL,X ; get color from table
sta HGR_COLOR
; HPLOT X,Y: X= (y,x), Y=a
ldx X_OLDER
lda Y_OLDER
ldy #0
jsr HPLOT0 ; hplot(x_old,y_old);
2018-09-05 20:48:54 +00:00
; HPLOT to X,Y X=(x,a), y=Y
lda X_OLD
ldx #0
ldy Y_OLD
jsr HGLIN ; hplot_to(x_old,y_old);
2018-09-05 20:07:34 +00:00
done_with_loop:
lda CURRENT_STEP
cmp MAX_STEPS
beq draw_explosion
2018-09-05 20:48:54 +00:00
lda #$c0
jsr WAIT
2018-09-05 20:07:34 +00:00
inc CURRENT_STEP
jmp draw_rocket_loop
;==================================
; Draw explosion near x_old, y_old
;==================================
draw_explosion:
2018-09-06 02:02:29 +00:00
jsr random16
lda SEEDL
and #$f
sec
sbc #8
adc X_OLD
sta XPOS_L ; xpos=x_old+(random()%16)-8; x +/- 8
; FIXME: XPOS can overlow
jsr random16
lda SEEDL
and #$f
sec
sbc #8
adc Y_OLD
sta YPOS_H ; ypos_h=y_old+(random()%16)-8; // y +/- 8
; draw white (with fringes)
lda COLOR_GROUP
clc
adc #$3
tax
lda COLORTBL,X ; get color from table
sta HGR_COLOR
2018-09-05 20:07:34 +00:00
2018-09-05 19:04:31 +00:00
; hplot(xpos,ypos_h); // draw at center of explosion
2018-09-06 02:02:29 +00:00
; HPLOT X,Y: X= (y,x), Y=a
ldx XPOS_L
lda YPOS_H
ldy #0
jsr HPLOT0 ; hplot(x_old,y_old);
; Spread the explosion
ldy #1
sty TEMPY ; save Y
explosion_loop:
ldy TEMPY
;================================
; Draw spreading dots in white
cpy #9
2018-09-06 03:04:25 +00:00
beq explosion_erase
; hcolor_equals(color_group+3);
lda COLOR_GROUP
clc
adc #$3
tax
lda COLORTBL,X ; get color from table
sta HGR_COLOR
ldx TEMPY
stx OFFSET
jsr explosion
2018-09-06 02:02:29 +00:00
explosion_erase:
;======================
; erase old
; erase with proper color black (0 or 4)
ldx COLOR_GROUP
lda COLORTBL,X ; get color from table
sta HGR_COLOR
2018-09-06 03:04:25 +00:00
ldx TEMPY
dex
stx OFFSET
2018-09-06 02:02:29 +00:00
jsr explosion
done_with_explosion:
lda #$c0
jsr WAIT
inc TEMPY
lda TEMPY
2018-09-06 03:04:25 +00:00
cmp #10
2018-09-06 02:02:29 +00:00
bne explosion_loop
2018-09-05 19:04:31 +00:00
2018-09-05 20:07:34 +00:00
;==================================
; randomly draw more explosions
;==================================
jsr random16
lda SEEDL
and #$1
beq draw_explosion
; see if key pressed
lda KEYPRESS ; check if keypressed
bmi done_fireworks ; if so, exit
jmp launch_firework
done_fireworks:
2018-09-05 19:04:31 +00:00
rts
2018-09-06 02:02:29 +00:00
explosion:
2018-09-06 03:04:25 +00:00
; HPLOT X,Y: X= (y,x), Y=a
clc
lda XPOS_L
adc OFFSET
tax
ldy #0
clc
lda YPOS_H
adc OFFSET
jsr HPLOT0 ; hplot(xpos+o,ypos_h+o); SE
2018-09-06 02:02:29 +00:00
2018-09-06 03:04:25 +00:00
clc
lda XPOS_L
adc OFFSET
tax
ldy #0
sec
lda YPOS_H
sbc OFFSET
jsr HPLOT0 ; hplot(xpos+o,ypos_h-o); NE
sec
lda XPOS_L
sbc OFFSET
tax
ldy #0
sec
lda YPOS_H
sbc OFFSET
2018-09-06 02:02:29 +00:00
2018-09-06 03:04:25 +00:00
jsr HPLOT0 ; hplot(xpos-o,ypos_h-o); NW
sec
lda XPOS_L
sbc OFFSET
tax
ldy #0
clc
lda YPOS_H
adc OFFSET
jsr HPLOT0 ; hplot(xpos-o,ypos_h+o); SW
; HPLOT X,Y: X= (y,x), Y=a
ldx XPOS_L
ldy #0
clc
lda OFFSET
adc OFFSET
adc OFFSET
lsr
adc YPOS_H
jsr HPLOT0 ; hplot(xpos,ypos_h+(o*1.5)); S
ldx XPOS_L
ldy #0
clc ; O O*1.5 NEG
lda OFFSET ; 0 = 0 0
adc OFFSET ; 1 = 1 -1
adc OFFSET ; 2 = 3 -3
lsr ; 3 = 4 -4
eor #$FF ; 4 = 6 -6
clc
adc #1
adc YPOS_H
jsr HPLOT0 ; hplot(xpos,ypos_h-(o*1.5)); N
; HPLOT X,Y: X= (y,x), Y=a
clc
lda OFFSET
adc OFFSET
adc OFFSET
lsr
adc XPOS_L
tax
ldy #0
lda YPOS_H
jsr HPLOT0 ; hplot(xpos+(o*1.5),ypos_h); E
clc ; O O*1.5 NEG
lda OFFSET ; 0 = 0 0
adc OFFSET ; 1 = 1 -1
adc OFFSET ; 2 = 3 -3
lsr ; 3 = 4 -4
eor #$FF ; 4 = 6 -6
clc
adc #1
adc XPOS_L
tax
ldy #0
lda YPOS_H
2018-09-06 02:02:29 +00:00
2018-09-06 03:04:25 +00:00
jsr HPLOT0 ; hplot(xpos-(o*1.5),ypos_h); // W
2018-09-06 02:02:29 +00:00
rts
2018-09-05 20:07:34 +00:00
;=============================
; Draw the stars
;=============================
2018-09-05 19:04:31 +00:00
draw_stars:
; HCOLOR = 3, white (though they are drawn purple)
ldx #3
lda COLORTBL,X ; get color from table
sta HGR_COLOR
ldy #0
star_loop:
tya
pha
; HPLOT X,Y
; X= (y,x), Y=a
ldx stars,Y
lda stars+1,Y
ldy #0
jsr HPLOT0
pla
tay
iny
iny
cpy #NUMSTARS*2
bne star_loop
rts
stars: ; even x so they are purple
.byte 28,107, 108, 88, 126, 88, 136, 95
.byte 150,108, 148,120, 172,124, 180,109
.byte 216, 21, 164, 40, 124, 18, 60, 12
.byte 240,124, 94,125, 12, 22, 216,116