Re: Im requesting a TI-83 game
[Prev][Next][Index][Thread]
Re: Im requesting a TI-83 game
GuitrPro16@AOL.COM wrote:
> Can you please send me the text for Space Invaders. Thank you.
>
Here you go.
--
- Michael Astrauskas ICQ UIN: 1946065, Trevelyan
My humble Anime-type art site:
www.geocities.com/timessquare/6300/
;ZDDDDDDDDDDDDDDDDBDDDDDDDDDDDDDDDDBDDDDDDDDDDDDDDDDDDDDDBDDDDDDDBDDDDDDDDDDDD?
;3[[[[[ Z80 [[[[[[3 Spaze Invaders 3[[[[[[[[[[[[[[[[[[[[[3 movax 3[[[[[[[[[[[[3
;@DDDDDDDDDDDDDDDDADDDDDDDDDDDDDDDDADDDDDDDDDDDDDDDDDDDDDADDDDDDDADDDDDDDDDDDDY
; Spaze Invaders v1.1 by Hannes Edfeldt
; Here's the source code to my game Spaze Invaders. I've released it to help
; other budding TI-83 asm programmers to get started. Don't forget to give me
; some credit if you use anything from my code. Have a nice day! =)
; Hannes Edfeldt * movax@algonet.se * http://www.algonet.se
.org 9327h
;ZDDDDDDDDDDDDDDDDBDDDDDDDDDDDDDDDDBDDDDDDDDDDDDDDDDDDDDDBDDDDDDDBDDDDDDDDDDDD?
;3[[[[[ Z80 [[[[[[3 MAIN 3[[[[[[[[[[[[[[[[[[[[[3 movax 3[[[[[[[[[[[[3
;@DDDDDDDDDDDDDDDDADDDDDDDDDDDDDDDDADDDDDDDDDDDDDDDDDDDDDADDDDDDDADDDDDDDDDDDDY
START:
call INIT ; Init
call INTRO ; Intro
call MENU01 ; Menu, wait for 2nd
call MENU02 ; Menu, choose difficulty
call LVINIT ; Level init
MAIN: ; Normal level
call KEYS ; Read keys
call SHIP ; Update ship
call LASER ; Update laser
call ALIENS ; Move the aliens
call ALASR ; Alien laser
call COLDT1 ; Collision detection between alien and laser
call COLDT2 ; Collision detection between player and laser
call COLDT3 ; Collision detection between barrier and laser
call BUFCOPY ; Copy graphbuf to LCD
call ALIENY ; Check if aliens has moved down to the bottom
jp MAIN
MBOSS: ; Boss level
call KEYS ; Read keys
call BOSS ; Manage boss an related stuff
call SHIP ; Update ship
call COLDT2 ; Collision detection between player and laser
call BUFCOPY ; Copy graphbuf to LCD
ld a,(BOSSf) ; Check if boss still is alive
cp 1
jp z,MBOSS
call BOSSKILL ; If not, call boss killed routine
;ZDDDDDDDDDDDDDDDDBDDDDDDDDDDDDDDDDBDDDDDDDDDDDDDDDDDDDDDBDDDDDDDBDDDDDDDDDDDD?
;3[[[[[ Z80 [[[[[[3 PROCEDURES 3[[[[[[[[[[[[[[[[[[[[[3 movax 3[[[[[[[[[[[[3
;@DDDDDDDDDDDDDDDDADDDDDDDDDDDDDDDDADDDDDDDDDDDDDDDDDDDDDADDDDDDDADDDDDDDDDDDDY
;\[[[[[[[[[[[[_ NEWGAME _[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[
;ZDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDD?
;3 Init for a new game 3
;@DDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDY
NEWGAME:
inc sp ; Don't return to GAMEOVER
inc sp
inc sp ; Don't return to ALIENY/COLDT2
inc sp
inc sp ; Don't return to MAIN/MBOSS
inc sp
ld hl,858fh+100 ; -- Restore the variables start values
ld de,SHIPx
ld bc,DBYTES
ldir
ld a,0
ld (SCOREb),a
ld (SCOREb+1),a
ld (STARTy),a
ld a,'0'
ld (SCR1),a
ld (SCR2),a
ld (SCR3),a
ld (SCR4),a
ld a,'1'
ld (LEVELa),a
ld a,1
ld (LEVELb),a
ld (TIME),a
ld a,3
ld (LIVESb),a
ld a,'3'
ld (LIVESa),a
ld hl,START ; Make program ret to START
push hl
ret
;\[[[[[[[[[[[[\ NEWGAME \[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[
;\[[[[[[[[[[[[_ INTRO _[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[
;ZDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDD?
;3 Intro 3
;@DDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDY
INTRO:
;[[[[ Initiate for intro [[[[
call BUFCLR ; Clear the graphbuf
call BUFCOPY ; Copy graphbuf to LCD
ld hl,8e29h ; Clear safe ram area
ld de,8265h
ld bc,768
ldir
ld hl,8e29h ; Clear top of safe ram area 2
ld de,858fh
ld bc,80
ldir
;[[[[ Alien Code text [[[[
res 7,(iy+20)
ld hl,0191eh ; Print "Alien Code"
ld (08252H),hl ; Update cursorslocation
ld hl,TXT6
call 04781h ; Vputs
ld hl,01f22h ; Print "presents"
ld (08252H),hl ; Update cursorslocation
ld hl,TXT7
call 04781h ; Vputs
ld b,4
WAITL6:
push bc
ld hl,65535
call WAIT
pop bc
djnz WAITL6
;[[[[ Copy logo to graphbuf [[[[
LOGO:
ld hl,SPZLOGO ; Copy logo to graphbuf
ld de,8e29h+38
ld b,17
YLOP1: push bc
ld b,8
XLOP1: ld a,(hl)
ld (de),a
inc hl
inc de
djnz XLOP1
pop bc
inc de
inc de
inc de
inc de
djnz YLOP1
;[[[[ Do logo fx [[[[
LOGOFX:
set 7,(iy+20)
ld hl,01413h ; Print "By Hannes Edfeldt"
ld (08252H),hl ; Update cursorslocation
ld hl,TXT1
call 04781h ; Vputs
ld hl,8e29h ; Copy graphbuf to safe ram area
ld de,8265h
ld bc,768
ldir
ld b,27
FXLOP2: push bc
ld a,(LOGOl) ; Get line number
ld e,a
ld d,0
ld hl,0 ; Do hl=de*12
add hl,de
add hl,de
add hl,de
add hl,hl
add hl,hl
push hl
ld bc,8e29h
add hl,bc
ld (TEMP),hl
ld de,(TEMP) ; de->graphbuf
pop hl
ld bc,8265h
add hl,bc ; hl->spzlogo
ld a,(LOGOl) ; Calculate how many lines to draw
ld c,a
ld a,64
sub c
ld b,a
FXLOP1: push bc ; Copy one line
ld bc,12
ldir
ld bc,-12
add hl,bc
pop bc
djnz FXLOP1
ld hl,LOGOl ; Update logoline counter
inc (hl)
call BUFCOPY
ld hl,12500
call WAIT
pop bc
djnz FXLOP2
ld hl,01e10h+7 ; - Print highscore text
ld (08252H),hl ; Update cursorslocation
ld hl,HSCORE
call 04781h ; Vputs
ld hl,01e34h+7 ; - Print highscore number
ld (08252H),hl ; Update cursorslocation
ld hl,HSCR4
call 04781h ; Vputs
ld hl,03a51h ; Print "vX.X" (version number)
ld (08252H),hl ; Update cursorslocation
ld hl,VERt
call 04781h ; Vputs
ret
;\[[[[[[[[[[[[\ INTRO \[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[
;\[[[[[[[[[[[[_ MENU01 _[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[
;ZDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDD?
;3 Menu part 1 3
;@DDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDY
MENU01:
;[[[[ Prepare for textflash [[[[
ld hl,8e29h ; Copy graphbuf to safe ram area
ld de,8265h
ld bc,768
ldir
ld hl,00011h ; - Print "PRESS 2nd TO START"
ld (08252H),hl ; Update cursorlocation
ld hl,TXT2
call 04781h ; Vputs
ld hl,8e29h ; Copy top of graphbuf to safe ram area 2
ld de,858fh
ld bc,72
ldir
ld de,8e29h ; Copy safe ram area to graphbuf
ld hl,8265h
ld bc,768
ldir
;[[[[[[[[ Menu loop [[[[
MENUL:
;[[[[ Textflash [[[[
ld a,(FLASHt) ; Time to flash text?
inc a
ld (FLASHt),a
cp 32
jp nz,SKP13
ld a,0
ld (FLASHt),a
ld a,(FLASHf) ; Get flashflag
cp 1
jp z,ERASE1
DRAW1: ld hl,858fh
ld de,8e29h+540
ld bc,72
ldir
ld a,1
ld (FLASHf),a
jp SKP13
ERASE1: ld hl,8e29h+612
ld de,8e29h+540
ld bc,72
ldir
ld a,0
ld (FLASHf),a
SKP13:
call BUFCOPY
SKP29:
ld a,0ffh ; Reset the keyport (kinda)
out (1),a
ld a,0bfh ; Enable the row with 2nd
out (1),a
in a,(1)
cp 223 ; Has anyone pressed 2nd?
jp nz,MENUL
ret
;\[[[[[[[[[[[[\ MENU01 \[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[
;\[[[[[[[[[[[[_ MENU02 _[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[
;ZDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDD?
;3 Menu part 2 3
;@DDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDY
MENU02:
;[[[[ Prepare for diff. menu [[[[
call READKEY ; Fetch last 2nd press
ld hl,9009h ; Erase "PRESS 2nd TO START" msg
ld de,8e29h+540
ld bc,72
ldir
ld hl,02629h ; - Print "EASY"
ld (08252H),hl ; Update cursorlocation
ld hl,TXT3
call 04781h ; Vputs
ld hl,02d25h ; - Print "MEDIUM"
ld (08252H),hl ; Update cursorlocation
ld hl,TXT4
call 04781h ; Vputs
ld hl,03429h ; - Print "HARD"
ld (08252H),hl ; Update cursorlocation
ld hl,TXT5
call 04781h ; Vputs
ld hl,38*12+8e29h
ld b,7
INVL2: ld de,4 ; Invert loop
add hl,de
ld a,(hl)
cpl
and 01111111b
ld (hl),a
inc hl
ld a,(hl)
cpl
ld (hl),a
inc hl
ld a,(hl)
cpl
ld (hl),a
inc hl
ld a,(hl)
cpl
ld (hl),a
ld de,5
add hl,de
djnz INVL2
call BUFCOPY
;[[[[[[[[ Menu loop 2 [[[[
MENUL2:
ld a,0ffh ; Reset the keyport (kinda)
out (1),a
ld a,0fdh ; Enable the row with clear
out (1),a
in a,(1)
cp 191 ; Check for clear
jp nz,NOCLR_3
inc sp
inc sp
call XIT
NOCLR_3:
ld hl,MENUt ; Time to check for new arrowpress?
ld a,(hl)
cp 12
jp nz,SKP33
ld a,0ffh ; Reset the keyport (kinda)
out (1),a
ld a,0feh ; Enable the arrows
out (1),a
in a,(1)
cp 247 ; Pressed up?
jp nz,NOUP
ld hl,MENUt ; Reset timer
ld (hl),0
ld a,(MENUc) ; Update old menu choice
ld (MENUoc),a
ld hl,MENUc ; Move bar
dec (hl)
ld a,(hl)
cp 0
jp nz,NOUP
ld (hl),3 ; Warp
NOUP:
cp 254 ; Pressed down?
jp nz,NODOWN
ld hl,MENUt ; Reset timer
ld (hl),0
ld a,(MENUc) ; Update old menu choice
ld (MENUoc),a
ld hl,MENUc ; Move bar
inc (hl)
ld a,(hl)
cp 4
jp nz,NODOWN
ld (hl),1 ; Warp
NODOWN:
ld a,(MENUt) ; Has the bar moved?
cp 0
jp nz,SKP33
ld hl,MENUc
ld b,2 ; Loop to do two inverts (old and new bar)
BARL1:
ld a,(hl)
dec a
ld l,a
ld h,84
push bc
call HTIMESL
pop bc
ld de,(38*12)+8e29h
add hl,de
push bc
ld b,7 ; Invert loop
BARL2: ld de,4
add hl,de
ld a,(hl)
cpl
and 01111111b
ld (hl),a
inc hl
ld a,(hl)
cpl
ld (hl),a
inc hl
ld a,(hl)
cpl
ld (hl),a
inc hl
ld a,(hl)
cpl
ld (hl),a
ld de,5
add hl,de
djnz BARL2
pop bc
ld hl,MENUc
inc hl
djnz BARL1
SKP33:
call BUFCOPY
ld hl,MENUt
ld a,(hl)
cp 12
jp z,SKP32
inc (hl)
SKP32:
call READKEY ; Look for a 2nd press
call OP2TOP1
call CONVOP1
cp 21
jp nz,MENUL2
ld a,(MENUc) ; Set difficulty after menu choice
ld (DIFF),a
ret
;\[[[[[[[[[[[[\ MENU02 \[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[
;\[[[[[[[[[[[[_ OUTRO _[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[
;ZDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDD?
;3 Outro 3
;@DDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDY
OUTRO:
call BUFCLR ; Clear the graphbuf
call BUFCOPY
set 7,(iy+20)
ld hl,00010h ; - Print "CONGRATULATIONS!!!"
ld (08252h),hl ; Update cursorslocation
ld hl,MSG06
call 04781h ; Vputs
ld hl,0070ch ; - Print "You have saved all the"
ld (08252h),hl ; Update cursorslocation
ld hl,MSG07
call 04781h ; Vputs
ld hl,00d09h ; - Print "hamsters on earth from"
ld (08252h),hl ; Update cursorslocation
ld hl,MSG08
call 04781h ; Vputs
ld hl,0130dh ; - Print "the evil aliens' claws"
ld (08252h),hl ; Update cursorslocation
ld hl,MSG09
call 04781h ; Vputs
ld hl,01c16h+7 ; - Print score text
ld (08252H),hl ; Update cursorslocation
ld hl,SCORE
call 04781h ; Vputs
ld hl,01c2dh+7 ; - Print score number
ld (08252H),hl ; Update cursorslocation
ld hl,SCR4
call 04781h ; Vputs
ld hl,02417h ; - Print "Have a nice day!"
ld (08252h),hl ; Update cursorslocation
ld hl,MSG10
call 04781h ; Vputs
ld hl,02d1eh ; - Print "ALIEN CODE"
ld (08252h),hl ; Update cursorslocation
ld hl,TXT6
call 04781h ; Vputs
ld hl,03311h ; - Print "movax@algonet.se"
ld (08252h),hl ; Update cursorslocation
ld hl,MSG11
call 04781h ; Vputs
ld hl,03905h ; - Print "www.algonet.se/~movax"
ld (08252h),hl ; Update cursorslocation
ld hl,MSG12
call 04781h ; Vputs
ld hl,8e29h ; Copy graphbuf to safe ram area
ld de,8265h
ld bc,768
ldir
call BUFCLR ; Clear the graphbuf
ld hl,0 ; Bytes to write
ld (TEMP),hl
ld hl,8e29h+768 ; Destination
ld (TEMP2),hl
ld b,64
YSCRLL: push bc
ld bc,12 ; - Update bytes to write
ld hl,(TEMP)
add hl,bc
ld (TEMP),hl
ld bc,-12 ; - Update destination
ld hl,(TEMP2)
add hl,bc
ld (TEMP2),hl
ld de,(TEMP2)
ld hl,8265h
ld bc,(TEMP)
ldir
ld b,8 ; Wait for a while
WAITL5:
push bc
call BUFCOPY
pop bc
djnz WAITL5
pop bc
djnz YSCRLL
call WAIT2ND
call GAMEOVER
ret
;\[[[[[[[[[[[[\ OUTRO \[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[
;\[[[[[[[[[[[[_ BOSS _[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[
;ZDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDD?
;3 Manage the boss and related stuff 3
;@DDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDY
BOSS:
;[[[[ Boss shot part 1 [[[[
ld a,(ALASRt) ; Is timer 0 yet?
cp 0
jp z,SKP56
ld hl,ALASRt ; Nope, update timer
dec (hl)
jp SKP57
SKP56:
ld hl,BOSSlt
inc (hl)
ld a,(ALASRf) ; Look for boss shot
cp 1
jp z,UPBLSR1 ; Jump to update shot if there already is one
ld a,(SHIPx) ; Move ship x value to boss shot destination
add a,6
ld (BOSSld),a
ld a,1 ; Set laserflag
ld (ALASRf),a
ld a,(BOSSx) ; Boss shot init x-coordinate
add a,12
ld (ALASRx),a
ld a,40 ; Boss shot init y-coordinate
ld (ALASRy),a
jp SKP57
UPBLSR1:
ld a,(ALASRy) ; Erase old laserbeam
ld e,a
ld a,(ALASRx)
ld hl,25*8+SPRITES
call CLRSPR
ld a,(ALASRy) ; Update boss shot y-coordinate
ld b,a
ld a,(BOSSlt)
and 00000001b
cp 0
jp nz,SKP59
ld a,b
inc a
ld (ALASRy),a
cp 57 ; Has boss shot reached the bottom?
jp nz,SKP59
ld a,0 ; Reset laserflag
ld (ALASRf),a
ld a,16
ld (ALASRt),a
jp SKP57
SKP59: ld a,(BOSSlt)
and 00000001b
cp 1
jp nz,SKP57
ld a,(BOSSld) ; -- Update boss shot x-coordinate
ld b,a
ld a,(ALASRx)
cp b
jp nz,SKP61
jp SKP57
SKP61:
cp b
jp c,SKP60
dec a
ld (ALASRx),a
jp SKP57
SKP60: inc a
ld (ALASRx),a
SKP57:
;[[[[ Ship laser part 1 [[[[
ld a,(LTIMER) ; Has timer reached zero yet?
cp 0
jp z,SKP50
ld hl,LTIMER ; Update laser timer
dec (hl)
SKP50:
ld a,(SLASRy) ; Is there a laserbeam to update?
cp 252
jp z,SKP52
ld a,(SLASRy) ; Erase old laserbeam
ld e,a
ld a,(SLASRx)
ld hl,80+SPRITES
call CLRSPR
SKP52:
;[[[[ Boss movement [[[[
ld hl,BOSSmc ; Time to move boss?
inc (hl)
ld a,(hl)
cp 4
jp nz,SKP41
ld (hl),0
ld hl,BOSSxc ; Time to change direction?
inc (hl)
ld a,(hl)
cp 64
jp nz,SKP40
ld (hl),0 ; Change direction
ld a,(BOSSmd)
neg
ld (BOSSmd),a
SKP40: ld a,(BOSSmd)
cp 1
jp nz,MOVLEFT
MOVRGTH:
ld hl,8e29h+96 ; Move right
ld b,32
BMOVL1: push bc
ld b,12
and a
BMOVL2: ld a,(hl)
rr a
ld (hl),a
inc hl
djnz BMOVL2
pop bc
djnz BMOVL1
ld hl,BOSSx
inc (hl)
jp SKP41
MOVLEFT:
ld hl,8e29h+383+96 ; Move left
ld b,32
BMOVL3: push bc
ld b,12
and a
BMOVL4: ld a,(hl)
rl a
ld (hl),a
dec hl
djnz BMOVL4
pop bc
djnz BMOVL3
ld hl,BOSSx
dec (hl)
SKP41:
;[[[[ Boss and laser collision [[[[
ld a,(SLASRy) ; Check y
cp 41
jp nc,SKP54
ld a,(SLASRx) ; Check x left edge
ld b,a
inc b
ld a,(BOSSx)
cp b
jp nc,SKP54
add a,32 ; Check x right edge
cp b
jp c,SKP54
ld hl,BOSShl
dec (hl)
ld a,(hl)
cp 0
jp nz,SKP55
ld a,(DIFF)
ld (hl),a
ld b,3 ; Three pixels wide health point to erase
HPL4: push bc
ld hl,8e29h+23 ; Erase health point
ld b,4
HPL2: push bc
and a
ld b,12
HPL3: ld a,(hl)
rl a
ld (hl),a
dec hl
djnz HPL3
ld bc,24
add hl,bc
pop bc
djnz HPL2
pop bc
djnz HPL4
ld hl,BOSShp ; Update boss health points
dec (hl)
ld a,(hl)
cp 0
jp nz,SKP55
ld a,0
ld (BOSSf),a
SKP55:
ld a,240 ; Make boss freeze for a while
ld (BOSSmc),a
ld a,32 ; Initiate laser timer
ld (LTIMER),a
ld a,252 ; Stop shiplaserbeam
ld (SLASRy),a
call USCORE ; Update score
SKP54:
;[[[[ Ship laser part 2 [[[[
ld a,(SLASRy) ; Is there a laserbeam to update?
cp 252
jp z,SKP53
ld a,(SLASRy) ; Has the laserbeam reached the top yet?
cp 6
jp nz,SKP51
ld a,252
ld (SLASRy),a
jp SKP53
SKP51:
ld hl,SLASRy ; Move laserbeam two pixels up
dec (hl)
dec (hl)
ld a,(SLASRy) ; Draw new laserbeam
ld e,a
ld a,(SLASRx)
ld hl,80+SPRITES
call SPRITE
SKP53:
;[[[[ Boss shot part 2 [[[[
ld a,(ALASRf)
cp 1
jp nz,SKP58
ld a,(ALASRy) ; Draw new laserbeam
ld e,a
ld a,(ALASRx)
ld hl,25*8+SPRITES
call SPRITE
SKP58:
ret
;\[[[[[[[[[[[[\ BOSS \[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[
;\[[[[[[[[[[[[_ BOSSKILL _[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[
;ZDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDD?
;3 Boss killed 3
;@DDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDY
BOSSKILL:
ld ix,BOSSkr ; Get pointer to boss kill random
ld b,16
BKILL2: ; Loop to erase boss with cross sprite
ld a,(BOSSx)
add a,(ix+0)
inc ix
ld e,(ix+0)
inc ix
push ix
push bc
push af
push de
ld hl,SPRITES
call CLRSPR ; Clear a 8x8 part of the boss
pop de
pop af
push af
push de
ld hl,SPRITES+72
call SPRITE ; Put the cross
call BUFCOPY
ld hl,24000
call WAIT ; Wait for a while
pop de
pop af
ld hl,SPRITES
call CLRSPR ; Clear cross
pop bc
pop ix
djnz BKILL2
call BUFCOPY
ld hl,40000
call WAIT ; Wait for a while
call STGCLR
ret
;\[[[[[[[[[[[[\ BOSSKILL \[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[
;\[[[[[[[[[[[[_ ALIENY _[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[
;ZDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDD?
;3 Check if aliens has reached the last line 3
;@DDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDY
ALIENY:
ld a,(ALIENmy) ; Look for alien movement change
cp 0
ret nz
ld c,26 ; Get right y-value to compare with
ld hl,ALIENr4
ld b,3
GETYL: ld a,(hl)
cp 0
jp nz,LXIT01
ld a,c
add a,10
ld c,a
dec hl
djnz GETYL
LXIT01:
ld a,(ALIENli)
cp c
jp nz,DONE9
;[[[[ Aliens has reached bottom [[[[
ld b,6
INVL5:
push bc
call INVERT
pop bc
djnz INVL5
ld a,0
ld (LIVESb),a
ld a,'0'
ld (LIVESa),a
call STAT ; Show stats in a box and wait for 2nd
ld hl,02621h ; - Print msg to press 2nd
ld (08252h),hl ; Update cursorslocation
ld hl,MSG01
call 04781h ; Vputs
call WAIT2ND ; Wait for 2nd to be pressed
ld de,8e29h ; Copy safe ram area to graphbuf
ld hl,8265h
ld bc,768
ldir
call GAMEOVER
DONE9:
ret
;\[[[[[[[[[[[[\ ALIENY \[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[
;\[[[[[[[[[[[[_ MATH _[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[
;ZDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDD?
;3 Mathsteacher key 3
;@DDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDY
MATH:
ld hl,8e29h ; Copy graphbuf to safe ram area
ld de,8265h
ld bc,768
ldir
call BUFCLR ; Clear graphbuf
call BUFCOPY
call HOMEUP
ld hl,MSG05
call STRING
call READKEY ; Fetch first MATH press
KEYL3:
call READKEY ; Wait for MATH press
call OP2TOP1
call CONVOP1
cp 41
jp nz,KEYL3
ld de,8e29h ; Copy safe ram area to graphbuf
ld hl,8265h
ld bc,768
ldir
call BUFCOPY
ld hl,65000
call WAIT
ret
;\[[[[[[[[[[[[\ MATH \[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[
;\[[[[[[[[[[[[_ STGCLR _[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[
;ZDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDD?
;3 Stage cleared 3
;@DDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDY
STGCLR:
inc sp ; Don't return to ALIENS/BOSSKILL
inc sp
inc sp ; Don't return to MAIN/MBOSS
inc sp
;[[[[ Draw a box and print info [[[[
ld a,20 ; Draw a box
ld e,12
ld b,5
ld c,2
call BOX
set 7,(iy+20)
ld hl,01018h ; - Print Stage Cleared!
ld (08252H),hl ; Update cursorslocation
ld hl,MSG04
call 04781h ; Vputs
ld hl,01920h ; - Print "BONUS:"
ld (08252H),hl ; Update cursorslocation
ld hl,BONUS
call 04781h ; Vputs
ld hl,01935h ; - Print bonus points
ld (08252H),hl ; Update cursorslocation
ld hl,BONUS3
call 04781h ; Vputs
call BUFCOPY
;[[[[ Bonus counter [[[[
ld a,(BONUSt2) ; Get number of bonus points
cp 0
jp z,SKP84
ld b,a
SCRL4: push bc
ld hl,(SCOREb) ; Give player one point
inc hl
ld (SCOREb),hl
ld hl,SCR1 ; -- Update the ascii score
inc (hl)
ld b,3 ; Look for overflow loop
SCRL3: ld a,(hl)
cp ':'
jp nz,SKP80
ld (hl),'0'
dec hl
inc (hl)
djnz SCRL3
SKP80:
ld hl,BONUS1 ; -- Update the bonus score
inc (hl)
ld b,3 ; Look for overflow loop
SCRL5: ld a,(hl)
cp ':'
jp nz,SKP81
ld (hl),'0'
dec hl
inc (hl)
djnz SCRL5
SKP81:
ld hl,01935h ; - Print bonus points
ld (08252H),hl ; Update cursorslocation
ld hl,BONUS3
call 04781h ; Vputs
call BUFCOPY
pop bc
djnz SCRL4
SKP84:
ld hl,02221h ; - Print msg to press 2nd
ld (08252H),hl ; Update cursorslocation
ld hl,MSG01
call 04781h ; Vputs
call BUFCOPY
call WAIT2ND
;[[[[ Update variables [[[[
ld hl,858fh+100 ; Restore the variables start values
ld de,SHIPx
ld bc,DBYTES
ldir
ld hl,TIME ; Time for a boss level?
inc (hl)
ld a,(hl)
cp 3
jp nz,SKP70
ld (hl),0
ld a,1
ld (BOSSf),a
jp SKP71
SKP70:
ld a,(STARTy)
add a,2
ld (STARTy),a
ld c,a
ld ix,ALIENd1+2 ; - Update aliens y-coordinates
ld (ALIENli),a ; Update nr of lines aliens has moved down
ld de,3
ld b,32
LOOP01: ld a,(ix+0)
add a,c
ld (ix+0),a
add ix,de
djnz LOOP01
SKP71:
ld hl,LEVELa ; Increase level
inc (hl)
ld hl,LEVELb
inc (hl)
ld a,(hl) ; Last level?
cp 10
jp nz,SKP75
call OUTRO ; Then call outro
SKP75:
call LVINIT
ret
;\[[[[[[[[[[[[\ STGCLR \[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[
;\[[[[[[[[[[[[_ COLDT3 _[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[
;ZDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDD?
;3 Collision detection between barrier and laser 3
;@DDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDY
COLDT3:
;[[[[ Alien laser and barrier [[[[
ld a,(ALASRf) ; Is there an alien laser beam?
cp 0
jp z,SKP20
ld a,(ALASRy) ; Has the laserbeam reached the barriersection?
add a,7
cp 47
jp c,SKP20
ld a,(ALASRy) ; Has the laserbeam left the barriersection?
add a,7
cp 55
jp nc,SKP20
ld a,(ALASRy) ; Get laser y-coordinate
add a,7
ld e,a
ld hl,0 ; Do y*12
ld d,0
add hl,de
add hl,de
add hl,de
add hl,hl
add hl,hl
ld a,(ALASRx) ; Get laser x-coordinate
ld e,a
ld d,0 ; Do x/8
srl e
srl e
srl e
add hl,de
ld bc,8e29h+12 ; Add graphbuf address + one line
add hl,bc
ld c,10000000b ; Initiate laserpoint
ld a,(ALASRx)
ld b,00000111b ; Get the remainder of x/8
and b
cp 0 ; Is the beam aligned to 8*n,y?
jp z,SKP21
ld b,a
SHLOP3: srl c ; Shift the point to get right pixel bit
djnz SHLOP3
SKP21: ld a,(hl) ; Get barrier byte
and c ; And with laser point
cp 0
jp z,SKP20
ld a,(hl)
xor c
ld (hl),a
ld a,(ALASRy) ; Erase alien laser
ld e,a
ld a,(ALASRx)
ld hl,80+SPRITES
call CLRSPR
ld ix,(ALASRp) ; Redraw alien
ld l,(ix+0)
ld a,0
cp l
jp z,SKP27
ld h,0
ld bc,SPRITES
add hl,bc
ld a,(ix+1)
ld e,(ix+2)
call SPRITE
SKP27:
ld a,0 ; Reset the alien laser flag
ld (ALASRf),a
SKP20:
;[[[[ Player laser and barrier [[[[
ld a,(SLASRy) ; Is there an alien laser beam?
cp 252
jp z,SKP22
ld a,(SLASRy) ; Has the laserbeam reached the barriersection?
cp 57
jp nc,SKP22
ld a,(SLASRy) ; Has the laserbeam left the barriersection?
cp 48
jp c,SKP22
ld a,(SLASRy) ; Get laser y-coordinate
ld e,a
ld hl,0 ; Do y*12
ld d,0
add hl,de
add hl,de
add hl,de
add hl,hl
add hl,hl
ld a,(SLASRx) ; Get laser x-coordinate
ld e,a
ld d,0 ; Do x/8
srl e
srl e
srl e
add hl,de
ld bc,8e29h-12 ; Add graphbuf address - one line
add hl,bc
ld c,10000000b ; Initiate laserpoint
ld a,(SLASRx)
ld b,00000111b ; Get the remainder of x/8
and b
cp 0 ; Is the beam aligned to 8*n,y?
jp z,SKP23
ld b,a
SHLOP4: srl c ; Shift the point to get right pixel bit
djnz SHLOP4
SKP23: ld a,(hl) ; Get barrier byte
and c ; And with laser point
cp 0
jp z,SKP22
ld a,(hl)
xor c
ld (hl),a
ld a,(SLASRy) ; Erase player laser
ld e,a
ld a,(SLASRx)
ld hl,80+SPRITES
call CLRSPR
ld a,16 ; Initiate laser timer
ld (LTIMER),a
ld a,252 ; Reset the alien laser flag
ld (SLASRy),a
SKP22:
ret
;\[[[[[[[[[[[[\ COLDT3 \[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[
;\[[[[[[[[[[[[_ GAMEOVER _[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[
;ZDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDD?
;3 Game Over 3
;@DDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDY
GAMEOVER:
ld a,24
ld e,24
ld b,4
ld c,0
call BOX
set 7,(iy+20) ; Enable text-direct-to-lcd
ld hl,01d1fh ; - Print Game Over
ld (08252H),hl ; Update cursorslocation
ld hl,MSG02
call 04781h ; Vputs
ld a,(SCOREb+1) ; Check for new highscore
ld b,a
ld a,(HSCOREb+1)
cp b
jp c,HIGH
jp z,NXT03
jp NOHIGH
NXT03:
ld a,(SCOREb)
ld b,a
ld a,(HSCOREb)
cp b
jp c,HIGH
jp NOHIGH
HIGH: ; Update highscore
ld hl,(SCOREb)
ld (HSCOREb),hl
ld a,(SCR1)
ld (HSCR1),a
ld a,(SCR2)
ld (HSCR2),a
ld a,(SCR3)
ld (HSCR3),a
ld a,(SCR4)
ld (HSCR4),a
NOHIGH:
ld b,100 ; Wait for a while
WAITL7: push bc
call BUFCOPY
pop bc
djnz WAITL7
call NEWGAME
;\[[[[[[[[[[[[\ GAMEOVER \[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[
;\[[[[[[[[[[[[_ STAT _[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[
;ZDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDD?
;3 Print player status in a box and wait for 2nd 3
;@DDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDY
STAT:
ld hl,8e29h ; Copy graphbuf to safe ram area
ld de,8265h
ld bc,768
ldir
ld a,16 ; Draw a box
ld e,8
ld b,6
ld c,3
call BOX
res 7,(iy+20) ; Print text to LCD only
ld hl,00b16h ; - Print title text
ld (08252H),hl ; Update cursorslocation
ld hl,PRGNAME
call 04781h ; Vputs
ld hl,01316h+7 ; - Print score text
ld (08252H),hl ; Update cursorslocation
ld hl,SCORE
call 04781h ; Vputs
ld hl,0132dh+7 ; - Print score number
ld (08252H),hl ; Update cursorslocation
ld hl,SCR4
call 04781h ; Vputs
ld hl,01916h+7 ; - Print level text
ld (08252H),hl ; Update cursorslocation
ld hl,LEVEL
call 04781h ; Vputs
ld hl,01939h+7 ; - Print level number
ld (08252H),hl ; Update cursorslocation
ld hl,LEVELa
call 04781h ; Vputs
ld hl,01f16h+7 ; - Print lives text
ld (08252H),hl ; Update cursorslocation
ld hl,LIVES
call 04781h ; Vputs
ld hl,01f39h+7 ; - Print lives number
ld (08252H),hl ; Update cursorslocation
ld hl,LIVESa
call 04781h ; Vputs
ret
;\[[[[[[[[[[[[\ STAT \[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[
;\[[[[[[[[[[[[_ COLDT2 _[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[
;ZDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDD?
;3 Collision detection between alien laser and player 3
;@DDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDY
COLDT2:
ld a,(ALASRf) ; Is there an alien laser beam?
cp 0
ret z
;[[[[ Scan in y [[[[
ld a,(BOSSf)
cp 1
jp nz,SKP64
ld a,(ALASRy) ; Reached the player in y-level yet?
add a,7
cp 59
ret c
jp SKP65
SKP64:
ld a,(ALASRy) ; Reached the player in y-level yet?
add a,7
cp 59
ret c
SKP65:
;[[[[ Scan in x [[[[
ld a,(BOSSf)
cp 1
jp nz,SKP66
ld a,(ALASRx) ; Get boss shot x-coordinate
add a,7
ld c,a
ld a,(SHIPx) ; Get player x-coordinate
cp c
ret nc ; Return if not above
jp SKP67
SKP66:
ld a,(ALASRx) ; Get alien laserbeam x-coordinate
inc a
ld c,a
ld a,(SHIPx) ; Get player x-coordinate
cp c
ret nc ; Return if not above
SKP67:
ld a,(ALASRx) ; Get alien laserbeam x-coordinate
inc a
ld c,a
ld a,(SHIPx) ; Get player x-coordinate+13
add a,13
cp c
ret c ; Return if above
;[[[[ !!! HIT !!! [[[[
ld a,(BOSSf)
cp 1
jp z,SKP62
ld a,(ALASRy) ; Erase alien laser
ld e,a
ld a,(ALASRx)
ld hl,80+SPRITES
call CLRSPR
ld a,128 ; Init alien laser timer
ld (ALASRt),a
jp SKP63
SKP62:
ld a,(ALASRy) ; Erase alien laser
ld e,a
ld a,(ALASRx)
ld hl,25*8+SPRITES
call CLRSPR
ld a,32
ld (ALASRt),a
SKP63:
ld a,0 ; Reset the alien laser flag
ld (ALASRf),a
ld e,56
ld a,(OSHIPx) ; Load x-coordinate
ld hl,88+SPRITES
call CLRSPR ; Erase ship
ld e,56
ld a,(OSHIPx) ; Load x-coordinate
add a,8
ld hl,96+SPRITES
call CLRSPR ; Erase ship
ld e,56
ld a,(SHIPx) ; Load x-coordinate
ld hl,176+SPRITES
call SPRITE ; Draw wreck
ld e,56
ld a,(SHIPx) ; Load x-coordinate
add a,8
ld hl,184+SPRITES
call SPRITE ; Draw wreck
ld a,(BOSSf) ; Don't redraw alien if it was a boss shot
cp 1
jp z,SKP26
ld ix,(ALASRp) ; Redraw alien
ld l,(ix+0)
ld a,0
cp l
jp z,SKP26
ld h,0
ld bc,SPRITES
add hl,bc
ld a,(ix+1)
ld e,(ix+2)
call SPRITE
SKP26:
ld hl,LIVESa ; Decrement lives left
dec (hl)
ld hl,LIVESb
dec (hl)
call INVERT
call INVERT
call STAT ; Show stats in a box and wait for 2nd
ld hl,02621h ; - Print msg to press 2nd
ld (08252h),hl ; Update cursorslocation
ld hl,MSG01
call 04781h ; Vputs
call WAIT2ND ; Wait for 2nd to be pressed
ld de,8e29h ; Copy safe ram area to graphbuf
ld hl,8265h
ld bc,768
ldir
ld hl,LIVESb ; Last life?
ld a,(hl)
cp 0
jp nz,SKP18
call GAMEOVER
SKP18:
ld a,16 ; Initiate laser timer
ld (LTIMER),a
ld a,0
ld (SHIPx),a
DONE8:
ret
;\[[[[[[[[[[[[\ COLDT2 \[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[
;\[[[[[[[[[[[[_ ALASR _[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[
;ZDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDD?
;3 Alien laser 3
;@DDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDY
ALASR:
ld a,(ALASRt) ; Alien laser timer = 0 yet?
cp 0
jp z,SKP24
ld hl,ALASRt ; Update alien laser timer
dec (hl)
ret
SKP24:
ld a,(ALASRf) ; Look for alien laserbeam
cp 1
jp z,UPLASR ; Jump to update laser if there already is one
ld a,(DIFF) ; If DIFF=3, shoot now
cp 3
jp z,SKP74
ld a,(ALIENc) ; Has every single alien moved yet?
cp 0
ret nz
SKP74:
;[[[[ Look for ship in alien x area [[[[
ld ix,ALAST
SCNX1: ; Scan x
ld b,32 ; 32 possible aliens
SCNXL1: ld a,(ix) ; Pointer to the alien line data
cp 0 ; Is the alien dead?
jp z,NXT02
ld a,(SHIPx) ; Get player x-coordinate
add a,4
ld c,(ix+1) ; Get alien x-coordinate
cp c
jp c,NXT02 ; Jump if below
ld a,(ix+1) ; Get alien x-coordinate+8
add a,8
ld c,a
ld a,(SHIPx) ; Get player x-coordinate
cp c
jp nc,NXT02 ; Jump if not below
jp CFREE
NXT02: dec ix ; Next alien in datalist
dec ix
dec ix
djnz SCNXL1
jp DONE6 ; No ship in any alien x area
CFREE: ld (TEMP),ix
ld hl,(TEMP)
ld de,-ALIENd1
add hl,de
ld (TEMP2),hl
ld de,(TEMP2)
ld c,e
ld hl,(TEMP)
ld de,24
ld b,4 ; Check if there's an alien under
FREEL: ld a,c
add a,24
cp 96
jp nc,LXIT02
ld c,a
add hl,de
ld a,(hl)
cp 0
jp nz,NOFREE
djnz FREEL
NOFREE: jp DONE6 ; There's at least one alien under, don't shoot
LXIT02: ; No alien under, shoot!
;[[[[ Initiate alien laser [[[[
FIRE: ld a,r ; Init alien laser
srl a
and 00000001b
ld b,a
ld a,(ix+1)
add a,4
add a,b
ld (ALASRx),a
ld a,(ix+2)
ld (ALASRy),a
ld a,1
ld (ALASRf),a
ld (ALASRp),ix
jp DONE6
;[[[[ Update alien laser [[[[
UPLASR:
ld a,(ALASRy) ; Erase old alien laser
ld e,a
ld a,(ALASRx)
ld hl,80+SPRITES
call CLRSPR
ld a,(ALASRy) ; Update alien laser y-coordinate
inc a
ld (ALASRy),a
cp 57 ; Has alien laser reached the bottom?
jp nz,SKP16
ld a,0 ; If so, reset the alien laser flag
ld (ALASRf),a
jp DONE6
SKP16:
ld e,a ; Draw new alien laser
ld a,(ALASRx)
ld hl,80+SPRITES
call SPRITE
ld ix,(ALASRp) ; Draw alien over laser
ld a,(ix)
cp 0
jp z,DONE6
ld h,0
ld l,(ix)
ld bc,SPRITES
add hl,bc
ld a,(ix+1)
ld e,(ix+2)
call SPRITE
DONE6:
ret
;\[[[[[[[[[[[[\ ALASR \[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[
;\[[[[[[[[[[[[_ ALIENS _[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[
;ZDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDD?
;3 Move the aliens 3
;@DDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDY
ALIENS:
;[[[[ Check if alien is RIP'ing [[[[
ld a,(RIPt)
cp 0
jp z,NXT01
cp 1
jp nz,SKP14
ld ix,(RIPp) ; Erase RIP
ld (ix+0),0
ld a,(ix+1) ; Get x-coordinate for alien
ld e,(ix+2) ; Get y-coordinate for alien
ld hl,72+SPRITES
call CLRSPR
ld a,(ALIENk) ; Last alien?
cp 32
jp nz,SKP14
call STGCLR
SKP14:
ld a,(RIPt)
dec a
ld (RIPt),a
ret
;[[[[ Calculate pointer to alien data [[[[
NXT01:
ld ix,ALIENd1 ; Get pointer to alien data
ld a,(ALIENc) ; Get current offset in alien data
ld c,a ; Do c*3
add a,c
add a,c
ld c,a
ld b,0
add ix,bc
;[[[[ Check if alien is dead [[[[
ld a,(ix+0) ; Check if alien is dead
cp 0
jp nz,SKP11
ld hl,ALIENc ; Update alien counter
inc (hl)
ld a,(hl)
cp 32 ; Time to reset counter?
jp nz,NXT01
jp RESC1 ; Reset counter and return to main
;[[[[ Erase old alien [[[[
SKP11:
ld l,a ; Erase old alien
ld h,0
ld bc,SPRITES
add hl,bc
ld a,(ix+1)
ld e,(ix+2)
push ix
call CLRSPR
pop ix
;[[[[ Update alien data [[[[
ld a,(ALIENa) ; Anim frame
add a,(ix+0)
ld (ix+0),a
ld a,(ALIENmy) ; Y-coordinate
add a,(ix+2)
ld (ix+2),a
ld a,(ALIENmy) ; Skip x movement if y movement
cp 0
jp nz,NOXMOV
ld a,(ALIENm) ; X-coordinate
add a,(ix+1)
ld (ix+1),a
cp 88 ; Aliens reached the right edge?
jp nz,SKP9
ld a,1
ld (ALIENmc),a
jp SKP10
SKP9:
cp 0 ; Aliens reached the left edge?
jp nz,SKP10
ld a,1
ld (ALIENmc),a ; Set movement change flag
NOXMOV:
;[[[[ Draw new alien [[[[
SKP10:
ld l,(ix+0) ; Draw new alien
ld h,0
ld bc,SPRITES
add hl,bc
ld a,(ix+1)
ld e,(ix+2)
call SPRITE
;[[[[ Update alien counter [[[[
SKP8:
ld hl,ALIENc ; Update alien counter
inc (hl)
ld a,(hl)
cp 32 ; Time to reset counter?
jp nz,DONE3
RESC1:
ld (hl),0 ; Reset alien counter
ld a,(ALIENa) ; Change anim frame add
neg
ld (ALIENa),a
ld a,0
ld (ALIENmy),a ; Reset alien y movement flag
;[[[[ Look for alien movement change [[[[
ld a,(ALIENmc) ; Look for alien movement change
cp 1
jp nz,DONE3
ld a,(ALIENm) ; Change direction in movement
neg
ld (ALIENm),a
ld a,(ALIENys) ; Get alien y speed
ld (ALIENmy),a ; Set alien y movement flag
ld b,a
ld a,(ALIENli)
add a,b
ld (ALIENli),a ; Increase lines alien has moved down
ld a,0 ; Reset alien movement change flag
ld (ALIENmc),a
DONE3:
ret
;\[[[[[[[[[[[[\ ALIENS \[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[
;\[[[[[[[[[[[[_ COLDT1 _[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[
;ZDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDD?
;3 Collision detection between alien and laser 3
;@DDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDY
COLDT1:
ld a,(SLASRy) ; Is there a laserbeam on screen?
cp 252
ret z
;[[[[ Scan y-coordinates [[[[
TROW1:
ld a,(ALIENli) ; Get number of lines the aliens has moved down
add a,8
ld b,a
ld a,(SLASRy) ; Get laserbeam y-coordinate
cp b
jp nc,TROW2 ; Jump if not below
ld ix,ALIENd1
ld hl,ALIENr1
jp SCAN1
TROW2:
ld a,(ALIENli) ; Get number of lines the aliens has moved down
add a,18
ld b,a
ld a,(SLASRy) ; Get laserbeam y-coordinate
cp b
jp nc,TROW3 ; Jump if not below
ld ix,ALIENd2
ld hl,ALIENr2
jp SCAN1
TROW3:
ld a,(ALIENli) ; Get number of lines the aliens has moved down
add a,28
ld b,a
ld a,(SLASRy) ; Get laserbeam y-coordinate
cp b
jp nc,TROW4 ; Jump if not below
ld ix,ALIENd3
ld hl,ALIENr3
jp SCAN1
TROW4:
ld a,(ALIENli) ; Get number of lines the aliens has moved down
add a,38
ld b,a
ld a,(SLASRy) ; Get laserbeam y-coordinate
cp b
jp nc,DONE2 ; Jump if not below
ld ix,ALIENd4
ld hl,ALIENr4
jp SCAN1
;[[[[ Scan x-coordinates [[[[
SCAN1:
ld b,8 ; Eight possible aliens
SCAN1L: ld a,(ix) ; Pointer to the alien line data
cp 0 ; Is the alien dead?
jp z,NXT0
ld a,(SLASRx) ; Get laserbeam x-coordinate
ld c,(ix+1) ; Get alien x-coordinate
cp c
jp c,NXT0 ; Jump if below
ld a,(ix+1) ; Get alien x-coordinate+8
add a,8
ld c,a
ld a,(SLASRx) ; Get laserbeam x-coordinate
cp c
jp nc,NXT0 ; Jump if not below
jp HIT
NXT0: inc ix
inc ix
inc ix
djnz SCAN1L
jp DONE2
;[[[[ Erase the alien and the laserbeam [[[[
HIT:
dec (hl) ; ALIENrX=ALIENrX-1
ld h,0 ; -- Erase the alien and the laserbeam
ld l,(ix+0)
ld bc,SPRITES
add hl,bc
ld (ix+0),72 ; Erase alien in alien datalist (72=RIP)
ld a,(ix+1) ; Get x-coordinate for alien
ld e,(ix+2) ; Get y-coordinate for alien
push ix
call CLRSPR
pop ix
ld a,(SLASRy) ; Erase laserbeam
ld e,a
ld a,(SLASRx)
ld hl,80+SPRITES
push ix
call CLRSPR
pop ix
ld a,252
ld (SLASRy),a
call USCORE
ld hl,ALIENk ; Update number of killed aliens
inc (hl)
ld a,16 ; Initiate laser timer
ld (LTIMER),a
;[[[[ R.I.P. alien [[[[
ld a,(ix+1) ; Get x-coordinate for alien
ld e,(ix+2) ; Get y-coordinate for alien
ld hl,72+SPRITES
push ix
call SPRITE ; Blit RIP
pop ix
ld (RIPp),ix ; Init pointer and counter
ld a,16
ld (RIPt),a
DONE2:
ret
;\[[[[[[[[[[[[\ COLDT1 \[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[
;\[[[[[[[[[[[[_ SCORE _[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[
;ZDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDD?
;3 Update score 3
;@DDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDY
USCORE:
;[[[[ Update score [[[[
ld a,(DIFF)
ld b,a
POINTL: push bc ; Point loop based on DIFF
ld hl,(SCOREb) ; Give player point(s)
inc hl
ld (SCOREb),hl
ld hl,SCR1 ; -- Update the ascii score
inc (hl)
ld b,3 ; Look for overflow loop
SCRL: ld a,(hl)
cp ':'
jp nz,SKP17
ld (hl),'0'
dec hl
inc (hl)
djnz SCRL
SKP17:
pop bc
djnz POINTL
ret
;\[[[[[[[[[[[[\ SCORE \[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[
;\[[[[[[[[[[[[_ LASER _[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[
;ZDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDD?
;3 Update the ship's laserbeam 3
;@DDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDY
LASER:
ld a,(LTIMER) ; Has timer reached zero yet?
cp 0
jp z,SKP12
ld hl,LTIMER ; Update laser timer
dec (hl)
SKP12:
ld a,(SLASRy) ; Is there a laserbeam to update?
cp 252
ret z
ld a,(SLASRy) ; Erase old laserbeam
ld e,a
ld a,(SLASRx)
ld hl,80+SPRITES
call CLRSPR
ld a,(SLASRy) ; Has the laserbeam reached the top yet?
cp 0
jp nz,SKP01
ld a,252
ld (SLASRy),a
ret
SKP01:
ld hl,SLASRy ; Move laserbeam two pixels up
dec (hl)
dec (hl)
ld a,(SLASRy) ; Draw new laserbeam
ld e,a
ld a,(SLASRx)
ld hl,80+SPRITES
call SPRITE
DONE4:
ret
;\[[[[[[[[[[[[\ LASER \[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[
;\[[[[[[[[[[[[_ SHIP _[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[
;ZDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDD?
;3 Update the ship 3
;@DDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDY
SHIP:
;[[[[ Update the ship [[[[
ld e,56
ld a,(OSHIPx) ; Load old x-coordinate
ld hl,88+SPRITES
call CLRSPR ; Erase last ship
ld e,56
ld a,(OSHIPx) ; Load old x-coordinate
add a,8
ld hl,96+SPRITES
call CLRSPR ; Erase last ship
ld e,56
ld a,(SHIPx) ; Load x-coordinate
ld hl,88+SPRITES
call SPRITE ; Draw new ship
ld e,56
ld a,(SHIPx) ; Load x-coordinate
add a,8
ld hl,96+SPRITES
call SPRITE ; Draw new ship
ld a,(SHIPx) ; Update coordinates
ld (OSHIPx),a
;[[[[ Update bonus [[[[
ld a,(BONUSt2) ; If bonus = 0, don't dec any more
cp 0
jp z,SKP83
ld hl,BONUSdc
dec (hl)
ld a,(hl)
cp 0
jp nz,SKP83
ld a,(DIFF)
ld (BONUSdc),a
ld hl,BONUSt1 ; Dec lower byte
dec (hl)
ld a,(hl)
cp 0
jp nz,SKP83
ld (hl),20
inc hl ; Dec higher byte (the actual bonus score)
dec (hl)
SKP83:
ret
;\[[[[[[[[[[[[\ SHIP \[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[
;\[[[[[[[[[[[[_ KEYS _[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[
;ZDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDD?
;3 Look for keypress 3
;@DDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDY
KEYS:
ld a,0ffh ; Reset the keyport (kinda)
out (1),a
ld a,0feh ; Enable the arrows
out (1),a
in a,(1)
cp 253 ; Has anyone pressed left?
jp nz,NOLEFT
ld hl,SHIPx
ld a,(hl)
cp 0 ; Check for left edge
jp z,NOLEFT
dec (hl) ; Decrease SHIPx
NOLEFT:
cp 251 ; Has anyone pressed right?
jp nz,NORIGHT
ld hl,SHIPx
ld a,(hl)
cp 83 ; Check for right edge
jp z,NORIGHT
inc (hl) ; Increase SHIPx
NORIGHT:
ld a,0ffh ; Reset the keyport (kinda)
out (1),a
ld a,0bfh ; Enable the row with 2nd
out (1),a
in a,(1)
cp 223 ; Has anyone pressed 2nd
jp nz,NO2nd
ld a,(SLASRy) ; Check if there already is a laserbeam
cp 252
jp nz,NO2nd
ld a,(LTIMER) ; Ok to fire laser?
cp 0
jp nz,NO2nd
ld a,(SHIPx) ; Initiate laser
add a,6
ld (SLASRx),a
ld a,58
ld (SLASRy),a
NO2nd:
cp 191 ; Has anyone pressed MODE?
jp nz,NOMODE
call PAUSE
NOMODE:
ld a,0ffh ; Reset the keyport (kinda)
out (1),a
ld a,0fdh ; Enable the row with CLEAR
out (1),a
in a,(1)
cp 191 ; Check for CLEAR
jp nz,NOCLR ; Exit if clear is pressed
inc sp ; Adjust stack
inc sp
call XIT
NOCLR:
ld a,0ffh ; Reset the keyport (kinda)
out (1),a
ld a,0dfh ; Enable the row with MATH
out (1),a
in a,(1)
cp 191 ; Has anyone pressed MATH
jp nz,NOMATH
call MATH
NOMATH:
ret
;\[[[[[[[[[[[[\ KEYS \[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[
;\[[[[[[[[[[[[_ WAIT2ND _[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[
;ZDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDD?
;3 Wait for 2nd to be pressed 3
;@DDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDY
WAIT2ND:
call READKEY ; Fetch first 2nd press
KEYL2:
call READKEY ; Wait for 2nd press
call OP2TOP1
call CONVOP1
cp 21
jp nz,KEYL2
ret
;\[[[[[[[[[[[[\ WAIT2ND \[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[
;\[[[[[[[[[[[[_ INVERT _[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[
;ZDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDD?
;3 Inverts the graphbuf 3
;@DDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDY
INVERT:
ld de,8e29h ; Invert graphbuf
ld hl,768
ld bc,-1
INVL1: ld a,(de)
cpl
ld (de),a
inc de
add hl,bc
jp c,INVL1
ld b,8
WAITL2:
push bc
call BUFCOPY
pop bc
djnz WAITL2
ret
;\[[[[[[[[[[[[\ INVERT \[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[
;\[[[[[[[[[[[[_ PAUSE _[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[
;ZDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDD?
;3 Pause and show stats 3
;@DDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDY
PAUSE:
call STAT
ld hl,0261fh ; - Print msg to press MODE
ld (08252H),hl ; Update cursorslocation
ld hl,MSG03
call 04781h ; Vputs
call READKEY ; Fetch first mode press
KEYL1:
call READKEY ; Wait for mode press
call OP2TOP1
call CONVOP1
cp 22
jp nz,KEYL1
ld de,8e29h ; Copy safe ram area to graphbuf
ld hl,8265h
ld bc,768
ldir
ld b,16 ; Wait for a while
WAITL1:
push bc
call BUFCOPY
pop bc
djnz WAITL1
ret
;\[[[[[[[[[[[[\ PAUSE
\[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[
;\[[[[[[[[[[[[_ BOX _[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[
;ZDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDD?
;3 Draws a box @ a,e with size b,c 3
;@DDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDY
BOX:
ld (BOXx),a
ld (TEMP),a
ld a,e
ld (BOXy),a
ld a,b
ld (BOXxs),a
ld a,c
ld (BOXys),a
ld bc,13*8 ; - Left upper corner
ld (BOXp),bc
call DBOX
ld a,(BOXx)
add a,8
ld (BOXx),a
ld bc,14*8 ; - Middle of first row
ld (BOXp),bc
ld a,(BOXxs)
ld b,a
BOXL1: push bc
call DBOX
pop bc
ld a,(BOXx)
add a,8
ld (BOXx),a
djnz BOXL1
ld bc,15*8 ; - Right upper corner
ld (BOXp),bc
call DBOX
ld a,(TEMP)
ld (BOXx),a
ld a,(BOXy)
add a,8
ld (BOXy),a
ld a,(BOXys)
cp 0
jp z,SKP19
ld b,a
BOXL2: push bc
ld bc,16*8 ; - Left edge
ld (BOXp),bc
call DBOX
ld a,(BOXx)
add a,8
ld (BOXx),a
ld bc,21*8 ; - Middle of box
ld (BOXp),bc
ld a,(BOXxs)
ld b,a
BOXL3: push bc
call DBOX
pop bc
ld a,(BOXx)
add a,8
ld (BOXx),a
djnz BOXL3
ld bc,17*8 ; - Right edge
ld (BOXp),bc
call DBOX
ld a,(TEMP)
ld (BOXx),a
ld a,(BOXy)
add a,8
ld (BOXy),a
pop bc
djnz BOXL2
SKP19:
ld bc,18*8 ; - Left lower corner
ld (BOXp),bc
call DBOX
ld a,(BOXx)
add a,8
ld (BOXx),a
ld bc,19*8 ; - Middle of last row
ld (BOXp),bc
ld a,(BOXxs)
ld b,a
BOXL4: push bc
call DBOX
pop bc
ld a,(BOXx)
add a,8
ld (BOXx),a
djnz BOXL4
ld bc,20*8 ; - Right lower corner
ld (BOXp),bc
call DBOX
jp DONE7
DBOX: ld a,(BOXy) ; -- Erase area under and draw boxsprite
ld e,a
ld a,(BOXx)
ld hl,SPRITES
call CLRSPR
ld a,(BOXy)
ld e,a
ld a,(BOXx)
ld hl,(BOXp)
ld bc,SPRITES
add hl,bc
call SPRITE
ret
DONE7:
call BUFCOPY
ret
;\[[[[[[[[[[[[\ BOX \[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[
;\[[[[[[[[[[[[_ SPRITE _[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[
;ZDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDD?
;3 Blit or erase sprite ~ a=x, e=y, hl=sprite address 3
;@DDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDY
SPRITE:
push hl ; Save sprite address
;[[[[ Calculate the address in graphbuf [[[[
ld hl,0 ; Do y*12
ld d,0
add hl,de
add hl,de
add hl,de
add hl,hl
add hl,hl
ld d,0 ; Do x/8
ld e,a
srl e
srl e
srl e
add hl,de
ld de,8e29h
add hl,de ; Add address to graphbuf
ld b,00000111b ; Get the remainder of x/8
and b
cp 0 ; Is this sprite aligned to 8*n,y?
jp z,ALIGN
;[[[[ Non aligned sprite blit starts here [[[[
pop ix ; ix->sprite
ld d,a ; d=how many bits to shift each line
ld e,8 ; Line loop
LILOP: ld b,(ix+0) ; Get sprite data
ld c,0 ; Shift loop
push de
SHLOP: srl b
rr c
dec d
jp nz,SHLOP
pop de
ld a,b ; Write line to graphbuf
or (hl)
ld (hl),a
inc hl
ld a,c
or (hl)
ld (hl),a
ld bc,11 ; Calculate next line address
add hl,bc
inc ix ; Inc spritepointer
dec e
jp nz,LILOP ; Next line
jp DONE1
;[[[[ Aligned sprite blit starts here [[[[
ALIGN: ; Blit an aligned sprite to graphbuf
pop de ; de->sprite
ld b,8
ALOP1: ld a,(de)
or (hl) ; xor=erase/blit
ld (hl),a
inc de
push bc
ld bc,12
add hl,bc
pop bc
djnz ALOP1
DONE1:
ret
;\[[[[[[[[[[[[\ SPRITE \[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[
;\[[[[[[[[[[[[_ CLRSPR _[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[
;ZDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDD?
;3 Blit or erase sprite ~ a=x, e=y, hl=sprite address 3
;@DDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDY
CLRSPR:
push hl ; Save sprite address
;[[[[ Calculate the address in graphbuf [[[[
ld hl,0 ; Do y*12
ld d,0
add hl,de
add hl,de
add hl,de
add hl,hl
add hl,hl
ld d,0 ; Do x/8
ld e,a
srl e
srl e
srl e
add hl,de
ld de,8e29h
add hl,de ; Add address to graphbuf
ld b,00000111b ; Get the remainder of x/8
and b
cp 0 ; Is this sprite aligned to 8*n,y?
jp z,ALIGN2
;[[[[ Non aligned sprite erase starts here [[[[
pop ix ; ix->sprite
ld d,a ; d=how many bits to shift each line
ld e,8 ; Line loop
LILOP2: ld b,(ix+0) ; Get sprite data
ld c,0 ; Shift loop
push de
SHLOP2: srl b
rr c
dec d
jp nz,SHLOP2
pop de
ld a,b ; Write line to graphbuf
cpl
and (hl)
ld (hl),a
inc hl
ld a,c
cpl
and (hl)
ld (hl),a
ld bc,11 ; Calculate next line address
add hl,bc
inc ix ; Inc spritepointer
dec e
jp nz,LILOP2 ; Next line
jp DONE5
;[[[[ Aligned sprite erase starts here [[[[
ALIGN2: ; Erase an aligned sprite in graphbuf
pop de ; de->sprite
ld b,8
ALOP2: ld a,(de)
cpl
and (hl)
ld (hl),a
inc de
push bc
ld bc,12
add hl,bc
pop bc
djnz ALOP2
DONE5:
ret
;\[[[[[[[[[[[[\ CLRSPR \[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[
;\[[[[[[[[[[[[_ WAIT _[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[
;ZDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDD?
;3 Wait for a while ~ hl=times to do waitloop 3
;@DDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDY
WAIT:
push bc
ld bc,-1
WAITL: ld (TEMP),bc ; This instruction takes 20 cycles to execute
add hl,bc
jp c,WAITL
pop bc
ret
;\[[[[[[[[[[[[\ WAIT \[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[
;\[[[[[[[[[[[[_ LVINIT _[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[
;ZDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDD?
;3 Level init 3
;@DDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDY
LVINIT:
call BUFCLR ; Clear the graphbuf
ld a,'0' ; - Init bonus variables
ld (BONUS1),a
ld (BONUS2),a
ld (BONUS3),a
ld a,20
ld (BONUSt1),a
ld a,128
ld (BONUSt2),a
ld a,(DIFF)
ld (BONUSdc),a
ld a,(BOSSf)
cp 1
jp z,BOSSINI
;[[[[ Initiate barrier [[[[
ld a,8 ; Initiate barrier 1
ld e,48
ld hl,SPRITES+8
call SPRITE
ld a,16
ld e,48
ld hl,SPRITES+16
call SPRITE
ld a,40 ; Initiate barrier 2
ld e,48
ld hl,SPRITES+8
call SPRITE
ld a,48
ld e,48
ld hl,SPRITES+16
call SPRITE
ld a,72 ; Initiate barrier 3
ld e,48
ld hl,SPRITES+8
call SPRITE
ld a,80
ld e,48
ld hl,SPRITES+16
call SPRITE
;[[[[ Initiate aliens [[[[
ld a,8 ; -- Initiate aliens
ld e,0
ld ix,ALIENd1
ALIENL: ld a,(ix+0)
cp 255
jp z,SKP25
ld l,(ix+0)
ld h,0
ld bc,SPRITES
add hl,bc
ld a,(ix+1)
ld e,(ix+2)
push ix
call SPRITE
pop ix
inc ix
inc ix
inc ix
jp ALIENL
jp SKP25
;[[[[ Initiate boss [[[[
BOSSINI:
ld a,(LEVELb) ; Initiate values for current boss
cp 3
jp z,BOSSNR1
cp 6
jp z,BOSSNR2
jp BOSSNR3
BOSSNR1: ; Init for boss number 1
ld hl,56
ld a,9
ld (BOSShp),a
ld a,3
ld (BOSShs),a
ld a,160
ld (BONUSt2),a
jp ENLARGE
BOSSNR2: ; Init for boss number 2
ld hl,40
ld a,18
ld (BOSShp),a
ld a,6
ld (BOSShs),a
ld a,192
ld (BONUSt2),a
jp ENLARGE
BOSSNR3: ; Init for boss number 3
ld hl,24
ld a,27
ld (BOSShp),a
ld a,9
ld (BOSShs),a
ld a,255
ld (BONUSt2),a
ENLARGE:
ld bc,SPRITES ; hl contains sprite_nr*8 to enlarge
add hl,bc
ld de,8265h
ld b,8
BINIL2: push bc
ld c,10000000b
ld b,4
BINIL1: ld a,(hl) ; x-enlarge loop
and c
cp 0
jp z,SKP43
ld a,11110000b
ld (de),a
jp SKP44
SKP43:
ld a,0
ld (de),a
SKP44:
srl c
ld a,(hl)
and c
cp 0
jp z,SKP45
ld a,(de)
or 00001111b
ld (de),a
jp SKP46
SKP45:
ld a,(de)
and 11110000b
ld (de),a
SKP46:
srl c
inc de
djnz BINIL1
pop bc
inc de
inc de
inc de
inc de
inc de
inc de
inc de
inc de
inc hl
djnz BINIL2
ld hl,8265h
ld ix,8e29h+96+4
ld b,8
BINIL4: push bc
ld b,4
BINIL3: ld a,(hl) ; y-enlarge loop
ld (ix+0),a
ld (ix+12),a
ld (ix+24),a
ld (ix+36),a
inc ix
inc hl
djnz BINIL3
ld bc,44
add ix,bc
ld bc,8
add hl,bc
pop bc
djnz BINIL4
ld hl,24*8+SPRITES
ld a,(BOSShs)
ld b,a
ld a,0
HPL: ld e,0 ; Blit out boss health points
push af
push bc
push hl
call SPRITE
pop hl
pop bc
pop af
add a,9
djnz HPL
ld a,(DIFF)
ld (BOSShl),a
ld a,32
ld (ALASRt),a
;[[[[ Print stats and wait for 2nd [[[[
SKP25:
call STAT
ld hl,02621h ; - Print msg to press 2nd
ld (08252H),hl ; Update cursorslocation
ld hl,MSG01
call 04781h ; Vputs
call WAIT2ND
ld de,8e29h ; Copy safe ram area to graphbuf
ld hl,8265h
ld bc,768
ldir
;[[[[ Init variables [[[[
ld a,16 ; Initiate laser timer
ld (LTIMER),a
ld a,(DIFF) ; Set right difficulty
and 00000010b
srl a
ld b,a
ld a,(ALIENys)
add a,b
ld (ALIENys),a
inc sp ; Adjust stack
inc sp
ld a,(BOSSf)
cp 1
jp nz,SKP73
ld hl,MBOSS
push hl
jp DONE0
SKP73: ld hl,MAIN
push hl
DONE0:
ret
;\[[[[[[[[[[[[\ LVINIT \[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[
;\[[[[[[[[[[[[_ INIT _[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[
INIT:
call RINDOFF ; Runindicator off
call BUFCLR ; Clear the graphbuf
res 0,(iy+20) ; Reset G-T mode and hor. split mode
res 1,(iy+20)
ld de,858fh+100 ; Make backup of the variables start values
ld hl,SHIPx
ld bc,DBYTES
ldir
ret
;\[[[[[[[[[[[[\ INIT \[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[
;\[[[[[[[[[[[[_ XIT _[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[
;ZDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDD?
;3 Exit program and clean up 3
;@DDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDY
XIT:
ld bc,HSCR4
ld a,c
sub 27h
ld c,a
ld a,b
sbc a,93h
ld b,a
ld hl,(PROGPTR)
add hl,bc
ld a,(HSCR4)
ld (hl),a
inc hl
ld a,(HSCR3)
ld (hl),a
inc hl
ld a,(HSCR2)
ld (hl),a
inc hl
ld a,(HSCR1)
ld (hl),a
inc hl
inc hl
ld a,(HSCOREb)
ld (hl),a
inc hl
ld a,(HSCOREb+1)
ld (hl),a
call CLRTSHD ; Clear textshadow
call GOHOME ; Leave graphscreen and go to homescreen
call BUFCLR ; Clear the graphbuf
call READKEY ; Catch the clear press
call HOMEUP ; Place cursor at home
inc sp ; Adjust stack
inc sp
res 7,(iy+20) ; Enable text-direct-to-lcd
res 6,(iy+9) ; Reset statsvalid (I've used safe ram area 2)
ei ; Enable interrupts
ret ; Exit program
;\[[[[[[[[[[[[\ XIT \[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[[
;ZDDDDDDDDDDDDDDDDBDDDDDDDDDDDDDDDDBDDDDDDDDDDDDDDDDDDDDDBDDDDDDDBDDDDDDDDDDDD?
;3[[[[[ Z80 [[[[[[3 EQUALS 3[[[[[[[[[[[[[[[[[[[[[3 movax 3[[[[[[[[[[[[3
;@DDDDDDDDDDDDDDDDADDDDDDDDDDDDDDDDADDDDDDDDDDDDDDDDDDDDDADDDDDDDADDDDDDDDDDDDY
WAITKEY .equ 4CFEh ; Wait for a key and read
BUFCLR .equ 515Bh ; Clear the graph backup
BUFCOPY .equ 5164h ; Copy the graph backup to the screen
RINDOFF .equ 4795h ; Turn off runindicator
PRINTHL .equ 4709h ; Print HL in dec. on the screen
OP2TOP1 .equ 41C2h ; Move OP2 to OP1
CONVOP1 .equ 4EFCh ; Convert fp value in OP1 to a 2 byte hex
READKEY .equ 4A18h ; Read key and place it in OP2 as a fp value
GOHOME .equ 47A1h ; Go to home screen (finish gfx program)
CLRTSHD .equ 4765h ; Clear text shadow
HOMEUP .equ 4775h ; Place cursor at home
STRING .equ 470Dh ; Print 0 terminated string to screen (hl->string)
HTIMESL .equ 4382h ; hl=h*l
;ZDDDDDDDDDDDDDDDDBDDDDDDDDDDDDDDDDBDDDDDDDDDDDDDDDDDDDDDBDDDDDDDBDDDDDDDDDDDD?
;3[[[[[ Z80 [[[[[[3 DATA 3[[[[[[[[[[[[[[[[[[[[[3 movax 3[[[[[[[[[[[[3
;@DDDDDDDDDDDDDDDDADDDDDDDDDDDDDDDDADDDDDDDDDDDDDDDDDDDDDADDDDDDDADDDDDDDDDDDDY
.include sprites.db
.include spzlogo.db
PRGNAME .db "Spaze Invaders",0
PROGPTR .dw 0
DIFF .db 1 ; Difficulty (1=easy, 2=medium, 3=hard)
HSCORE .db "HighScore:",0 ; HighScore text
HSCR4 .db "0" ; Multiples of thousand in ascii
HSCR3 .db "3" ; Multiples of hundred in ascii
HSCR2 .db "0" ; Multiples of ten in ascii
HSCR1 .db "3",0 ; Multiples of one in ascii
HSCOREb .dw 303 ; HighScore in binary
MSG01 .db "Press 2nd",0
MSG02 .db "Game Over",0
MSG03 .db "Press MODE",0
MSG04 .db "Stage Cleared!",0
MSG05 .db "cos(42)*sin(303)",0
MSG06 .db "CONGRATULATIONS!!!",0
MSG07 .db "You have saved all the",0
MSG08 .db "hamsters on earth from",0
MSG09 .db "the evil aliens",39," claws",0
MSG10 .db "Have a nice day!",0
MSG11 .db "movax@algonet.se",0
MSG12 .db "www.algonet.se/~movax",0
TXT1 .db "By Hannes Edfeldt",0
TXT2 .db "PRESS 2nd TO START",0
TXT3 .db "EASY",0
TXT4 .db "MEDIUM",0
TXT5 .db "HARD",0
TXT6 .db "ALIEN CODE",0
TXT7 .db "presents",0
VERt .db "v1.0" ; Version text
LEVEL .db "Level:",0 ; Level text
LEVELa .db "1",0 ; Level in ascii
LEVELb .db 1 ; Level in binary
SCORE .db "Score:",0 ; Score text
SCR4 .db "0" ; Multiples of thousand in ascii
SCR3 .db "0" ; Multiples of hundred in ascii
SCR2 .db "0" ; Multiples of ten in ascii
SCR1 .db "0",0 ; Multiples of one in ascii
SCOREb .dw 0 ; Player score in binary
LIVES .db "Lives:",0 ; Lives text
LIVESa .db "3",0 ; Lives in ascii
LIVESb .db 3 ; Lives left in binary
BONUS .db "Bonus:",0 ; Bonus text
BONUS3 .db "0"
BONUS2 .db "0"
BONUS1 .db "0",0
BONUSt1 .db 20 ; Bonus timer 1
BONUSt2 .db 128 ; Bonus timer 2 (the actual bonus to get)
BONUSdc .db 0 ; Bonus decrement timer
BOXx .db 0 ; Box x-coordinate
BOXy .db 0 ; Box y-coordinate
BOXxs .db 0 ; Box x-size
BOXys .db 0 ; Box y-size
BOXp .dw 0 ; Box sprite ptr
TEMP .db 0 ; Temp store
.db 0 ; Extra temp byte
TEMP2 .db 0 ; Temp store 2
.db 0 ; Extra temp byte
TIME .db 1 ; Time for a boss level?
STARTy .db 0 ; y-coordinate for aliens to start at
SHIPx .db 0 ; Ship x-coordinate
OSHIPx .db 0 ; Old ship x-coordinate
SLASRx .db 0 ; Ship laser x-coordinate
SLASRy .db 252 ; Ship laser y-coordinate (252=no laserbeam)
LTIMER .db 0 ; 0=ok to fire laser, >0=wait
ALIENm .db 2 ; Alien x movement speed
ALIENys .db 1 ; Alien y movement speed (based on DIFF)
ALIENmy .db 0 ; Alien movement y (0=no movement, 1=movement)
ALIENmc .db 0 ; Alien movement change (0=no change, 1=time to change)
ALIENli .db 0 ; How many lines down has aliens moved yet
ALIENc .db 0 ; Alien counter (which alien to move)
ALIENa .db 8 ; Alien anim frame add
ALIENk .db 0 ; Number of aliens killed
ALIENr1 .db 8 ; Aliens left in row 1
ALIENr2 .db 8 ; Aliens left in row 2
ALIENr3 .db 8 ; Aliens left in row 3
ALIENr4 .db 8 ; Aliens left in row 4
RIPt .db 0 ; RIP timer
RIPp .dw 0 ; RIP pointer
ALASRx .db 0 ; Alien laser x coordinate
ALASRy .db 0 ; Alien laser y coordinate
ALASRf .db 0 ; Alien laser flag
ALASRt .db 0 ; Alien laser timer
ALASRp .dw 0 ; Pointer to the alien who shot the last beam
BOSSx .db 32 ; Boss x-coordinate
BOSSmd .db 1 ; Boss movement direction
BOSSxc .db 31 ; Boss x-movement counter
BOSSmc .db 0 ; Boss "time-to-move?" counter
BOSSf .db 0 ; Is this a boss level? / Boss alive?
BOSShp .db 03 ; Boss health points
BOSShs .db 01 ; Boss health point sprites
BOSSld .db 0 ; Boss shot destination
BOSSlt .db 0 ; Boss shot timer
BOSShl .db 0 ; Hits left before boss lose on hp
BOSSkr .db 16,8,8,32,16,24,24,8 ; Boss kill random
.db 0,16,24,32,0,8,16,16
.db 24,24,8,8,0,32,8,24
.db 24,16,16,32,8,16,0,24
MENUc .db 1 ; Menu choice (1=easy, 2=medium, 3=hard)
MENUoc .db 1 ; Menu old choice
MENUt .db 12 ; Menu timer
FLASHt .db 16 ; Flash timer
FLASHf .db 0 ; Flash flag
LOGOl .db 0 ; Logo line in fx process
ALIENd1 .db 24,8,0 ; First line of alien data (sprite address,x,y)
.db 24,18,0
.db 24,28,0
.db 24,38,0
.db 24,48,0
.db 24,58,0
.db 24,68,0
.db 24,78,0
ALIENd2 .db 40,8,10 ; Second line of alien data (sprite address,x,y)
.db 40,18,10
.db 40,28,10
.db 40,38,10
.db 40,48,10
.db 40,58,10
.db 40,68,10
.db 40,78,10
ALIENd3 .db 56,8,20 ; Third line of alien data (sprite address,x,y)
.db 56,18,20
.db 56,28,20
.db 56,38,20
.db 56,48,20
.db 56,58,20
.db 56,68,20
.db 56,78,20
ALIENd4 .db 56,8,30 ; Fourth line of alien data (sprite address,x,y)
.db 56,18,30
.db 56,28,30
.db 56,38,30
.db 56,48,30
.db 56,58,30
.db 56,68,30
ALAST: .db 56,78,30
.db 255 ; End of alien data
DBYTES .equ ($-SHIPx-1)
.end
;ZDDDDDDDDDDDDDDDDBDDDDDDDDDDDDDDDDBDDDDDDDDDDDDDDDDDDDDDBDDDDDDDBDDDDDDDDDDDD?
;3[[[[[ Z80 [[[[[[3 Spaze Invaders 3[[[[[[[[[[[[[[[[[[[[[3 movax 3[[[[[[[[[[[[3
;@DDDDDDDDDDDDDDDDADDDDDDDDDDDDDDDDADDDDDDDDDDDDDDDDDDDDDADDDDDDDADDDDDDDDDDDDY
References: