	device ZXSPECTRUM128

        include "defs.asm"
;gameplay:
FIREXRADIUS=8
FIREYRADIUS=5
HEROXRADIUS=5
HEROYRADIUS=5
bombradius=16 ;32 пикс во все стороны
MAXSPEED=16;24;32 ;48 глючит (влетел в стену слева)
SLOWJUMP=1
SOSULKA_MOTIONDETECT_RADIUS=10

;debug:
;PENT=0
DISK=PENT
NOIM=0;1
BORDER=0
EDITOR=0;1
MAPSPACKED=1
CHEAT=0;1
FONT=1

;speedup:
MAXDOTS=24
TIMERWAITLOGIC=0
NOEXX=1 ;-20t, нельзя юзать альтернативные регистры bcdehl', но можно af' (иначе наоборот)
SPRPAGED=0
FULL7FFD=0
;для фирменных машин: в плейере можно убрать ld (),sp...ld sp,:exx:ret, заменить на jp
        if PENT
PAGEOR=0x10
        else
PAGEOR=0x50
        endif
pgmain=0 ;там код и тайлы
pgspr=0        
pgmuz0=1 ;slowmem                               ;menu music
pgmuz1=6 ;fastmem (contended at +3!!!)          ;easy music
pgmuz2=4 ;fastmem                               ;hard music
pgmuz3=3 ;slowmem                               ;boss music
pgmuz4=7 ;slowmem                               ;end music
mus_play=0xc021
        
IMVEC=0x80ff
ON_INT_test=0x7f7f
ON_INT=0x7f7f ;slow mem

STACK=0x6000
IMSTACK=0x6100

attr=0xa000 ;0xa000, чтобы быстро пересчитывать из адреса экрана ;0x800 bytes + 0x400 для клипирования снизу
tilegfx_sz=0x400
tileattr_sz=0x200
MCHGT=16

MAXKEYCARDS=10
MAXKILLEDMONSTERS=8*10*8 ;8*7*8 ;на нижних 3 строках (8..10) учебные уровни без монстров
        
	org 0x6100
sprscriptbuf=0x6000 ;сюда сохраняем пустой скрипт
begin
        ld hl,sprscript ;там пустой скрипт
        ;ld de,sprscriptbuf
        call ldirsprscript
        ;ld bc,resprscript_end-sprscript
        ;ldir
        if 1==0
        ld hl,0x4eeb ;там цифры (нижний пиксель не нужен)
        ld de,digitsgfx
        ld c,10
getdigits0
        push hl
        ld a,(hl)
        ld (de),a ;нижняя линия
        inc e
        dec h
        ld a,(hl)
        ld (de),a ;нижнее очко
        inc e
;        ld b,7
;getdigits1
;        ld a,(hl)
;        ld (de),a
;        inc e
;        dec h
;        djnz getdigits1
        res 5,l
        ld h,0x49
        ld a,(hl)
        ld (de),a ;верхняя линия
        inc e
        inc h
        ld a,(hl)
        ld (de),a ;верхнее очко
        inc e
        ld h,0x4f
        ld a,(hl)
        ld (de),a ;средняя линия
;        ld b,8
;getdigits2
;        inc h
;        ld a,(hl)
;        ld (de),a
;        inc e
;        djnz getdigits2
        ld a,e
        or 7
        inc a
        ld e,a
        pop hl
        inc l
        dec c
        jr nz,getdigits0
        endif

        ;ld hl,sfx
        ;call SFXINIT

        if 1==1
        call test128 ;z=48K/TK90X, nz=128K
        else
        ld h,0xff
        ld a,pgmuz0+PAGEOR
        out (0xfd),a
        ld (hl),a
        ld a,pgmain+PAGEOR
        out (0xfd),a
        ld (hl),a
        ld a,pgmuz0+PAGEOR
        ;ld bc,0x7ffd
        ;out (c),a
        out (0xfd),a
        ld a,pgmain+PAGEOR
        cp (hl)
        endif
         ;jr noloadmuz
        jr z,noloadmuz
        
;load player
        ld a,pgmuz0+PAGEOR
        call loadfile
        ld hl,0xc000
        ld (iniplayaddr),hl
	call 0xc000 ;ini player
        ld hl,mus_play;0xc003
        ld (muzplayaddr),hl
        if PENT
        ld (muzplayaddr_mc),hl
        endif
        ld a,pgmuz1+PAGEOR
        call loadfile
        ld a,pgmuz2+PAGEOR
        call loadfile
        ld a,pgmuz3+PAGEOR
        call loadfile
        ld a,pgmuz4+PAGEOR
        call loadfile
noloadmuz

        ;ei
        ld b,50
        halt
        djnz $-1
        ld hl,0x5800
        ld bc,0x2ff
        call clearblock
        
        ld a,pgmain+PAGEOR
        ;ld bc,0x7ffd
        ;out (c),a
        out (0xfd),a
        
        ;ld hl,wastileattr
        ;ld de,tileattr
        ;ld bc,tileattr_sz
        ;ldir
        ;ld hl,wastilegfx+tilegfx_sz-1
        ;ld de,tilegfx+tilegfx_sz-1
        ;ld bc,tilegfx_sz
        ;lddr
        
        if 1==0
	if IMVEC==#3bff
       ;LD hl,#c9fb
       ;LD (#fff4),hl
	   ld a,#c3
	   ld (#fff4),a
       ld hl,ON_INT_test
       ld (#fff5),hl
	   ld a,#18
	   ld (#ffff),a
	else
       ;ld hl,ON_INT_test
       ;ld (IMVEC),hl
       ld hl,IMVEC&0xff00
       ld (hl),ON_INT_test/256
       inc l
       jr nz,$-3
       inc h
       ld (hl),ON_INT_test/256
	endif
        endif
	ld a,IMVEC/256
    ld i,a
    im 2
    ;ei 
        ;if $<(sprscriptbuf+0xa0)
        ;ds sprscriptbuf+0xa0-$
        ;endif
        ;jr $
	jp maingo

loadfile
        ;ld bc,0x7ffd
        ;out (c),a
        out (0xfd),a
       if DISK;PENT
         ld hl,tmodule
	ld de,#5cdd
	ld bc,9
	ldir
	ld c,#a ;find
	call #3d13
	ld a,c
	ld c,#8 ;load descr
	call #3d13
	xor a
	ld (23801),a
         ld hl,tmodule+6
         inc (hl)
	ld hl,0xc000
	ld de,(#5ce8) ;length
	ld a,3
	ld c,#e ;load file
	jp #3d13
       else
        ld ix,0xc000
        ld de,17
        xor a
        scf
        call 1366
        ld ix,0xc000
        ld de,(0xc000+11);0x4000
        scf
        sbc a,a
        jp 1366
       endif

tmodule
        db "MODULE0 C"
;tmodule1
;        db "MODULE1 C"

prtime
        ld h,digitsgfx/256
        ld e,0x6e
        ld a,(curtenseconds)
        call prdigit
        ld e,0x6f
        ld a,(cursecond)
        call prdigit
        ld e,0x71
        ld a,(cursubsecond)
prdigit
        ld d,0x56
        add a,a
        add a,a
        add a,a
        ;add a,a
        ld l,a
        ;PRDIGIT
        ld a,(hl)
        inc l
        ld (de),a ;нижняя линия
        dec d
        ld a,(hl)
        inc l
         ld b,6
        ;dup 6
        ld (de),a ;нижнее очко
        dec d
        ;edup
        ;org $-1
         djnz $-2
        res 5,e
        ld d,0x51;inc d
        ld a,(hl)
        inc l
        ld (de),a ;верхняя линия
        inc d
        ld a,(hl)
        inc l
         ld b,5
       ;dup 5
        ld (de),a ;верхнее очко
        inc d
       ;edup
         djnz $-2
        ld a,(hl)
        ld (de),a ;средняя линия
        ret

setkeys
        ld hl,tkeyaddrs
        ld hx,5
         ld a,(bc)
         inc bc
         ld lx,a
setkeys0
        ld e,(hl)
        inc hl
        ld d,(hl)
        inc hl
        ld a,(bc)
        inc bc
        ld (de),a ;ld
        inc de
        inc de
        ld a,(bc)
        inc bc
        ld (de),a ;port
        inc de
        inc de
        ld a,(bc)
        inc bc
        ld (de),a ;and
        inc de
        ld a,lx
        ld (de),a ;jr nz(keyboard)/z(kempston)
        dec hx
        jr nz,setkeys0 ;можно короче через ldi
        ret

tkeyaddrs
        dw fireld ;+2 = fireport, +4 = fireand
        dw upld
        dw downld
        dw leftld
        dw rightld

topqakeys
        db 0x20
        db 0x7f,0xfe,1 ;fire
        db 0xfb,0xfe,1 ;up
        db 0xfd,0xfe,1 ;down
        db 0xdf,0xfe,2 ;left
        db 0xdf,0xfe,1 ;right
tsinclairkeys
        db 0x20
        db 0xef,0xfe,1 ;fire
        db 0xef,0xfe,2 ;up
        db 0xef,0xfe,4 ;down
        db 0xef,0xfe,16 ;left
        db 0xef,0xfe,8 ;right
tkempstonkeys
        db 0x28
        db 0x1f,0x1f,16 ;fire
        db 0x1f,0x1f,8 ;up
        db 0x1f,0x1f,4 ;down
        db 0x1f,0x1f,2 ;left
        db 0x1f,0x1f,1 ;right
tcursorkeys
        db 0x20
        db 0xef,0xfe,1 ;fire
        db 0xef,0xfe,8 ;up
        db 0xef,0xfe,16 ;down
        db 0xf7,0xfe,16 ;left
        db 0xef,0xfe,4 ;right

test128
;z=48K/TK90X, nz=128K
	ld bc,#7ffd
	;ld h,c
        ;ld l,c ;hl=0xfdfd
        ld hl,0xffff
	ld de,#1011
	out (c),d
	ld (hl),c ;#fd
	out (c),e
	dec (hl)
	ld a,(hl)
	out (c),d
	cp (hl)
        ret
;-----------------
delmonsters
        if EDITOR
        ld b,6;7
        else
        ld b,7
        endif
;b=number of objects to clear
        ld ix,objects
        ld de,OBJSIZE
filltilemap_delmonsters0
        ;ld (ix+OBJ_GFX),ID_NONE
        ;ld (ix+OBJ_PROC_ADDR),moveobj_none&0xff
        ;ld (ix+OBJ_PROC_ADDR+1),moveobj_none/256
        call setidnone_procnone;_nosety
        add ix,de
        djnz filltilemap_delmonsters0
        ;ld a,ID_HARDYRIGHT
        ;ld (objects+(7*OBJSIZE)+OBJ_GFX)
        ret

newlevel
;показать поздравление с учётом оставшегося времени и levelmonsterskilled/levelmonsters
         ld a,3 ;3 перезвяк, 5 диньк, 7 тормоз, 9 миниприз, 10 приз, 11 бум
         call SFXPLAY
         
         ld a,(level)
         cp HARDLEVEL-1
         jr nz,newlevel_nohard
        push af
        ld a,pgmuz2+PAGEOR ;hard music
        call iniplay
        pop af
newlevel_nohard
         cp BOSSLEVEL-1
         jr nz,newlevel_noboss
        push af
        ld a,pgmuz3+PAGEOR ;boss music
        call iniplay
        pop af
newlevel_noboss
;         cp BOSSLEVEL
;         jr nz,newlevel_noreturn
;        push af
;        ld a,pgmuz2+PAGEOR ;hard music
;        call iniplay
;        pop af
;newlevel_noreturn
         cp LASTLEVEL
         jp nz,newlevel_nolast
        call addtimebonus
;добавим 500 ("5000") за каждую жизнь
        ld a,(lives_chr) ;там 0(dead)..5(max)
        ld b,a
        ld de,500
        ld hl,(score)
        add hl,de
        djnz $-1
        ld (score),hl
        call prscore
        
        ld a,pgmuz4+PAGEOR ;end music
        call iniplay
        ld hl,resprq
        ld (resprscript),hl
         halt
        ld hl,emptyprsprscriptwithmc
        ld (prsprscriptaddr),hl ;потом надо восстановить, gamemenu восстанавливает
        call setemptysprscript
         
;нарисовать пустой фон
        ld hl,tilemap
        ld (hl),0
        inc l
        jr nz,$-3
        call prtilemap
         
         ld a,4
         ld (cursubsubsecond),a
         call waitkey_prepareseconds
         call prcongratulations

         call pausekeeptimer

finalcutwaitkey0
        call waitkey_haltgetkey
        jr nz,finalcutwaitkey0 ;ждём отпускания кнопок
;чтобы бегал персонаж
        ld ix,objects+(7*OBJSIZE)
        ld (ix+OBJ_X),80
        ld (ix+OBJ_Y),64-9
        ld (ix+OBJ_DX),0
        ld (ix+OBJ_GFX),ID_HARDYRIGHT
        call delmonsters

        halt
        ld hl,sprscript ;pop hl
        ld (prsprscriptaddr),hl
        ld hl,resprq ;pop hl
        ld (resprscript),hl
        ld a,0xc3
        ld (mainloop_patch),a
        ld hl,selfmove
        ld (mainloop_patch+1),hl
        
        ;halt
;jpmainloop
;        jp mainloop;+1 ;skip halt, generate rescript

selfmove
selfmove_right
        call selfmove_anim ;set ix
        inc (ix+OBJ_DX)
        inc (ix+OBJ_DX)
        call selfmove_movex
        cp 120-9 +1
        jr nc,selfmove_rightedge
selfmoveq
        call restoreseconds
        call getkey
        jp z,mainloop
        jp updatehiscore_gamemenu

selfmove_rightedge
        ld (ix+OBJ_DX),-16
selfmove_edge
        ld (ix+OBJ_DY),-3
        ld hl,selfmove_otkat
        ld (mainloop_patch+1),hl
        ld a,2;xor a
        ld (timer),a
        jr selfmoveq

selfmove_left
        call selfmove_anim ;set ix
        dec (ix+OBJ_DX)
        dec (ix+OBJ_DX)
        call selfmove_movex
        cp 8
        jr nc,selfmoveq
        ld (ix+OBJ_DX),16
        jr selfmove_edge
        
selfmove_otkat
        ;ld ix,objects+(7*OBJSIZE)
        call selfmove_anim ;set ix
        call selfmove_movex
        ld a,(timer3flag)
        add a,(ix+OBJ_DY)
        ld (objects+(7*OBJSIZE)+OBJ_DY),a
        add a,(ix+OBJ_Y)
        ld (ix+OBJ_Y),a
        cp 64-9
        ;jr z,selfmove_otkat_end
        jr nz,selfmoveq
selfmove_otkat_end
         call rnd
         rra
        ld (ix+OBJ_GFX),ID_HARDYLEFT
        ld hl,selfmove_left
         jr c,selfmove_patch_q;selfmove_otkat_end_left
        ld (ix+OBJ_GFX),ID_HARDYRIGHT
        ld hl,selfmove_right
selfmove_patch_q
        ld (mainloop_patch+1),hl
        jr selfmoveq
;selfmove_otkat_end_left
;        ld (ix+OBJ_GFX),ID_HARDYLEFT
;        ld hl,selfmove_left
;        jr selfmove_patch_q
         
newlevel_nolast         
         
        ld hl,emptyprsprscript ;выход без мультиколора и восстановления спрайтов
        ld (prsprscriptaddr),hl

        call clwindow

        ld hl,0x5882
        ld bc,(28-1)*256+0x44
        ld (hl),c
        inc l
        djnz $-2
        ld l,0xe2
        ld bc,(17-1)*256+0x42
        ld (hl),c
        inc l
        djnz $-2
        ld hl,0x5922
        ld bc,(17-1)*256+0x05
        ld (hl),c
        inc l
        djnz $-2
        ld l,0x62
        ld bc,(17-1)*256+0x03
        ld (hl),c
        inc l
        djnz $-2

        ld a,4
        ld (cursubsubsecond),a ;чтобы бонус соответствовал видимому времени

        ld hl,tlevelcomplete
        ;ld de,0x40c9
        call prtext
        ;ld hl,tmonsterskilled
        ;ld de,0x4803;2
        call prtext
       push hl
        ld hl,(monsterskilledhere)
        call prnum
        ld a,'/'
        call prchr
        ld hl,(monstershere)
        call prnum

        call addtimebonus
       ex de,hl
;hl=health bonus
;bc=time bonus
       ex (sp),hl;ld hl,ttimebonus
       push bc
        ;ld de,0x4847
        call prtext
       ex (sp),hl ;hl=time bonus
        call prnum
        ld a,'0'
        call prchr
       pop hl
        call prtext ;thealthbonus
       pop hl
        call prnum
        ld a,'0'
        call prchr
;TODO медленно перелить бонус в score? это не соответствует ритму игры
        ;call prscore ;потом покажем, а тут бонус показываем отдельно
        call prinfopanel
        
newlevelpp
;при переходе на финалкат не вызывается!
         call waitkey_prepareseconds
         call waitkey_withupdseconds
        call empty_restore_sprscript

;зафиксируем достижения        
        ld a,(keycards)
        ld (levelkeycards),a
        ld hl,(takenkeycardslist_addr)
        ld (leveltakenkeycardslist_addr),hl ;в списке все ключи, которые мы взяли к этому моменту (в том числе использованные)
        ld hl,takenkeycardslist
        ld de,leveltakenkeycardslist
        ;ld bc,takenkeycardslist_sz
        ;ldir
        ;ld hl,killedmonsterslist
        ;ld de,levelkilledmonsterslist
        ;ld bc,killedmonsterslist_sz
        ld bc,takenkeycardslist_sz+killedmonsterslist_sz
        ldir
        ld hl,(score)
        ld (levelscore),hl
        
        ld hl,level
        inc (hl) ;TODO проверить, что последний
         ;ld a,3 ;3 перезвяк, 5 диньк, 7 тормоз, 9 миниприз, 10 приз, 11 бум
         ;call SFXPLAY
        ;jp initlevel;filltilemap
initlevel
;restore energy bar 
        ld a,80/4
        ld (energy_bonus),a
        xor a
        ld (energy_malus),a

levelscore=$+1
        ld hl,0
        ld (score),hl
        ;call prscore
        call prinfopanel
        
        ld a,(level)
        ld c,a
        add a,a
        add a,a
        add a,a
        sub c ;*7
        ld c,a
        ld b,0
        ld hl,tlevels
        add hl,bc
        ld c,(hl)
        inc hl
        ld b,(hl)
        ld (mapxy),bc
        inc hl
        ld a,(hl)
        ld (objects+(7*OBJSIZE)+OBJ_X),a
        inc hl
        ld a,(hl)
        ld (objects+(7*OBJSIZE)+OBJ_Y),a
        inc hl
        ld a,(hl)
        ld (curtenseconds),a
        inc hl
        ld a,(hl)
        ld (cursecond),a
        inc hl
        ld a,(hl)
        ld (monstershere),a

        xor a
        ld (objects+(7*OBJSIZE)+OBJ_DX),a
        ld (objects+(7*OBJSIZE)+OBJ_DY),a ;персонаж не двигается

        ;xor a
        ld (monsterskilledhere),a
        
        ld a,4
        ld (cursubsubsecond),a
        ld a,9
        ld (cursubsecond),a
        halt
        call prtime ;чтобы увидеть время на резинке
        ;di
        ;halt

        display "levelkeycards-1=",$
levelkeycards=$+1
        ld a,0
        ld (keycards),a
leveltakenkeycardslist_addr=$+1
        ld hl,0
        ld (takenkeycardslist_addr),hl

        ld hl,leveltakenkeycardslist
        ld de,takenkeycardslist
        ;ld bc,takenkeycardslist_sz
        ;ldir
        ;ld hl,levelkilledmonsterslist
        ;ld de,killedmonsterslist
        ;ld bc,killedmonsterslist_sz
        ld bc,takenkeycardslist_sz+killedmonsterslist_sz
        ldir
        ;jp filltilemap

filltilemap
;обновить тайлмап из глобальной карты по глобальным координатам
;врагов тоже (тип (3 бит), y (3 бит), minx (4 бит), maxx (4 бит), x (2 бит: x=0:нач->, 1:сер->, 2:сер<-, 3:кон<-) - а скорость, health и процедура определяются типом)
;сейчас на экране нет спрайтов
;keep ix!!!
        ;jr $
        ;ld hl,(prsprscriptaddr)
        ;push hl
        ld hl,emptyprsprscript ;выход без мультиколора и восстановления спрайтов
        ld (prsprscriptaddr),hl

         ld a,(objects+(7*OBJSIZE)+OBJ_Y)
         sub HEROYRADIUS
         ld (herocollision_heroymin),a ;если Y координата сменилась (а X обновляется после выхода отсюда)
;для перехода на следующий уровень надо и X обновить:
         ld a,(objects+(7*OBJSIZE)+OBJ_X)
         sub HEROXRADIUS
         ld (herocollision_heroxmin),a
         add a,HEROXRADIUS*2+1
         ld (herocollision_heroxmax),a

        xor a
        ld (fireyx_x),a ;уничтожить пулю
        ld (refire_scraddr+1),a ;уничтожить восстановилку пули
        ld (ndots),a ;уничтожить партиклы

        ;xor a
        call clearattr

        push ix
        
        call delmonsters ;очистим все объекты (moveobj_none), графика у всех чистая, кроме героя

        call getmapaddr ;hl=map addr

        ld ix,objects
	ld de,tilemap
        ld b,8
filltilemap0
        push bc
        inc e
        inc e
         ld a,(hl)
         add a,a
         add a,a
         add a,a
         and 15*8
         ld (filltilemap_maxx),a
         ld a,(hl)
         rra
         and 15*8
         ld (filltilemap_minx),a
         inc hl
        ld b,14
filltilemap1
	ld a,(hl)
        add a,a
        add a,a
        jp p,$+5 ;bit7 (оригинальный бит 5 = маленькие буквы)
        add a,2
        and 0x7e
        push hl
        add a,metatiles&0xff
        ld l,a
        adc a,metatiles/256
        sub l
        ld h,a
        ld a,(hl)
	ld (de),a ;номера тайлов (16x8) делятся на 4
        inc hl
        inc e
        ld a,(hl)
        ld (de),a
        pop hl
	inc hl
	inc e
        djnz filltilemap1
        push de
filltilemap_minx=$+1
filltilemap_maxx=$+2
        ld bc,0
        ld (ix+OBJ_MINX),c
        ld (ix+OBJ_MAXX),b
        ld a,b
        cp c
        jp c,filltilemap_nomonster
         ld a,e
        if EDITOR
         cp 0xc0
        else
         cp 0xe0
        endif
         jp nc,filltilemap_nomonster
;проверить монстра в killedmonsterslist
        push hl
        call getmaproom
        pop hl
        ld de,killedmonsterslist
        add a,e
        ld e,a
        adc a,d
        sub e
        ld d,a
        ld a,(de)
        and (ix+OBJ_NUMBERMASK)
        jp nz,filltilemap_nomonster ;монстр уже уничтожен

        push hl
        ld a,(hl) ;x*64+(y*8)+type ;x=0:нач->, 1:сер->, 2:сер<-, 3:кон<-
        and 7*8
        ld (ix+OBJ_Y),a ;TODO корректировать в зависимости от высоты персонажа
        ld a,(hl) ;x*64+(y*8)+type ;x=0:нач->, 1:сер->, 2:сер<-, 3:кон<-
        and 7
        ld l,a
        add a,a
        add a,l
        add a,a ;type*6
        ld hl,objtypes
        add a,l
        ld l,a
        adc a,h
        sub l
        ld h,a
;OBJ_GFX
        ld e,(hl)
        inc hl
        ld (ix+OBJ_GFX),e
;OBJ_DX
        ld a,(hl)
        inc hl
        ld (ix+OBJ_DX),a
;OBJ_DY
        ld a,(hl)
        inc hl
        ld (ix+OBJ_DY),a
;OBJ_HEALTH
        ld a,(hl)
        inc hl
        ld (ix+OBJ_HEALTH),a
;OBJ_PROC_ADDR (16bit)
        ld a,(hl)
        inc hl
        ld (ix+OBJ_PROC_ADDR),a
        ld a,(hl)
        ld (ix+OBJ_PROC_ADDR+1),a
	pop hl
        
        ld a,(hl) ;x*64+(y*8)+type ;x=0:нач->, 1:сер->, 2:сер<-, 3:кон<-
         rla
         jr c,filltilemap_xright
;filltilemap_xleft
         rla
         jr nc,filltilemap_xleftend
         ;turn right
        set SPRTURNBIT,(ix+OBJ_GFX)
         ld a,b ;maxx
         add a,c ;minx
         rra ;
        jp filltilemap_xrightq
filltilemap_xleftend
         ;turn right
        set SPRTURNBIT,(ix+OBJ_GFX)
         ld a,c ;minx
        jp filltilemap_xrightq
filltilemap_xright
         rla
         jr c,filltilemap_xrightend
         ;turn left
        xor a
        sub (ix+OBJ_DX)
        ld (ix+OBJ_DX),a
         ld a,b ;maxx
         add a,c ;minx
         rra ;
        jp filltilemap_xrightq
filltilemap_xrightend
         ;turn left
        xor a
        sub (ix+OBJ_DX)
        ld (ix+OBJ_DX),a
         add a,b ;maxx
        ;jp filltilemap_xrightq
filltilemap_xrightq
        ld (ix+OBJ_X),a

        ld a,(ix+OBJ_DY)
        or a
        jr z,filltilemap_noverticalenemy
        ld a,(ix+OBJ_Y)
        ld b,(ix+OBJ_X)
        add a,a
        ld (ix+OBJ_X),a
        ;ld a,b
        ;jr $
        ld (ix+OBJ_Y),b
         inc (ix+OBJ_MINX) ;а то налезало на потолок
filltilemap_noverticalenemy
        ld a,e
        cp ID_BOSS
        jr nz,filltilemap_noboss
        ld (ix+OBJSIZE+OBJ_GFX),ID_BOSSEYE
        ld a,(ix+OBJ_X)
        ld (ix+OBJSIZE+OBJ_X),a
        ld a,(ix+OBJ_Y)
        sub 5;9
        ld (ix+OBJSIZE+OBJ_Y),a
         ;dec (ix+OBJ_MAXX) ;а то босс налезал на пол (он высотой 18, а не 16) ;этот параметр не используется у босса, там константы
;OBJ_DX = не важно
;OBJ_DY = не важно
;OBJ_HEALTH = не важно
;OBJ_PROC_ADDR (16bit) = none
filltilemap_noboss

filltilemap_nomonster
         inc hl
         ld bc,OBJSIZE
         add ix,bc
         pop de
        inc e
        inc e
         pop bc
        dec b
	jp nz,filltilemap0
        pop ix

;стираем взятые ключи
        call getmaproom ;a=current room
        ld c,a ;c=current room
        ld hl,takenkeycardslist
        ld b,MAXKEYCARDS
        ;ld a,(keycards)
        ;or a
        ;jr z,filltilemap_nokeycards
        ;ld b,a
filltilemap_delkeys0
        ld a,(hl) ;mapxy
        inc hl
        cp c
        jr nz,filltilemap_delkeysskip
        ld e,(hl) ;xy
        ld d,tilemap/256
        xor a
        ld (de),a
filltilemap_delkeysskip
        inc hl
        djnz filltilemap_delkeys0
filltilemap_nokeycards

        call prtilemap

empty_restore_sprscript
;ставим пустой скрипт, т.к. скрипт восстановилки хранит номера тайлов под спрайтами!
        call setemptysprscript
        jp restore_sprscript
setemptysprscript
        ld hl,sprscriptbuf
        ld de,sprscript
ldirsprscript
        ld bc,resprscript_end-sprscript
        ldir
        ret
        ;pop hl
        ;ld (prsprscriptaddr),hl ;новый скрипт ещё не сгенерён, спрайты выведутся в старых местах (точнее, не выведутся с пустым скриптом)        
	;ret
remove_sprscript
;выключает мультиколор, но оставляет спрайты на экране
;заодно чистит атрибуты
;a=attr
        ld hl,(resprscript)
        push hl
        ld hl,resprq
        ld (resprscript),hl
        if NOIM
        ei
        halt ;теперь на экране остались спрайты, но двигать их нельзя, иначе на следующем перепечатывании они нарисуются по старым
        di
        else
        halt
        endif
        pop hl
        ld (resprscript),hl
        ;ld hl,(prsprscriptaddr)
        ;push hl
        ld hl,emptyprsprscript ;выход без мультиколора и восстановления спрайтов
        ld (prsprscriptaddr),hl        
        jp clearattr

prtilemap
	ld hl,0x4000;2
	ld de,tilemap
	ld hy,8
prtilemap_lines0
	push de
	push hl
	ld ly,32;28        
        call prtilemap_columns
	pop hl
	pop de
	ld a,e
	add a,32
	ld e,a ;next tile line
	ld a,l
	add a,64
	ld l,a
	jr nc,$+6
	ld a,h
	add a,8
	ld h,a
	dec hy
	jp nz,prtilemap_lines0
        ret

        include "objtypes.asm"

        if MAPSPACKED
getmapaddr
        ld a,(mapy)
        add a,a
        ld hl,tmaplines
        add a,l
        ld l,a
        adc a,h
        sub l
        ld h,a
        ld a,(hl)
        inc hl
        ld h,(hl)
        ld l,a
        ld de,maplinebuf
        ;halt
        ;jr $
        ;di
        call unpack ;uses af'! но занимает 2 фрейма!
        ;ei
        ld a,(mapx)
        ld h,a
        ld l,0
        srl h
        rr l
        ld bc,maplinebuf
        add hl,bc
;hl=map addr
        ret
tmaplines
        dw mapline0
        dw mapline1
        dw mapline2
        dw mapline3
        dw mapline4
        dw mapline5
        dw mapline6
        dw mapline7
        dw mapline8
        dw mapline9
        else
getmapaddr
        call getmaproom
;одна карта=112 b
metatilemapsize=128
        inc a
        ld b,a
	ld hl,metatilemap-metatilemapsize        
        ld de,metatilemapsize
        add hl,de
        djnz $-1
;hl=map addr
        ret
        endif

getmaproom
        ld hl,(mapx) ;h=mapy
        ld a,h
        add a,a
        add a,a
        add a,a
        add a,l
        ret

prtilemap_columns
;ly=number of columns
;de=tilemap
;hl=screen
prtilemap_columns0
	push de
	push hl
	ex de,hl
	ld l,(hl) ;tile
	push de
	push hl ;l=tile
	ld h,tilegfx/256/4
	add hl,hl
	add hl,hl
	ld b,2;16
prtilemap_gfx0
        dup 8
	ld a,(hl)
	ld (de),a
	inc l
        inc d
        edup
        ;org $-1
	;call dde
        ld a,e
        sub -32
        ld e,a
        sbc a,a
        and -8
        add a,d
        ld d,a
	djnz prtilemap_gfx0
	pop hl ;l=tile
	pop de
	 scf
	 rr d ;attr addr
	ld h,tileattr/256/2
	add hl,hl
	 ld a,l
	 or 7
	 ld l,a
	ld b,2;8
prtilemap_attr0
        dup 4
	ld a,(hl)
	ld (de),a
	dec l;inc l
	inc d
        edup
	;ld a,d
	;and 3
	;jr nz,prtilemap_attr0ok
	ld a,e
	add a,32
	ld e,a
	jr c,prtilemap_attr0ok
	ld a,d
	sub 4
	ld d,a
prtilemap_attr0ok
	djnz prtilemap_attr0
	
	pop hl
	pop de
	inc l ;scr
	inc e ;next tile
	dec ly
	jp nz,prtilemap_columns0
        ret

        if EDITOR
moveobj_editor_changeroom
        ld hl,mapx
        rra
        jr c,moveobj_editor_changeroom_noleft
        dec (hl)
moveobj_editor_changeroom_noleft
        rra
        jr c,moveobj_editor_changeroom_noright
        inc (hl)
moveobj_editor_changeroom_noright
        inc hl ;mapy
        rra
        jr c,moveobj_editor_changeroom_nodown
        inc (hl)
moveobj_editor_changeroom_nodown
        rra
        jr c,moveobj_editor_changeroom_noup
        dec (hl)
moveobj_editor_changeroom_noup

        jp filltilemap

moveobj_editor
        ld a,0xf7
        in a,(0xfe)
         bit 4,a
         jr z,moveobj_editor_changeroom
        rra
        jr c,moveobj_editor_noleft
        dec (ix+OBJ_X)
moveobj_editor_noleft
        rra
        jr c,moveobj_editor_noright
        inc (ix+OBJ_X)
moveobj_editor_noright
        res 7,(ix+OBJ_X)
        rra
        jr c,moveobj_editor_nodown
        inc (ix+OBJ_Y)
moveobj_editor_nodown
        rra
        jr c,moveobj_editor_noup
        dec (ix+OBJ_Y)
moveobj_editor_noup
        res 6,(ix+OBJ_Y)
        res 7,(ix+OBJ_Y)
;вводим метатайл
        ld a,0x10 ;все полуряды, кроме 67890
        in a,(0xfe)
        cpl
        and 31
        ret z ;ничего не нажато
        
        ld bc,0xfefe
        in e,(c) ;shiftstate
        ld hl,tkeys
getkey0
        in a,(c)
        ld d,5
getkey1
        rra
         inc (hl)
         dec (hl)
         jr z,getkeyskip
        jr nc,getkeyok
getkeyskip
        inc hl
        dec d
        jr nz,getkey1
        rlc b
        jr c,getkey0
        ret
getkeyok
        ld a,(hl) ;маленькая буква
        bit 0,e
        jr nz,$+4 ;no shift
        sub 32 ;большая буква

printmetatile
;печатаем метатайл в текущее место (под персонаж ix)
;a=буква
        push af
        call getmapaddr ;hl=map addr
	ld a,(ix+OBJ_X)
        rra
        rra
         inc a ;на одно знакоместо правее, чем левая граница персонажа
        and 30;31
        LD c,A
        ld a,(ix+OBJ_Y)
        and 0x38
        add a,a
        add a,a
        add a,c
        ld e,a ;e=смещение в тайлмапе
        rrca ;чётное
        add a,l
        ld l,a
        jr nc,$+3
        inc h ;hl=адрес в нужной карте
        pop af
        ld (hl),a ;рисуем в карте
        
        add a,a
        add a,a
        jp p,$+5 ;bit7 (оригинальный бит 5 = маленькие буквы)
        add a,2
        and 0x7e
        add a,metatiles&0xff
        ld l,a
        adc a,metatiles/256
        sub l
        ld h,a ;hl=описатель метатайла

        ld d,tilemap/256 ;32*8 tiles
        ld a,(hl)
	ld (de),a ;номера тайлов (16x8) делятся на 4
        inc hl
        inc e
        ld a,(hl)
        ld (de),a ;рисуем в тайлмапе
        dec e

;печатаем метатайл на экран
        ld a,(ix+OBJ_Y)
        and 0x38
        ld l,a
        ld a,c
        add a,0x40
;a=x/8 + 0x40
;l=y/2
        ld h,tytoscr/256
        add a,(hl)
        inc h
        ld h,(hl)
        ld l,a ;hl=scr
        ld ly,2
;ly=number of columns
;de=tilemap
;hl=screen
        jp prtilemap_columns

tkeys
        db 0,"zxcv"
        db "asdfg"
        db "qwert"
        db 0,0,0,0,0
        db 0,0,0,0,0
        db "poiuy"
        db 0,"lkjh"
        db " ",0,"mnb"
        endif

prtextwithattr
        ld lx,0x47
;hl=text
;de=scr
prtextwithattr0
        ld a,(hl)
        inc hl
        or a
        ret z
         jp p,prtextwithattr_nocolor
         and 0x7f
         ld lx,a
         jr prtextwithattr0
prtextwithattr_nocolor
        push hl
        call prchrwithattr
        pop hl
        jr prtextwithattr0

prchrwithattr
        inc e
        cp ' '
        ret z
        call prchrpp
        scf
        rr d
        ld a,lx;0x47
        ld b,4
prchrwithattr1
        ld (de),a
        inc d
        djnz prchrwithattr1
        ld d,c
        ret

prtext
;hl=text
        ld e,(hl)
        inc hl
        ld d,(hl)
        inc hl
prtext_de
;de=scr
prtext0
        ld a,(hl)
        inc hl
        or a
        ret z
        push hl
        call prchr
        pop hl
        jr prtext0

prchr
        inc e
prchrpp
        if FONT
        add a,a
        ld c,a
        xor a
        ld b,a
        ld hl,fnt-(6*32)
        add hl,bc
        add hl,bc
        add hl,bc
        ld c,d
        ld (de),a
        inc d
        ld b,6
prchrwithattr0
        ld a,(hl)
        inc hl
        ld (de),a
        inc d
        djnz prchrwithattr0
        xor a
        ld (de),a
        else
        add a,a
        ld l,a
        ld h,15
        add hl,hl
        add hl,hl
        ld c,d
        ld b,8
prchrwithattr0
        ld a,(hl)
        rrca
        or (hl)
        inc l
        ld (de),a
        inc d
        djnz prchrwithattr0
        endif
        ld d,c
        ret

inctimeandlife
        ld a,127;9
        ld (curtenseconds),a
        call prtime
inclife2
        call inclife
inclife
;0x06,0x46
;0x47,0x47
        ld hl,lives_chr ;там 0(dead)..5(max)
        ld a,(hl)
        cp 5
        ret nc ;нельзя больше 5
        inc a
        ld (hl),a
        add a,a
        add a,0x40
        ld e,a
        ld d,0x5a
        ld a,0x06
        ld (de),a
        inc e
        ld a,0x46
        ld (de),a
        set 5,e
        ld a,0x47
        ld (de),a
        dec e
        ld (de),a
        ret

incenergy
        ld ix,objects+(6*OBJSIZE)
        ld (energy_bonus),a
         jr nz,$+2+3 ;energy bonus ended?
         res 2,(IX+OBJSIZE+OBJ_FLAGS) ;ended => blink off

        ld a,(energy_mask) ;0b11..10..0 != 0
        scf
        rra
        scf
        rra
        scf
        rra
        scf
        rra
         ;jr $
        ld hl,energy_chr ;может указывать на пустое знакоместо (при mask=0xff)
        jr nc,incenergy_nochr
         ld a,(hl)
         cp 10
         jr z,$+3
         inc (hl)
         ld a,0xf0;0x80
incenergy_nochr
        ld (energy_mask),a
        ld c,a
        ld a,(hl)        
        add a,0x53
        ld e,a
        ld d,0x51;0x50
        ld a,(de)
        or c
        and 0xee ;разлиновка
        dup 7;8
        ld (de),a
        inc d
        edup
        org $-1
        set 5,e
         dec d
        dup 7;8
        ld (de),a
        dec d
        edup
        org $-1
        jp decenergyq

prscore ;вызывается при убийстве монстра (чтобы не перепечатывать всю панель)
        ld de,0x50c8-1
        ld hl,(score)
prnum
        ld bc,10000
        call prscoredig
        ld bc,1000
        call prscoredig
        ld bc,100
        call prscoredig
        ld bc,10
        call prscoredig
        ld bc,1
prscoredig
        ld a,'0'-1
        or a
        inc a
        sbc hl,bc
        jr nc,$-4
        add hl,bc
        push hl
        call prchr
        pop hl
        ret

initgame
        xor a
        ld (level),a
        ;xor a
        ld (levelkeycards),a
        ld hl,takenkeycardslist
        ld (leveltakenkeycardslist_addr),hl
        ld h,a
        ld l,a;0
        ld (levelscore),hl

;restore lives
        call inclife2
        call inclife2
        call inclife
        
        ld hl,leveltakenkeycardslist
        ;ld bc,takenkeycardslist_sz-1
        ;call clearblock ;чистим все, потому что выводить дырки тоже будем на все (длина списка не равна числу имеющихся ключей keycards)
        ;ld hl,levelkilledmonsterslist
        ;ld bc,killedmonsterslist_sz-1
        ld bc,takenkeycardslist_sz+killedmonsterslist_sz-1
        jp clearblock ;можно склеить с предыдущим
       
declivespp
        ;call restoreenergy

        ld hl,objects+(7*OBJSIZE)+OBJ_FLAGS
        set 2,(hl) ;blink (с ним малус не начисляется)
         ;ret ;infinite lives

        ld hl,lives_chr
        ld a,(hl)
        add a,a
        add a,0x40
        ld e,a
        ld d,0x5a
        xor a
        ld (de),a
        inc e
        ld (de),a
        set 5,e
        ld (de),a
        dec e
        ld (de),a
        dec (hl)
        ret nz

         call waitkey_prepareseconds
        
        ;ld hl,(resprscript)
        ;push hl
        ld hl,resprq
        ld (resprscript),hl
        halt
        ;ld hl,(prsprscriptaddr)
        ;push hl
        ld hl,emptyprsprscriptwithmc
        ld (prsprscriptaddr),hl

        ld hl,tgameover
        ld de,0x4810-5
        call prtextwithattr
        ;call promg

         call waitkey_withupdseconds

        ;ld hl,sprscript ;pop hl
        ;ld (prsprscriptaddr),hl
        ;ld hl,resprq ;pop hl
        ;ld (resprscript),hl
updatehiscore_gamemenu
        ld hl,(score)
        ld de,(hiscore)
        or a
        sbc hl,de
        add hl,de
        jr c,$+5 ;не рекорд
        ld (hiscore),hl
        jp gamemenu

waitkey_prepareseconds
        ld a,(cursubsubsecond)
        ld (waitkeycursubsubsecond),a
        ld a,(cursubsecond)
        ld (waitkeycursubsecond),a
        ld a,(cursecond)
        ld (waitkeycursecond),a
        ld a,(curtenseconds)
        ld (waitkeycurtenseconds),a
        ret
waitkey_withupdseconds
gameoverwaitkey0
        call waitkey_haltgetkey
        jr nz,gameoverwaitkey0 ;ждём отпускания кнопок
gameoverwaitkey1
        call waitkey_haltgetkey
        jr z,gameoverwaitkey1
        ;ld a,0xf7
        ;in a,(0xfe)
        ;push af
gameoverwaitkey2
        call waitkey_haltgetkey
        jr nz,gameoverwaitkey2 ;ждём отпускания кнопок
        ;pop af
        ret

restoreseconds
waitkeycursubsubsecond=$+1
        ld a,0
        ld (cursubsubsecond),a
waitkeycursubsecond=$+1
        ld a,0
        ld (cursubsecond),a
waitkeycursecond=$+1
        ld a,0
        ld (cursecond),a
waitkeycurtenseconds=$+1
        ld a,0
        ld (curtenseconds),a
        ret

pausekeeptimer
        ld b,20
        call waitkey_haltgetkey
        djnz $-3
        ret

waitkey_haltgetkey
;kempston тоже, если он выбран в качестве управления
        call restoreseconds
        halt
getkey
         ld a,(fireport)
         cp 0x1f
         jr nz,waitkeynokempston
         in a,(0x1f)
         and 0x1f
         ret nz
waitkeynokempston
        xor a
        in a,(0xfe)
        cpl
        and 0x1f
        ret

addtimebonus
;out: bc=timebonus, de=energybonus
;пусть одна полоска энергии соответствует 50 ("500") очков (как 1/2 убийства звезды)
        ld a,(energy_chr) ;energy=1..10
        ld b,a
        ld de,50
        ld h,d;0
        ld l,d;0
        add hl,de
        djnz $-1
        ;xor a
        ;ld h,a
        ;call mul10add
        ;xor a
        ;call mul10add
        ; srl h
        ; rr l ;energybonus=50..500 ("500..5000")
        ex de,hl       
        ld hl,(curtenseconds)
        ld h,0
        ld a,(cursecond)
        call mul10add
        ld a,(cursubsecond)
        call mul10add
        ld b,h
        ld c,l
        ld hl,(score)
        add hl,bc
        add hl,de
        ld (score),hl
        ret
        
prinfopanel
        ld hl,0x5ac1
        ld de,0x5ac1+1
        ld bc,7
        ld (hl),0x44
        ldir
        ld c,6
        ld (hl),0x47
        ldir
        ld c,11
        ld (hl),0x44
        ldir
        ld c,6-1
        ld (hl),0x47
        ldir
        ld hl,0x5aec
        ld de,0x5aec+1
        ld c,8-1
        ld (hl),0x05
        ldir
        ld (hl),0x47
        ;ld de,0x50c1
        ld hl,tscore
        call prtext
        ;ld hl,(score)
        ;call prnum
        call prscore
        ld hl,thiscore
        call prtext_de
        ld hl,(hiscore)
        call prnum
        ld a,'0'
        call prchr
        
        ;ld de,0x50ec
        ld hl,tlevel
        call prtext
        ld a,(level)
        add a,'0';'1'
        jp prchr

promg
        ld de,0x408e-1
        ld hl,tomg
        call prtextwithattr
        ld de,0x40c6-1;5-1
        ;ld hl,twrongmonster
        call prtextwithattr
        ld de,0x4802-1
        ;ld hl,tkilledwrongmonster
        call prtextwithattr
        ld de,0x4843-1
        ;ld hl,treturn
        jp prtextwithattr

prcongratulations
        ;ld de,0x4008-1
        ld de,0x4028-1
        ld hl,tcongratulations
        call prtextwithattr
        ;ld de,0x4044-1
        ld de,0x4064-1
        call prtextwithattr
        ;ld de,0x4088-1
        ld de,0x40a8-1
        call prtextwithattr
        ;ld de,0x40a5-1
        ld de,0x40e6-1;5-1
        call prtextwithattr
        ;ld de,0x40e5-1
        ld de,0x4825-1
        jp prtextwithattr

clearmenu
        ld hl,0x4800
        ld bc,0x1000-1
        jp clearblock
        ;ld b,128 ;bc,0x1000-1
;clearblock32
;для экрана нельзя ldir, т.к. обработчик прерываний?
        
prmenu
        call clearmenu
        ld hl,0x5922
        ld de,0x5922+1
        ld bc,32*3-2
        ld (hl),5
        ldir
        inc b
        ld (hl),7
        ldir
        ld c,32*4-1
        ld (hl),6
        ldir
        
        ld hl,tmenu
prtext6
        call prtext3
prtext3
        call prtext
prtext2
        call prtext
        jp prtext
        
prcredits
        call clearmenu
        ld hl,0x5902
        ld de,0x5902+1
        ld bc,32*1-4-1
        ld (hl),5
        ldir
        ld hl,0x5940
        ld de,0x5940+1
        ld bc,32*14-1
        ld (hl),7
        ldir
        
        ld hl,thardy
        call prtext6
        jr prtext2

tlevel
        dw 0x50ec-1
        db "LEVEL: ",0
tscore
        dw 0x50c1-1
        db "SCORE: ",0
thiscore
        db "0  HISCORE: ",0
tgameover
        db 0xcf,"GAME OVER",0
ttimeout
        db 0xcf,"TIME OUT!",0
touch
        db 0xcf,"OUCH!!!",0

tlevelcomplete
        dw 0x4089-1
        db "LEVEL COMPLETE!",0
tmonsterskilled
        ;dw 0x47e3-1;2-1
        ;db "ALIENS KILLED: ",0
        dw 0x40e2-1
        db "MONSTERS KILLED: ",0
ttimebonus
        dw 0x4827-1
        db "TIME BONUS: ",0
thealthbonus
        dw 0x4865-1
        db "HEALTH BONUS: ",0

thardy
        dw 0x480c-1
        db "STARRING",0
        dw 0x4842-1
        db "Sgt. Hardy Lil as THE HARDY",0
        dw 0x4885-1
        db "Loopeye Slime as BOSS",0
        dw 0x48c0-1
        db "SAND as producer & pixel artist",0
        dw 0x50ff;-1
        db "ALONE CODER as engineer & coder",0
        dw 0x5042-1
        db "bfox & nq as AY/YM musicians",0
        dw 0x5082-1
        db "KAEL as loadin' screen maker",0
        dw 0x50c0-1
        db "Space Monsters as SPACE MONSTERS",0
        
tmenu
        dw 0x4826-1
        db "PRESS KEYS FOR START",0
        dw 0x48aa-1
        db "1...KEYBOARD",0
        dw 0x48ea-1
        db "2...SINCLAIR",0
        dw 0x502a-1
        db "3...KEMPSTON",0
        dw 0x506a-1
        db "4.....CURSOR",0
        dw 0x50e3-1
        db "MAYhEM & CONSCIENCE, 2019",0;;;;

tomg
        db 0xd7,"OMG!",0
twrongmonster
        ;db 0xc3,"IT WAS NOT THAT ALIEN!",0
        db 0xd7,"IT WAS NOT THAT GUY!",0;;;
tkilledwrongmonster
        ;db 0xc2,"YOU KILLED THE WRONG ALIEN!",0
        db 0xd6,"YOU KILLED A WRONG MONSTER!!",0
treturn
        db 0xcf,"RETURN TO THE BASE, NOW!!!",0

tcongratulations
        db "CONGRATULATIONS!",0
        ;db 0xc6,"YOU'VE SCREWED UP THE TASK",0
        ;db 0xc2,"AND KILLED WRONG MONSTER",0
        ;db 0xc2,"SHITHAPPENS, YEAH...",0
        ;db 0x87,"...TO BE CONTINUED",0
        db 0xc6,"YOU DESTROYED EVERYTHING.",0
        db 0xc2,"YOU ARE THE BEST",0
        db 0xc2,"KILLER IN THE GALAXY.",0
        db 0x87,"...NOW LIVE WITH IT...",0

takenkeycardslist
;список взятых ключей
;mapxy,xy
;в этих местах при отрисовке карты заменим тайл на 0 (метатайлы не трогаем)
;при старте игры там нули
        ds MAXKEYCARDS*2
takenkeycardslist_sz=$-takenkeycardslist
killedmonsterslist ;непосредственно примыкает
;битмаска убитых монстров
;одна карта = один байт
;в этих местах при отрисовке карты не будем делать монстра
        ds MAXKILLEDMONSTERS/8
killedmonsterslist_sz=$-killedmonsterslist

;копии на момент начала уровня:
leveltakenkeycardslist
        ds MAXKEYCARDS*2
levelkilledmonsterslist ;непосредственно примыкает
        ds MAXKILLEDMONSTERS/8

        include "prmacro.asm"
        include "prslwmem.asm"
        
        include "bomb.asm"
        include "moveobj.asm"

;wastilegfx
;        include "hrdtiles.ast" ;0x400
;wastileattr
;        include "hrdtattr.ast" ;0x200

;если тут, то в их адреса попадают в таблицу в обратном порядке (независимо от порядка здесь)
;spr_deadbody_x0=sprhardy0_x0
;spr_deadbody_x2=sprhardy0_x2
;spr_deadbody_x4=sprhardy0_x4
;spr_deadbody_x6=sprhardy0_x6

        include "mapinfo.asm"

panekattr
        incbin "panekattr.mlz"

level
        db 0
monstershere
        dw 0 ;to use hl
monsterskilledhere
        dw 0 ;to use hl
energy_chr
        db 10
lives_chr
        db 5
keycards
        db 0
score
        dw 0
hiscore
        dw 0

        display "mapxy=",$
mapxy
mapx    db 0
mapy    db 0

spr_none
	dw prspr_y0_x0_hgt0

mul10add
;hl=sum
;a=to add
;keep de!!!
        ld b,h
        ld c,l
        add hl,hl
        add hl,hl
        add hl,bc
        add hl,hl ;*10
        ld c,a
        ld b,0
        add hl,bc
        ret

rnd
;keep bc!
;Patrik Rak
rndseed1=$+1
        ld  hl,0xA280   ; xz -> yw
rndseed2=$+1
        ld  de,0xC0DE   ; yw -> zt
        ld  (rndseed1),de  ; x = y, z = w
        ld  a,e         ; w = w ^ ( w << 3 )
        add a,a
        add a,a
        add a,a
        xor e
        ld  e,a
        ld  a,h         ; t = x ^ (x << 1)
        add a,a
        xor h
        ld  d,a
        rra             ; t = t ^ (t >> 1) ^ w
        xor d
        xor e
        ld  h,l         ; y = z
        ld  l,a         ; w = t
        ld  (rndseed2),hl
        ;ex de,hl
        ;ld hl,0
        ;res 7,c ;int
;rnd0
        ;sub c
        ;jr nc,rnd0
        ;add a,c
moveobj_none
reter
        ret

selfmove_movex
        ld hl,(objects+(7*OBJSIZE)+OBJ_DX-1) ;h=dx (-128..127) (реально -MAXSPEED..+MAXSPEED)
        xor a
        sra h
        rra
        sra h
        rra
        sra h
        rra
        add a,(ix+OBJ_XLOW)
        ld (objects+(7*OBJSIZE)+OBJ_XLOW),a
        ld a,(objects+(7*OBJSIZE)+OBJ_X)
        adc a,h
        ld (objects+(7*OBJSIZE)+OBJ_X),a
        ld h,a
        ret
        
selfmove_anim
        ld ix,objects+(7*OBJSIZE)
        ld l,(ix+OBJ_GFX)
	ld a,(timer3flag)
	or a;and 3
	jr z,selfmove_leftrightqq
        inc l
        ld a,l
        and 3
        jr nz,selfmove_leftrightqq ;фаза не >3
        ld a,l
        sub 3 ;фаза 1
        ld l,a ;gfx
selfmove_leftrightqq
        ld (ix+OBJ_GFX),l
        ret
        display "$-selfmove_anim=",$-selfmove_anim
        
         ;ds 110
        display "slowmem before align=",$
        align 256
digitsgfx
        ;ds 10*8
        incbin "digitgfx.bin"
        ds 3 ;остаток цифры 9 (не используется)
        ds 5 ;пустая цифра

timer
	dw 0 ;иногда работаем как с 16бит

clearblock
        ld d,h
        ld e,l
        inc de
        ld (hl),0
        ldir
        ret

panekpix
        incbin "panekpix.mlz"

dde
	inc d
	ld a,d
	and 7
	ret nz
	ld a,e
	add a,32
	ld e,a
	ret c
	ld a,d
	sub 8
	ld d,a
	ret

        display "free slow memory=",ON_INT_test-$
        ds ON_INT_test-$
	
	;if IMVEC!=#3bff
;ON_INT_test
	push af,bc,hl
	ld hl,timer
	inc (hl)
	pop hl,bc,af
	ei
	ret
	;endif

wasint
;ON_INT
;вход = +19t? (Unreal Speccy)
        push af
        push bc
        push de
        push hl
        push ix
        push iy
         if FULL7FFD
         ld bc,0x7ffd
         endif
        if NOEXX
        add hl,hl
        add hl,hl
        ;nop
        ;add hl,hl
        ex af,af'
        push af
        else
        exx
        push bc
        push de
        push hl
        endif
        ld (onintsp),sp
prsprscriptaddr=$+1+ON_INT-wasint
        ld hl,sprscript
        ;ld hl,emptyprsprscript
        ld de,6 ;досюда от входа=161
;+180 от начала кадра
        GOPRSPR
;и так 8 спрайтов
        ;...
;выход - prsprq/nomcq
wasint_sz=$-wasint

;=====================================
	ds 0x8000-$ ;fastmem
        ds 257,ON_INT/256
	;ds ON_INT-$

        display "prsprq=",$
prsprq
;досюда от входа=14009
        ;add hl,de
        ;ld (resprscript),hl ;можно пересчитать ниже
;синхронизатор не ставим, чтобы не терять 8 строк и не получить неудачную разлиновку атрибутов (не с круглого адреса), хотя при клипировании сверху-снизу безразлично - нужно лишнюю треть
        ;...
;мультиколор (128 строк)
        if PENT==0
;при 8 sprites (attr=0xa000) при включенном push iy на 128K остаётся свободно только 9t (28t при FULL7FFD=0)
;на +3 свободно 7t
;на 48K (там на 26 тактов меньше) надо без паузы (на 128K нельзя без паузы) и нельзя FULL7FFD=1
        ld l,0
         ld l,0:jr $+2 ;19t for FULL7FFD=0
        endif
prsprq48
        if PENT
        display "pentagon"
        include "mcpent.asm"
        else
        include "mc.asm"
        endif
        display "after mc=",$
        ld iy,0x0303
        if 1==1
        ld sp,resprscript
        ld hl,resprscript+2
        ld de,4
        else ;общий случай, если подменяем таблицы не атомарно
        ld hl,(prsprscriptaddr)
        ld de,8*6 + 4
        add hl,de
        ld  e,4
        ld sp,hl
         inc l
         inc hl ;+=2
        endif
        ret ;restorer (8 веток yphase)
;стиратель спрайтов=восстановитель тайлов (64 строки? реально больше, т.к. contention? или код восстановителя подогнать под 8t?)
;стирает по продолжению того же скрипта (нельзя два патча - надо один атомарно)
        ;...
;выход - resprq
;остаётся меньше 56 (48 при синхронизаторе) строк на логику, генерацию скрипта вывода и стирания спрайтов, партиклы, [sprite cycling (при 8 спрайтах не нужен?)]

        display "$ before respr=",$
        include "respr1.asm"
        
        display "sprscript=",$
        align 2
sprscript
        dup 8
        dw PAGEOR+0+(prspr_y0&0xff00) ;важно h
        dw gfxspr_no
        dw 0x4800
        edup
sprscript_end
;на выходе включает pgmain, там или ниже должны быть тайлы
prsprqvalueHSB=$+1
        dw PAGEOR+pgmain+(prsprq&0xff00) ;важно h
        dw p_sprq
        ;dw 0 ;не важно
;непосредственно примыкает! желательно fastmem
resprscript
        dup 8
        dw resprq;respr_y0 ;restorer (8 веток yphase)
        dw 0x4800 ;scr
        dw 0x0000 ;tile1_tile2
        dw 0x4800 ;scr
        dw 0x0000 ;tile1_tile2
        dw 0x4800 ;scr
        dw 0x0000 ;tile1_tile2
        edup
resprscript_end
emptyresprscript
        dw resprq

emptyprsprscript
;на выходе включает pgmain, выход в неё
;prsprqvalueHSB=$+1
        dw PAGEOR+pgmain+(nomcq&0xff00) ;важно h
        dw p_nomcq ;выход без восстановления спрайтов
        ;dw 0 ;не важно

p_sprq
prsprqvalue=$
        dw prsprq

p_nomcq
;nomcqvalue=$
        dw nomcq ;выход без восстановления спрайтов

        display "$ before align=",$
        align 256
        include "prspr.asm"

        ;display $,"<= 0xa000"

        display "free before 09d00: ",0x9d00-$
        ds 0x9d00-$
tilemap
        ds 0x100 ;32x8 тайлов ;номера тайлов (16x8) делятся на 4
tileattr
        ;ds 0x200
        include "hrdtattr.ast" ;0x200
;attr
        ds 0x800 ;attrs
        ds 0x400 ;attrs (3rd third) for clipping below

tilegfx
        ;ds 0x400 ;0x400 aligned!!!
        include "hrdtiles.ast" ;0x400

        align 256
tytoscr ;LSB,HSB ;y/2 = 0..64
__=0x4000
      dup 256/32
       dup 8
_=__
        dup 4
         db (_-0x40)&0xff
_=_+256
        edup
__=__+32
       edup
__=__-(8*32)+0x800
      edup
__=0x4000
      dup 256/32
       dup 8
_=__
        dup 4
         db _/256
_=_+0x200
        edup
__=__+32
       edup
__=(__-(8*32)+0x800)&0x4fff
      edup

        align 256 ;сразу после tytoscr!!!
;gfxdescr ;gfxLSB,gfxHSB,pg
;для каждого спрайта 4 записи: X=0, X=2, X=1, X=3
;размер графики спрайта зависит от высоты
        db sprhardyl0_x0&0xff;gfxspr0&0xff
        db sprhardyl0_x4&0xff
        db sprhardyl0_x2&0xff
        db sprhardyl0_x6&0xff
        db sprhardyl1_x0&0xff;gfxspr0&0xff
        db sprhardyl1_x4&0xff
        db sprhardyl1_x2&0xff
        db sprhardyl1_x6&0xff
        db sprhardyl2_x0&0xff;gfxspr0&0xff
        db sprhardyl2_x4&0xff
        db sprhardyl2_x2&0xff
        db sprhardyl2_x6&0xff
        db sprhardyl3_x0&0xff;gfxspr0&0xff
        db sprhardyl3_x4&0xff
        db sprhardyl3_x2&0xff
        db sprhardyl3_x6&0xff
        db sprhardyr0_x0&0xff;gfxspr0&0xff
        db sprhardyr0_x4&0xff
        db sprhardyr0_x2&0xff
        db sprhardyr0_x6&0xff
        db sprhardyr1_x0&0xff;gfxspr0&0xff
        db sprhardyr1_x4&0xff
        db sprhardyr1_x2&0xff
        db sprhardyr1_x6&0xff
        db sprhardyr2_x0&0xff;gfxspr0&0xff
        db sprhardyr2_x4&0xff
        db sprhardyr2_x2&0xff
        db sprhardyr2_x6&0xff
        db sprhardyr3_x0&0xff;gfxspr0&0xff
        db sprhardyr3_x4&0xff
        db sprhardyr3_x2&0xff
        db sprhardyr3_x6&0xff
        
        db sprcalmarl0_x0&0xff;gfxspr0&0xff
        db sprcalmarl0_x4&0xff
        db sprcalmarl0_x2&0xff
        db sprcalmarl0_x6&0xff
        db sprcalmarl1_x0&0xff;gfxspr0&0xff
        db sprcalmarl1_x4&0xff
        db sprcalmarl1_x2&0xff
        db sprcalmarl1_x6&0xff
        db sprcalmarr0_x0&0xff;gfxspr0&0xff
        db sprcalmarr0_x4&0xff
        db sprcalmarr0_x2&0xff
        db sprcalmarr0_x6&0xff
        db sprcalmarr1_x0&0xff;gfxspr0&0xff
        db sprcalmarr1_x4&0xff
        db sprcalmarr1_x2&0xff
        db sprcalmarr1_x6&0xff
        
        db sprredl0_x0&0xff;gfxspr0&0xff
        db sprredl0_x4&0xff
        db sprredl0_x2&0xff
        db sprredl0_x6&0xff
        db sprredl1_x0&0xff;gfxspr0&0xff
        db sprredl1_x4&0xff
        db sprredl1_x2&0xff
        db sprredl1_x6&0xff
        db sprredr0_x0&0xff;gfxspr0&0xff
        db sprredr0_x4&0xff
        db sprredr0_x2&0xff
        db sprredr0_x6&0xff
        db sprredr1_x0&0xff;gfxspr0&0xff
        db sprredr1_x4&0xff
        db sprredr1_x2&0xff
        db sprredr1_x6&0xff
        
        db sprpinkl0_x0&0xff;gfxspr0&0xff
        db sprpinkl0_x4&0xff
        db sprpinkl0_x2&0xff
        db sprpinkl0_x6&0xff
        db sprpinkl1_x0&0xff;gfxspr0&0xff
        db sprpinkl1_x4&0xff
        db sprpinkl1_x2&0xff
        db sprpinkl1_x6&0xff
        db sprpinkr0_x0&0xff;gfxspr0&0xff
        db sprpinkr0_x4&0xff
        db sprpinkr0_x2&0xff
        db sprpinkr0_x6&0xff
        db sprpinkr1_x0&0xff;gfxspr0&0xff
        db sprpinkr1_x4&0xff
        db sprpinkr1_x2&0xff
        db sprpinkr1_x6&0xff
        
        db sprwhitel0_x0&0xff;gfxspr0&0xff
        db sprwhitel0_x4&0xff
        db sprwhitel0_x2&0xff
        db sprwhitel0_x6&0xff
        db sprwhitel1_x0&0xff;gfxspr0&0xff
        db sprwhitel1_x4&0xff
        db sprwhitel1_x2&0xff
        db sprwhitel1_x6&0xff
        db sprwhiter0_x0&0xff;gfxspr0&0xff
        db sprwhiter0_x4&0xff
        db sprwhiter0_x2&0xff
        db sprwhiter0_x6&0xff
        db sprwhiter1_x0&0xff;gfxspr0&0xff
        db sprwhiter1_x4&0xff
        db sprwhiter1_x2&0xff
        db sprwhiter1_x6&0xff
        
        db sprboss0_x0&0xff;gfxspr0&0xff
        db sprboss0_x4&0xff
        db sprboss0_x2&0xff
        db sprboss0_x6&0xff
        db sprboss1_x0&0xff;gfxspr0&0xff
        db sprboss1_x4&0xff
        db sprboss1_x2&0xff
        db sprboss1_x6&0xff
        db sprboss2_x0&0xff;gfxspr0&0xff
        db sprboss2_x4&0xff
        db sprboss2_x2&0xff
        db sprboss2_x6&0xff
        db sprboss3_x0&0xff;gfxspr0&0xff
        db sprboss3_x4&0xff
        db sprboss3_x2&0xff
        db sprboss3_x6&0xff
        
        db sprbosseye0_x0&0xff;gfxspr0&0xff
        db sprbosseye0_x4&0xff
        db sprbosseye0_x2&0xff
        db sprbosseye0_x6&0xff
        db sprbosseye1_x0&0xff;gfxspr0&0xff
        db sprbosseye1_x4&0xff
        db sprbosseye1_x2&0xff
        db sprbosseye1_x6&0xff
        db sprbosseye2_x0&0xff;gfxspr0&0xff
        db sprbosseye2_x4&0xff
        db sprbosseye2_x2&0xff
        db sprbosseye2_x6&0xff
        db sprbosseye3_x0&0xff;gfxspr0&0xff
        db sprbosseye3_x4&0xff
        db sprbosseye3_x2&0xff
        db sprbosseye3_x6&0xff
        
        db sprsosulka0_x0&0xff;gfxspr0&0xff
        db sprsosulka0_x4&0xff
        db sprsosulka0_x2&0xff
        db sprsosulka0_x6&0xff
        
        db sprwhitel0_x0&0xff;gfxspr0&0xff
        db sprwhitel0_x4&0xff
        db sprwhitel0_x2&0xff
        db sprwhitel0_x6&0xff

        db spr_none&0xff
        db spr_none&0xff
        db spr_none&0xff
        db spr_none&0xff
        
        db sprhardyr3_x0&0xff;gfxspr0&0xff
        db sprhardyr3_x4&0xff
        db sprhardyr3_x2&0xff
        db sprhardyr3_x6&0xff

        db sprcalmarr0_x0&0xff;gfxspr0&0xff
        db sprcalmarr0_x4&0xff
        db sprcalmarr0_x2&0xff
        db sprcalmarr0_x6&0xff

        db sprredr0_x0&0xff;gfxspr0&0xff
        db sprredr0_x4&0xff
        db sprredr0_x2&0xff
        db sprredr0_x6&0xff

        db sprpinkr0_x0&0xff;gfxspr0&0xff
        db sprpinkr0_x4&0xff
        db sprpinkr0_x2&0xff
        db sprpinkr0_x6&0xff

        db sprwhiter0_x0&0xff;gfxspr0&0xff
        db sprwhiter0_x4&0xff
        db sprwhiter0_x2&0xff
        db sprwhiter0_x6&0xff

        db spr_none&0xff
        db spr_none&0xff
        db spr_none&0xff
        db spr_none&0xff
        
        ds ($+255)/256*256-$
        db sprhardyl0_x0/256;gfxspr0/256
        db sprhardyl0_x4/256
        db sprhardyl0_x2/256
        db sprhardyl0_x6/256
        db sprhardyl1_x0/256;gfxspr0/256
        db sprhardyl1_x4/256
        db sprhardyl1_x2/256
        db sprhardyl1_x6/256
        db sprhardyl2_x0/256;gfxspr0/256
        db sprhardyl2_x4/256
        db sprhardyl2_x2/256
        db sprhardyl2_x6/256
        db sprhardyl3_x0/256;gfxspr0/256
        db sprhardyl3_x4/256
        db sprhardyl3_x2/256
        db sprhardyl3_x6/256
        db sprhardyr0_x0/256;gfxspr0/256
        db sprhardyr0_x4/256
        db sprhardyr0_x2/256
        db sprhardyr0_x6/256
        db sprhardyr1_x0/256;gfxspr0/256
        db sprhardyr1_x4/256
        db sprhardyr1_x2/256
        db sprhardyr1_x6/256
        db sprhardyr2_x0/256;gfxspr0/256
        db sprhardyr2_x4/256
        db sprhardyr2_x2/256
        db sprhardyr2_x6/256
        db sprhardyr3_x0/256;gfxspr0/256
        db sprhardyr3_x4/256
        db sprhardyr3_x2/256
        db sprhardyr3_x6/256

        db sprcalmarl0_x0/256;gfxspr0/256
        db sprcalmarl0_x4/256
        db sprcalmarl0_x2/256
        db sprcalmarl0_x6/256
        db sprcalmarl1_x0/256;gfxspr0/256
        db sprcalmarl1_x4/256
        db sprcalmarl1_x2/256
        db sprcalmarl1_x6/256
        db sprcalmarr0_x0/256;gfxspr0/256
        db sprcalmarr0_x4/256
        db sprcalmarr0_x2/256
        db sprcalmarr0_x6/256
        db sprcalmarr1_x0/256;gfxspr0/256
        db sprcalmarr1_x4/256
        db sprcalmarr1_x2/256
        db sprcalmarr1_x6/256

        db sprredl0_x0/256;gfxspr0/256
        db sprredl0_x4/256
        db sprredl0_x2/256
        db sprredl0_x6/256
        db sprredl1_x0/256;gfxspr0/256
        db sprredl1_x4/256
        db sprredl1_x2/256
        db sprredl1_x6/256
        db sprredr0_x0/256;gfxspr0/256
        db sprredr0_x4/256
        db sprredr0_x2/256
        db sprredr0_x6/256
        db sprredr1_x0/256;gfxspr0/256
        db sprredr1_x4/256
        db sprredr1_x2/256
        db sprredr1_x6/256

        db sprpinkl0_x0/256;gfxspr0/256
        db sprpinkl0_x4/256
        db sprpinkl0_x2/256
        db sprpinkl0_x6/256
        db sprpinkl1_x0/256;gfxspr0/256
        db sprpinkl1_x4/256
        db sprpinkl1_x2/256
        db sprpinkl1_x6/256
        db sprpinkr0_x0/256;gfxspr0/256
        db sprpinkr0_x4/256
        db sprpinkr0_x2/256
        db sprpinkr0_x6/256
        db sprpinkr1_x0/256;gfxspr0/256
        db sprpinkr1_x4/256
        db sprpinkr1_x2/256
        db sprpinkr1_x6/256

        db sprwhitel0_x0/256;gfxspr0/256
        db sprwhitel0_x4/256
        db sprwhitel0_x2/256
        db sprwhitel0_x6/256
        db sprwhitel1_x0/256;gfxspr0/256
        db sprwhitel1_x4/256
        db sprwhitel1_x2/256
        db sprwhitel1_x6/256
        db sprwhiter0_x0/256;gfxspr0/256
        db sprwhiter0_x4/256
        db sprwhiter0_x2/256
        db sprwhiter0_x6/256
        db sprwhiter1_x0/256;gfxspr0/256
        db sprwhiter1_x4/256
        db sprwhiter1_x2/256
        db sprwhiter1_x6/256

        db sprboss0_x0/256;gfxspr0&0xff
        db sprboss0_x4/256
        db sprboss0_x2/256
        db sprboss0_x6/256
        db sprboss1_x0/256;gfxspr0&0xff
        db sprboss1_x4/256
        db sprboss1_x2/256
        db sprboss1_x6/256
        db sprboss2_x0/256;gfxspr0&0xff
        db sprboss2_x4/256
        db sprboss2_x2/256
        db sprboss2_x6/256
        db sprboss3_x0/256;gfxspr0&0xff
        db sprboss3_x4/256
        db sprboss3_x2/256
        db sprboss3_x6/256

        db sprbosseye0_x0/256;gfxspr0&0xff
        db sprbosseye0_x4/256
        db sprbosseye0_x2/256
        db sprbosseye0_x6/256
        db sprbosseye1_x0/256;gfxspr0&0xff
        db sprbosseye1_x4/256
        db sprbosseye1_x2/256
        db sprbosseye1_x6/256
        db sprbosseye2_x0/256;gfxspr0&0xff
        db sprbosseye2_x4/256
        db sprbosseye2_x2/256
        db sprbosseye2_x6/256
        db sprbosseye3_x0/256;gfxspr0&0xff
        db sprbosseye3_x4/256
        db sprbosseye3_x2/256
        db sprbosseye3_x6/256

        db sprsosulka0_x0/256;gfxspr0&0xff
        db sprsosulka0_x4/256
        db sprsosulka0_x2/256
        db sprsosulka0_x6/256
        
        db sprwhitel0_x0/256;gfxspr0/256
        db sprwhitel0_x4/256
        db sprwhitel0_x2/256
        db sprwhitel0_x6/256

        db spr_none/256
        db spr_none/256
        db spr_none/256
        db spr_none/256

        db sprhardyr3_x0/256;gfxspr0/256
        db sprhardyr3_x4/256
        db sprhardyr3_x2/256
        db sprhardyr3_x6/256

        db sprcalmarr0_x0/256;gfxspr0/256
        db sprcalmarr0_x4/256
        db sprcalmarr0_x2/256
        db sprcalmarr0_x6/256

        db sprredr0_x0/256;gfxspr0/256
        db sprredr0_x4/256
        db sprredr0_x2/256
        db sprredr0_x6/256

        db sprpinkr0_x0/256;gfxspr0/256
        db sprpinkr0_x4/256
        db sprpinkr0_x2/256
        db sprpinkr0_x6/256

        db sprwhiter0_x0/256;gfxspr0/256
        db sprwhiter0_x4/256
        db sprwhiter0_x2/256
        db sprwhiter0_x6/256

        db spr_none/256
        db spr_none/256
        db spr_none/256
        db spr_none/256

        ds ($+255)/256*256-$
        
       if SPRPAGED
        dup 256
        db pgspr+PAGEOR
        edup
       endif

HARDYSPRTURN=4
HARDYSPRTURNBIT=2
SPRTURN=2
SPRTURNBIT=1

ID_HARDYLEFT=0
ID_HARDYRIGHT=4
ID_CALMAR=8 ;..9 (10..11 right)
ID_RED=12 ;+0..3
ID_PINK=16 ;+0..3
ID_WHITE=20 ;+0..3
ID_BOSS=24
ID_BOSSEYE=28
ID_SOSULKA=32 ;начиная отсюда не реагируют на взрыв
ID_BOSSPROJECTILE=33
ID_HARDYBLINK=34
ID_DEAD=35 ;начиная отсюда все неживые
ID_CALMARDEAD=ID_DEAD+1
ID_REDDEAD=ID_DEAD+2
ID_PINKDEAD=ID_DEAD+3
ID_WHITEDEAD=ID_DEAD+4
ID_NONE=ID_DEAD+5

OBJSIZE=11+(4+3+3)
OBJ_X=0;x
OBJ_Y=OBJ_X+1;y/2
OBJ_GFX=OBJ_Y+1;gfxdescraddrLSB/4
OBJ_DX=OBJ_GFX+1;x/2
OBJ_DY=4;y/2
OBJ_XLOW=5
;OBJ_YLOW=OBJ_XLOW+1
OBJ_HEALTH=6
OBJ_FLAGS=7 ;b0=on ground, b1=jump not released, b2=blinking, b4=провалиться
OBJ_MINX=8;
OBJ_MAXX=9;
OBJ_NUMBERMASK=10;
OBJ_PROC=11
OBJ_PROC_ADDR=OBJ_PROC+4+1
	macro OBJDB x,y,gfx,dx,dy,minx,maxx
_=$
        db x
        db y
        db gfx
	db dx
	db dy
        db 0
        db 100
        db 0 ;flags
        db minx
        db maxx
        db __ ;OBJ_NUMBERMASK
        ld ix,_
        call moveobj
        jp $+3+OBJ_PROC
__=__/2
	endm
objects
__=0x80 ;OBJ_NUMBERMASK
        dup 7
	OBJDB 0,0,ID_NONE,1,0,10,70
        edup
        org $-6
        if EDITOR
        call moveobj_editor
        else
        call moveobj_none
        endif
movehero_addr=$+1
        jp movemainobj ;TODO разные процедуры (фазы шага, смерть...)
	OBJDB 0,0,ID_HARDYRIGHT,0,0,0,0 ;hero
                  ;54 max for hgt=18

        ;include "scroll.asm"
        include "ayfxplay.asm"
sfx
        incbin "sfx.afb"

emptyprsprscriptwithmc
        dup 8
        dw PAGEOR+0+(prspr_y0&0xff00) ;важно h
        dw gfxspr_no
        dw 0x4000
        edup
prsprqvalueHSB2=$+1
        dw PAGEOR+pgmain+(prsprq&0xff00) ;важно h
        dw p_sprq
        
gfxspr_no
        dw prspr_y0_x0_hgt0 ;важно l (т.е. y0 не важит)
        
        if 1==0
gfxspr0
        dw prspr_y0_x0_hgt18 ;важно l (т.е. y0 не важит)
        dup 9*10
        db $&0xff
        edup
gfxspr1
        dw prspr_y0_x0_hgt18 ;важно l (т.е. y0 не важит)
        dup 9*10
        db $&0xff
        edup
gfxspr2
        dw prspr_y0_x4_hgt18 ;важно l (т.е. y0 не важит)
        dup 9*10
        db $&0xff
        edup
gfxspr3
        dw prspr_y0_x4_hgt18 ;важно l (т.е. y0 не важит)
        dup 9*10
        db $&0xff
        edup
        endif

        macro PRDIGIT
        ld a,(hl)
        inc l
        ld (de),a ;нижняя линия
        dec d
        ld a,(hl)
        inc l
        dup 6
        ld (de),a ;нижнее очко
        dec d
        edup
        org $-1
        res 5,e
        inc d
        ld a,(hl)
        inc l
        ld (de),a ;верхняя линия
        inc d
        ld a,(hl)
        inc l
       dup 5
        ld (de),a ;верхнее очко
        inc d
       edup
        ld a,(hl)
        ld (de),a ;средняя линия
        endm

ayplay
        ld sp,IMSTACK;0x4822;0x4002
curpgmuz=$+1
        ld a,pgmuz0+PAGEOR
        ;ld bc,0x7ffd
        ;out (c),a
        out (0xfd),a ;+28
muzplayaddr=$+1
        call reter;0xc003 ;+1271
        ld a,pgmain+PAGEOR
        ;ld bc,0x7ffd
        ;out (c),a
        out (0xfd),a ;+18 = 1317 = 62*21 + 15

        if PENT
        call counttime ;+sfx
        jp muzq
counttime
        endif
        ;jr $
counttime_callsfx_addr=$+1
        call SFXFRAME ;/muzq, чтобы не показывать цифры

cursubsubsecond=$+1
        ld a,4
       if PENT
        sub 1
        jr c,$+4
        jr nc,$+4
        ld a,4
        ld (cursubsubsecond),a
       else
        sub 1
        jr nc,$+4
        ld a,4
        ld (cursubsubsecond),a
        jp nc,muzq ;ret nc
       endif
        ld h,digitsgfx/256
cursubsecond=$+1
        ld a,0
       if PENT
        sbc a,0
        jr c,$+4
        jr nc,$+4
        ld a,9
        ld (cursubsecond),a
       else
        sbc a,0
        jr nc,$+4
        ld a,9
        ld (cursubsecond),a
        jr nc,counttime_prsubsecond
       endif
         ld c,a
cursecond=$+1
        ld a,0        
       if PENT
        sbc a,0
        jr c,$+4
        jr nc,$+4
        ld a,9
        ld (cursecond),a
       else
        sbc a,0
        jr nc,$+4
        ld a,9
        ld (cursecond),a
        jr nc,counttime_prsecond
       endif
         ld b,a
curtenseconds=$+1
        ld a,5
        sbc a,0
        jr c,$+4
        jr nc,$+4
        ld a,-1;10;9 ;TODO game over
        ld (curtenseconds),a
        ld a,(curtenseconds)
        add a,a
        add a,a
        add a,a
        ;add a,a
        ld l,a
        ld de,0x566e
        PRDIGIT
         ld a,b;ld a,(cursecond)
counttime_prsecond
        add a,a
        add a,a
        add a,a
        ;add a,a
        ld l,a
        ld de,0x566f
        PRDIGIT
         ld a,c;ld a,(cursubsecond)
counttime_prsubsecond
        add a,a
        add a,a
        add a,a
        ;add a,a
        ld l,a
        ld de,0x5671
        PRDIGIT
       if PENT
        ret
       else
        jp muzq
       endif

inctimermuzq
        ld hl,(timer)
        inc hl
        ld (timer),hl
        ;ld hl,timer+1
        ;ld a,(hl)
        ;add a,0x80
        ;ld (hl),a
        ;dec hl
        ;jr nc,$+3
        ;inc (hl)
        jp muzq

maingo
	;jp mainTK90X
	ei
	halt
	
        if PENT==0
	ld hl,(timer)
	push hl
	ld h,0
	ld d,h
	ld bc,3400
	ldir
	
	pop de
	ld hl,(timer)
	or a
	sbc hl,de
	jr z,mainpent

	ld hl,(timer)
	push hl
	ld h,0
	ld d,h
	ld bc,3300
	ldir
	pop de
	ld hl,(timer)
	or a
	sbc hl,de
	;nz=48K/ATM, z=128K
	jr nz,main48k

        call test128
	;z=TK90X, nz=128K
	jr z,mainTK90X
main128
	 ;ld a,1
	 ;out (#fe),a
	;ld hl,295-1 -78
	;ld (waits),hl
	;ld hl,tmc128
	;ld (mkmcdata),hl
	;ld hl,mc0t
	;ld (mainmc),hl
	jr main48kq
mainTK90X
	 ;ld a,3
	 ;out (#fe),a
	;ld hl,295-1 +8 +4 -78
	;ld (waits),hl
	;ld hl,tmc128
	;ld (mkmcdata),hl
	;ld hl,mc10t
	;ld (mainmc),hl
	jr main48kq
main48k
	;ld bc,#7ffd
	;ld h,c
        ;ld l,c
	;ld de,#1011
	;out (c),d
	;ld (hl),c ;#fd
	;out (c),e
	;dec (hl)
	;ld a,(hl)
	;out (c),d
	;cp (hl)
	;z=48K, nz=ATM (Harlequin 128K - fail!)
	ei
	halt
	ld hl,(timer)
	push hl
	ld h,#40
	ld d,h
        ld e,l
	ld bc,3300
	ldir
	pop de
	ld hl,(timer)
	or a
	sbc hl,de
	;nz=48K, z=ATM
        jr z,mainatm
        ld hl,prsprq48
        ld (prsprqvalue),hl
        ld a,h
        ld (prsprqvalueHSB),a
        ld (prsprqvalueHSB2),a
	jr main48kq
mainatm
	;ld hl,434-138 -78
	jr mainpenthl
        endif
mainpent
	 ;ld a,2
	 ;out (#fe),a
	;ld hl,434 -78
mainpenthl
	;ld (waits),hl
	;ld hl,tmcpent;tmc128
	;ld (mkmcdata),hl

main48kq
        if 1==1
        ei
        halt
        ld hl,wasint
        ld de,ON_INT
        ld bc,wasint_sz
        ldir
        else

        if IMVEC==0x3bff
       ld hl,ON_INT
       ld (#fff5),hl
	else
       ;ld hl,ON_INT
       ;ld (IMVEC),hl
       ld hl,IMVEC&0xff00
       ld (hl),ON_INT/256
       inc l
       jr nz,$-3
       inc h
       ld (hl),ON_INT/256
        endif
        endif

	if 1==0
        ld hl,attr
        ld b,MCHGT*4
clsmc0
        push bc
        push hl
        ld a,MCHGT*4
        sub b
        and 7
        add a,a
        add a,a
        add a,a
        ld c,a
        ld b,32
clsmc1
        ;ld a,r
        ld (hl),0;c
        inc hl
        djnz clsmc1
        pop hl
        call downhlattr
        pop bc
        djnz clsmc0
	endif

        if TIMERWAITLOGIC
        ld a,(timer)
        ld (oldtimer),a
        endif

        jr gamemenugo

        if PENT
muztormoz
;заменяет музыку (длится столько же по времени)
        if 1==1 ;bfox's player
        ld b,95+13
        djnz $
        nop
        else ;TmK's player
        ld b,95
        djnz $
        ld a,(hl)
        endif
        ret
        endif

iniplay        
        halt
        ld (curpgmuz),a
        if PENT
        ld (curpgmuz_mc),a
        endif
        ;ld bc,0x7ffd
        ;out (c),a
        out (0xfd),a
iniplayaddr=$+1
      	call reter;0xc000 ;ini player
        ld a,pgmain+PAGEOR
        ;ld bc,0x7ffd
        ;out (c),a
        out (0xfd),a
        ret
gamemenu
        display "gamemenu=",$
        ld a,pgmuz0+PAGEOR
        call iniplay
gamemenugo
        ld sp,STACK;0x6000
        ld (mainloopsp),sp

         ld hl,0
         ld (timer),hl

        ;ld hl,sprscript ;pop hl
        ;ld (prsprscriptaddr),hl
        ;ld hl,resprq ;pop hl
        ;ld (resprscript),hl

         call waitkey_prepareseconds
        call initgame
        
        ld hl,emptyprsprscript ;выход без мультиколора и восстановления спрайтов
        ld (prsprscriptaddr),hl

        ld hl,inctimermuzq
        ld (counttime_callsfx_addr),hl ;чтобы не показывать цифры

        ld hl,0x4000
        push hl
        ld bc,0x1aff
        call clearblock ;не ldir! т.к. обработчик прерывания портит экран в невидимых местах, а размазывать нельзя
        ;ld b,192+24 ;bc,0x1aff
        ;call clearblock32 ;не ldir! т.к. обработчик прерывания портит экран в невидимых местах, а размазывать нельзя

        ;call clwindow

        ;jr $
        ld hl,logopix
        pop de ;ld de,0x4000
        call unpack
        ld hl,logoattr
        ld de,0x5800
        call unpack

        ld d,0x55;ld hy,0
        jr gamemenu_switch0go
gamemenu_switch0
         ld hl,0
         ld (timer),hl
gamemenu_switch0go
         ;inc hy
         ;ld a,hy
         ;rra
         rrc d
         push de
         push af
        call c,prmenu
         pop af
        call nc,prcredits
         pop de
gamemenu0
        ;ld hx,64*3
         ;call waitkey_withupdseconds
gamemenuwaitkey1
         ld hl,(timer)
         ld a,l
         rr h
         rra
         ;ld a,(timer)
         cp 10*16
         ;dec hx
         jr nc,gamemenu_switch0
        call waitkey_haltgetkey
        jr z,gamemenuwaitkey1
        if 1==1
;1 keyboard
;2 sinclair
;3 kempston
;4 cursor
        ld a,0xf7
        in a,(0xfe)
        ld bc,topqakeys
        rra
        jr nc,dosetkeys
        ld bc,tsinclairkeys
        rra
        jr nc,dosetkeys
        ld bc,tkempstonkeys
        rra
        jr nc,dosetkeys
        ld bc,tcursorkeys
        rra
        ;jr nc,dosetkeys
        jr c,gamemenu0
dosetkeys
        call setkeys

        endif

        ld hl,panekpix
        ld de,0x5000
        call unpack
        ld hl,panekattr
        ld de,0x5a00
        call unpack
        ld hl,0x5800
        ld bc,0x1ff
        call clearblock

        ld hl,SFXFRAME
        ld (counttime_callsfx_addr),hl ;чтобы показывать цифры

        ld hl,sprscript ;pop hl
        ld (prsprscriptaddr),hl
        ld hl,resprq ;pop hl
        ld (resprscript),hl
        
        call initgame
        ;ld hl,movemainobj
        ;ld (movehero_addr),hl
        ld a,0x3a
        ld (mainloop_patch),a
        ld hl,ndots
        ld (mainloop_patch+1),hl
        ld a,pgmuz1+PAGEOR ;easy music
        call iniplay
restartlevel
        call initlevel
        jr mainloop
;----------------------------------
ouch
;сюда попадаем из declives
        call loselife_settime

        ld hl,touch
        ld de,0x40ec
        call prtextwithattr
        jr waitrestartlevel
outoftime
        call loselife_settime

        ld hl,ttimeout
        ld de,0x40cb
        call prtextwithattr
        
        call declivespp ;может переходить с гамовером на gamemenu
waitrestartlevel
         call waitkey_prepareseconds
         call waitkey_withupdseconds
        ;ld hl,sprscript ;pop hl
        ;ld (prsprscriptaddr),hl
        ;ld hl,resprq ;pop hl
        ;ld (resprscript),hl
        jr restartlevel

loselife_settime
        ld a,4
        ld (cursubsubsecond),a
        xor a
        ld (cursubsecond),a
        ld (cursecond),a
        ld (curtenseconds),a
        call prtime ;чтобы увидеть время на резинке
        ld hl,resprq
        ld (resprscript),hl
        halt
        ld hl,emptyprsprscriptwithmc
        ld (prsprscriptaddr),hl
        ret

decenergyq

        if TIMERWAITLOGIC
        pop af
        dec a
        jp nz,logic0
        endif

        if BORDER
	xor a
	out (0xfe),a
        endif

	;ld hl,0
	;ld de,0
	;ld bc,115 ;130 OK for 128K, 115 for 48K, 66 for Pentagon!!!
	;ldir
	
        if 1==0
        ld a,r
        and 15
        jr z,$+2
        and 7
        jr z,mainloop
        ld ix,0
        rl (ix) ;проверка настройки мультиколора на вшивость
        endif
        
        ;jp mainloop
mainloop
        ;dup 10
        halt
        ;edup
;сейчас на экране спрайтов нет, они отрисованы, показаны и уже стёрты в обработчике прерывания
	;ld hl,scrollupscript
	;ld (prsprscript),hl
        if BORDER
	ld a,2
	out (0xfe),a
        endif

        ld hl,timer
        inc (hl) ;можно ниже мультиколора
	ld a,(hl)
        and 3
        sub 1
        sbc a,a
        and 1
        ld (timer3flag),a

         ld a,(curtenseconds)
         rla
         jr c,outoftime;restartlevel

        ld sp,sprscript_end
        ;call genprscript ;нельзя прерывать!
        include "genscrpt.asm"
	ld sp,resprscript_end
	;call genrescript ;нельзя прерывать!
        include "genscrre.asm"
mainloopsp=$+1
        ld sp,0
        
mainloop_patch=$ ;здесь может быть jp selfmove
        ld a,(ndots)
        or a
        call nz,redots
        ;call refire
refire_scrdata=$+1
        ld hl,0
refire_scraddr=$+1
        ld (0),hl
         ;ld a,(scraddr)
         ;sub 0x40
         ;cp 0x18
         ;jr c,$
        
	;call control ;среди всего прочего сначала создадим пулю, ниже будем её двигать
;control
	ld ix,objects+(7*OBJSIZE) ;hero
	ld hl,(objects+(7*OBJSIZE)+OBJ_GFX) ;GFX, DX
fireld=$+1
        ld a,0xef
fireport=$+1
        in a,(0xfe)
fireand=$+1
        and 1
        ;rra
        ;jp c,control_nofire
        jr nz,control_nofire
        ;ld e,a
        ld a,(fireyx_x) ;(fire_scraddr+1)
        or a
        jp nz,control_fireq ;старая пуля ещё летит
;берём координаты героя и рассчитываем, в каких координатах у него пушка
        ld a,(objects+(7*OBJSIZE)+OBJ_Y) ;y/2
        add a,6
        ld (fireyx_y),a
         add a,2;3
         ld (firecollision_firey),a
        ld a,(objects+(7*OBJSIZE)+OBJ_X) ;x/2
        add a,2 ;add a,3
        ld (fireyx_x),a        
        bit HARDYSPRTURNBIT,l
        ld a,8;4
        jr nz,$+4
        ld a,-8;-4
        ld (movefire_direction_dx),a
         push hl
         ld a,0
         call SFXPLAY
         pop hl
control_fireq
        ;ld a,e
control_nofire
upld=$+1
        ld a,0xef
upport=$+1
        in a,(0xfe)
upand=$+1
        and 2
        ;rra ;u
        ;jr c,control_noup
        jr nz,control_noup
         bit 0,(ix+OBJ_FLAGS) ;on ground?
         jr z,control_upq ;no
         bit 1,(ix+OBJ_FLAGS) ;jump has been released?
         jr nz,control_upq ;no
         res 0,(ix+OBJ_FLAGS) ;not on ground
       if SLOWJUMP
       ;ld e,a
       xor a
       ld (timer),a ;костыль!!!
       ld (timer3flag),a ;костыль!!!
       ;ld a,e
        ld (ix+OBJ_DY),-3
       else
       and 0xfe ;or 1
       ld (timer),a ;костыль!!!
       inc a
        ld (ix+OBJ_DY),-5
        endif
         set 1,(ix+OBJ_FLAGS) ;jump has not been released
        jp control_upq
control_noup
         res 1,(ix+OBJ_FLAGS) ;jump has been released
control_upq
downld=$+1
        ld a,0xef
downport=$+1
        in a,(0xfe)
downand=$+1
        and 4
        ;rra ;d
        ;jp c,control_nodown
        jr nz,control_nodown
         set 4,(ix+OBJ_FLAGS) ;drop
         ;ld (ix+OBJ_DY),2 ;нельзя для шипов
control_nodown
rightld=$+1
         ld a,0xef
rightport=$+1
         in a,(0xfe)
rightand=$+1
         and 8
        ;rra ;r
        ;jr c,control_noright
        jr nz,control_noright
        set HARDYSPRTURNBIT,l
        ld a,h
        inc a ;add a,1;2
        cp MAXSPEED
        jp p,control_leftrightok;$+4 ;dx>=MAXSPEED
        ld h,a        
        jp control_leftrightok
control_noleft
;если на земле, то dx=0
        bit 0,(ix+OBJ_FLAGS)
        jr z,control_leftrightqq ;не на земле
        ;sra h ;dx
        ; bit 0,h
        ; jr z,$+4
         ld h,0 ;dx
        ld a,l ;gfx
        and 0xfc ;стоим
        jp control_leftrightq
control_noright
leftld=$+1
         ld a,0xef
leftport=$+1
         in a,(0xfe)
leftand=$+1
         and 16
        ;rra ;l
        ;jr c,control_noleft
        jr nz,control_noleft
        res HARDYSPRTURNBIT,l
        ld a,h
        dec a ;sub 1;2
        cp -(MAXSPEED-1)
        jp m,$+4 ;dx<=-MAXSPEED
        ld h,a        
control_leftrightok
;двигать ногами (0..2 в мл. битах)
;если кнопки не нажаты, можно ноги не двигать
	ld a,(timer3flag)
	or a;and 3
	jr z,control_leftrightqq
        inc l
        ld a,l
        and 3
        jr nz,control_leftrightqq ;фаза не >3
        ld a,l
        sub 3 ;фаза 1
;control_noanim
control_leftrightq
        ld l,a ;gfx
control_leftrightqq
	ld (objects+(7*OBJSIZE)+OBJ_GFX),hl ;GFX, DX
	;ret

        if NOIM
        di
        endif

        if TIMERWAITLOGIC
;костыль, чтобы не входило навечно в режим "за 2 фрейма, т.к. два раза вызов логики не успевает за 1 фрейм"
         ld a,(timer)
         dec a
         ld (oldtimer),a
        endif

        ;call drawfire
fireyx=$+1
fireyx_y=$+1
fireyx_x=$+2 ;0=нет пули
        ld bc,0 ;b=x/2, c=y/2
        ld a,b ;x (не делится на 4)
        scf
        rra
        or a
        rra
         ld b,a
;a=x/8 + 0x40
         ld l,c
;l=y/2
        ld h,tytoscr/256
        add a,(hl)
        inc h
        ld h,(hl)
        ld l,a ;hl=scr
        scf
         sbc a,a
        rr h ;hl=attr
        ld (refire_scraddr),hl
        ld e,(hl)
        ld (hl),a;0xff
        inc l
        ld d,(hl)
        ld (hl),a;0xff
        ld (refire_scrdata),de
;посмотреть тайл и при бетоне (>=0xc0) убить огонь
         ld a,c;(fireyx_y)
        and 0x38
        add a,a
        add a,a
         add a,b
         sub 0x40
        ld l,a
        ld h,tilemap/256 ;32*8 tiles
        ld a,(hl) ;тайлы >=0xC0 непроходимы
        cp 0xc0
        jp c,nodestroyfire
        xor a
        ld (fireyx_x),a
nodestroyfire

        if TIMERWAITLOGIC
        ld a,(timer)
oldtimer=$+1
        ld c,0
        ld (oldtimer),a
        sub c
logic0
        push af
        endif

        if CHEAT
        ld a,0x7f
        in a,(0xfe)
        bit 1,a
        call z,newlevel;inctimeandlife
        
        ld a,0xfe
        in a,(0xfe)
        rra
        call nc,inctimeandlife;newlevel
        endif
        
        ld hl,fireyx_x
        ld a,(hl)
        or a ;0 = no move
        call nz,movefire

	;call moveobjects ;там же клипирование ;поздно на случай тормозов, т.к. genprscript нельзя прерывать
        call objects+OBJ_PROC

ndots=$+1
        ld a,0;12
        or a
        call nz,move_drawdots
        if NOIM
        ei
        endif

        ;call decenergy
;decenergy
;вызывать в главном цикле, пока не истечёт малус
;как сделать однократный малус при столкновении с шипами? просто подменять старый малус, а не прибавлять? или временная неуязвимость?
energy_bonus=$+1
        ld a,0
        dec a
        jp p,incenergy
energy_malus=$+1
        ld a,0
        dec a
        jp m,decenergyq ;ret m
        ld ix,objects+(6*OBJSIZE)
         res 2,(IX+OBJSIZE+OBJ_FLAGS) ;energy bonus ended => blink off
        ld (energy_malus),a
        ;push de
        ld hl,energy_chr
        ld a,(hl)
        add a,0x53
        ld e,a
        ld d,0x51;0x50
energy_mask=$+1
        ld a,0xff ;сдвигаем по add a,a
        add a,a
        add a,a
        add a,a
        add a,a
        ld c,a
        ld a,(de)
        and c
        dup 7;8
        ld (de),a
        inc d
        edup
        org $-1
        set 5,e
         dec d
        dup 7;8
        ld (de),a
        dec d
        edup
        org $-1
        ld a,c
        or a
        jr nz,$+4
         dec a
         dec (hl)
        ld (energy_mask),a
        ;pop de
        jp nz,decenergyq ;ret nz
        ;ld (hl),10
        call declivespp
        jp ouch
        ;;call restoreenergy
        ;call initlevel
        ;jp decenergyq

        if 1==0
instantkill
;called from moveobj
        ;jr $
        call declivespp
        ;call restoreenergy
        jp initlevel
        endif
	
unpack
	include "megaLZunpack.asm"
        if MAPSPACKED==0
        include "maps.asm"
        else
mapline0
        incbin "mapline0.c.mlz"
mapline1
        incbin "mapline1.c.mlz"
mapline2
        incbin "mapline2.c.mlz"
mapline3
        incbin "mapline3.c.mlz"
mapline4
        incbin "mapline4.c.mlz"
mapline5
        incbin "mapline5.c.mlz"
mapline6
        incbin "mapline6.c.mlz"
mapline7
        incbin "mapline7.c.mlz"
mapline8
        incbin "mapline8.c.mlz"
mapline9
        incbin "mapline9.c.mlz"
        endif
	

	include "hardyspr.ast"

        include "bombscro.asm" ;fastmem

        if FONT
        include "hardyfnt.ast"
        endif

logopix
        incbin "logopix.mlz"
logoattr
        incbin "logoattr.mlz"
        
        if MAPSPACKED
maplinebuf
        ds 128*8
        endif

        display "endmain=",$

;если тут, то в их адреса попадают в таблицу в обратном порядке (независимо от порядка здесь)
;spr_deadbody_x6=sprhardy0_x6
;spr_deadbody_x4=sprhardy0_x4
;spr_deadbody_x2=sprhardy0_x2
;spr_deadbody_x0=sprhardy0_x0
        
end
	display "end=",end

	display "Size ",/d,end-begin," bytes"
	
        ;display "metatilemap=",metatilemap
        display "metatiles=",metatiles
	
	savebin "hardycod.c",begin,end-begin
	
	LABELSLIST "..\us\user.l"
