worm 0.83.0317: peaworm mode, bouncy balls, hiscore
[wormy.git] / worm.asm
index 8d0bab19e702045dc9706836d894d6a971d05c45..d8f61e0b88a5b453177a0cf28cd44eca856a9483 100644 (file)
--- a/worm.asm
+++ b/worm.asm
@@ -1,7 +1,7 @@
 ; Title                      : Worm
 ; Version                    : 0.92
 ; Release Date               : soon (I hope)
-; Filename                   : worm.86p
+; Filename                   : worm.86p (3404)
 ; Author(s)                  : Shiar
 ; Email Address              : shiar@mailroom.com
 ; ICQ UIN                    : #43840958
 ;----------- TO-DO -----------
 ;-----------------------------
 
-;       Shiar 23.I .00
+;       Shiar 3.III.00
 
 ;Feel like doing something? (name indicates who's working on it)
-;  * linkplay TESTING! (+faster)
+;  * linkplay
 ;  * singleplay ending
 ;  * titlescreen
 ;  * make linkplay available for all gametypes (not just deathmatch)
 ;  * two worms collide with heads -> both should die
-;  * bouncing balls :)
 ;  * game types:
-;    * hot pursuit/hunting/kodh: catch the other player and vv
 ;1)  * ctf: take enemy flag (right-bottom) and return to your flag (left-top)
 ;1)  * domination?: take control points by running over them and hold them
-;  * AI worms?
 ;1)* sprites for picks instead of blocks
-;  * fix linedraw procedure
-;  * save hiscore
 
-;1) Shiar: working on a new pickup-system allowing more than one "food" and different pickup-handling
+;1) Working on a new pickup-system allowing more than one "food" and different pickup-handling
 
 #include "TI86.inc"
 
@@ -63,9 +58,9 @@ WormIcon:
   .db %11000011,%10000000
 
 Start:
-  ld (SpSave),sp
+  ld  (SpSave),sp
   call _runIndicOff
-;  call _flushAllMenus
+  call _flushAllMenus
   call _clrLCD
   res 2,(iy+13) ;appAutoScroll
 
@@ -76,25 +71,25 @@ Start:
 ;----- build trig tables -----
 ;-----------------------------
 
-  ld hl,TrigPrecalc
-  ld de,SinCosTable
+  ld  hl,TrigPrecalc
+  ld  de,SinCosTable
   push de                        ; >> 1
-  ld bc,65
+  ld  bc,65
   ldir
   dec hl
-  ld b,63
+  ld  b,63
 MirrorSineWave:
   dec hl
-  ld a,(hl)
-  ld (de),a
+  ld  a,(hl)
+  ld  (de),a
   inc de
   djnz MirrorSineWave
   pop hl                         ; << 0k
-  ld b,128+64
+  ld  b,128+64
 NegativeSineWave:
   xor a
   sub (hl)
-  ld (de),a
+  ld  (de),a
   inc hl
   inc de
   djnz NegativeSineWave
@@ -126,7 +121,7 @@ select:
   ld  a,b
   or  a
   jr  nz,gooptionsMenu
-  jp  ThePartyIsOn
+  jp  LetsGetThisPartyOn
 notselect
   cp  K_EXIT
   jp  z,ExitNoStats
@@ -238,7 +233,7 @@ notup:
 ;-------- start game ---------
 ;-----------------------------
 
-ThePartyIsOn:
+LetsGetThisPartyOn:
   ld  hl,Gametype
   ld  a,(hl)
   add a,a
@@ -248,17 +243,19 @@ ThePartyIsOn:
   ld  hl,gamesdata
   add hl,de
 
-  or  a
-  jr  nz,notsingle
-  inc a
+  ld  a,(hl)
+  push af
+  and _datasingl
+  jr  z,notsingle
+  ld  a,1
   ld  (nrworms),a
 notsingle:
-  ld  a,(hl)
+  pop af
   ld  (gameCar),a
   push af
 
   and _datascore
-  ld  de,$FF64
+  ld  de,$FF64 ;virt.infinate
   jr  z,setscorelimit
   ld  d,0 ;de=100
 setscorelimit:
@@ -273,8 +270,14 @@ setscorelimit:
 
 linkmatch:
   call _clrWindow
+
+
+; in  a,(7)
+; and %11
+; cp  %11
   ld  a,WormVersion
-  call SendByte
+; jr  nz,host
+  call send
   jr  c,host
 
 client:
@@ -306,22 +309,19 @@ multiplayer:
 
 GameOver:
   call _clrLCD
-  xor a
-  ld  (worm1+died),a
-  ld  (worm2+died),a
-  ld  (worm3+died),a
-  ld  (worm4+died),a
-  ld  h,a
-  ld  l,a
-  ld  (worm1+score),hl
-  ld  (worm2+score),hl
-  ld  (worm3+score),hl
-  ld  (worm4+score),hl
-  inc a
-  ld  (worm1+delay),a
-  ld  (worm2+delay),a
-  ld  (worm3+delay),a
-  ld  (worm4+delay),a
+  ld  hl,0
+  ld  (worm1+died),hl
+;+died=0 \ +score1=0
+  ld  (worm2+died),hl
+  ld  (worm3+died),hl
+  ld  (worm4+died),hl
+  inc h
+  ld  (worm1+score+1),hl
+;+score2=0 \ +delay=1
+  ld  (worm2+score+1),hl
+  ld  (worm3+score+1),hl
+  ld  (worm4+score+1),hl
+  ld  a,l
   ld  (Level),a
   ld  hl,worm1set+4
   ld  de,worm1+lives
@@ -342,19 +342,39 @@ GameOver:
   pop de
 
 StartLevel:
-  ld  a,(de)
-  ld  (Left),a
-  inc de
-  ld  a,(de)
-  ld  (Speed),a
-  inc de
-  ld  a,(de)
+  ex  de,hl
+  ld  de,Left
+  ldi
+  ld  de,Speed
+  ldi
+  ld  a,(hl)
   ld  (worm1+grow),a
   ld  (worm2+grow),a
   ld  (worm3+grow),a
   ld  (worm4+grow),a
-  inc de
+  ld  (beginsize),a
+  inc hl
+
+  ld  a,(hl)
+  inc hl
+  ld  (nrballs),a
+  or  a
+  jr  z,toobad_noballs
+  ld  de,ballpos
+  ldi
+  ldi
+toobad_noballs:
+
+#ifdef 0
+  ld  a,(gameCar)
+  and _datahunt
+  jr  z,nohunter
+  ld  a,huntersize
+  ld  (worm2+grow),a
+nohunter:
+#endif
 
+  ex  de,hl
   ld  (thislevel),de
   push de
   ld  hl,worm1set
@@ -587,6 +607,22 @@ GameLoop:
   ld  bc,(worm1+pos)
   call DisplayField
 
+  ld  a,1
+flashtime =$-1
+  dec a
+  jr  z,noflash
+  ld  (flashtime),a
+  ld  hl,$fc00+(16*7)
+screeninvertloop:
+  ld  a,(hl)
+  cpl
+  ld  (hl),a
+  inc hl
+  xor a
+  cp  h
+  jr  nz,screeninvertloop
+noflash:
+
   ld  a,0
 Speed =$-1
   or  a
@@ -597,6 +633,8 @@ Delay:
   jr  nz,Delay
 NoDelay:
 
+  call handlethatneatlittleball
+
   ld  ix,worm1
   ld  a,(nrworms)
   ld  b,a
@@ -630,9 +668,14 @@ NotPaused:
   jr  Exit ;&&
 
 WormDead:
+  ld  a,2
+  ld  (flashtime),a
+
   ld  h,(ix+tail+1)
   ld  l,(ix+tail)
-  push hl
+  ld  d,(ix+head+1)
+  ld  e,(ix+head)
+  jr  DoesWormTailEqualsWormHead ;chk4 size=0
 removewormloop:
   ld  c,(hl)
   inc hl
@@ -642,32 +685,22 @@ removewormloop:
   push hl
   call res4pixels
   pop hl
-  ld  a,(ix+head)
-  cp  l
-  jr  nz,removewormloop
-  ld  a,(ix+head+1)
-  cp  h
+  inc (ix+grow)
+DoesWormTailEqualsWormHead:
+  call _cphlde
   jr  nz,removewormloop
 
-  ;hl=ix+head
-  pop de ;ix+tail
-  or  a
-  sbc hl,de
-  ld  a,l
-  rr  h
-  rra
-  inc a
+  ld  a,(gameCar)
+  and _datasingl
+  jr  nz,safewormsizedone
+  ld  a,0
+beginsize =$-1
   ld  (ix+grow),a
+safewormsizedone:
 
-  push ix
-  ld  de,10
-  call DecScore
-  pop ix
-
-  ld  h,(ix+head+1)
-  ld  l,(ix+head)
-  ld  (ix+tail+1),h
-  ld  (ix+tail),l
+  ;de=ix+head
+  ld  (ix+tail+1),d
+  ld  (ix+tail),e
   ld  a,50
   ld  (ix+delay),a
 
@@ -684,6 +717,10 @@ thislevel =$+1
 
   inc (ix+died)
   dec (ix+lives)
+  push af
+  ld  de,10
+  call DecScore
+  pop af
   ret nz ;HandleWorm done
   ld  a,(gameCar)
   and _datalivel
@@ -751,7 +788,7 @@ NoLinkIndic:
 
   ld  a,16
   ld  (_curCol),a
-  inc hl
+  inc hl ;worm+score
   call _ldHLind ;ld hl,(hl)
   call showHL ;worm+score
 
@@ -761,6 +798,29 @@ NoLinkIndic:
   pop bc
   djnz displayWormStats
 
+  ld  a,(gameCar)
+  and _datasingl
+  jr  z,hiscorecheckdone
+checkhiscore:
+  ld  de,(worm1+score)
+HiScore =$+1
+  ld  hl,0
+  ld  a,e
+  cp  l
+  jr  c,NotNewHigh
+  ld  a,d
+  cp  h
+  jr  c,NotNewHigh
+  ld  (HiScore),de
+  ex  de,hl ;disp.new hiscore
+NotNewHigh:
+  ex  de,hl
+  ld  hl,txthiscore
+  call _puts
+  ex  de,hl
+  call showHL
+hiscorecheckdone:
+
 waitkey:
   halt
   halt
@@ -781,14 +841,6 @@ waitkey:
 ;8Snaky   @    00 04820
 
 ExitNoStats:
-;  ld  a,(Eaten)
- xor a
-  ld  hl,HiScore
-  cp  (hl)
-  jr  c,NotNewHigh
-  ld  (hl),a
-NotNewHigh:
-
   ld  hl,_asapvar
   rst 20h ;_ABS_MOV10TOOP1
   rst 10h ;_FINDSYM
@@ -798,7 +850,7 @@ NotNewHigh:
   adc a,0
   call _SET_ABS_DEST_ADDR
 
-  xor a        
+  xor a
   ld  hl,start
   call _SET_ABS_SRC_ADDR
   ld  hl,end-start
@@ -924,14 +976,7 @@ notmoveY: ;bc=newpos
   xor 3
   ld  d,a
 GotFour:
-  call CheckPixel
-  inc b
-  call CheckPixel
-  inc c
-  call CheckPixel
-  dec b
-  call CheckPixel
-  dec c
+  call chk4pixels
   rl  d
   jp  nc,Drawworm
 
@@ -967,22 +1012,19 @@ PeaX =$-1
   ld  hl,Left
   dec (hl)
   push af
-  push ix
   ld  de,10
   call IncScore
-  pop ix
   pop af
-  jr  nz,NotNextLevel
+  jr  nz,still_alive_not_dead
   ld  a,(gameCar)
   and _datafoodl
-  jr  z,NotNextLevel
+  jr  z,still_alive_not_dead
   ld  hl,Level
   ld  a,(hl)
   inc (hl)
   pop hl                         ; << call
   pop hl                         ; << call
   pop de                         ; << levelp new
-;  pop hl                         ; << levelp old
   cp  NUM_LEVELS
   jp  z,Exit
   ld  a,(gameCar)
@@ -996,17 +1038,17 @@ checkhitotherworm:
   .db $dd,$7d ;ld a,lx
   cp  worm2&255
   ret nz
-
-  ld  hl,worm1+tail
-  ld  d,20
+ThisIsJustASillyUselessLabel:
+  ld  hl,(worm1+tail)
+  ld  de,(worm1+head)
 nextotherwormbit:
-  ld  a,b
+  ld  a,c
   sub (hl)
   inc hl
   inc a
   cp  4
   jr  nc,nothit1 ;no
-  ld  a,c
+  ld  a,b
   sub (hl)
   inc a
   cp  4
@@ -1014,19 +1056,9 @@ nextotherwormbit:
 nothit1:
   inc hl
   res resbit,h
-  push bc
-  push de
-  push hl
-;  ld  de,worm1+head
-;  call _cphlde
- dec d
-  pop hl
-  pop de
-  pop bc
+  call _cphlde
   jr  nz,nextotherwormbit
   ret
-otherwormHIT:
-  jp Exit
 
 checkhitlapline:
   ld  a,63
@@ -1036,26 +1068,36 @@ checkhitlapline:
   ret nz
 nextlaphalf:
   ld  a,c
-  and 32 ;>=32?
+  and 32 ;y>=32?
   jr  nz,nolap
   cp  (ix+reserv)
   jr  z,nolap
-  push ix
   push bc
   ld  de,20
   call IncScore
   pop bc
-  pop ix
   xor a
 nolap:
   ld  (ix+reserv),a
   ret
 
-NotNextLevel:
+otherwormHIT:
+  push ix
+  ld  de,10
+  call IncScore
+  ld  ix,worm1
+  call WormDead
+  pop ix
+  pop bc
+still_alive_not_dead:
 
 ;-------- draw worm ----------
 
 Drawworm:
+  ld  a,(gameCar)
+  and _datahunt
+  call nz,HuntingTimeScore
+
   ld  c,(ix+pos)
   ld  b,(ix+pos+1)
 
@@ -1073,13 +1115,7 @@ Drawworm:
   ld  (ix+head),l
   ld  (ix+head+1),h
 
-  call SetPixel
-  inc b
-  call SetPixel
-  inc c
-  call SetPixel
-  dec b
-  call SetPixel
+  call set4pixels
 
   ld  a,(ix+grow)
   dec a
@@ -1105,7 +1141,59 @@ res4pixels:
   inc c
   call ResPixel
   dec b
-  jp  ResPixel
+ResPixel:
+  call FindPixel
+  cpl
+  and (hl)
+  ld  (hl),a
+  ret
+
+;-----------------------------
+;---------- ball -------------
+;-----------------------------
+
+handlethatneatlittleball:
+  ld  a,0
+nrballs =$-1
+  or  a
+  ret z
+ballpos =$+1
+  ld  bc,$0503
+  call res4pixels
+  dec c
+  ld  e,b
+ballxmove:
+  inc b ;=%000100 dec=%000101
+  call checkballhit
+  jr  z,ballxdone
+  ld  b,e
+  ld  hl,ballxmove
+  call letsmovetheotherway
+ballxdone:
+  ld  e,c
+ballymove:
+  inc c ;=%001100 dec=%001101
+  call checkballhit
+  jr  z,balldone
+  ld  c,e
+  ld  hl,ballymove
+  call letsmovetheotherway
+balldone:
+  ld  (ballpos),bc
+  jp  set4pixels
+
+letsmovetheotherway:
+  ld  a,1
+  xor (hl)
+  ld  (hl),a
+  ret
+
+checkballhit:
+  ld  d,0
+  call chk4pixels
+  xor a
+  cp  d
+  ret
 
 ;-----------------------------
 ;----------- procs -----------
@@ -1116,8 +1204,8 @@ NewPea:
   ld hl,0
   ld de,12345
 Seed =$-2
-  ld a,7921 & 255
-  ld bc,1000h+(7921/256)
+  ld a,7921&255
+  ld bc,$1000+(7921/256)
 domult16:
   add hl,hl
   rla
@@ -1127,12 +1215,12 @@ domult16:
 noadd16:
   djnz domult16
   inc hl
-  ld  (Seed),hl ;seed=(seed*7921+1) MOD 65536
+  ld  (Seed),hl ;seed=(seed*7921+1)\65536
 
   ld  a,(FieldWidth)
   add a,123
   cp  h
-  jr c,NewPea
+  jr  c,NewPea
   inc h
   inc h
   ld a,(FieldHeight)
@@ -1180,19 +1268,29 @@ DrawPeaPixel:
 
 ;-------- pixelprocs ---------
 
-ResPixel: ;at bc
-  call FindPixel
-  cpl
-  and (hl)
-  ld  (hl),a
-  ret
-
+set4pixels:
+  call SetPixel
+  inc b
+  call SetPixel
+  inc c
+  call SetPixel
+  dec b
 SetPixel: ;at bc
   call FindPixel
   or  (hl)
   ld  (hl),a
   ret
 
+chk4pixels: ;&&
+  call CheckPixel
+  inc b
+  call CheckPixel
+  inc c
+  call CheckPixel
+  dec b
+  call CheckPixel
+  dec c
+  ret
 CheckPixel: ;at bc in d
   call FindPixel
   and (hl)
@@ -1200,48 +1298,57 @@ CheckPixel: ;at bc in d
   dec d
   ret
 
-FindPixel: ;bc to ahl + de gone
-  push de
-  push bc
-  ld  a,b
-  and 7
-  add a,offsets_table & 255
-  ld  e,a
-  ld  d,offsets_table/256
-  ld  h,0
-  ld  l,c
-  add hl,hl
-  add hl,hl
-  add hl,hl
-  add hl,hl
-  add hl,hl
+;CLEM's FIND_PIXEL (131 cycles; 28 bytes)
+;            (b,c) to hl:a; destroyes: -)
+
+FindPixel:
+  ld  h,ScrBuffer/$800
+  ld  a,c
+  add a,a
+  add a,a
+  ld  l,a    ;hl=4*y + offset/8
   ld  a,b
-  and %11111000
-  rra
   rra
+  add hl,hl
   rra
+  add hl,hl
+  add hl,hl  ;hl=32*y + offset
+  rra        ;a=x/8
   or  l
   ld  l,a
-  ld  a,(de)
-  ld  de,ScrBuffer
-  add hl,de
-  pop bc
-  pop de
+  ld  a,b
+  and 7
+  cpl
+  rlca
+  rlca
+  rlca
+  ld  (FP_Bit),a
+  xor a
+FP_Bit =$+1
+  set 0,a
   ret
 
 ;----------- score -----------
 
-DecScore:
+HuntingTimeScore:
+  .db $dd,$7d ;ld a,lx
+  cp  worm2&255
+  ret z ;=worm#2
+  dec (ix+reserv)
+  ret nz
+  ld  de,10
+
+IncScore:
   ld  h,(ix+score+1)
   ld  l,(ix+score)
-  or  a
-  sbc hl,de
-  ret c
+  add hl,de
   jr  scorecommon
-IncScore:
+DecScore: ;&&&
   ld  h,(ix+score+1)
   ld  l,(ix+score)
-  add hl,de
+  or  a
+  sbc hl,de
+  ret c
 scorecommon:
   ld  (ix+score+1),h
   ld  (ix+score),l
@@ -1251,8 +1358,9 @@ scorelimit =$-2
   jp  nc,Exit
 
 showstats:
-  xor a
-  sbc hl,hl
+  push ix
+  ld  h,0
+  ld  l,h
   ld  (_penCol),hl
   ld  a,(nrworms)
   ld  b,a
@@ -1262,9 +1370,7 @@ showstats:
   jr  nz,showstatsS
 showstatloop:
   push bc
-  push ix
   call showstat
-  pop ix
   ld  de,worm2-worm1
   add ix,de
   ld  hl,_penCol
@@ -1273,6 +1379,7 @@ showstatloop:
   ld  (hl),a
   pop bc
   djnz showstatloop
+  pop ix
   ret
 
 showstat:
@@ -1283,16 +1390,19 @@ showscore:
   ld  h,(ix+score+1)
   ld  l,(ix+score)
   call _D_HL_DECI
-  jp  _vputs
+  jr __vputs
 showlives:
   ld  a,(ix+lives)
   add a,'0'
-  jp  _vputmap
+__vputmap:
+  push ix
+  call _vputmap
+  pop ix
+  ret
 
 showstatsS:
-  push ix
   ld  hl,txtLevel
-  call _vputs
+  call __vputs
   ld  a,(Level)
   cp  10
   jr  c,tilllevel9
@@ -1302,12 +1412,11 @@ showstatsS:
   push af
   ld  a,l
   add a,'0'
-  call _vputmap
+  call __vputmap
   pop af
 tilllevel9:
   add a,'0'
-  call _vputmap
-  pop ix
+  call __vputmap
 
   ld  a,98
   ld  (_penCol),a
@@ -1315,6 +1424,10 @@ tilllevel9:
   ld  a,123
   ld  (_penCol),a
   call showlives
+  ld  a,(gameCar)
+  and _datafoodl
+  pop ix
+  ret z
 showleft:
   ld  a,31
   ld  (_penCol),a
@@ -1323,12 +1436,16 @@ Left =$-1
   push af
   call _divAby10
   add a,'0'
-  call _vputmap
+  call __vputmap
   pop af
   add a,'0'
-  call _vputmap
+  call __vputmap
   ld  hl,txtLeft
-  jp _vputs
+__vputs:
+  push ix
+  call _vputs
+  pop ix
+  ret
 
 showLevel:
   ld  hl,txtLevel
@@ -1369,9 +1486,6 @@ savestr:
 
 ;-----------------------------
 
-offsets_table:
-  .db 128,64,32,16,8,4,2,1
-
 DisplayField:
   ld  a,c
   sub 29
@@ -1607,10 +1721,10 @@ Line: ;draw line from de to hl (d<h)
   push hl
   push de
   ld a,d
-;  cp h
-;  jr c,lineOrdered
-;  ex de,hl
-lineOrdered:  
+  cp h
+  jr c,lineOrdered
+  ex de,hl
+lineOrdered:
   ld  b,d
   ld  c,e
   push hl
@@ -1633,11 +1747,11 @@ connectedLine:
   jr  DoneLine
 LineNotPoint:
   sub h
-  ld  de,16
+  ld  de,32
   jr  nc,LinePositiveY
   neg
-  ld  de,-16
-LinePositiveY:  
+  ld  de,-32
+LinePositiveY:
   cp  b
   jr  nc,SteepLine
   add a,a
@@ -1650,7 +1764,7 @@ LinePositiveY:
   ld  a,h
   sub b
   pop hl
-LineLoopGentle: 
+LineLoopGentle:
   push af
   ld  a,(hl)
   or  c
@@ -1658,7 +1772,7 @@ LineLoopGentle:
   rrc c
   jr  nc,$+3
   inc hl
-  pop af       
+  pop af
   jp  m,line2sm
 line1sm:
   add a,0
@@ -1684,7 +1798,7 @@ SteepLine:
   sub h
   ld  b,h
   pop hl
-LineLoopSteep: 
+LineLoopSteep:
   push af
   ld  a,(hl)
   or  c
@@ -1736,6 +1850,8 @@ boxloopx:
 ;-----------------------------
 ;----------- link ------------
 ;-----------------------------
+#ifdef 0
+TIMEOUT = $1200
 
 send:
   push af ;ld b,a
@@ -1769,6 +1885,7 @@ ReceiveByteCont:
 ReceiveByte:
   call LinkPrep
 ReceiveBits:
+ ld de,TIMEOUT
 WaitRecBit:
   call checklink
   jr  z,LinkFailed
@@ -1786,6 +1903,7 @@ ReceiveLow:
   ld  (AckBit),a
   ld  a,d
   out (7),a
+ ld de,TIMEOUT
 WaitAckRec:
   call checklink
   cp  0
@@ -1818,12 +1936,14 @@ sendbit:
   ld  a,D0hD1l
 sendselected:
   out (7),a
+ ld de,TIMEOUT
 waitacknowledge:
   call checklink
   jr  nz,waitacknowledge
 SendAcked:
   ld  a,D0hD1h
   out (7),a
+ ld de,TIMEOUT
 waitsendready:
   call checklink
   cp  %11
@@ -1845,6 +1965,11 @@ linkerror:
   jp  Exit
 
 checklink:
+ pop hl
+ dec de
+ ld a,d
+ or e
+ jr z,LinkFailed
   ld  a,$BF ;key
   call _readkeypad
   bit 6,a
@@ -1852,6 +1977,7 @@ checklink:
 
   in  a,(7)
   and %11
+ jp (hl)
   ret
 
 _readkeypad:
@@ -1862,21 +1988,110 @@ _readkeypad:
   out (1),a
   pop af
   ret
+#endif
+
+send:
+SendByte:
+  in  a,(7)
+  and %11
+  jr  z,nolink
+  ld  b,8
+sendloop:
+  ld  de,$8000
+  rl  c
+  ld  a,%11010100
+  jr  nc,sendbit
+  ld  a,%11101000
+sendbit:
+  out (7),a
+sendwait1:
+  call checklink
+  in  a,(7)
+  and  %11
+  jr  nz,sendwait1
+  ld  a,%11000000
+  out (7),a
+sendwait2:
+  call checklink
+  in  a,(7)
+  and %11
+  cp  %11
+  jr  nz,sendwait2
+  djnz sendloop
+  xor a
+  ret
+timeout:
+  scf
+  ret
+
+
+receive:
+  in  a,(7)
+  and %11
+  jr  z,nolink
+  cp  %11
+  jr  z,receive
+  ld  b,8
+receiveloop:
+  ld  de,$8000
+receivewait1:
+  call checklink
+  in  a,(7)
+  and %11
+  cp  %11
+  jr  z,receivewait1
+  rra
+  rl  c
+  rra
+  ld  a,%11010100
+  jr  nc,receivebit
+  ld  a,%11101000
+receivebit:
+  out (7),a
+receivewait2:
+  call checklink
+  in  a,(7)
+  and %11
+  jr  z,receivewait2
+  ld  a,%11000000
+  out (7),a
+  djnz receiveloop
+  xor a
+  ret
+
+checklink:
+  dec de
+  ld  a,d
+  or  e
+  jr  z,timeout
+  ld  a,$BF ;key
+  call _readkeypad
+  bit 6,a
+  jr  z,timeout
+  ret
+_readkeypad:
+  out (1),a
+  in  a,(1)
+  push af
+  ld  a,%11111111
+  out (1),a
+  pop af
+  ret
+nolink:
+  jp  Exit
 
 ;-----------------------------
 ;---------- levels -----------
 ;-----------------------------
 
 LevelsDM:
-
-  .db 8,5,15
+  .db 8,5,15,0
   .db $40,30,2,$C0,30,125, $00,2,64,$80,54,64
   .db 128,57
   .db 0,0
 
 LevelsDM2:
-
-  .db 8,5,31
+  .db 8,5,31,0
   .db $40,28,2,$C0,28,125, $00,2,63,$80,54,63
   .db 128,57
   .db 0
@@ -1887,31 +2102,53 @@ LevelsDM2:
   .db 4,19,80,34
 
 LevelsR:
-  .db 8,5,24
+  .db 8,5,24,0
   .db $40,3,2,$40,6,2, $40,9,2,$40,12,2
   .db 128,57
   .db 0
   .db 1
   .db 8,29,32,20
 
-NUM_LEVELS = 9
+LevelsH:
+  .db 8,7,17,0
+#ifdef 0
+huntersize = 31
+#endif
+  .db $40,28,2,$C0,28,125, $00,2,63,$80,54,63
+  .db 128,57
+  .db 0
+  .db 4
+  .db 4,19,16,14
+  .db 4,19,80,14
+  .db 4,19,16,34
+  .db 4,19,80,34
+
+NUM_LEVELS = 10
 
 LevelsS:
 
-  .db 5,4,15        ;5 peas, speed 5
+ .db 4,5,10,1 \ .dw $20F
+ .db 0,2,63
+ .db 128,57
+ .db 2
+ .db 28,14,100,41
+ .db 28,41,100,14
+ .db 0
+
+  .db 5,4,15,0      ;peas,speed,begin_size,balls
   .db 0,2,63        ;d,y,x
   .db 128,57        ;field width, height
   .db 0             ;no additional lines
   .db 0             ;no boxes
 
-  .db 8,4,15
+  .db 8,4,15,0
   .db $40,14,2
   .db 128,57
   .db 1
   .db 28,28,100,28  ;line coords: x1,y1,x2,y2
   .db 0
 
-  .db 9,4,15
+  .db 9,4,15,0
   .db $40,8,2
   .db 128,57
   .db 2
@@ -1919,7 +2156,7 @@ LevelsS:
   .db 28,41,100,41
   .db 0
 
-  .db 9,3,15
+  .db 9,3,15,0
   .db $40,8,2
   .db 128,80
   .db 2
@@ -1927,7 +2164,7 @@ LevelsS:
   .db 20,40,108,40
   .db 0
 
-  .db 10,3,15
+  .db 10,3,15,0
   .db 2,8,$40
   .db 128,90
   .db 3
@@ -1936,7 +2173,7 @@ LevelsS:
   .db 18,45,110,45
   .db 0
 
-  .db 7,3,15
+  .db 7,3,15,0
   .db 64,4,0
   .db 128,86
   .db 6
@@ -1948,7 +2185,7 @@ LevelsS:
   .db 110,20,110,64
   .db 0
 
-  .db 9,2,15
+  .db 9,2,15,0
   .db 4,10,$40
   .db 128,82
   .db 3
@@ -1957,7 +2194,7 @@ LevelsS:
   .db 0,60,74,60
   .db 0
 
-  .db 12,2,15
+  .db 12,2,15,0
   .db 64,4,0
   .db 128,90
   .db 6
@@ -1969,7 +2206,7 @@ LevelsS:
   .db 74,72,110,72
   .db 0
 
-  .db 8,2,15
+  .db 8,2,15,0
   .db 72,52,$c0
   .db 128,128
   .db 13
@@ -2008,31 +2245,33 @@ txtWelcome: .db "Welcome to Worm!! ",
             .db "by Shiar",0
 txtOptions: .db "Options",0
 txtGame:    .db "Singleplayer",0  ;0
-txtGame2:   .db "Deathmatch  ",0  ;1
-            .db "Foodmatch ",0    ;2
-            .db "LinkMatch",0     ;3 (>options)
-            .db "Hunting  ",0     ;4
-            .db "Race   ",0       ;5
-            .db "CTF ",0          ;6
-            .db "Domination",0    ;7
+txtGame2:   .db "Peaworm     ",0  ;1
+            .db "Deathmatch",0    ;2
+            .db "Foodmatch ",0    ;3
+            .db "LinkMatch",0     ;4 (>options)
+            .db "Hunting  ",0     ;5
+            .db "Race   ",0       ;6
+            .db "CTF ",0          ;7
+            .db "Domination",0    ;(>=8)
 txtWaiting: .db "Waiting...",0
 txtReceive: .db "Receiving...",0
 
 WormVersion = 092
-WormMsg:  .db "WORM by SHIAR -- test version",0
-txtLevel: .db "Level ",0
-txtWorms: .db "Worms: 0",0 ;follows txtLevel
-txtDied:  .db "Died ",0
-txtScore: .db "Score",0  ;follows txtDied
-txtLeft:  .db " left",0   ;follows txtScore
-txtReady: .db "Prepare!",0
+WormMsg:   .db "WORM by SHIAR -- test version",0
+txtLevel:  .db "Level ",0
+txtWorms:  .db "Worms: 0",0 ;follows txtLevel
+txtDied:   .db "Died ",0
+txtScore:  .db "Score",0  ;follows txtDied
+txtLeft:   .db " left",0   ;follows txtScore
+txthiscore:.db "HiScore:",0
+txtReady:  .db "Prepare!",0
 txtposReady = 7
-txtGO:    .db "----- GAME OVER -----",0
-HiScore:  .db 0
+txtGO:     .db "----- GAME OVER -----",0
 
 gamesdata:
 
 _datalink  = %00000001
+_datasingl = %00001000 ;singleplayer=1
 _datalivel = %00000010 ;ix+lives=0 limit
 _datafoodl = %00000100 ;left=0 limit
 _datanextl = %00001000 ;next level if left=0
@@ -2043,14 +2282,16 @@ _datascore = %10000000 ;score>=100 limit
 
 datasingle: .db %00011110
             .dw LevelsS
+datapeas:   .db %00011010
+            .dw LevelsS
 datadeathm: .db %00000010
             .dw LevelsDM2
 datafoodm:  .db %10010000
             .dw LevelsDM
 datalinkm:  .db %00000011
             .dw LevelsDM
-datahuntin: .db %00110100
-            .dw LevelsDM
+datahuntin: .db %10100000
+            .dw LevelsH
 datarace:   .db %11000000
             .dw LevelsR
 datactf:    .db %00000000
@@ -2060,17 +2301,17 @@ datadomin:  .db %00000000
 
 
 setdata = 18
-resbit  = 2 ;and%11111011
-worm1set:  .dw $B000,$B000 ;10110000
+resbit  = 2             ;and%11111011
+worm1set:  .dw $B000,$B000 ;%10110000
            .db 3,0,%01111110,%10,%100 ;< >
            .db "Worm #1",0
-worm2set:  .dw $B800,$B800 ;10111000
+worm2set:  .dw $B800,$B800 ;%10111000
            .db 3,0,%00111111,%10000,%1000 ;f1 f2
            .db "Worm #2",0
-worm3set:  .dw $E800,$E800 ;11101000 ;$D748+$1000+
+worm3set:  .dw $E800,$E800 ;%11101000 ;$D748+$1000+
            .db 3,0,%01011111,%10,%100 ;sto ,
            .db "Worm #3",0
-worm4set:  .dw $F000,$F000 ;11110000
+worm4set:  .dw $F000,$F000 ;%11110000
            .db 3,0,%01111101,%10,%1 ;enter +
            .db "Worm #4",0
 worm1 = $B400
@@ -2084,14 +2325,15 @@ pos     = 2   ;level*
 pos2    = 4   ;level
 grow    = 6   ;level
 died    = 8   ;game
-delay   = 9   ;game
-score   = 10  ;game
+score   = 9   ;game
+delay   = 11  ;game
 
 head    = 12  ;level
 tail    = 14  ;level
 lives   = 16  ;game
 reserv  = 17  ;loop
- ;race=lap
+ ;race:lap
+ ;hunt:time
 input   = 18  ;&
 left    = 19  ;&
 right   = 20  ;&
@@ -2100,11 +2342,11 @@ name    = 21  ;game
 Level =$+1
 DispBuffer =$+2 ;912 bytes
 
-ScrBuffer   = $8200 ;32x256 bytes
-SinCosTable = $A200
+ScrBuffer   = $8000 ;-$A1FF (32x256)
+SinCosTable = $A200 ;-$A300 (4x64)
 
 ;-----------------------------
 ;----------- end -------------
 ;-----------------------------
 
-.end
+.end
\ No newline at end of file