parse-wormedit: seperate parsing module Parse::Binary::Nested
[wormy.git] / wormy.z80
index 785cea953f037c4c1c8ebe62b6e3df2182c5ec03..bd08056296c32208b896f6486104fac4f2068743 100644 (file)
--- a/wormy.z80
+++ b/wormy.z80
@@ -1,34 +1,35 @@
-;___����________________________________________________________����____________
-;  ����                                                         �����
-; ���                                                            ����     ����
-;���      �����          ��������       �����     ����  ����      ���     �����
-;���     �������       �����������     �������   �������������     ��    ��� ���
-;��     ���   ���     �����    ����   ����  ��� ���  ����  ���     ���  ���� ���
-;��     ��     ��     ��  �      ��� ����      ���  ������  ���    ���  ���   ��
-;��     ��     ��     �� ��      ��� ���       ��� ���� ��� ���    ��� ����   ��
-;��     ���   ���     �� ��       �� ���       �������   ��� ��     �������   ��
-;��     ���   ���    ��� ��       �� ��        �� ���    ��� ���     �����   ���
-;���     ��� ���     ��� ��       �� ���       �� ����  ���� ���             ���
-;���      �����     ���  ���     ��� ���       ��  ��������  ���            ���
-; ���      ���      ���  ���     ��� ���       ���  ������   ���            ���
-;  ����  �������  ����    ���   ���  ����      ���            �����       ����
-;   �������� ��������     ���������   ���      ���             ���������������
-;    �����     �����       �������     ��       ���              �����������
+;___▄███________________________________________________________▄▄▄▄____________
+;  ███▀                                                         ████▌
+; ███                                                            ▀███     ▐██▄
+;▐██      ▄███▄          ▄▄████▄▄       ▄████     ▄██▄  ▄██▄      ▐██     █████
+;██▌     ███████       ▄██████████     ███████   ████████████▄     ██    ███ ███
+;██     ██▀   ▀██     ▐██▀▀    ▀███   ███▀  ██▌ ██▀  ████  ▀██     ██▌  ▐██▌ ▐██
+;██     ██     ██     ██  ▄      ██▌ ▐██▌      ▐██  ██████  ██▌    ███  ███   ██
+;██     ██     ██     ██ ██      ▐██ ███       ██▌ ███▀ ▐██ ▀██    ███ ▐███   ██
+;██     ██▌   ▐██     ██ ██       ██ ██▌       ██▌▐██▌   ██▌ ██     ██████▀   ██
+;██     ▐██   ██▌    ▐██ ██       ██ ██        ██ ▐██    ██▌ ██▌     ▀███▀   ▐██
+;██▌     ██▄ ▄██     ██▌ ██       ██ ██▌       ██ ▐██▌  ▐██▌ ██▌             ██▌
+;▐██      █████     ▐██  ██▌     ▐██ ██▌       ██  ▀██▄▄██▀  ███            ▐██
+; ███      ███      ██▌  ▐██     ██▌ ███       ██▌  ▀████▀   ▐██            ███
+;  ███▄  ▄█████▄  ▄███    ██▌   ███  ▐██▌      ██▌            ███▄▄       ▄███
+;   ███████▀ ▀███████     ▐██▄▄███▌   ███      ▐██             ██████████████▌
+;    ▀███▀     ▀██▀▀       ▀█████▀     ██       ██▌              ▀█████████▀
 ;_______________________________________________________________________________
 ;
-; Version                  :                                      98% (0.98.118)
-; Release Date             :                                     2002 January 18
+; Version                  :                                      100% (1.00.36)
+; Release Date             :                                        2002 March 6
 ; Author(s)                :                                               Shiar
 ; Email Address            :                                     wormy@shiar.org
 ; Web Page                 :                                       www.shiar.org
-; Description              :       perfect Nibbles game with free movement, nine
-;                                                    game modes, for 1-4 players
-; Where to get this game   :                                       www.shiar.org
+; Description              :  perfect Nibbles game with free movement, nine game
+;                                 modes, for 1-4 players, many levels and editor
+; Where to get this game   :                                     wormy.shiar.org
 ; Other games by author(s) :                                        Nemesis beta
 ; Additional Credits to    : Matthew Shepcar  :   wrote original Peaworm, end'98
 ;                            Jonah Cohen      :              helped writing worm
-; Files                    : wormy.z80 (89kB) : 515ad14b922572bdc8a96e780b8b24ca
-;                            wormy.86p (6512) : efef32a8c541b4585087f55deb31f51d
+; Files                    : wormy.txt (9283) : ed15e942a99b40e5a584c597cb13df46
+;                            wormy.z80 (100k) : 977109a7d25f3227fe817edbcc36ad9a
+;                            wormy.86g (8914) : fbff7c36687c1e7e3113c29069021718
 ;_______________________________________________________________________________
 
 ;--- notes ---------------------------------------------------------------------
 ; * Game README is wormy.txt
 ;  * Use for LEARNING practises ONLY!
 ;   * Don't _ever_ release altered code w/o permission!
-;    * Give me credits when you use stuff inhere
+;    * Give me credits when you use any of this stuff
 ;     * I'm not responsible for any damage this might cause, yada yada...
 ;      * Although I've commented & labeled quite some stuff, due to
 ;         crazy optimizations and weird coding, it may be harder to
 ;          understand than the average blob of code. This is probably _not_
 ;           the best source to learn z80 from. w00t the Shyer Way (tm).
-;          * Email me. If you've got suggestions, tell me.
+;          * Email me. If you've got suggestions|patches|questions: tell me.
 ;           * Don't scroll down if you get scared easily.
 
 ;--- index ---------------------------------------------------------------------
 
-;-* TO_DO
-; | future features
-;--* #INCLUDE
-;---* STORAGE
-;   | permanent
-;   | temporary
-;   | layout
-;----* PROG_START
-;    | search levels
-;-----* LEV_SELECT
-;------* MORE_INIT
-;      | trig tables
-;-------* MAIN_MENU
-;       | draw menu
-;       | options menu
-;       | main menu
-;       | display current settings
-;       | handle menukeys
-;       | change name
-;--------* MISC_PROCS
-;---------* START_GAME
-;         | link
-;         | client
-;         | set/send worms
-;         | host
-;         | load game
-;         | draw level
-;         | prepare
-;----------* GAME_LOOP
-;-----------* KEYS
-;           | pause menu
-;------------* GAME_OVER
-;            | who won?
-;            | display worms
-;            | quit
-;-------------* WORM_STUFF
-;--------------* WORM_ALIVE
-;              | move worm
-;              | draw worm
-;---------------* BOUNCYBALL
-;----------------* WORMY_HIT
-;                | multifood
-;                | ctf
-;                | main
-;                | foodmatch|SP
-;                | take pea
-;                | misc
-;-----------------* PROCS
-;------------------* SCORE
-;-------------------* DISPLAY
-;--------------------* DRAW
-;                    | pixel
-;                    | findpixel
-;                    | objects
-;                    | circle
-;                    | box
-;                    | fatline
-;                    | line
-;---------------------* LINK!
-;                     | multiple bytes
-;                     | foo
-;                     | send
-;                     | recv
-;                     | common
-;----------------------* INT_LEVELS
-;-----------------------* DATA
-;                       | graphics
-;                       | menus
-;                       | text
-;                       | foo
-;                       | game settings
-;------------------------* THAT'S_ALL
+; * TO_DO                       :                                future features
+;  * #INCLUDE
+;   * STORAGE                   :                   permanent; temporary; layout
+;    * PROG_START               :                                  search levels
+;     * LEV_SELECT
+;      * MORE_INIT              :                                    trig tables
+;       * MAIN_MENU             :    draw menu; options menu; main menu; display
+;                                 current settings; handle menukeys; change name
+;        * MISC_PROCS
+;         * START_GAME          : link; client; set/send worms; host; load game;
+;                                                            draw level; prepare
+;          * GAME_LOOP
+;           * KEYS              :                                     pause menu
+;            * GAME_OVER        :                  who won?; display worms; quit
+;             * WORM_STUFF
+;              * WORM_ALIVE     :                           move worm; draw worm
+;               * BOUNCYBALL
+;                * WORMY_HIT    :  multifood; ctf; main; foodmatch|SP; take pea;
+;                                                                           misc
+;                 * PROCS
+;                  * SCORE
+;                   * DISPLAY
+;                    * DRAW     :        pixel; findpixel; objects; circle; box;
+;                                                                  fatline; line
+;                     * LINK!   :        multiple bytes; foo; send; recv; common
+;                      * INT_LEVELS
+;                       * DATA  :      graphics; menus; text; foo; game settings
+;                        * THAT'S_ALL
 
 ;_______________________________________________________________________________
 ; _______  _____       ______   _____
 ;    |    |_____| ____ |_____/ |_____|
 ;_______________________________________________________________________________
 
-; 97% = PREVIOUS
-;     X [15] lives >9 dispay
-;     X [15] sp modes not configurable
-;     X [16] LVL: episode #2: 10 sp levels
-;     X [17] lives stats for every liveslimited game (also !dm)
-;     X [18] LINK: fix transmit game/level data
-;     X [19] datalevels+nrlevels not in program if !intlevels
-;     X [19] mem at worm #4 (still 12 bytes or so.. or more? or less?)
-;     X [19] alter level editor to use new address and set level id #97
-;     X [19A] team score!
-;     X [19A] autogrowth doesn't always work -> init (turn)
-;     X [111] ED: disabled objects counted causing CRASH when writing hiscore!
-;     X [111] LINK: init+multiple pea transmit seems to work..
-;     X [111] LINK: host/client swapped (host now sends level config)
-;     X [111] LINK: optimize transmit (most initcode same for client+host)
-;     X [113] menu limit in multifm not x10
-;     X [113] wormhit procedure seperate (called now)
-;     X [114] LINK: peas sent again :P
-;     X [114] internal level check and sprite storage removed
-;     X [115] layout data stuff at bottom
-;     X [115] ED: init place bar fixed
-;     X [115] ED: keys also usable together with mouse
-;     X [115] ED: improved version handling
-;     X [115] LINK: receive message not needed anymore afaik
-;     X [115A] $D8 used for spacing at g/o screen. i rule B)
-;     X [115A] exit at g/o goes back to menu
-;     X [115A] more in menu lets you reselect the levelfile
-;     X [115A] LINK: fixed waiting mode (minor display problem)
-;     X [116] incs at skiplevels effectively replaced by add (-4 bytes)
-;     X [116] another 2 bytes shaved off
-;     X [116] LINK: received gamemode now displayed correctly at g/o
-;     X [116] gamecar right after gametype saves about 20 bytes
-;     X [116] LINK: minimize sent data
-;     X [116] remove +input in worm storage
-;     X [116] head position init uses same data as tail (-4 bytes)
-;     X [116] fix bug at no levels (115A intro)
-;     X [117] saved 6 bytes by hardcoding some empty bytes in title graphics
-;     X [117] two pieces of duplicate code removed
-;     X [117] combined temporary storage for _D_HL_DECI and temp hiscore
-;     X [117] more repetitious code shortened
-;     X [117] wrong stack handling in checkpea, and unnecessary bloat
-;     X [117] stopworm after eating pea (pea|wall overwrite fixed!)
-;     X [117] old code removed from hitworm
-;     X [117] replace jps by jrs (moved code around a bit)
-;     X [117] scorebar doesn't diplay 1st wormname char anymore
-;     X [117] scorebar can display both lives and score when appropriate
-;     X [118] look at init-z in line routine again -> fixed steepline init-z
-;     X [118] snake86 findpixel (saves 1 byte)
-;     X [118] removed flash at new level start
-;     X [118] begin growth set in normal worm init loop
-;     X [118] bad code and potentially bad code reviewed and optimized
-;     X [118] final sourcecode layout ((sub)captions, index, indents, etc)
-; 98% = CURRENT
-;     X [119] ED: new 53 file format with support for 128 objects instead of 32
-;     X [119] LVL: episode #4: 10 hard sp levels (ordered XO-XO-XO-X)
-;  1% * LINK: >Somehow do a lot of testing with 2 calcs< *sigh*
-;     * LVL: episode #1: add 2-3 circle- and line levels.
-;     * LVL: episode #3: 6x5 multiplayer levels
-;     * LVL: episode #5: 10 easy sp levels (do i _have_ to?)
-;     * LVL: Eric? (ep#5?)
-;     * LVL: Wormage
-;     * LVL: Free Bird
-;     * LVL: Jonah?
-;  1% * fix any bugs that come up
+; 99% = PREVIOUS
+;     X [34] freeze when no space left to place pea (break after 10k tries)
+;     X [34] wow another bit of code 'reniced' (easter egg or something :)
+;     X [34] two more jp to jr
+;     X [34] highly improved randomizer (values >127 were rare)
+;     X [36] replace 'left' at the change-control prompt
+;     X [36] ED: fixed immediate exit at level preview when using enter key
+;     X [36] bouncies drawn after placing peas (causing overwrites)
+;     X [36] FIX: skip string length bytes when running from yas
+;     X [36] ED: pointer to ending message realigned
+;     X [36] LVL: end messages fixed in affected episodes
+;100% = CURRENT
+;     * scorebar last digit (at 128-3) not displayed by _vputs :(
+;     * save last played level (in levelfile prolly)
+;     * automatically start players in multiplayer games after certain time
+;     * muliplayer bonuses/powerups (shrink, lives, stun, inverse, etc.)
+;     * levels with random pixels appearing during game
+;     * no borders (move players from one side to another)
+;     * hiding levels crashes?? (ishell 2.01 rom 1.6)
+;     * use selected player on main menu as first player in singleplayer games
+
 
 ;--- future features -----------------------------------------------------------
 
 ;
 ; * correct team winners
 ;  * level compression
-;   * arrow to offscreen peas
-;    * sound
-;     * startpos
-;      * pause in linkplay
-;       * coop (DON'T COUNT ON IT)
+;   * ubersized bouncies (sprites)
+;    * arrow to offscreen peas
+;     * w00t AI
+;      * sound
+;       * startpos
+;        * pause in linkplay
+;         * coop (DON'T COUNT ON IT)
 
 ;_______________________________________________________________________________
 ;  _/_/_____ __   _ _______        _     _ ______  _______
@@ -228,11 +144,11 @@ _MOV4B             = $429B ;4x ld (de),(hl)
 _MOV5B             = $4297 ;5x ld (de),(hl)
 _mov9b             = $4283 ;9x ld (de),(hl)
 _ldHLind           = $4010 ;ld hl,(hl)
-_swapt_            = $45F3 ;ex_ahl_bde
+_swapt_            = $45F3 ;ex ahl,bde (doesn't work?)
 _Get_Word_ahl      = $521D ;ld de,(ahl)
 _Set_Word_ahl      = $5221 ;ld (ahl),de
-_INC_PTR_AHL       = $4637 ;ahl=ahl+1
-_AHL_PLUS_2_PG3    = $4C3F ;ahl=ahl+2
+_INC_PTR_AHL       = $4637 ;inc ahl
+_AHL_PLUS_2_PG3    = $4C3F ;add ahl,2
 _SET_ABS_SRC_ADDR  = $4647 ;set source for mm.ldir =ahl
 _LOAD_ABS_SRC_ADDR = $5209 ;ahl = mm.ldir source
 _SET_ABS_DEST_ADDR = $5285 ;set destination for mm.ldir = ahl
@@ -247,14 +163,19 @@ _writeb_inc_ahl    = $5567 ;ld (ahl++),c
 _jforce            = $409C ;TI-OS stack restored
 _EXLP              = $4493 ;swap (hl),(de) b times
 _GETB_AHL          = $46C3 ;a=(ahl) \ hl=ahl
+_OP1TOOP6          = $4263
 
- #define buffer     ;use display buffer (otherwise write directly to screen)
- #define readymask  ;"greys" out the field before starting a level
- #define coolzgfx   ;nice graphics for game over screen
+ #define id2        ;yas2 level identifier - this'll add (65) bytes
+ #define buffer     ;use display buffer, otherwise write directly to screen (11)
+ #define readymask  ;"greys" out the field before starting a level (20)
+;#define readytext  ;-displays "prepare" before level starts (42)
+ #define coolzgfx   ;nice graphics for game over screen (98)
  #define spprotect  ;options not changable for singleplayer modes
 ;#define intlevels  ;-internal levels
-;#define readytext  ;-displays "prepare" before level starts
-;#define invincible ;-worms cannot die =)
+                    ;-to become invincible, define the magic word :D
+
+levelhead   = 'w'
+levelhead2  = 97 ;wormy levels header = "0"
 
 ;_______________________________________________________________________________
 ; _______ _______  _____   ______ _______  ______ _______
@@ -275,7 +196,7 @@ worm3       = $AD3D ;-AD5A (1E)
 worm4       = $AD5B ;-AD78 (1E)
 balls       = $AD79 ;-AE00 (<=3x2D) (bb<=45)
 turn10      = $AE01 ;-AE01 (1)     (counter)
-peaspos     = $AE02 ;-AF05 (4-260)    (peas)
+peaspos     = $AE02 ;-AF05 (4-104)    (peas)
 ;free       = $AF06 ;-AFFF (F9)
 worm1p      = $B000 ;-B7FF (800)      %1011O000
 worm3p      = $B800 ;-BBFF (400)      %10111O00
@@ -309,23 +230,23 @@ drawctfpea2 = peaspos+6
 
 ;--- layout --------------------------------------------------------------------
 
-;(wormN)             set:
+;(wormN)      offs:  set:
 heading     =   0   ;level*
 pos         =   2   ;level*
 pos2        =   4   ;level
 grow        =   6   ;level
 died        =   8   ;game:
 score       =   9
-delay       =   11
+wdelay      =   11
 lives       =   12
 head        =   13
-                    ; 15B (wormNset)
-tail        =   15  ; |also@next level
-storepos    =   17  ; |
-reserv      =   18  ; |loop (race:lap|ctf:pea)
-left        =   19  ; |
-right       =   20  ; |
-name        =   21  ; |_
+                    ; 15B (wormNset)
+tail        =   15  ; also@next level
+storepos    =   17  ; 
+reserv      =   18  ; loop (race:lap|ctf:pea)
+wleft       =   19  ; │
+wright      =   20  ; │
+name        =   21  ; _
 
 wormsize    =   30 ;^mark^
 
@@ -339,10 +260,19 @@ wormsize    =   30 ;^mark^
 
 start:         ;turn back NOW!
   nop      ;and so it begins...
-  jp  Start
+  jp  codestart
+#ifndef id2
   ld  bc,$5242
   rst 10h
  .dw  WormIcon
+#else
+  ld  (bc),a
+  nop
+  ld  d,h
+  rst 10h
+ .dw  WormIcon
+ .dw  WormData
+#endif
   ld  d,a
   ld  c,a
   ld  d,d
@@ -356,20 +286,66 @@ start:            ;turn back NOW!
  .db  %1010010
   jr  nz,$+47
   dec l
- .db  " 98% .118",0
+ .db  " v1.00.36",0
 WormIcon:
- .db  8,2
- .db  %00000000,%00111100
- .db  %00000000,%01010010
- .db  %00000000,%01100001
- .db  %01100011,%10011001
- .db  %10010100,%01101001
- .db  %10011001,%00011001
- .db  %01000010,%11000001
- .db  %00111100,%00111110
-
-levelhead  = 'w'
-levelhead2 = 97 ;wormy levels header = "97"
+ .db  8,2                ;Rkaydees' icon:
+ .db  %00000000,%00111100 ;      XX
+ .db  %00000000,%01010010 ;     XXX
+ .db  %00000000,%01100001 ;     XX
+ .db  %01100011,%10011001 ;     XX
+ .db  %10010100,%01101001 ;      XX
+ .db  %10011001,%00011001 ;      XX
+ .db  %01000010,%11000001 ; X   XX
+ .db  %00111100,%00111110 ;  XXXX
+#ifdef id2
+WormData:
+ .db  1
+ .dw  wormlevel
+wormlevel:
+ .db  4        ;priority
+ .db  12       ;string
+ .db  "wor"    ;description
+ .dw  yasexec  ;execution routine
+ .dw  yascomment-yasdetect
+ .dw  yasdetect-$-1    ;detection routine
+ .dw  yasicon-yascomment
+ .dw  yascomment-$-1   ;comment routine
+ .dw  yasdataend-yasicon
+ .dw  yasicon-$-1      ;icon routine
+yasexec:
+  rst 10h
+  ex  de,hl
+  ld  a,b
+  cal _AHL_PLUS_2_PG3 ;skip past length bytes
+  cal skiptitle ;title (plus size+header <- all non-0)
+; cal skiptitle ;description
+  jp  leveldataAHL-3
+yasdetect:
+  cal _AHL_PLUS_2_PG3 ;skip past length bytes
+  cal _Get_Word_ahl
+  ld  hl,levelhead+(levelhead2*256)
+  cal _cphlde
+  ret z
+  scf
+  ret
+yascomment:
+  inc hl
+  inc hl ;skip header
+  ret
+yasicon:
+  ld  hl,$F400+levelicon-yasicon
+  ld  bc,6+(256*1)
+  or  a
+  ret
+levelicon:
+ .db %00011100 ;..XXX...  ...XXX..
+ .db %00011110 ;.X...X..  ...XXXX.
+ .db %00000011 ;.X..X...  ......XX
+ .db %10000001 ;X..X..XX  X......X
+ .db %01011011 ;X..X..XX  .X.XX.XX
+ .db %01101110 ;X...XXX.  .XX.XXX.
+yasdataend:
+#endif
 
 int_handler:
   ex  af,af'
@@ -381,34 +357,12 @@ int_handler:
   jp  $0039
 int_end:
 
-Start:
-  ld  (SpSave),sp
+;--- search levels -------------------------------------------------------------
+
+codestart:
   cal _runindicoff
   cal _flushallmenus
 
-  im  1
-  ld  a,$D4
-  ld  h,a
-  ld  l,0 ;ld hl,$D400
-  ld  d,a
-  ld  e,1 ;ld de,$D401
-  ld  b,e
-  ld  c,l ;ld bc,$0100
-  dec a   ;ld a,$D3
-  ld  (hl),a
-  ldir
-  ld  hl,int_handler
-  ld  d,a
-  ld  e,a ;ld de,$D3D3
-  ld  bc,int_end-int_handler
-  ldir
-  inc a   ;ld a,$D4
-  ld  i,a
-  im  2 ;...it *does* work ;)
-
-;--- search levels -------------------------------------------------------------
-
-restart:
   cal _RAM_PAGE_7
   ld  hl,$BFFF ;VAT start
   ld  ix,templevels
@@ -448,15 +402,12 @@ stringfound:
   cp  e
   jr  nz,_searchnext ;not worm
   ld  a,levelhead2
-  cp  d
+  cp  d ;=0
   jr  nz,_searchnext
-  inc ix ;save level's ahl
-  ld a,h
-  ld (ix),a
-  inc ix
-  ld a,l
-  ld (ix),a
-  inc ix
+  ld (ix+1),h ;save level's ahl
+  ld (ix+2),l
+  ld  de,3 ;&&&d=0
+  add ix,de
 _searchnext:
   cal _RAM_PAGE_7
   jr  searchnext
@@ -510,16 +461,21 @@ levelselectmenu: ;load next page
   cal menuinvloop
   ld  hl,$FC00+$380 ;(*,56)
   cal hr
-  ld  hl,$0601 ;x=1
+  ld  hl,$0C01 ;x=1
   ld  (_penCol),hl
 dispnextlevel:
   ld  de,3
-  add ix,de
+  add ix,de ;goto next
   ld  a,(ix)
-  ld  b,a
+  ld  h,(ix+1)
+  ld  l,(ix+2)
+  cal _load_ram_ahl ;hl=ahl
+  cal _vputs
+  ld  hl,availevels
+  inc (hl)
+  ld  a,(ix+3) ;next
   inc a ;cp 255
   jr  z,__levselect
-displevel:
   ld  hl,_penCol
   ld  (hl),$01 ;x=1
   inc hl
@@ -528,13 +484,6 @@ displevel:
   ld  (hl),a ;y+6
   cp  49 ;bottom of screen
   jr  nc,_levselect
-  ld  hl,availevels
-  inc (hl)
-  ld  a,b ;(ix+0)
-  ld  h,(ix+1)
-  ld  l,(ix+2) ;ahl=(ix)
-  cal _load_ram_ahl ;hl=ahl
-  cal _vputs
   jr  dispnextlevel
 
 loadlevel1:
@@ -604,7 +553,7 @@ levdescclearloop:
   cp  d ;de>$FFFF (offscreen)
   jr  nz,levdescclearloop
   cal _vputs
-  jr  levselectmenu+1
+  jr  levselectmenuloop+1
 __levselect:
 #ifdef intlevels
   ld  ix,templevels-6 ;reset 2 1st page
@@ -614,7 +563,7 @@ __levselect:
 _levselect:
   ld  b,-2 ;level selected
   jr  levselect
-levselectmenu:
+levselectmenuloop:
   psh hl
   psh bc
   cal ubergetkey
@@ -631,7 +580,7 @@ levselectmenu:
   sub K_EXIT-K_RIGHT
   jp  z,ExitNoStats
   inc a ;cp K_SECOND
-  jr  nz,levselectmenu
+  jr  nz,levselectmenuloop
 ; jr  z,loadlevel
 
 loadlevel:
@@ -641,7 +590,7 @@ loadlevel:
   jr  z,levelloaded
 #endif
   cal skiptitle ;skip description
-
+leveldataAHL:
   cal _Get_Word_ahl
   ld  (leveldataSize),de
 
@@ -673,6 +622,36 @@ leveldataSize =$-2
 levelloaded:
   cal _RAM_PAGE_1
 
+;_______________________________________________________________________________
+; _______  _____   ______ _______       _____ __   _ _____ _______
+; |  |  | |     | |_____/ |______         |   | \  |   |      |
+; |  |  | |_____| |    \_ |______ _____ __|__ |  \_| __|__    |
+;_______________________________________________________________________________
+
+; cal _runindicoff   ;this is after level selection (run from yas1 or restart)
+; cal _flushallmenus ;so this stuff should already be done earlier or by yas
+  ld  (SpSave),sp
+
+  im  1
+  ld  a,$D4
+  ld  h,a
+  ld  l,0 ;ld hl,$D400
+  ld  d,a
+  ld  e,1 ;ld de,$D401
+  ld  b,e
+  ld  c,l ;ld bc,$0100
+  dec a   ;ld a,$D3
+  ld  (hl),a
+  ldir
+  ld  hl,int_handler
+  ld  d,a
+  ld  e,a ;ld de,$D3D3
+  ld  bc,int_end-int_handler
+  ldir
+  inc a   ;ld a,$D4
+  ld  i,a
+  im  2 ;...it *does* work ;)
+
   res 2,(iy+13) ;appAutoScroll
   ld  a,r
   ld  (Seed),a
@@ -685,12 +664,6 @@ setdeflevels:
   add hl,de ;next
   dnz setdeflevels
 
-;_______________________________________________________________________________
-; _______  _____   ______ _______       _____ __   _ _____ _______
-; |  |  | |     | |_____/ |______         |   | \  |   |      |
-; |  |  | |_____| |    \_ |______ _____ __|__ |  \_| __|__    |
-;_______________________________________________________________________________
-
 ;--- trig tables ---------------------------------------------------------------
 
   ld  hl,trigtable   ;I believe this
@@ -804,8 +777,8 @@ dispoptionmenu:
 dispomenusets:
 #ifdef spprotect
   ld  a,(gamecar)
-  rra ;and _datasingl
-  jp  nc,LetsGetThisPartyOn ;SP -> start game
+  and _datasingl
+  jp  nz,LetsGetThisPartyOn ;SP -> start game
 #endif
   cal clrold
 
@@ -895,30 +868,30 @@ notoselect
   jr  nz,optionMenu
 
 seloright:
-  dec a
+  dec a ;Lives
   jr  z,changelives
-  dec a
+  dec a ;Limit
   jr  z,changelimit
-  dec a
+  dec a ;Speed
   jr  z,changespeed
-  dec a
+  dec a ;Rotation
   jr  z,changeturn
-  dec a
+  dec a ;Growth
   jr  z,changegrowth
-
+        ;Back
 seloleft:
   ld  a,b
-  dec a
+  dec a ;Lives
   jr  z,bchangelives
-  dec a
+  dec a ;Limit
   jr  z,bchangelimit
-  dec a
+  dec a ;Speed
   jr  z,bchangespeed
-  dec a
+  dec a ;Rotation
   jr  z,bchangeturn
-  dec a
+  dec a ;Growth
   jr  z,bchangegrowth
-_optionMenu:
+_optionMenu: ;Back
   jr  optionMenu
 
 changelives:
@@ -1047,7 +1020,7 @@ notselect
   cp  K_EXIT
   jp  z,ExitNoStats
   cp  K_MORE
-  jp  z,restart
+  jp  z,codestart
   psh af
   cal menupos
   cal loadgamecar
@@ -1060,15 +1033,15 @@ notselect
   jr  nz,mainMenu
 
 selright:
-  or  a
+  or  a ;Mode
   jr  z,changegame
-  dec a
+  dec a ;Level
   jr  z,changelevel
-  dec a
+  dec a ;Link
   jr  z,changelink
-  dec a
+  dec a ;Worms
   jr  z,changenrworms
-; dec a
+; dec a ;worm#
 ; jr  z,changecurworm
 
 changecurworm:
@@ -1081,15 +1054,15 @@ changecurworm:
 
 selleft:
   ld  a,b
-  or  a
+  or  a ;Mode
   jr  z,bchangegame
-  dec a
+  dec a ;Level
   jr  z,bchangelevel
-  dec a
+  dec a ;Link
   jr  z,bchangelink
-  dec a
+  dec a ;Worms
   jr  z,bchangenrworms
-; dec a
+; dec a ;worm#
 ; jr  z,bchangecurworm
 
 bchangecurworm:
@@ -1189,9 +1162,9 @@ waitcustomkey:
   or  a
   jr  z,waitcustomkey
   cp  K_EXIT
-  ret z
+  ret z ;cancel
   cp  K_MORE
-  jr  z,waitcustomkey
+  jr  z,waitcustomkey ;ignore
   ld  (ix),a
   ret
 
@@ -1199,6 +1172,8 @@ changekeys:
   cal getwormname
   ld  hl,txtKleft
   cal getcustomkey ;left
+  ld  a,93
+  ld  (_penCol),a
   cal getcustomkey ;right
 ; jr  dispmenusets
 
@@ -1369,9 +1344,8 @@ enternameloop:
   ld  (_penCol),hl
   pop hl
   psh hl
-  ld  (ix),0
+  ld  (ix),a ;clroldcustom -> a=0
   cal __vputs
-  ld  (ix),' '
   ld  a,'_'
   cal __vputmap
 nokeypressed:
@@ -1390,6 +1364,7 @@ backspace:
   dec ix
   jr  enternameloop
 continue:
+  ld  d,0
   cp  K_ENTER
   jr  z,nameentered
   cp  K_EXIT
@@ -1398,8 +1373,7 @@ continue:
   dec (hl) ;(namelength)
   jr  z,nameentered
   ld  hl,chartable-1
-  ld  e,a
-  ld  d,0
+  ld  e,a ;d=0
   add hl,de
   ld  a,(hl)
   or  a
@@ -1409,19 +1383,19 @@ continue:
   cal releasekeys
   jr  enternameloop
 
-chartable: ;("!@#$%,0" also used in _D_HL_DECI)
-  .db ".<>!"           ;down|L|R|up|-|-|-|-
+chartable:
+  .db ".<>!"           ;down|L|R|up|-|-|-|-|[enter]
   .db "w00t!"          ;(makes code look way better)
-  .db "XTOJE0",-2      ;enter|+|-|*|/|^|clear|-
-  .db " WSNID9",-3     ;(-)|3|6|9|)|tan|custom|-
-  .db "ZVRMHC8",-4     ;.|2|5|8|(|cos|prgm|del
-  .db "YUQLGB7#"       ;0|1|4|7|ee|sin|table|xvar
-  .db $D9,"-PKFA6'"    ;on|sto|,|x2|ln|log|graph|alpha
-  .db "54321*",-5,$D0  ;F5|F4|F3|F2|F1|2nd|exit|more
-
-nameentered:
+  .db "XTOJE0",'w'     ;+|-|*|/|^|clear|-              w
+  .db " WSNID9",$F8    ;(-)|3|6|9|)|tan|custom|-       o
+  .db "ZVRMHC8",$A7    ;.|2|5|8|(|cos|prgm|[del]       o
+  .db "YUQLGB7#",$C2   ;0|1|4|7|ee|sin|table|xvar|[on] t
+  .db "-PKFA6'"        ;sto|,|x2|ln|log|graph|alpha
+  .db "54321*",$AE,$D0 ;F5|F4|F3|F2|F1|2nd|[exit]|more
+
+nameentered: ;d=0
   pop ix ;stringbegin
-  ld  (ix+8),0 ;end mark
+  ld  (ix+8),d ;end mark
   jp  DisplayMenu
 
 ;_______________________________________________________________________________
@@ -1569,7 +1543,7 @@ createwormsloop:
   ld  (hl),b ;+score+1=0
   inc hl
   ld  c,2
-  ld  (hl),c ;+delay=2
+  ld  (hl),c ;+wdelay=2
   inc hl
   ld  (hl),3 ;+lives=x
 wormbeglives =$-1
@@ -1590,8 +1564,8 @@ OhMyGodItsALabel:  ;pj34r my coding skillz
   ex  (sp),hl ;pop \ psh leveldata
   psh hl ;psh loadgamecar
   ld  a,(gamecar)
-  and _datalink
-  jr  z,_StartLevel
+  rra ;and _datalink
+  jr  nc,_StartLevel
 
 ;--- link ----------------------------------------------------------------------
 
@@ -1619,11 +1593,11 @@ client:
  ;                 2 = link    = 0  + link (name1)
  ;                 3 = worm #2 = #2 + local(name2)
  ;                 4 = link    = 0  + link (name2)
-  ld  e,worm3+left&255
+  ld  e,worm3+wleft&255
   cal moveworm2 ;3=2
   ld  l,worm1+name&255
   cal sendworm
-  ld  l,worm2+left&255
+  ld  l,worm2+wleft&255
   cal linkworm ;worm2+4 over link
   pop hl ;loadgamecar
   pop de ;leveldata
@@ -1652,21 +1626,21 @@ linkerror:
 ;--- set/send worms ------------------------------------------------------------
 
 moveworm2:
-  ld  hl,worm2+left
-moveworm: ;hl=wormN+left
+  ld  hl,worm2+wleft
+moveworm: ;hl=wormN+wleft
   ld  d,worm1/256
   ld  bc,11
   ldir ;keys+name worm(de) = worm(hl)
   ret
-linkworm: ;hl=wormN+left
-  ld  (hl),0 ;worm1|2+left
+linkworm: ;hl=wormN+wleft
+  ld  (hl),0 ;worm1|2+wleft
   inc hl
   inc hl ;+name
   ld  b,9
   cal recvstuff
   ld  bc,worm3-worm1-11 ;+2
   add hl,bc ;b=0
-  ld  (hl),b ;worm3|4+left
+  ld  (hl),b ;worm3|4+wleft
   inc hl
   inc hl ;+name
   ld  b,9
@@ -1691,12 +1665,12 @@ host:
  ;                 2 = worm #1 = #1 + local(name1)
  ;                 3 = link    = 0  + link (name2)
  ;                 4 = worm #2 = #2 + local(name2)
-  ld  e,worm4+left&255
+  ld  e,worm4+wleft&255
   cal moveworm2 ;4=2
-  ld  e,worm2+left&255
-  ld  hl,worm1+left
+  ld  e,worm2+wleft&255
+  ld  hl,worm1+wleft
   cal moveworm ;2=1
-  ld  l,worm1+left&255
+  ld  l,worm1+wleft&255
   cal linkworm ;worm1+3 over link
   ld  l,worm2+name&255
   cal sendworm
@@ -1746,7 +1720,7 @@ teamset:
   ld  l,(hl)
   ld  h,0
   ld  a,(gamecar)
-  rla
+  rla ;and _dataPmult
   ld  a,h ;(Left)=256
   jr  nc,setscorelimit
   ld  a,l
@@ -1774,29 +1748,32 @@ Nextlevel:
   inc hl   ;location of ending-code
   jp  (hl) ;go there ("call")
 donextlevel:
-  ld  bc,gametype
-  ld  a,(bc)
+  ld  de,gametype
+  ld  a,(de)
   or  a ;gamesingle
   psh af
-  cal nz,skiplvltitle
+  jr  nz,customnrpeas
+;--sp--
+  inc de
+  ld  a,(de) ;gamecar
+  rla ;prepare a
+  rlc (hl) ;bit 7 of (hl)...
+  rra ;...to bit 7 of (gamecar)
+  rrc (hl) ;restore (hl)
+  ld  (de),a
   ld  a,(hl)
-  and 127
-  jr  nz,setleft
-customleft =$+1
+  and 127 ;actual #peas
+  jr  setnrpeas
+;--!sp--
+customnrpeas:
+  cal skiplvltitle
   ld  a,0
-setleft:
+customleft =$-1
+
+setnrpeas:
   ld  (Left),a
   inc a
   ld  (lefttotal),a
-  dec a
-  xor (hl) ;bit (hl),7
-  inc bc ;gamecar
-  ld  a,(bc)
-  jr  z,leftloaded
-  or  128+32
-leftloaded:
-  ld  (bc),a
-  inc de
   inc hl
   ld  de,Speed
   ld  a,0
@@ -1988,23 +1965,32 @@ levelhasbeensetup:
 leveldone:
   psh hl                        ; >> levelp new
   cal forceshowstats
+  cal handlethoseneatlittleballs
+
+  ld  a,(gamecar)
+  rla ;and _dataPmult
+  cal c,multnewpea ;a=0
+  rla ;and _datafood
+  cal nc,NewPea
+nofood:
+  ld  bc,(worm1+pos)
+  cal DisplayField
 
 #ifdef readymask
   ld  hl,$FC70
-  ld  d,%10101010
-  ld  c,56
+  ld  de,57*256+%10101010
 maskloop:
-  ld  a,d
-  xor %11111111
-  ld  d,a
+  ld  a,e
+  cpl
+  ld  e,a
   ld  b,$10
 maskline:
   ld  a,(hl)
-  or  d
+  and e
   ld  (hl),a
   inc hl
   dnz maskline
-  dec c
+  dec d
   jr  nz,maskloop
 #endif
 #ifdef readytext
@@ -2021,15 +2007,6 @@ maskline:
   res 3,(iy+5)
 #endif
 
-  ld  a,(gamecar)
-  rla ;bit __bitPmult,a
-  cal c,multnewpea ;a=0
-  rla ;bit __bitfood,a
-  cal nc,NewPea
-nofood:
-  ld  bc,(worm1+pos)
-  cal DisplayField
-
   ld  b,startdelay
 ReadyDelay:
   halt
@@ -2044,7 +2021,7 @@ ReadyDelay:
 
 GameLoop:
   ld  bc,(worm1+pos) ;camera worm #1
-  ld  a,(worm1+left)
+  ld  a,(worm1+wleft)
   or  a ;if #1 not over link
   jr  nz,showfield
   ld  bc,(worm2+pos) ;otherwise view from #2
@@ -2111,11 +2088,7 @@ nodispupdate:
   cal tryDrawPea ;pea#2
 noctfpeas2draw:
 
-
-  ld  a,0
-nrballs =$-1
-  or  a
-  cal nz,handlethoseneatlittleballs
+  cal handlethoseneatlittleballs
 
   ld  ix,worm1
   ld  a,1
@@ -2147,7 +2120,7 @@ CheckExit:
   rla  ;=$17 (c=EXIT-key)
       ;or$A7 (c=0)
   jp  c,GameLoop
-  jp  Exit ;jr?
+  jr  Exit
 
 ;--- pause menu ----------------------------------------------------------------
 
@@ -2346,10 +2319,10 @@ displayWormStats:
   psh bc
 
   psh hl
-  ld  bc,left-died
-  add hl,bc ;+left
+  ld  bc,wleft-died
+  add hl,bc ;+wleft
   xor a
-  cp  (hl)  ;left=0 = link
+  cp  (hl)  ;wleft=0 = link
   jr  nz,NoLinkIndic
   ld  a,9
   ld  (_curCol),a
@@ -2423,8 +2396,8 @@ hilevelcheckdone:
 
   inc de
   ld  a,(de) ;gamecar
-  rra ;and _datasingl
-  jr  c,hiscorecheckdone ;no SP
+  and _datasingl
+  jr  z,hiscorecheckdone ;no SP
 checkhiscore:
   cal loadhiscoreposinahl ;cf=0 (and)
   cal _SET_ABS_SRC_ADDR ;from ahl (lvlfile)
@@ -2510,7 +2483,7 @@ hiscrposhl =$-2
 hiscrposa =$+1
   adc a,0 ;ahl=saveloc
   ret
-savestr: ;hiscore (00AAA) _D_HL_DECI (00000)
+savestr: ;hiscore (01ABC) _D_HL_DECI (01234)
   .db $BB,"w00t",0
 
 iswinner:
@@ -2570,8 +2543,8 @@ DoesWormTailEqualsWormHead:
   jr  nz,removewormloop ;head=tail/size=0
 
   ld  a,(gamecar)
-  rra ;and _datasingl
-  jr  nc,savetailpos
+  and _datasingl
+  jr  nz,savetailpos
   ld  (ix+grow+1),a ;=0
   ld  a,0
 growsize =$-1
@@ -2592,10 +2565,10 @@ respawndue:
   ld  a,h ;previous
   cp  l   ;changed?
   ret z
-  ld  (ix+delay),a ;=0
+  ld  (ix+wdelay),a ;=0
   ret
 saverespawncounter:
-  ld  (ix+delay),a
+  ld  (ix+wdelay),a
   jr  inputcall
 
 chkkey: ;key=a
@@ -2630,7 +2603,7 @@ inkeys: ;use jp not call!
 turnright =$-1
   ld  l,a
 notright:
-  ld  a,(ix+right)
+  ld  a,(ix+wright)
   cal chkkey
   ret nc
   ld  a,l
@@ -2639,13 +2612,13 @@ turnleft =$-1
   ld  l,a
   ret
 inputcall:
-  ld  a,(ix+left)
+  ld  a,(ix+wleft)
   or  a
   jr  z,inlink ;input by link
   cal inkeys ;input by keys
   ld  a,(gamecar)
-  and _datalink
-  ret z ;no link
+  rra ;and _datalink
+  ret nc ;no link
   ld  c,l ;send our keys
   jp  Qsend
 inlink:
@@ -2667,7 +2640,7 @@ HandleWorm:
   or  a
   ret nz ;live limit
 alive:
-  ld  a,(ix+delay)
+  ld  a,(ix+wdelay)
   dec a
   jp  nz,respawncheck
 
@@ -2769,7 +2742,10 @@ drawworm:
   inc hl
   ld  (hl),b
   inc hl
-  cal resbit
+  ;(resbit)
+  ld  a,h
+  and (ix+storepos)
+  ld  h,a
   ld  (ix+head),l
   ld  (ix+head+1),h
 
@@ -2798,7 +2774,10 @@ removetailbit:
   inc hl
   ld  b,(hl)
   inc hl
-  cal resbit
+  ;(resbit)
+  ld  a,h
+  and (ix+storepos)
+  ld  h,a
   psh hl
   cal res4pixels ;rm last bit
   pop hl
@@ -2825,8 +2804,12 @@ ResPixel:
 ;_______________________________________________________________________________
 
 handlethoseneatlittleballs:
+  ld  a,0
+nrballs =$-1
+  or  a
+  ret z ;no bouncies to handle
+  ld  b,a ;(nrballs)
   ld  hl,balls
-  ld  b,a ;a=(nrballs)
 handleballs
   psh bc
   psh hl
@@ -2964,12 +2947,11 @@ sel_otherpea:
   jr  c,hitflag
 ;no peas hit:
   ld  a,e ;peek a (that's x86asm for pop\push ;)
-  bit 1,a ;%10 = carrying flag?
+  bit 1,a ;%1O = carrying flag?
   jr  z,_wormdead ;if not just die
-  xor %11 ;drop flag
-  ld  (ix+reserv),a
+  and %1 ;which flag?
   ld  hl,drawctfpea1 ;restore #1
-  jr  z,nottheotherflag ;which flag? (=and %1)
+  jr  nz,nottheotherflag
   inc hl ;ld hl,drawctfpea2
   inc hl ;restore #2
 nottheotherflag:
@@ -2982,14 +2964,16 @@ hitflag: ;correct pea hit
   xor %11 ;invert flag taken + ownflag
   ld  (ix+reserv),a
   and %10 ;just returned?
-  psh af ;safe z-flag
   psh bc ;safe position
+  psh af ;safe z-flag
   cal DrawPea ;remove
-  ld  e,20 ;flag captured+returned
-  cal z,IncScore
-  pop bc
   pop af
+  pop bc
   ret nz ;flag taken: continue game ;drawworm
+  ld  e,20 ;flag captured+returned
+  psh bc
+  cal IncScore
+  pop bc
   ld  a,3 ;draw delay
   ld  (drawctfpea1),a ;redraw..
   ld  (drawctfpea2),a ;..both flags
@@ -3012,7 +2996,7 @@ hitworm:
 PeaY =$-2
 PeaX =$-1
   cal chkpeahit
-  jr  nc,_wormdead
+  jp  nc,wormdead
 
 ;--- take pea ------------------------------------------------------------------
 
@@ -3055,7 +3039,7 @@ wormset2grow:
   pop hl ;<<call hitworm
   pop hl ;<<call HandleWorm
   pop hl ;<<$some other call
-  ld  (ix+delay),2
+  ld  (ix+wdelay),2
   jp  Nextlevel
 
 chkpeahit: ;bc=ownpos;hl=peapos (destr:ad)
@@ -3076,12 +3060,12 @@ chkpeahit: ;bc=ownpos;hl=peapos (destr:ad)
 ;--- misc ----------------------------------------------------------------------
 
 checkhitlapline:
-  ld  a,(peaspos) ;63
+  ld  a,(peaspos) ;63 usually
   sub b ;x==63
   jr  z,nextlaphalf
-  inc a
-  ret nz
-nextlaphalf:
+  inc a ;(more checkin' since wormies just have those _huge_ heads ;)
+  ret nz ;x!=62
+nextlaphalf: ;x==62|63; a=0
   ld  a,(peaspos+1) ;yline
   cp  c ;ypos
   ld  a,1
@@ -3108,30 +3092,25 @@ checklap:
 ; |       |    \_ |_____| |_____  ______|
 ;_______________________________________________________________________________
 
-releasekeys:
-  halt
+releasekeys: ;---------->promise me you'll never let go...
+  halt ;-------------------->i won't let go....
   ld  a,%10000000    ;all key-masks
   out (1),a
-  in  a,(1)
+  in  a,(1) ;--------------->i'll never let go.....
   inc a              ;cp %11111111 (no keys pressed)
   jr  nz,releasekeys ;keep waitin
   cal GET_KEY        ;clear buffer
-  ret
-
-resbit:
-  ld  a,h
-  and (ix+storepos)
-  ld  h,a
-  ret
+  ret ;--------------------->*die* (we are VICTORIOUS! muha)
 
 randompos:
   ld  b,a
 Random: ;(2..b+2)
-  ld  a,r
+  ld  a,r ;0..127
+  scf ;not just even values:
+  rla ;6543210C
 Seed =$+1
   add a,0
   ld  (Seed),a
-  and %01111110
   cp  b
   jr  nc,Random
   add a,2
@@ -3154,13 +3133,15 @@ mmldir5:
 
 wormdead:
   pop hl ;<<call
-WormDead:
-#ifdef invincible
-  jp  stopworm
-#endif
   ld  a,2
   ld  (flashtime),a
-  ld  (ix+delay),rspawndelay
+#ifdef w00t
+  ld  h,201
+ .org $-2
+  nop
+ .org $+1
+#endif
+  ld  (ix+wdelay),rspawndelay
 
 thislevel =$+1
   ld  hl,0
@@ -3181,11 +3162,16 @@ handledworm =$-2
   ld  (ix+pos2),a ;y2
   ld  (ix+pos2+1),a ;x2
 
+  ld  a,(handledworm) ;who are we? (1-4)
+  cpl ;invert (just bit 0 actually)
+  and 1 ;group 1 (1,3) or 0 (2,4)
+  ld  (ix+reserv),a ;reset halflap|flags to starting settings
+
   inc (ix+died)
   dec (ix+lives)
   psh af
-  ld  a,(gametype)
-  cp  gamectf ;ctf no death penalty
+  ld  a,(gamecar)
+  and _datadecs ;ctf and race no death penalty
   cal nz,DecScore10
   pop af
   ret nz ;HandleWorm done
@@ -3276,16 +3262,24 @@ multpealoop:
   ret
 
 NewPea:
+  ld  de,$293A ;counter :)
+newpealoop:
+  dec de
+  ld  a,d
+  or  e
+  jp  z,Exit ;break after 10554 tries to prevent freeze when field filled
   ld  a,(FieldWidth)
-  add a,127-4
+  add a,126
   cal randompos
   ld  h,a
   ld  a,(FieldHeight)
-  add a,56-4
+  add a,55
   cal randompos
   ld  l,a
+  psh de
   cal CheckPea
-  jr  nz,NewPea
+  pop de ;counter
+  jr  nz,newpealoop
   cal sendnewpeaoverlink
   ld  (PeaY),hl
 DrawPea: ;hl=(PeaY)
@@ -3452,8 +3446,8 @@ forceshowstats:
   ld  b,a
   ld  ix,worm1
   ld  a,(gamecar)
-  rra ;and _datasingl
-  jr  nc,showstatsS
+  and _datasingl
+  jr  nz,showstatsS
 showstatloop:
 #ifdef gamenames
 #ifdef longnames
@@ -3965,6 +3959,8 @@ circledraw:               ;destr:de
   psh hl
   ld  a,h              ;hl=x,y
   sub b                ;bc=xx,yy
+       jr  nc,$+3              ;x<xx
+       xor a                   ;left of screen -> x=0
   ld  d,a              ;d=x-xx
   add hl,bc            ;h=x+xx; l=y+yy
   ld  e,l              ;e=y+yy
@@ -3972,6 +3968,8 @@ circledraw:               ;destr:de
   ld  a,l
   sub c                ;a=y again
   sub c
+       jr  nc,$+3              ;y<yy
+       xor a                   ;above screen -> y=0
   ld  l,a              ;l=y-yy
   ld  e,l              ;e=l=y-yy
   cal drawline         ;(h-b,l-c)-(h+b,l-c)
@@ -4157,9 +4155,9 @@ receivenewpeaoverlink:
   ret
 sendnewpeaoverlink:
   ld  a,(gamecar)
-  and _datalink
-  ret z ;no link
-  ld  a,(worm1+left)
+  rra ;and _datalink
+  ret nc ;no link
+  ld  a,(worm1+wleft)
   or  a
   jr  z,receivenewpeaoverlink
   ld  c,l ;send pea's pos
@@ -4248,7 +4246,7 @@ linktest:
   out (1),a            ;select keys
   in  a,(1)            ;input
   bit 6,a              ;exit key
-  jp  z,Exit           ;break!
+  jr  z,linkerr                ;break!
 linkfine:
   in  a,(7)
   and %11
@@ -4357,6 +4355,7 @@ wtPicture: ;title
 .db %00011111,%11101111,%11110000,%00111111,%10000111,%00000001,%10000000,%00000011,%11111111,%11110000,%00111110,%00011110,%00010111,%01011101,%10010101,%01100101
 .db %00001111,%10000011,%11100000,%00011111,%00000011,%00000001,%10000000,%00000000,%11111111,%11100000,%00000000,%00000000,%11100101,%01010101,%01000110,%01010011
 
+#ifdef coolzgfx
 wtWormy: ;g/o
 .db %00000110,%00111000,%00000000,%00111100,%00001111,%10001110,%00111100,%01111000,%00001100,%11011000,%11100011,%10000000,%00000000,%11111100,%00111000,%00000000
 .db %00011001,%01000110,%11100000,%11000010,%00011100,%11011111,%01111110,%11111000,%00011110,%11011101,%11110111,%11000000,%00111111,%00000011,%01000110,%11100000
@@ -4365,10 +4364,8 @@ wtWormy: ;g/o
 .db %01001100,%00011000,%00000000,%00000100,%00011000,%11011111,%01100010,%11001100,%00110011,%01101101,%10000111,%11000001,%00011100,%00111000,%00011000,%10000010
 .db %01010010,%00100100,%01100000,%00011000,%00011111,%11011011,%11101110,%11111100,%00011111,%01111000,%11110110,%11100000,%11000000,%11000110,%00101001,%10000010
 .db %01100001,%11000011,%10011111,%11100000,%00001111,%10001001,%11001100,%01111000,%00001110,%00110000,%01100110,%01100000,%00111111,%00000001,%11000110,%01111100
-
 ;.db %00000000,%00000001,%10000000,%00000000,%00001111,%10000000
-
-#ifndef coolzgfx
+#else
 txtGO:     .db 5,5,5,5,5," GAME OVER ",$CF,$CF,$CF,$CF,$CF,0
 #endif
 
@@ -4426,7 +4423,7 @@ txtDef:    .db               "Default",0
 txtYes:    .db                   "Yes",0
 txtNo:     .db                    "No",0
 txtKleft:  .db                 ":left",0
-txtKright: .db                "/right",0
+txtKright: .db                 "right",0
 posLevsel   =  $0320
 txtLevsel: .db $CF," SELECT LEVELS ",5,0
 txtWaitn:  .db         "Waiting";"...",0
@@ -4480,49 +4477,49 @@ worm4set:  .dw worm4p
            .db  %11111101,0,K_PLUS,K_ENTER
 worm4name: .db   "JIM     ",0
 
-_datasingl  =  %00000001 ;singleplayer=0 (=hiscore+keep_length+nextlevel)
+_datalink   =  %00000001 ;linkplay (1!)
 _datafoodl  =  %00000010 ;left=0 limit
-_datalink   =  %00000100 ;linkplay (1!)
+_datasingl  =  %00000100 ;singleplayer=1 (=hiscore+keep_length+nextlevel)
 _dataPctf   =  %00001000 ;ctf peas=1
 __bitPctf   =  3
 _datatime   =  %00010000 ;time incs score (timematch)
-;reserved      %00100000 ;for future use
+_datadecs   =  %00100000 ;decrease score on death=1
 _datafood   =  %01000000 ;food present=0 (6!)
 _dataPmult  =  %10000000 ;multiple peas=1 (no _datafood) (7!)
 
-         ;            game info (see above)
-          ;           | �lives (0=unlimited)
-           ;          | | �nrworms (can be altered by user)
-            ;         | | | �level (reset to 1 at startup)
-             ;        | | | |  �speed/delay (-1=def)
-              ;       | | | |  |  �grow speed (-1=none; 0=continuous)
-               ;      | | | |  |  |  �turn speed (8=def)
-                ;     | | | |  |  |  |  �score limit (0=none)
-gamesingle  =  0 ;    | | | |  |  |  |  |
-datasingle:.db %00000010,3,1,1,-1,-1, 8, 0 ;Singleplayer (SP; 3 lives)
+         ;            game info (see above)
+          ;           │ ┌lives (0=unlimited)
+           ;          │ │ ┌nrworms (can be altered by user)
+            ;         │ │ │ ┌level (reset to 1 at startup)
+             ;        │ │ │ │  ┌speed/delay (-1=def)
+              ;       │ │ │ │  │  ┌grow speed (-1=none; 0=continuous)
+               ;      │ │ │ │  │  │  ┌turn speed (8=def)
+                ;     │ │ │ │  │  │  │  ┌score limit (0=none)
+gamesingle  =  0 ;    │ │ │ │  │  │  │  │
+datasingle:.db %00100110,3,1,1,-1,-1, 8, 0 ;Singleplayer (SP; 3 lives)
 gamepeas    =  1
-datapeas:  .db %00000000,1,1,1,-1,126,8, 0 ;Peaworm (SP; 1 live, 127 growth)
+datapeas:  .db %00100100,1,1,1,-1,126,8, 0 ;Peaworm (SP; 1 live, 127 growth)
 gametron    =  2
-datatron:  .db %01010000,1,1,1,-1, 0, 8, 0 ;Tron (SP; 1 live, cont.growth)
+datatron:  .db %01110100,1,1,1,-1, 0, 8, 0 ;Tron (SP; 1 live, cont.growth)
 gamedeathm  =  3
-datadeathm:.db %01000001,3,2,1,-1,49, 8, 0 ;Deathmatch (3 lives, 50 growth)
+datadeathm:.db %01100000,3,2,1,-1,42, 8, 0 ;Deathmatch (3 lives, 50 growth)
 gamefoodm   =  4
-datafoodm: .db %00000001,0,2,1,-1,-1, 8,10 ;Foodmatch (100 score)
+datafoodm: .db %00100000,0,2,1,-1,-1, 8,10 ;Foodmatch (100 score)
 gamemfoodm  =  5
-datamfoodm:.db %11000011,0,2,1,-1,-1, 8,10 ;MuchFoodmatch (10 peas)
+datamfoodm:.db %11100010,0,2,1,-1,-1, 8,10 ;MuchFoodmatch (10 peas)
 gametimem   =  6
-datatimem: .db %01010001,1,2,1,-1, 0, 8, 0 ;Timematch (1 live, cont.growth)
+datatimem: .db %01110000,1,2,1,-1, 0, 8, 0 ;Timematch (1 live, cont.growth)
 gamerace    =  7
-datarace:  .db %01000001,0,2,1,-1,-1, 8,10 ;Race (100 score)
+datarace:  .db %01000000,0,2,1,-1,-1, 8,10 ;Race (100 score)
 gamectf     =  8
-datactf:   .db %01001001,0,6,1,-1,-1, 8,10 ;CTF (100 score)
+datactf:   .db %01001000,0,6,1,-1,-1, 8,10 ;CTF (100 score)
 
 gametype:  .db 0 ;last gamemode
 gamecar:         ;made before needed (not saved)
 
 saveend:;---
 
-startdelay  =  17
+startdelay  =  42
 rspawndelay =  31
 maxnamesize =  8+1
 
@@ -4549,4 +4546,4 @@ templevels:
 
   .end
 
-.end
\ No newline at end of file
+.end