'***************************************
'THE FORGOTTEN TREASURE
'AUTHOR JEAN-MILOST REYMOND
'THANKS TO TIMO FOR THE GRAPHICS IMPROVEMENTS
'***************************************

'GLOBAL VARIABLES
GLOBAL PAGE, LEVEL, LIVES, STARTTIME, LEVELTIME, STEPTIME, TIMERSTART, DOLOOSELIVE, NEXTLEVEL, LASTLEVEL, PLAYMUSIC, PLAYFX, DIRCHANGECOUNT, STONECOUNT, ITEMCOUNT, COINCOUNT, COINITEMCOUNT, SPIRITINDEX

'GAME VARIABLES
STEPTIME       = 0
TIMERSTART     = 0
LASTLEVEL      = 0
PLAYMUSIC      = 1
PLAYFX         = 1
DIRCHANGECOUNT = 0
STONECOUNT     = 0
ITEMCOUNT      = 8
COINCOUNT      = 0
COINITEMCOUNT  = 0
SPIRITINDEX    = 0

'SPRITES ARE ORGANIZED AS FOLLOW:
'0  TO 8  = CHARACTERS
'9        = BULLET
'10 TO 19 = FIRES
'20 TO 29 = STONES
'30       = KEY
'31       = DOOR
'32       = TIME STOP RING
'33       = INVINCIBILITY RING
'34       = SPEED UP RING
'35       = GUN
'36       = EXTRA-LIVE
'37 TO 46 = COINS
'47       = MENU CURSOR
'48 TO 64 = UNUSED

'CHARACTERS DATA, ORGANIZED AS FOLLOW:
'0 - THE CHARACTER X POSITION
'1 - THE CHARACTER Y POSITION
'2 - THE CHARACTER X OFFSET
'3 - THE CHARACTER Y OFFSET
'4 - FLIP INDEX OR MOVE DIR (0 = LEFT, 1 = TOP, 2 = RIGHT, 3 = BOTTOM)
'5 - IF 1 THE CHARACTER IS ABOVE WATER, IF 0 ABOVE EARTH OR GRASS
'6 - CHAR TYPE, WHICH MAY BE:
'    0 = PLAYER (OR NONE)
'    1 = ZOMBIE
'    2 = GHOST
'    3 = DEVIL
'    4 = SPIRIT
'    5 = BULLET
'7 - MOVE AROUND DIR AND TYPE:
'    0 = ROTATE CW AROUND CONVEX OBJECTS
'    1 = ROTATE CCW AROUND CONVEX OBJECTS
'    2 = ROTATE CW AROUND CONCAVE OBJECTS
'    3 = ROTATE CCW AROUND CONCAVE OBJECTS
'NOTE THE CHARACTER INDEX MATCHES WITH THE SPRITE INDEX (0 TO 9)
'NOTE THE BULLET IS CONSIDERED AS A SPECIAL CHARACTER (NB. 9)
DIM GLOBAL CHARACTERS(10, 8)

'FIRES DATA, ORGANISED AS FOLLOW:
'0 - IF THE FIRE IS VISIBLE (1) OR NOT (0)
'1 - THE FIRE X POSITION
'2 - THE FIRE Y POSITION
'3 - THE FIRE ANIMATION FRAME
DIM GLOBAL FIRES(10, 4)

'COINS DATA, ORGANIZED AS FOLLOW:
'0 - IF THE COIN IS VISIBLE (1) OR NOT (0)
'1 - THE COIN X POSITION
'2 - THE COIN Y POSITION
'3 - THE COIN ANIMATION FRAME
DIM GLOBAL COINS(10, 4)

'THE ITEMS STATE AND INVENTORY CONTENT, ORGANIZED AS FOLLOW:
'0 - THE KEY WAS GET (1) OR NOT (0)
'1 - THE BARRIER SWITCH WAS PRESSED (1) OR NOT (0)
'2 - THE FIRE SWITCH WAS PRESSED (1) OR NOT (0)
'3 - THE TIME STOP RING WAS GET (1) OR NOT (0)
'4 - THE INVINCIBILITY RING WAS GET (1) OR NOT (0)
'5 - THE WATER SPEEDUP RING WAS GET (1) OR NOT (0)
'6 - THE GUN WAS GET (1) OR NOT (0)
'7 - A BULLET WAS FIRED (1) OR NOT (0)
DIM GLOBAL ITEMS(ITEMCOUNT)

'THE BARRIER SWITCH POSITION (WARNING UPDATED ONLY AFTER PRESSED)
DIM GLOBAL BARRIERSWITCH(2)

'THE FIRE SWITCH POSITION (WARNING UPDATED ONLY AFTER PRESSED)
DIM GLOBAL FIRESWITCH(2)

'THE MENU CURSOR
DIM GLOBAL CURSOR(2)

RANDOMIZE TIMER

GAMEPAD 1

'***************************************
'MAIN FUNCTION
'***************************************
MAIN:
    DO
        CLS
        SPRITE OFF

        PAGE = 0

        CALL MAINMENU

        LEVEL     = 1
        LIVES     = 2
        COINCOUNT = 0

        CALL GAMELOOP
    LOOP

'***************************************
'MAIN MENU
'***************************************
SUB MAINMENU
    STARTTIME = TIMER

    MUSIC(7)

    REPEAT
        PAL 1

        'SHOW THE GAME TITLE
        FOR I = 0 TO 8
            CELL 5 + I, 1, 145 + I
            CELL 5 + I, 2, 161 + I
        NEXT I

        'DO SHOW THE OPTIONS?
        IF BUTTON TAP(0, 1) THEN
            CALL SHOWOPTIONS
        END IF

        'DRAW THE PAGE CONTENT
        IF PAGE = 0 THEN
            PAL 7

            IF ((TIMER - STARTTIME) MOD 192) >= 144 THEN
                BG FILL 0, 8 TO 20, 8 CHAR 0
            ELSE IF ((TIMER - STARTTIME) MOD 192) >= 96 THEN
                TEXT 1, 8, "PRESS B FOR OPTIONS"
            ELSE IF ((TIMER - STARTTIME) MOD 192) >= 48 THEN
                BG FILL 0, 8 TO 20, 8 CHAR 0
            ELSE
                TEXT 2, 8, "PRESS A TO START"
            END IF
        ELSE IF PAGE = 1 THEN
            PAL 2
            TEXT 4, 4,  "SO YOU'RE AN"
            TEXT 1, 5,  "ADVENTURER, WHICH"
            TEXT 0, 6,  "HEARD A LEGEND ABOUT"
            TEXT 0, 7,  "A FORGOTTEN TREASURE"
            TEXT 1, 8,  "JUST IN THE MIDDLE"
            TEXT 0, 9,  "OF AN HAUNTED PLACE."
            TEXT 0, 10, "OF COURSE YOU'LL TRY"
            TEXT 1, 11, "YOUR CHANCE... BUT"
            TEXT 1, 12, "THE DEADS WILL NOT"
            TEXT 3, 13, "LET YOU QUIET."
        ELSE IF PAGE = 2 THEN
            PAL 7
            TEXT 6, 6, "ENEMIES"

            PAL 2
            SPRITE 0 FLIP 0, 1 PAL 5
            SPRITE 0, 32, 64, 67
            TEXT 6, 8, "ZOMBIE"
            SPRITE 1 FLIP 0, 1 PAL 0
            SPRITE 1, 32, 72, 69
            TEXT 6, 9, "GHOST"
            SPRITE 2 FLIP 0, 1 PAL 6
            SPRITE 2, 32, 80, 71
            TEXT 6, 10, "DEVIL"
            SPRITE 3 PAL 7
            SPRITE 3, 32, 88, 72
            TEXT 6, 11, "SPIRIT"
        ELSE IF PAGE = 3 THEN
            PAL 7
            TEXT 6, 5, "BARRIERS"

            PAL 0
            CELL 4, 7, 1
            PAL 2
            TEXT 6, 7, "WALL"
            PAL 1
            CELL 4, 8, 2
            PAL 2
            TEXT 6, 8, "WATER"
            SPRITE 0 PAL 1
            SPRITE 0, 32, 72, 13
            TEXT 6, 9, "BARRIER"
            SPRITE 1 PAL 1
            SPRITE 1, 32, 80, 10
            TEXT 6, 10, "BARRIER SWITCH"
            PAL 0
            CELL 4, 11, 18
            PAL 2
            SPRITE 2 PAL 7
            SPRITE 2, 32, 88, 75
            TEXT 6, 11, "FIRE"
            SPRITE 3 PAL 7
            SPRITE 3, 32, 96, 10
            TEXT 6, 12, "FIRE SWITCH"
            SPRITE 4 PAL 0
            SPRITE 4, 32, 104, 9
            TEXT 6, 13, "STONE"
        ELSE IF PAGE = 4 THEN
            PAL 7
            TEXT 6, 5, "BONUS"

            PAL 2
            SPRITE 0 FLIP 0, 0 PAL 4
            SPRITE 0, 32, 56, 19
            TEXT 6, 7, "STOP TIME"
            SPRITE 1 FLIP 0, 0 PAL 6
            SPRITE 1, 32, 64, 19
            TEXT 6, 8, "SPEED UP"
            SPRITE 2 FLIP 0, 0 PAL 7
            SPRITE 2, 32, 72, 19
            TEXT 6, 9, "INVINCIBLE"
            SPRITE 3 FLIP 0, 0 PAL 0
            SPRITE 3, 32, 80, 20
            TEXT 6, 10, "GUN"
            SPRITE 4 FLIP 0, 0 PAL 7
            SPRITE 4, 32, 88, 23
            TEXT 6, 11, "COIN"
            SPRITE 5 FLIP 0, 0 PAL 7
            SPRITE 5, 32, 96, 24
            TEXT 6, 12, "EXTRA-LIVE"
        END IF

        'DO CHANGE THE PAGE?
        IF ((TIMER - STARTTIME) MOD 384) = 383 THEN
            INC PAGE

            'CLEAR THE PREVIOUS PAGE
            FOR I = 3 TO 20
                BG FILL 0, I TO 20, I CHAR 0
            NEXT I

            SPRITE OFF
        END IF

        'DO LOOP TO FIRST PAGE?
        IF PAGE > 4 THEN
            PAGE = 0
            MUSIC(7)
        END IF

        WAIT VBL
    UNTIL BUTTON TAP(0, 0)

    STOP
END SUB

'***************************************
'SHOW THE OPTIONS MENU
'***************************************
SUB SHOWOPTIONS
    'CLEAR THE PREVIOUS PAGE
    FOR I = 3 TO 20
        BG FILL 0, I TO 20, I CHAR 0
    NEXT I

    SPRITE OFF

    'SET THE CURSOR START POSITION
    CURSOR(0) = 2
    CURSOR(1) = 8

    DO
        PAL 7

        'DRAW THE MENU
        TEXT 3, 8, "SOUND:"
        TEXT 3, 9, "EXIT"

        PAL 1

        'CLEANUP THE PREVIOUS MUSIC/FX OPTION
        TEXT 10, 8, "        "

        'DRAW THE MUSIC/FX OPTION
        IF PLAYMUSIC AND PLAYFX THEN
            TEXT 10, 8, "MUSIC/FX"
        ELSE IF PLAYMUSIC THEN
            TEXT 10, 8, "MUSIC"
        ELSE IF PLAYFX THEN
            TEXT 10, 8, "FX"
        ELSE
            TEXT 10, 8, "NONE"
        END IF

        'MOVE THE CURSOR
        IF UP(0) THEN
            DEC CURSOR(1)
        ELSE IF DOWN(0) THEN
            INC CURSOR(1)
        END IF

        'CHECK IF THE CURSOR IS OUT OF BOUNDS
        IF CURSOR(1) < 8 THEN
            CURSOR(1) = 8
        ELSE IF CURSOR(1) > 9 THEN
            CURSOR(1) = 9
        END IF

        'CHECK WHICH OPTION WAS SELECTED
        IF BUTTON TAP(0, 0) THEN
            IF CURSOR(1) = 8 THEN
                IF PLAYMUSIC AND PLAYFX THEN
                    PLAYMUSIC = 1
                    PLAYFX    = 0
                ELSE IF PLAYMUSIC THEN
                    PLAYMUSIC = 0
                    PLAYFX    = 1
                ELSE IF PLAYFX THEN
                    PLAYMUSIC = 0
                    PLAYFX    = 0
                ELSE
                    PLAYMUSIC = 1
                    PLAYFX    = 1
                END IF
            ELSE IF CURSOR(1) = 9 THEN
                'EXIT MENU, CLEAN IT FIRST
                FOR I = 3 TO 20
                    BG FILL 0, I TO 20, I CHAR 0
                NEXT I

                EXIT SUB
            END IF
        END IF

        PAL 0

        'DRAW THE CURSOR
        CELL 2, 8, 0
        CELL 2, 9, 0
        CELL CURSOR(0), CURSOR(1), 160

        WAIT VBL
    LOOP
END SUB

'***************************************
'GAME LOOP
'***************************************
SUB GAMELOOP
    DOBREAKLOOP = 0

    REPEAT
        CLS
        SPRITE OFF

        'SHOW THE READY MESSAGE
        REPEAT
            PAL 7

            IF LEVEL < 10 THEN
                 TEXT 6, 7, "LEVEL 0"
                 LOCATE 13, 7
                 PRINT LEVEL
            ELSE
                 TEXT 6, 7, "LEVEL "
                 LOCATE 12, 7
                 PRINT LEVEL
            END IF

            PAL 1
            TEXT 7, 8, "READY?"

            WAIT VBL
        UNTIL BUTTON TAP(0, 0) OR BUTTON TAP(0, 1)

        CLS

        CALL INITLEVEL(LEVEL)

        'PLAY THE MUSIC
        IF PLAYMUSIC = 1 THEN
            MUSIC(2)
        END IF

        'GAME MAIN LOOP
        REPEAT
            CALL MOVEPLAYER
            CALL MOVEENEMIES
            CALL MOVEBULLET
            CALL CHECKITEMS
            CALL COUNTANDCHECKTIME

            CALL DRAWPLAYER
            CALL DRAWBULLET
            CALL DRAWENEMIES
            CALL DRAWTIME
            CALL DRAWLIVES
            CALL DRAWCOINCOUNT
            CALL DRAWLEVEL
            CALL DRAWFIRES
            CALL DRAWCOINS

            WAIT VBL
        UNTIL NEXTLEVEL = 1 OR DOLOOSELIVE = 1

        STOP

        'UPDATE LEVEL STATUS
        IF DOLOOSELIVE = 1 THEN
            CALL PLAYERDYING
            DEC LIVES
        ELSE IF NEXTLEVEL = 1 THEN
            'GAME END REACHED OR JUST NEED TO GO TO NEXT LEVEL?
            IF LEVEL = LASTLEVEL THEN
                CALL GAMEEND
                DOBREAKLOOP = 1
            ELSE
                INC LEVEL
            END IF
        END IF
    UNTIL DOBREAKLOOP OR LIVES = -1

    CLS
    SPRITE OFF
    MUSIC(1)

    'SHOW THE GAME OVER MESSAGE
    REPEAT
        PAL 7
        TEXT 5, 7, "GAME OVER!"

        WAIT VBL
    UNTIL BUTTON TAP(0, 0) OR BUTTON TAP(0, 1) OR MUSIC(3) = 0

    STOP
END SUB

'***************************************
'INITIALIZE THE LEVEL
'***************************************
SUB INITLEVEL(INDEX)
    STONECOUNT    = 0
    COINITEMCOUNT = 0

    'RESET THE FIRE AND COIN TABLE (SHOULD BE DONE BEFORE READING THE
    'NEXT LEVEL)
    FOR I = 0 TO 9
        FOR J = 0 TO 3
            FIRES(I, J) = 0
            COINS(I, J) = 0
        NEXT J
    NEXT I

    LASTLEVEL = 12

    'MOVE CURSOR TO LEVEL TO READ
    IF INDEX = 1 THEN
        RESTORE LEVEL1
    ELSE IF INDEX = 2 THEN
        RESTORE LEVEL2
    ELSE IF INDEX = 3 THEN
        RESTORE LEVEL3
    ELSE IF INDEX = 4 THEN
        RESTORE LEVEL4
    ELSE IF INDEX = 5 THEN
        RESTORE LEVEL5
    ELSE IF INDEX = 6 THEN
        RESTORE LEVEL6
    ELSE IF INDEX = 7 THEN
        RESTORE LEVEL7
    ELSE IF INDEX = 8 THEN
        RESTORE LEVEL8
    ELSE IF INDEX = 9 THEN
        RESTORE LEVEL9
    ELSE IF INDEX = 10 THEN
        RESTORE LEVEL10
    ELSE IF INDEX = 11 THEN
        RESTORE LEVEL11
    ELSE IF INDEX = 12 THEN
        RESTORE LEVEL12
    ELSE
        RESTORE LEVEL1
    END IF

    CALL DRAWPLAYFIELD
    CALL DRAWLABELS
    CALL DRAWITEMS

    'GET THE PLAYER POSITION AND DIRECTION
    READ PLAYERX
    READ PLAYERY
    READ PLAYERDIR

    'CONFIGURE THE PLAYER
    CHARACTERS(0, 0) = (5 + PLAYERX) * 8
    CHARACTERS(0, 1) = (3 + PLAYERY) * 8
    CHARACTERS(0, 2) = 0.0
    CHARACTERS(0, 3) = 0.0
    CHARACTERS(0, 4) = PLAYERDIR
    CHARACTERS(0, 5) = 0
    CHARACTERS(0, 6) = 1
    CHARACTERS(0, 7) = 0

    'GET LEVEL TIME
    READ LEVELTIME

    'GET THE MONSTERS COUNT
    READ MONSTERCOUNT

    'CONFIGURE THE MONSTERS
    IF MONSTERCOUNT THEN
        FOR I = 0 TO MONSTERCOUNT - 1
            'READ THE MONSTER DATA
            READ MONSTERX
            READ MONSTERY
            READ MONSTERDIR
            READ MONSTERTYPE
            READ SPIRITMOVETYPE

            'CONFIGURE THE MONSTER
            CHARACTERS(I + 1, 0) = (5 + MONSTERX) * 8
            CHARACTERS(I + 1, 1) = (3 + MONSTERY) * 8
            CHARACTERS(I + 1, 2) = 0.0
            CHARACTERS(I + 1, 3) = 0.0
            CHARACTERS(I + 1, 4) = MONSTERDIR
            CHARACTERS(I + 1, 5) = 0
            CHARACTERS(I + 1, 6) = MONSTERTYPE
            CHARACTERS(I + 1, 7) = SPIRITMOVETYPE
        NEXT I
    END IF

    'RESET THE REMAINING MONSTERS
    FOR I = MONSTERCOUNT + 1 TO 9
        'CONFIGURE THE MONSTER
        CHARACTERS(I, 0) = 0.0
        CHARACTERS(I, 1) = 0.0
        CHARACTERS(I, 2) = 0.0
        CHARACTERS(I, 3) = 0.0
        CHARACTERS(I, 4) = 0
        CHARACTERS(I, 5) = 0
        CHARACTERS(I, 6) = 0
        CHARACTERS(I, 7) = 0
    NEXT I

    'START TO MEASURE THE TIME
    TIMERSTART = TIMER

    'INITIALIZE THE ITEMS STATE
    FOR I = 0 TO ITEMCOUNT
        ITEMS(I) = 0
    NEXT I

    'PREPARE THE MAIN LOOP CONDITIONS
    DOLOOSELIVE = 0
    NEXTLEVEL   = 0
END SUB

'***************************************
'GAME END
'***************************************
SUB GAMEEND
    CLS
    SPRITE OFF

    OLDPLAYFX        = PLAYFX
    PLAYFX           = 1
    X                = 0
    STARTTIME        = 0
    COININDEX        = 0
    THUNDERINDEX     = 0
    COINPOSX         = 0
    COINPOSY         = 0
    COINMAX          = 36
    ANIMEND          = 0
    CHARACTERS(0, 0) = 56
    CHARACTERS(0, 1) = 64
    CHARACTERS(0, 4) = 2

    MUSIC(7)

    REPEAT
        CLS

        PAL 2

        'SELECT THE ANIMATION TO SHOW
        IF X < 56 THEN
            CALL DRAWCHEST(9, 7, 0, 0)

            'SHOW THE PLAYER SPRITE
            SPRITE 0 FLIP 1, 0 PAL 4
            SPRITE 0, X, 64, 64

            'PLAYER IS MOVING TO THE CHEST
            INC X
            STARTTIME = TIMER
        ELSE IF TIMER - STARTTIME <= 50 THEN
            'PLAYER REACHED THE CHEST
            CALL DRAWCHEST(9, 7, 0, 0)
        ELSE IF TIMER - STARTTIME <= 100 THEN
            'CHEST OPENS...
            CALL DRAWCHEST(9, 7, 1, 0)
        ELSE IF TIMER - STARTTIME <= 150 THEN
            'GUARDIAN IS POPPING...
            CALL DRAWCHEST(9, 7, 1, 0)
            CALL DRAWGUARDIAN(1, 0)
        ELSE IF TIMER - STARTTIME <= 250 THEN
            'GUARDIAN POPPED
            CALL DRAWCHEST(9, 7, 1, 0)
            CALL DRAWGUARDIAN(0, 0)
        ELSE IF TIMER - STARTTIME <= 550 THEN
            'GUARDIAN IS SPEAKING...
            PAL 7
            TEXT 0, 10, "SO YOU WANT TO TAKE"
            TEXT 0, 11, "MY TREASURE, RIGHT?"
            CALL GUARDIANSPEAK
        ELSE IF TIMER - STARTTIME <= 700 THEN
            'WAIT A TIME
            CALL DRAWCHEST(9, 7, 1, 0)
            CALL DRAWGUARDIAN(0, 0)
        ELSE IF TIMER - STARTTIME <= 1000 THEN
            'GUARDIAN IS SPEAKING AGAIN
            PAL 7
            TEXT 0, 10, "WELL LET ME KNOW HOW"
            TEXT 0, 11, "MANY COINS YOU HAVE."
            CALL GUARDIANSPEAK
        ELSE IF TIMER - STARTTIME <= 1100 THEN
            'WAIT A TIME
            CALL DRAWCHEST(9, 7, 1, 0)
            CALL DRAWGUARDIAN(0, 0)
        ELSE IF TIMER - STARTTIME <= 1500 THEN
            'COUNT THE COINS...
            CALL DRAWCHEST(9, 7, 1, 0)
            CALL DRAWGUARDIAN(0, 0)

            INDEX = 21

            'SELECT THE NEXT COIN INDEX
            IF COININDEX <= 10 THEN
                INDEX = 21
            ELSE IF COININDEX <= 20 THEN
                INDEX = 22
            ELSE IF COININDEX <= 30 THEN
                INDEX = 23
            ELSE IF COININDEX <= 40 THEN
                INDEX = 22
            ELSE IF COININDEX <= 50 THEN
                COININDEX = 0
            END IF

            'SHOW THE ROTATING COIN
            SPRITE 1 FLIP 0, 0 PAL 7
            SPRITE 1, 64, 64, INDEX

            'SHOW THE MOVING COIN
            SPRITE 2 FLIP 0, 0 PAL 7
            SPRITE 2, 64 + COINPOSX, 64 - COINPOSY, INDEX

            'CALCULATE THE NEXT COIN POSITION AND INCREASE THE INDEX
            COINPOSX = (COINPOSX + 2) MOD 16
            COINPOSY = (COINPOSY + 2) MOD 16
            INC COININDEX
        ELSE IF TIMER - STARTTIME <= 1700 THEN
            'DISABLE THE COIN SPRITES AND WAIT A TIME
            SPRITE OFF 1
            SPRITE OFF 2

            CALL DRAWCHEST(9, 7, 1, 0)
            CALL DRAWGUARDIAN(0, 0)
        ELSE IF TIMER - STARTTIME <= 2000 THEN
            'DEPENDING ON COIN COUNT THE GUARDIAN IS HAPPY, OR ANGRY
            PAL 7

            'ENOUGH COINS TO SATISFY THE GUARDIAN?
            IF COINCOUNT < COINMAX THEN
                'GUARDIAN IS ANGRY
                TEXT 1, 10, "HA! JUST THAT! ARE"
                TEXT 4, 11, "YOU JOKING?"
            ELSE
                'GUARDIAN IS HAPPY
                TEXT 0, 10, "WELL, THAT'S ENOUGH."
                TEXT 0, 11, "ENJOY YOUR TREASURE!"
            END IF

            CALL GUARDIANSPEAK
        ELSE IF TIMER - STARTTIME <= 2200 THEN
            'GUARDIAN REACTS TO THE RECEIVED COINS...
            PAL 7

            'ENOUGH COINS TO LET THE GUARDIAN HAPPY?
            IF COINCOUNT < COINMAX THEN
                'NOP, GUARDIAN THUNDERS THE PLAYER
                CALL DRAWCHEST(9, 7, 1, 0)
                CALL DRAWGUARDIAN(0, 0)

                INDEX = 28

                'GET THE THUNDER INDEX
                IF THUNDERINDEX = 0 THEN
                    CALL PLAYTHUNDERSOUND
                ELSE IF THUNDERINDEX <= 10 THEN
                    INDEX = 28
                ELSE IF THUNDERINDEX <= 20 THEN
                    INDEX = 29
                ELSE IF THUNDERINDEX <= 30 THEN
                    INDEX = 30
                ELSE IF THUNDERINDEX <= 40 THEN
                    INDEX = 29
                ELSE IF THUNDERINDEX <= 50 THEN
                    THUNDERINDEX = 0
                    CALL PLAYTHUNDERSOUND
                END IF

                'DRAW THE THUNDER
                SPRITE 1 FLIP 0, 0 PAL 4
                SPRITE 1, 64, 56, INDEX

                'ANIMATE THE THUNDER
                INC THUNDERINDEX
            ELSE
                'THE GUARDIAN IS HAPPY, POPPING DOWN
                CALL DRAWCHEST(9, 7, 1, 0)
                CALL DRAWGUARDIAN(1, 0)
            END IF
        ELSE IF TIMER - STARTTIME <= 2500 THEN
            'FINAL PART...
            SPRITE OFF 1

            'ENOUGH COINS TO LET THE GUARDIAN HAPPY?
            IF COINCOUNT < COINMAX THEN
                'GUARDIAN IS ANGRY, PLAYER IS DYING
                CALL DRAWCHEST(9, 7, 1, 0)
                CALL DRAWGUARDIAN(0, 0)
                CALL PLAYERDYING
                ANIMEND = 1
            ELSE
                'GUARDIAN IS HAPPY, CHEST IS FULL AND THE PLAYER WINS
                CALL DRAWCHEST(9, 7, 1, 1)

                'DRAW THE HAPPY PLAYER
                SPRITE 0 FLIP 0, 0 PAL 4
                SPRITE 0, 56, 64, 126
            END IF
        ELSE
            ANIMEND = 1
        END IF

        WAIT VBL
    UNTIL ANIMEND OR BUTTON TAP(0, 0) OR BUTTON TAP(0, 1)

    'RESTORE THE FX OPTION STATUS
    PLAYFX = OLDPLAYFX
END SUB

'***************************************
'ANIMATE THE GUARDIAN SPEAK
'***************************************
SUB GUARDIANSPEAK
    CALL DRAWCHEST(9, 7, 1, 0)

    IF (TIMER MOD 20) < 10 THEN
        CALL DRAWGUARDIAN(0, 0)
    ELSE
        CALL DRAWGUARDIAN(0, 1)
    END IF
END SUB

'***************************************
'SHOW THE PLAYER DYING SEQUENCE
'***************************************
SUB PLAYERDYING
    DI = 80

    CALL PLAYPLAYERDYING

    'SHOW THE LOOSE A LIVE SEQUENCE
    REPEAT
        'COPY THE INDEX BECAUSE CALLING DRAWCHAR MAY MODIFY IT
        CH = DI
        CALL DRAWCHAR(0, CH, 4, 0)
        INC DI
        INC DI
        WAIT 5
        WAIT VBL
    UNTIL DI > 104
END SUB

'***************************************
'CHECK THE ITEMS STATE
'***************************************
SUB CHECKITEMS
    Y = 28

    'THE KEY WAS FOUND?
    IF ITEMS(0) = 1 THEN
        'MOVE IT TO INVENTORY AND OPEN THE DOOR
        SPRITE 30, 140, Y, 8
        SPRITE 31, SPRITE.X(31), SPRITE.Y(31), 7
        ADD Y, 12
    END IF

    'THE BARRIER SWITCH WAS PRESSED?
    IF ITEMS(1) = 1 THEN
        'CHANGE THE BARRIER SWITCH STATE
        BG 0
        PAL 0
        CELL BARRIERSWITCH(0), BARRIERSWITCH(1), 11
        CALL PLAYSWITCHPRESSED

        'REMOVE THE BARRIER
        CALL REMOVEBARRIER

        'SWITCH IS NO LONGER PRESSED
        ITEMS(1) = 0
    END IF

    'THE FIRE SWITCH WAS PRESSED?
    IF ITEMS(2) = 1 THEN
        'CHANGE THE FIRE SWITCH STATE
        BG 0
        PAL 0
        CELL FIRESWITCH(0), FIRESWITCH(1), 11
        CALL PLAYSWITCHPRESSED

        'REMOVE THE FIRES
        FOR I = 0 TO 9
            FIRES(I, 0) = 0
        NEXT I

        'SWITCH IS NO LONGER PRESSED
        ITEMS(2) = 0
    END IF

    'FOUND A TIME STOP RING?
    IF ITEMS(3) = 1 THEN
        'MOVE IT TO INVENTORY
        SPRITE 32, 140, Y, 19
        ADD Y, 12
    END IF

    'FOUND AN INVINCIBILITY RING?
    IF ITEMS(4) = 1 THEN
        'MOVE IT TO INVENTORY
        SPRITE 33, 140, Y, 19
        ADD Y, 12
    END IF

    'FOUND A SPEED UP RING?
    IF ITEMS(5) = 1 THEN
        'MOVE IT TO INVENTORY
        SPRITE 34, 140, Y, 19
        ADD Y, 12
    END IF

    'FOUND A GUN?
    IF ITEMS(6) = 1 THEN
        'MOVE IT TO INVENTORY
        SPRITE 35, 140, Y, 20
    END IF
END SUB

'***************************************
'MOVE THE BULLET AND CHECK ITS POS AND STATE
'***************************************
SUB MOVEBULLET
    'PLAYER FIND THE GUN AND WANT TO FIRE A BULLET?
    IF ITEMS(6) = 1 AND ITEMS(7) = 0 AND BUTTON TAP(0, 1) THEN
        'FIND THE BULLET DIRECTION
        IF CHARACTERS(0, 4) = 0 THEN
            CHARACTERS(9, 2) = -1
            CHARACTERS(9, 3) =  0
        ELSE IF CHARACTERS(0, 4) = 1 THEN
            CHARACTERS(9, 2) =  0
            CHARACTERS(9, 3) = -1
        ELSE IF CHARACTERS(0, 4) = 2 THEN
            CHARACTERS(9, 2) = 1
            CHARACTERS(9, 3) = 0
        ELSE IF CHARACTERS(0, 4) = 3 THEN
            CHARACTERS(9, 2) = 0
            CHARACTERS(9, 3) = 1
        END IF

        'SET THE BULLET INITIAL POSITION
        CHARACTERS(9, 0) = CHARACTERS(0, 0) + (8 * CHARACTERS(9, 2))
        CHARACTERS(9, 1) = CHARACTERS(0, 1) + (8 * CHARACTERS(9, 3))
        CHARACTERS(9, 4) = CHARACTERS(0, 4)
        CHARACTERS(9, 6) = 5

        'NOTIFY THAT THE BULLET WAS FIRED
        ITEMS(7) = 1
    END IF

    'A BULLET WAS FIRED?
    IF ITEMS(7) = 1 THEN
        'MOVE THE BULLET
        ADD CHARACTERS(9, 0), CHARACTERS(9, 2)
        ADD CHARACTERS(9, 1), CHARACTERS(9, 3)

        'BULLET HIT A MONSTER?
        IF SPRITE HIT(9, 1 TO 8) THEN
            CHARACTERS(HIT, 6) = 0
            ITEMS(7) = 0
            EXIT SUB
        END IF

        C = 0

        'CHECK IF THE BULLET HIT SOMETHING
        CALL CHECKCOLLISION(9, CHARACTERS(9, 0), CHARACTERS(9, 1), 1, C)

        'FOUND A COLLISION?
        IF C = 1 THEN
            ITEMS(7) = 0
        END IF
    END IF
END SUB

'***************************************
'MOVE THE PLAYER AND CHECK ITS POSITION
'***************************************
SUB MOVEPLAYER
    'COPY THE CURRENT POSITION
    PREVX = CHARACTERS(0, 0)
    PREVY = CHARACTERS(0, 1)

    'RESET THE OFFSETS
    CHARACTERS(0, 2) = 0
    CHARACTERS(0, 3) = 0

    'CHECK IF A DIRECTION ARROW WAS PRESSED
    IF LEFT(0) THEN
        CHARACTERS(0, 2) = -1
        CHARACTERS(0, 4) =  0
    ELSE IF RIGHT(0) THEN
        CHARACTERS(0, 2) =  1
        CHARACTERS(0, 4) =  2
    ELSE IF UP(0) THEN
        CHARACTERS(0, 3) = -1
        CHARACTERS(0, 4) =  1
    ELSE IF DOWN(0) THEN
        CHARACTERS(0, 3) =  1
        CHARACTERS(0, 4) =  3
    END IF

    'MOVE THE PLAYER AND CHECK ITS COLLISIONS
    CALL MOVECHAR(0, 1)

    'CHECK IF THE CHAR HIT A FIRE WHILE HE ISN'T PROTECTED BY AN
    'INVINCIBILITY RING
    IF SPRITE HIT(0, 10 TO 19) AND ITEMS(4) <> 1 THEN
        DOLOOSELIVE = 1
        EXIT SUB
    END IF

    IF CHARACTERS(0, 2) <> 0 OR CHARACTERS(0, 3) <> 0 THEN
        INC STEPTIME

        'IS PLAYER WALKING ABOVE WATER?
        IF CHARACTERS(0, 5) THEN
            IF STEPTIME >= 20 THEN
                STEPTIME = 0
                CALL PLAYPLAYERSTEPWATER
            END IF
        ELSE IF STEPTIME >= 10 THEN
            STEPTIME = 0
            CALL PLAYPLAYERSTEP
        END IF
    END IF

    'THE PLAYER FOUND THE KEY, REACHED THE DOOR OR FOUND AN ITEM?
    IF SPRITE HIT(0, 30) THEN
        'FOUND THE KEY, MOVE IT TO INVENTORY
        ITEMS(0) = 1

        'PLAY THE FOUND ITEM SOUND
        CALL PLAYFOUNDITEM
    ELSE IF SPRITE HIT(0, 31) AND ITEMS(0) = 1 THEN
        'DOOR WAS REACHED AND KEY WAS FOUND
        NEXTLEVEL = 1
    ELSE IF SPRITE HIT(0, 32) THEN
        'FOUND A TIME STOP RING
        ITEMS(3) = 1

        'PLAY THE FOUND ITEM SOUND
        CALL PLAYFOUNDITEM
    ELSE IF SPRITE HIT(0, 33) THEN
        'FOUND AN INVINCIBILITY RING
        ITEMS(4) = 1

        'PLAY THE FOUND ITEM SOUND
        CALL PLAYFOUNDITEM
    ELSE IF SPRITE HIT(0, 34) THEN
        'FOUND A SPEED UP RING
        ITEMS(5) = 1

        'PLAY THE FOUND ITEM SOUND
        CALL PLAYFOUNDITEM
    ELSE IF SPRITE HIT(0, 35) THEN
        'FOUND A GUN
        ITEMS(6) = 1

        'PLAY THE FOUND ITEM SOUND
        CALL PLAYFOUNDITEM
    ELSE IF SPRITE HIT(0, 36) THEN
        'FOUND AN EXTRA-LIVE
        INC LIVES
        SPRITE OFF 36

        'PLAY THE FOUND ITEM SOUND
        CALL PLAYFOUNDITEM
    ELSE IF SPRITE HIT(0, 37 TO 46) THEN
        'FOUND A COIN
        INC COINCOUNT
        COINS(HIT - 37, 0) = 0

        'PLAY THE FOUND ITEM SOUND
        CALL PLAYFOUNDITEM
    END IF

    'THE PLAYER HIT A STONE?
    IF SPRITE HIT(0, 20 TO 29) THEN
        'ITERATE THROUGH STONES
        FOR I = 20 TO 29
            COLLISION = 0
            CALL CHECKCHARHITSTONE(0, I, COLLISION)

            'HIT THIS STONE?
            IF COLLISION THEN
                SX = SPRITE.X(I)
                SY = SPRITE.Y(I)

                'CALCULATE THE NEXT STONE POSITION
                NEXTSX = SX + (CHARACTERS(0, 2) * 2)
                NEXTSY = SY + (CHARACTERS(0, 3) * 2)

                'MOVE THE STONE
                SPRITE I, NEXTSX, NEXTSY, 9

                'CHECK IF THE STONE IS HITTING SOMETHING
                CALL CHECKCOLLISION(I, NEXTSX, NEXTSY, 1, COLLISION)

                'DON'T MOVE THE STONE IF HITTING SOMETHING
                IF COLLISION THEN
                    CHARACTERS(0, 0) = PREVX
                    CHARACTERS(0, 1) = PREVY
                    SPRITE I, SX, SY, 9
                END IF
            END IF
        NEXT I
    END IF
END SUB

'***************************************
'MOVE ENEMIES AND CHECK THEIR POSITION
'***************************************
SUB MOVEENEMIES
    COL = 0

    'ITERATE THROUGH CHARACTERS
    FOR I = 1 TO 9
        IF CHARACTERS(I, 6) = 1 THEN
            'IS A ZOMBIE, TRACK THE PLAYER
            CALL TRACKTARGET(I, 0, COL)
        ELSE IF CHARACTERS(I, 6) = 2 THEN
            'IS A GHOST, SELECT A TARGET AND MOVE THROUGH WALLS
            CALL MOVETOTARGET(I, 0, 0, 0.2, COL)
        ELSE IF CHARACTERS(I, 6) = 3 THEN
            'IS A DEVIL, SELECT A TARGET AND MOVE THROUGH WALLS
            CALL MOVETOTARGET(I, 0, 1, 0.4, COL)
        ELSE IF CHARACTERS(I, 6) = 4 THEN
            'IS A SPIRIT, MOVE AROUND WALLS
            CALL MOVEAROUND(I, 0, COL)
        END IF

        'FOUND A COLLISION WITH PLAYER, AND PLAYER ISN'T PROTECTED WITH
        'AN INVINCIBILITY RING?
        IF COL = 1 AND ITEMS(4) = 0 THEN
            DOLOOSELIVE = 1
            EXIT SUB
        END IF
    NEXT I
END SUB

'***************************************
'MOVE THE CHAR BY TRACKING A TARGET
'INDEX - CHAR INDEX
'TARGET - TARGET INDEX
'[OUT] COL - IF 1 CHAR COLLIDES TARGET
'***************************************
SUB TRACKTARGET(INDEX, TARGET, COL)
    'RESET THE OFFSETS
    CHARACTERS(INDEX, 2) = 0
    CHARACTERS(INDEX, 3) = 0

    NX = 0.0
    NY = 0.0

    'GET THE TARGET DIRECTION
    CALL GETTARGETDIR(INDEX, TARGET, NX, NY)

    'CALCULATE THE CHAR X AND Y OFFSETS
    CHARACTERS(INDEX, 2) = NX * -0.5
    CHARACTERS(INDEX, 3) = NY * -0.5

    'UPDATE THE CHAR LOOK AT DIRECTION
    CALL CHARLOOKAT(INDEX, NX, NY)

    'MOVE THE CHARACTER AND CHECK ITS COLLISIONS
    CALL MOVECHAR(INDEX, 1)

    'CHECK IF THE PLAYER HIT THE CHAR
    IF SPRITE HIT(TARGET, INDEX) THEN
        COL = 1
    ELSE
        COL = 0
    END IF
END SUB

'***************************************
'MOVE THE CHAR BY SELECTING A TARGET,
'THIS MOVE IS ALLOWED TO IGNORE COLLISIONS
'INDEX - CHAR INDEX
'TARGET - TARGET INDEX
'DOCHECKCOL - IF 1 COLLISIONS WILL BE CHECKED
'SPEED - MOVE SPEED
'[OUT] COL - IF 1 CHAR COLLIDES TARGET
'***************************************
SUB MOVETOTARGET(INDEX, TARGET, DOCHECKCOL, SPEED, COL)
    CHARACTERS(INDEX, 2) = 0.0
    CHARACTERS(INDEX, 3) = 0.0

    NX = 0.0
    NY = 0.0

    'GET THE TARGET DIRECTION
    CALL GETTARGETDIR(INDEX, TARGET, NX, NY)

    'KEEP THE PREVIOUS DIRECTION
    PREVDIR = CHARACTERS(INDEX, 4)

    IF ABS(NX) > ABS(NY) THEN
        IF NX > 0.0 THEN
            CHARACTERS(INDEX, 2) = -SPEED
            CHARACTERS(INDEX, 4) =  0
        ELSE
            CHARACTERS(INDEX, 2) = SPEED
            CHARACTERS(INDEX, 4) = 2
        END IF
    ELSE
        IF NY > 0.0 THEN
            CHARACTERS(INDEX, 3) = -SPEED
            CHARACTERS(INDEX, 4) =  1
        ELSE
            CHARACTERS(INDEX, 3) = SPEED
            CHARACTERS(INDEX, 4) = 3
        END IF
    END IF

    DIRCHANGECOUNT = (DIRCHANGECOUNT + 1) MOD 11

    IF DIRCHANGECOUNT > 0 THEN
        CHARACTERS(INDEX, 4) = PREVDIR
    END IF

    'UPDATE THE CHAR LOOK AT DIRECTION
    'CALL CHARLOOKAT(INDEX, NX, NY)

    'MOVE THE CHARACTER AND CHECK ITS COLLISIONS
    CALL MOVECHAR(INDEX, DOCHECKCOL)

    'CHECK IF THE PLAYER HIT THE CHAR
    IF SPRITE HIT(TARGET, INDEX) THEN
        COL = 1
    ELSE
        COL = 0
    END IF
END SUB

'***************************************
'MOVE THE ENEMY AROUND WALLS
'INDEX - CHAR INDEX
'TARGET - TARGET INDEX
'[OUT] COL - IF 1 CHAR COLLIDES TARGET
'***************************************
SUB MOVEAROUND(INDEX, TARGET, COL)
    'GET THE CURRENT POSITION AND DIR
    X      = CHARACTERS(INDEX, 0)
    Y      = CHARACTERS(INDEX, 1)
    DIR    = CHARACTERS(INDEX, 4)
    ORGDIR = DIR
    CS     = 8

    'CALCULATE THE INITIAL DIRECTION TO TEST (NOTE +3 MOD 4 IS IDENTICAL
    'TO SUBTRACT 1 TO THE VALUE)
    IF CHARACTERS(INDEX, 7) = 1 OR CHARACTERS(INDEX, 7) = 2 THEN
        DIR = (DIR + 3) MOD 4
    ELSE
        DIR = (DIR + 1) MOD 4
    END IF

    STARTDIR = DIR
    FOUNDDIR = 0
    FOUNDCOL = 0

    REPEAT
        'RESET THE OFFSETS
        CHARACTERS(INDEX, 2) = 0.0
        CHARACTERS(INDEX, 3) = 0.0

        'GET THE NEXT OFFSET TO APPLY
        IF (DIR = 0) THEN
            CHARACTERS(INDEX, 2) = -0.5
        ELSE IF (DIR = 1) THEN
            CHARACTERS(INDEX, 3) = -0.5
        ELSE IF (DIR = 2) THEN
            CHARACTERS(INDEX, 2) =  0.5
        ELSE IF (DIR = 3) THEN
            CHARACTERS(INDEX, 3) =  0.5
        END IF

        NX = X
        NY = Y

        'CALCULATE THE NEXT POSITION
        ADD NX, CHARACTERS(INDEX, 2)
        ADD NY, CHARACTERS(INDEX, 3)

        NXC = NX + SGN(CHARACTERS(INDEX, 2))
        NYC = NY + SGN(CHARACTERS(INDEX, 3))

        'CHECK THE COLLISION AGAINST WALLS (IGNORE STONES FOR NOW)
        COLLISION = 0
        CALL CHECKCOLLISION(INDEX, NXC, NYC, 0, COLLISION)

        'ITERATE THROUGH STONES AND CHECK THE COLLISION AGAINST THEIR
        'BOUNDING BOX. THIS IS REQUIRED, BECAUSE THE EXACT COLLISION
        'PREVENTS THE NEXT DIR TO BE SELECTED CORRECTLY
        IF COLLISION = 0 THEN
            FOR I = 20 TO 29
                'GET THE STONE X AND Y POSITIONS
                SX = SPRITE.X(I)
                SY = SPRITE.Y(I)
                C  = 0

                'CHECK THE COLLITION AGAINST THE BOUNDING BOX
                CALL CHECKRECTCOL(NX, NY, CS, CS, SX, SY, CS, CS, C)

                IF C = 1 THEN
                    COLLISION = 1
                END IF
            NEXT I
        END IF

        'IF NO COLLISION APPLY THE NEXT POS AND DIR
        IF FOUNDDIR = 0 AND COLLISION = 0 THEN
            CHARACTERS(INDEX, 0) = NX
            CHARACTERS(INDEX, 1) = NY
            CHARACTERS(INDEX, 4) = DIR
            FOUNDDIR             = 1
        ELSE IF COLLISION THEN
            FOUNDCOL = 1
        END IF

        'GET THE NEXT DIR TO CHECK
        IF CHARACTERS(INDEX, 7) = 1 OR CHARACTERS(INDEX, 7) = 2 THEN
            DIR = (DIR + 1) MOD 4
        ELSE
            DIR = (DIR + 3) MOD 4
        END IF
    UNTIL DIR = STARTDIR

    IF FOUNDCOL = 0 THEN
        CHARACTERS(INDEX, 4) = ORGDIR
    END IF

    'CHECK IF THE PLAYER HIT THE CHAR
    IF SPRITE HIT(TARGET, INDEX) THEN
        COL = 1
    ELSE
        COL = 0
    END IF
END SUB

'***************************************
'MOVE A CHAR AND CHECK ITS POSITION
'INDEX - THE CHAR INDEX
'DOCHECKCOL - IF 1 COLLISIONS WILL BE CHECKED
'***************************************
SUB MOVECHAR(INDEX, DOCHECKCOL)
    'COPY THE CURRENT POSITION IN ORDER TO CALCULATE THE NEW ONE
    X = CHARACTERS(INDEX, 0)
    Y = CHARACTERS(INDEX, 1)

    'GET THE CELL ATTRIBUTES THE CHARACTER IS WALKING ON
    CX = (X + 3) \ 8
    CY = (Y + 3) \ 8

    'GET THE ATTRIBUTE ON BACKGROUND 0
    BG 0
    CC0 = CELL.C(CX, CY)

    'GET THE ATTRIBUTE ON BACKGROUND 1
    BG 1
    CC1 = CELL.C(CX, CY)

    'CHECK IF THE CHARACTER IS ABOVE THE WATER
    IF (CC1 = 2) AND ((CELL.A(CX, CY) AND 7) = 1) THEN
        CHARACTERS(INDEX, 5) = 1
    ELSE
        CHARACTERS(INDEX, 5) = 0
    END IF

    'CHECKS IF THE PLAYER CHARACTER HITS A SWITCH
    IF INDEX = 0 AND CC0 = 10 THEN
        BG 0

        'BARRIER SWITCH WAS HIT?
        IF ((CELL.A(CX, CY) AND 7) = 1) THEN
            'SET THE BARRIER SWITCH AS HIT
            ITEMS(1)         = 1
            BARRIERSWITCH(0) = CX
            BARRIERSWITCH(1) = CY
        END IF

        'FIRE SWITCH WAS HIT?
        IF ((CELL.A(CX, CY) AND 7) = 7) THEN
            'SET THE FIRE SWITCH AS HIT
            ITEMS(2)      = 1
            FIRESWITCH(0) = CX
            FIRESWITCH(1) = CY
        END IF
    END IF

    'CHECK IF THE PLAYER CHARACTER HITS THE TREASURE CHEST
    IF INDEX = 0 AND (CC0 = 32 OR CC1 = 32 OR CC0 = 33 OR CC1 = 33 OR CC0 = 48 OR CC1 = 48 OR CC0 = 49 OR CC1 = 49) THEN
        NEXTLEVEL = 1
        EXIT SUB
    END IF

    MULTIPLIER = 1.0
    
    'PLAYER IS MOVING AND FOUND A SPEED UP RING?
    IF INDEX = 0 AND ITEMS(5) = 1 THEN
        MULTIPLIER = 2
    END IF

    'CALCULATE THE NEW POSITION
    IF CHARACTERS(INDEX, 5) AND DOCHECKCOL THEN
        ADD X, CHARACTERS(INDEX, 2) * 0.5 * MULTIPLIER
        ADD Y, CHARACTERS(INDEX, 3) * 0.5 * MULTIPLIER
    ELSE
        ADD X, CHARACTERS(INDEX, 2) * MULTIPLIER
        ADD Y, CHARACTERS(INDEX, 3) * MULTIPLIER
    END IF

    'CHARACTER MOVED?
    IF CHARACTERS(INDEX, 0) = X AND CHARACTERS(INDEX, 1) = Y THEN
        EXIT SUB
    END IF

    COLLISION = 0

    'CHECK IF CHAR IS HITTING SOMETHING (DON'T CHECK IF PLAYER HIT 
    'STONE BECAUSE THIS COLLISION WILL BE CHECKED IN ANOTHER PLACE)
    IF (DOCHECKCOL) THEN
        CALL CHECKCOLLISION(INDEX, X, Y, INDEX <> 0, COLLISION)
    END IF

    'FOUND A COLLISION?
    IF COLLISION THEN
        CURY = CHARACTERS(INDEX, 1)

        'TRY TO RESOLVE ON THE X AXIS
        CALL CHECKCOLLISION(INDEX, X, CURY, INDEX <> 0, COLLISION)

        'NO LONGER IN COLLISION?
        IF COLLISION = 0 THEN
            CHARACTERS(INDEX, 0) = X
            EXIT SUB
        END IF

        CURX = CHARACTERS(INDEX, 0)

        'TRY TO RESOLVE ON THE Y AXIS
        CALL CHECKCOLLISION(INDEX, CURX, Y, INDEX <> 0, COLLISION)

        'NO LONGER IN COLLISION?
        IF COLLISION = 0 THEN
            CHARACTERS(INDEX, 1) = Y
            EXIT SUB
        END IF

        EXIT SUB
    END IF

    'UPDATE THE NEW POSITION
    CHARACTERS(INDEX, 0) = X
    CHARACTERS(INDEX, 1) = Y
END SUB

'***************************************
'GET THE TARGET DIRECTION
'INDEX - THE CHAR INDEX
'TARGET - THE TARGET INDEX
'[OUT] NX - THE NORMALIZED X DIR
'[OUT] NY - THE NORMALIZED Y DIR
'***************************************
SUB GETTARGETDIR(INDEX, TARGET, NX, NY)
    'GET THE TARGET AND CHAR POSITIONS AND CALCULATE THE VECTOR BETWEEN
    V1X = CHARACTERS(TARGET, 0)
    V1Y = CHARACTERS(TARGET, 1)
    V2X = CHARACTERS(INDEX,  0)
    V2Y = CHARACTERS(INDEX,  1)
    RX  = 0.0
    RY  = 0.0
    CALL VEC2SUB(V1X, V1Y, V2X, V2Y, RX, RY)

    'CALCULATE THE WALK DIRECTION TO THE PLAYER
    NX = 0.0
    NY = 0.0
    CALL VEC2NORMALIZE(RX, RY, NX, NY)
END SUB

'***************************************
'UPDATE CHARACTER LOOK AT DIRECTION
'INDEX - CHARACTER INDEX TO UPDATE
'NX - THE CHAR DIR VECTOR X COMPONENT
'NY - THE CHAR DIR VECTOR Y COMPONENT
'***************************************
SUB CHARLOOKAT(INDEX, NX, NY)
    R = 0.0

    'CALCULATE THE CHAR LOOK AT DIRECTION ON THE X AXIS
    CALL VEC2DOT(NX, NY, 1.0, 0.0, R)
    DX = ACOS(R)

    'CALCULATE THE CHAR LOOK AT DIRECTION ON THE Y AXIS
    CALL VEC2DOT(NX, NY, 0.0, 1.0, R)
    DY = ACOS(R)

    'UPDATE THE CHAR LOOK AT DIRECTION
    IF DX >= PI - (PI / 4) THEN
        CHARACTERS(INDEX, 4) = 2
    ELSE IF DX <= (PI / 4) THEN
        CHARACTERS(INDEX, 4) = 0
    ELSE IF DY >= (PI / 2) THEN
        CHARACTERS(INDEX, 4) = 3
    ELSE
        CHARACTERS(INDEX, 4) = 1
    END IF
END SUB

'***************************************
'CHECK COLLISIONS AROUND A COORDINATE
'INDEX - CHAR INDEX
'X - CELL X COORDINATE TO CHECK
'Y - CELL Y COORDINATE TO CHECK
'DOCHECKSTONE - IF 0 STONE COLLISION WILL BE IGNORED
'[OUT] COLLISION - IF 1 COLLISION WAS FOUND
'***************************************
SUB CHECKCOLLISION(INDEX, X, Y, DOCHECKSTONE, COLLISION)
    DIM CS(4)
    COLLISION = 0

    FOR I = 0 TO 1
        BG I

        CALL GETCELLSAROUND(X, Y, CS())

        IF I = 0 THEN
            'HIT A BARRIER?
            FOR J = 12 TO 17
                IF CS(0) = J OR CS(1) = J OR CS(2) = J OR CS(3) = J THEN
                    COLLISION = 1
                    EXIT SUB
                END IF
            NEXT J
        ELSE IF I = 1 THEN
            'HIT A WALL?
            IF CS(0) = 1 OR CS(1) = 1 OR CS(2) = 1 OR CS(3) = 1 THEN
                COLLISION = 1
                EXIT SUB
            END IF
        END IF
    NEXT I

    'CHECK IF THE CHAR HIT A STONE
    IF DOCHECKSTONE AND SPRITE HIT(INDEX, 20 TO 29) THEN
        'NOTHING ELSE TO DO IF THE CHAR IS ITSELF A STONE
        IF INDEX >= 20 AND INDEX <= 29 THEN
            COLLISION = 1
            EXIT SUB
        END IF

        FOR I = 20 TO 29
            CALL CHECKCHARHITSTONE(INDEX, I, COLLISION)

            'HIT THIS STONE?
            IF COLLISION THEN
                EXIT SUB
            END IF
        NEXT I
    END IF
END SUB

'***************************************
'GET THE CELLS AROUND A POSITION
'X - CELL X COORDINATE TO CHECK
'Y - CELL Y COORDINATE TO CHECK
'[OUT] CELLS - CELLS AROUND THE POSITION
'***************************************
SUB GETCELLSAROUND(X, Y, CELLS())
    'GET THE CELLS SURROUNDING THE CHAR (LEFT AND TOP, RIGHT AND TOP,
    'LEFT AND BOTTOM, AND RIGHT AND BOTTOM)
    CELLS(0) = CELL.C( X \ 8,       Y \ 8)
    CELLS(1) = CELL.C((X + 7) \ 8,  Y \ 8)
    CELLS(2) = CELL.C( X \ 8,      (Y + 7) \ 8)
    CELLS(3) = CELL.C((X + 7) \ 8, (Y + 7) \ 8)
END SUB

'***************************************
'CHECK IF A CHARACTER HITS A STONE
'CINDEX - CHARACTER INDEX
'SINDEX - STONE INDEX
'[OUT] COLLISION - IF 1 A COLLISION WAS FOUND
'***************************************
SUB CHECKCHARHITSTONE(CINDEX, SINDEX, COLLISION)
    COLLISION = 0

    'THE CHAR HITS THE STONE?
    IF NOT SPRITE HIT(CINDEX, SINDEX) THEN
        EXIT SUB
    END IF

    'CALCULATE THE DISTANCE BETWEEN THE CHAR AND THE STONE
    CHX = CHARACTERS(CINDEX, 0)
    CHY = CHARACTERS(CINDEX, 1)
    SX  = SPRITE.X(SINDEX)
    SY  = SPRITE.Y(SINDEX)
    DX  = 0.0
    DY  = 0.0
    CALL VEC2SUB(CHX, CHY, SX, SY, DX, DY)

    'CALCULATE THE CHAR-STONE DIRECTION
    NX = 0.0
    NY = 0.0
    CALL VEC2NORMALIZE(DX, DY, NX, NY)

    'CALCULATE THE CHAR RUNNING DIRECTION
    CX  = CHARACTERS(CINDEX, 2)
    CY  = CHARACTERS(CINDEX, 3)
    CNX = 0.0
    CNY = 0.0
    CALL VEC2NORMALIZE(CX, CY, CNX, CNY)

    'CALCULATE THE ANGLE BETWEEN CHAR RUNNING DIR AND CHAR-STONE DIR
    A = 0.0
    CALL VEC2DOT(NX, NY, CNX, CNY, A)

    'IF THE ANGLE IS TOO BIG, THE CHAR ISN'T RUNNING AGAINST THE STONE
    IF (A >= 0.0) THEN
        COLLISION = 1
    END IF
END SUB

'***************************************
'REMOVE THE BARRIER
'***************************************
SUB REMOVEBARRIER
    BG 0

    'ITERATE THROUGH LEVEL ITEMS
    FOR Y = 0 TO 9
        FOR X = 0 TO 9
            C = CELL.C(X + 5, Y + 3)

            'FOUND A BARRIER ITEM?
            IF C >= 12 AND C <= 17 THEN
                'REMOVE IT
                CELL X + 5, Y + 3, 0
            END IF
        NEXT X
    NEXT Y
END SUB

'***************************************
'COUNT AND CHECK THE TIME
'***************************************
SUB COUNTANDCHECKTIME
    'PLAYER FOUND A TIME STOP RING?
    IF ITEMS(3) = 1 THEN
        'IF SPEED UP MUSIC WAS PLAYING, PLAY THE NORMAL ONE INSTEAD,
        'BECAUSE NOW THE TIME IS INFINITE FOR THIS LEVEL
        IF PLAYMUSIC = 1 AND MUSIC(0) = 0 THEN
            STOP
            MUSIC(2)
        END IF

        EXIT SUB
    END IF

    'DECREASE THE TIME EVERY 50 FRAMES
    IF TIMER - TIMERSTART > 50 THEN
        TIMERSTART = TIMER
        DEC LEVELTIME

        'IF TIME IS MISSING, PLAY THE TIME RUNNING SOUND
        IF LEVELTIME = 9 AND PLAYMUSIC = 1 THEN
            MUSIC(0)
        ELSE IF LEVELTIME < 10 THEN
            CALL PLAYTIMERUNNING
        END IF
    END IF

    IF LEVELTIME = 0 THEN
        DOLOOSELIVE = 1
    END IF
END SUB

'***************************************
'SUBTRACT 2 VECTORS
'V1X - THE FIRST VECTOR X COMPONENT
'V1Y - THE FIRST VECTOR Y COMPONENT
'V2X - THE SECOND VECTOR X COMPONENT
'V2Y - THE SECOND VECTOR Y COMPONENT
'[OUT] RX - THE RESULT VECTOR X COMPONENT
'[OUT] RY - THE RESULT VECTOR Y COMPONENT
'***************************************
SUB VEC2SUB(V1X, V1Y, V2X, V2Y, RX, RY)
    RX = V2X - V1X
    RY = V2Y - V1Y
END SUB

'***************************************
'CALCULATE THE LENGTH OF A VECTOR
'VX - THE VECTOR X COMPONENT
'VY - THE VECTOR Y COMPONENT
'[OUT] LN - THE VECTOR LENGTH
'***************************************
SUB VEC2LENGTH(VX, VY, LN)
    LN = SQR((VX * VX) + (VY * VY))
END SUB

'***************************************
'NORMALIZE A 2D VECTOR
'VX - THE VECTOR X COMPONENT
'VY - THE VECTOR Y COMPONENT
'[OUT] NX - THE NORMALIZED VECTOR X COMPONENT
'[OUT] NY - THE NORMALIZED VECTOR Y COMPONENT
'***************************************
SUB VEC2NORMALIZE(VX, VY, NX, NY)
    LN = 0.0

    'CALCULATE THE VECTOR LENGTH
    CALL VEC2LENGTH(VX, VY, LN)

    'NO VECTOR LENGTH?
    IF LN = 0.0 THEN
        NX = 0.0
        NY = 0.0
        EXIT SUB
    END IF

    'NORMALIZE VECTOR (THUS VALUES WILL ALWAYS BE BETWEEN 0.0 AND 1.0)
    NX = (VX / LN)
    NY = (VY / LN)
END SUB

'***************************************
'CALCULATE DOT PRODUCT BETWEEN 2 VECTORS
'V1X - FIRST VECTOR X COORDINATE
'V1Y - FIRST VECTOR Y COORDINATE
'V2X - SECOND VECTOR X COORDINATE
'V2Y - SECOND VECTOR Y COORDINATE
'[OUT] R - DOT PRODUCT
'***************************************
SUB VEC2DOT(V1X, V1Y, V2X, V2Y, R)
    R = ((V1X * V2X) + (V1Y * V2Y))
END SUB

'***************************************
'CHECK IF 2 RECTANGLES ARE IN COLLISION
'R1X - FIRST RECT X POS IN PIXELS
'R1Y - FIRST RECT Y POS IN PIXELS
'R1W - FIRST RECT WIDTH IN PIXELS
'R1H - FIRST RECT HEIGHT IN PIXELS
'R2X - SECOND RECT X POS IN PIXELS
'R2Y - SECOND RECT Y POS IN PIXELS
'R2W - SECOND RECT WIDTH IN PIXELS
'R2H - SECOND RECT HEIGHT IN PIXELS
'[OUT] COLLISION - IF TRUE RECTS COLLIDE
'***************************************
SUB CHECKRECTCOL(R1X, R1Y, R1W, R1H, R2X, R2Y, R2W, R2H, COLLISION)
    IF R1X + R1W >= R2X THEN
        IF R1X <= R2X + R2W THEN
            IF R1Y + R1H >= R2Y THEN
                IF R1Y <= R2Y + R2H THEN
                    COLLISION = 1
                    EXIT SUB
                END IF
            END IF
        END IF
    END IF

    COLLISION = 0
END SUB

'***************************************
'DRAW THE LABELS
'***************************************
SUB DRAWLABELS
    'DRAW THE LABELS
    BG 0
    PAL 1
    CELL 1,  2, 130
    CELL 2,  2, 131
    CELL 1,  5, 132
    CELL 2,  5, 133
    CELL 1,  8, 134
    CELL 2,  8, 135
    CELL 1, 11, 136
    CELL 2, 11, 137
    CELL 17, 2, 128
    CELL 18, 2, 129
END SUB

'***************************************
'DRAW THE TIME
'***************************************
SUB DRAWTIME
    BG 0

    LOCATE 1, 3

    IF LEVELTIME < 10 THEN
        PAL 7
        PRINT "0"

        LOCATE 2, 3
        PRINT LEVELTIME
    ELSE
        PAL 1
        PRINT LEVELTIME
    END IF
END SUB

'***************************************
'DRAW LIVES
'***************************************
SUB DRAWLIVES
    BG 0
    PAL 4

    'CLEAR THE PREVIOUS DISPLAY
    BG FILL 1, 6 TO 2, 6 CHAR 0

    'DRAW THE LIVES
    IF LIVES > 0 THEN
        IF LIVES <= 2 THEN
            BG FILL 1, 6 TO LIVES, 6 CHAR 144
        ELSE
            CELL 1, 6, 144
            NUMBER 2, 6, LIVES, 1
        END IF
    END IF
END SUB

'***************************************
'DRAW THE COIN COUNT
'***************************************
SUB DRAWCOINCOUNT
    BG 0
    PAL 1

    LOCATE 1, 12

    IF COINCOUNT < 10 THEN
        PRINT "0"
        
        LOCATE 2, 12
        PRINT COINCOUNT
    ELSE
        PRINT COINCOUNT
    END IF
END SUB

'***************************************
'DRAW THE LEVEL
'***************************************
SUB DRAWLEVEL
    PAL 1
    LOCATE 1, 9

    IF LEVEL < 10 THEN
        PRINT "0"

        LOCATE 2, 9
        PRINT LEVEL
    ELSE
        PRINT LEVEL
    END IF
END SUB

'***************************************
'DRAW THE PLAYFIELD
'***************************************
SUB DRAWPLAYFIELD
    BG 1

    FOR Y = 0 TO 11
        FOR X = 0 TO 11
            'DO DRAW THE BORDERS?
            IF X = 0 OR Y = 0 OR X = 11 OR Y = 11 THEN
                'DRAW THE BORDERS
                PAL 0
                CELL X + 4, Y + 2, 1
            ELSE
                'READ THE NEXT CELL TO DRAW
                READ ITEM

                'DRAW THE CELL CONTENT
                IF ITEM = 0 THEN
                    'WALL
                    PAL 0
                    CELL X + 4, Y + 2, 1
                ELSE IF ITEM = 1 THEN
                    'WATER
                    PAL 1
                    CELL X + 4, Y + 2, 2
                ELSE IF ITEM >= 2 AND ITEM <= 5 THEN
                    'EARTH
                    PAL 2
                    CELL X + 4, Y + 2, ITEM
                ELSE IF ITEM >= 6 AND ITEM <= 9 THEN
                    'GRASS
                    PAL 3
                    CELL X + 4, Y + 2, ITEM - 4
                END IF
            END IF
        NEXT X
    NEXT Y
END SUB

'***************************************
'DRAW THE ITEMS
'***************************************
SUB DRAWITEMS
    BG 0

    STARTX    = 5
    STARTY    = 3
    FIRECOUNT = 0

    FOR Y = 0 TO 9
        FOR X = 0 TO 9
            'READ THE NEXT CELL TO DRAW
            READ ITEM

            IF ITEM = 1 THEN
                'KEY ITEM
                SPRITE 30 PAL 6
                SPRITE 30, (STARTX + X) * 8, (STARTY + Y) * 8, 8
            ELSE IF ITEM = 2 THEN
                'DOOR ITEM
                SPRITE 31 PAL 2
                SPRITE 31, (STARTX + X) * 8, (STARTY + Y) * 8, 6
            ELSE IF ITEM = 3 THEN
                'ROCK ITEM (MAX 5)
                IF STONECOUNT < 10 THEN
                    SI = 20 + STONECOUNT
                    SPRITE SI PAL 0
                    SPRITE SI, (STARTX + X) * 8, (STARTY + Y) * 8, 9
                    INC STONECOUNT
                END IF
            ELSE IF ITEM = 4 THEN
                'BARRIER SWITCH ITEM
                PAL 1
                CELL STARTX + X, STARTY + Y, 10
            ELSE IF ITEM >= 5 AND ITEM <= 10 THEN
                'BARRIER ITEMS
                PAL 1
                CELL STARTX + X, STARTY + Y, ITEM + 7
            ELSE IF ITEM = 11 THEN
                'FIRE SWITCH ITEM
                PAL 7
                CELL STARTX + X, STARTY + Y, 10
            ELSE IF ITEM = 12 THEN
                'FIRE OUTPUT
                PAL 0
                CELL STARTX + X, STARTY + Y, 18

                'FIRE SPRITE
                FIRES(FIRECOUNT, 0) = 1
                FIRES(FIRECOUNT, 1) = (STARTX + X) * 8
                FIRES(FIRECOUNT, 2) = (STARTY + Y) * 8
                FIRES(FIRECOUNT, 3) = 0

                INC FIRECOUNT
            ELSE IF ITEM = 13 THEN
                'TIME STOP RING ITEM
                SPRITE 32 PAL 4
                SPRITE 32, (STARTX + X) * 8, (STARTY + Y) * 8, 19
            ELSE IF ITEM = 14 THEN
                'INVINCIBILITY RING ITEM
                SPRITE 33 PAL 7
                SPRITE 33, (STARTX + X) * 8, (STARTY + Y) * 8, 19
            ELSE IF ITEM = 15 THEN
                'SPEED UP RING ITEM
                SPRITE 34 PAL 6
                SPRITE 34, (STARTX + X) * 8, (STARTY + Y) * 8, 19
            ELSE IF ITEM = 16 THEN
                'GUN ITEM
                SPRITE 35 PAL 0
                SPRITE 35, (STARTX + X) * 8, (STARTY + Y) * 8, 20
            ELSE IF ITEM = 17 THEN
                'COIN
                COINS(COINITEMCOUNT, 0) = 1
                COINS(COINITEMCOUNT, 1) = (STARTX + X) * 8
                COINS(COINITEMCOUNT, 2) = (STARTY + Y) * 8
                COINS(COINITEMCOUNT, 3) = 0

                INC COINITEMCOUNT
            ELSE IF ITEM = 18 THEN
                'EXTRA-LIVE ITEM
                SPRITE 36 PAL 7
                SPRITE 36, (STARTX + X) * 8, (STARTY + Y) * 8, 24
            ELSE IF ITEM = 19 THEN
                'TREASURE CHEST ITEM
                CALL DRAWCHEST(STARTX + X, STARTY + Y, 0, 0)
            END IF
        NEXT X
    NEXT Y
END SUB

'***************************************
'DRAW THE PLAYER
'***************************************
SUB DRAWPLAYER
    'IS PLAYER INVINCIBLE?
    IF ITEMS(4) = 1 THEN
        'DRAW IT IN ORANGE
        CALL DRAWCHAR(0, 64, 7, 0)
    ELSE
        'DRAW THE PLAYER WITH ITS DEFAULT COLOR
        CALL DRAWCHAR(0, 64, 4, 0)
    END IF
END SUB

'***************************************
'DRAW THE BULLET
'***************************************
SUB DRAWBULLET
    IF ITEMS(7) = 1 THEN
        CALL DRAWCHAR(9, 78, 6, 0)
    ELSE
        SPRITE OFF 9
    END IF
END SUB

'***************************************
'DRAW THE ENEMIES
'***************************************
SUB DRAWENEMIES
    'ITERATE THROUGH CHARACTERS
    FOR I = 1 TO 8
        IF CHARACTERS(I, 6) = 1 THEN
            'DRAW A ZOMBIE
            CALL DRAWCHAR(I, 66, 5, 0)
        ELSE IF CHARACTERS(I, 6) = 2 THEN
            'DRAW A GHOST
            CALL DRAWCHAR(I, 68, 0, 0)
        ELSE IF CHARACTERS(I, 6) = 3 THEN
            'DRAW A DEVIL
            CALL DRAWCHAR(I, 70, 6, 0)
        ELSE IF CHARACTERS(I, 6) = 4 THEN
            'DRAW A SPIRIT
            CALL DRAWCHAR(I, 72 + SPIRITINDEX / 3, 7, 1)

            SPIRITINDEX = (SPIRITINDEX + 1) MOD 9
        ELSE
            SPRITE OFF I
        END IF
    NEXT I
END SUB

'***************************************
'DRAW A CHARACTER
'INDEX - THE CHARACTER AND SPRITE INDEX
'CH - THE CHARACTER RESOURCE
'PA - THE PALETTE NUMBER
'IGNOREDIR - IF 1 CHAR DIR WILL BE IGNORED
'***************************************
SUB DRAWCHAR(INDEX, CH, PA, IGNOREDIR)
    SPRITE INDEX PAL PA

    IF IGNOREDIR = 0 THEN
        IF CHARACTERS(INDEX, 4) = 0 THEN
            SPRITE INDEX FLIP 0, 0
        ELSE IF CHARACTERS(INDEX, 4) = 1 THEN
            SPRITE INDEX FLIP 0, 0
            INC CH
        ELSE IF CHARACTERS(INDEX, 4) = 2 THEN
            SPRITE INDEX FLIP 1, 0
        ELSE IF CHARACTERS(INDEX, 4) = 3 THEN
            SPRITE INDEX FLIP 0, 1
            INC CH
        END IF
    END IF

    SPRITE INDEX, CHARACTERS(INDEX, 0), CHARACTERS(INDEX, 1), CH
END SUB

'***************************************
'DRAW THE FIRES
'***************************************
SUB DRAWFIRES
    FOR I = 0 TO 9
        'IS FIRE VISIBLE?
        IF FIRES(I, 0) = 1 THEN
            C = 0

            'ANIMATE THE FIRE
            IF FIRES(I, 3) >= 40 THEN
                FIRES(I, 3) = 0
            ELSE IF FIRES(I, 3) >= 30 THEN
                C = 1
            ELSE IF FIRES(I, 3) >= 20 THEN
                C = 2
            ELSE IF FIRES(I, 3) >= 10 THEN
                C = 1
            ELSE
                C = 0
            END IF
   
            INC FIRES(I, 3)

            'DRAW THE FIRE
            SPRITE I + 10 PAL 7
            SPRITE I + 10, FIRES(I, 1), FIRES(I, 2), 75 + C
        ELSE
            SPRITE OFF I + 10
        END IF
    NEXT I
END SUB

'***************************************
'DRAW THE COINS
'***************************************
SUB DRAWCOINS
    FOR I = 0 TO 9
        'IS COIN VISIBLE?
        IF COINS(I, 0) = 1 THEN
            C = 0

            'ANIMATE THE COIN
            IF COINS(I, 3) >= 40 THEN
                COINS(I, 3) = 0
            ELSE IF COINS(I, 3) >= 30 THEN
                C = 1
            ELSE IF COINS(I, 3) >= 20 THEN
                C = 2
            ELSE IF COINS(I, 3) >= 10 THEN
                C = 1
            ELSE
                C = 0
            END IF
   
            INC COINS(I, 3)

            'DRAW THE COIN
            SPRITE I + 37 PAL 7
            SPRITE I + 37, COINS(I, 1), COINS(I, 2), 21 + C
        ELSE
            SPRITE OFF I + 37
        END IF
    NEXT I
END SUB

'***************************************
'DRAW THE TREASURE CHEST
'X - X POSITION
'Y - Y POSITION
'OPENED - IF TRUE, CHEST IS OPENED
'FULL - IF TRUE, CHEST CONTENT IS FULL
'***************************************
SUB DRAWCHEST(X, Y, OPENED, FULL)
    START = 32

    'UPDATE THE TOP INDEX IF CHEST IS OPENED
    IF OPENED THEN
        START = 34
    END IF

    PAL 2

    'DRAW THE CHEST
    FOR I = 0 TO 1
        BG 1
        CELL X + I, Y, I + START

        BG 0
        CELL X + I, Y + 1, I + 48
    NEXT I

    'DRAW THE CHEST CONTENT
    IF OPENED AND FULL THEN
        BG 0
        PAL 7

        CELL X,     Y, 50
        CELL X + 1, Y, 51
    END IF
END SUB

'***************************************
'DRAW THE TREASURE GUARDIAN
'POPPING - IF TRUE, GUARDIAN IS POPPING
'SPEAKING - IF TRUE, GUARDIAN IS SPEAKING
'***************************************
SUB DRAWGUARDIAN(POPPING, SPEAKING)
    PAL 5

    IF POPPING THEN
        FOR I = 0 TO 1
            BG 0
            CELL I + 9, 7, I + 36

            BG 1
            CELL I + 9, 8, I + 52
        NEXT I
    ELSE 
        START = 52

        IF SPEAKING THEN
            START = 54
        END IF

        BG 0

        FOR I = 0 TO 1
            CELL I + 9, 6, I + 36
            CELL I + 9, 7, I + START
        NEXT I
    END IF
END SUB

'***************************************
'PLAY THE PLAYER STEP SOUND
'***************************************
SUB PLAYPLAYERSTEP
    IF PLAYFX = 0 THEN
        EXIT SUB
    END IF

    SOUND 1, 3, 15, 10
    ENVELOPE 1, 0, 2, 0, 0
    LFO 1, 15, 15, 12, 12
    LFO WAVE 1, 0, 0, 1, 0
    PLAY 1, 50, 10
END SUB

'***************************************
'PLAY THE PLAYER STEP IN WATER SOUND
'***************************************
SUB PLAYPLAYERSTEPWATER
    IF PLAYFX = 0 THEN
        EXIT SUB
    END IF

    SOUND 1, 3, 14, 0
    ENVELOPE 1, 4, 13, 0, 3
    LFO 1, 15, 15, 12, 12
    LFO WAVE 1, 3, 0, 1, 0
    PLAY 1, 50, 10
END SUB

'***************************************
'PLAY THE SWITCH PRESSED SOUND
'***************************************
SUB PLAYSWITCHPRESSED
    IF PLAYFX = 0 THEN
        EXIT SUB
    END IF

    SOUND 2, 2, 15, 2
    ENVELOPE 2, 0, 0, 1, 13
    LFO 2, 0, 0, 0, 0
    LFO WAVE 2, 1, 0, 0, 0
    PLAY 2, 90, 2
END SUB

'***************************************
'PLAY THE FOUND ITEM SOUND
'***************************************
SUB PLAYFOUNDITEM
    IF PLAYFX = 0 THEN
        EXIT SUB
    END IF

    SOUND 2, 1, 14, 0
    ENVELOPE 2, 0, 13, 15, 7
    LFO 2, 0, 0, 0, 0
    LFO WAVE 2, 2, 0, 1, 0
    PLAY 2, 50, 5
END SUB

'***************************************
'PLAY THE TIME RUNNING SOUND
'***************************************
SUB PLAYTIMERUNNING
    IF PLAYFX = 0 OR PLAYMUSIC = 1 THEN
        EXIT SUB
    END IF

    SOUND 1, 1, 14, 2
    ENVELOPE 1, 0, 13, 15, 0
    LFO 1, 5, 9, 10, 0
    LFO WAVE 1, 2, 0, 1, 0
    PLAY 1, 60, 1
END SUB

'***************************************
'PLAY THE DYING SOUND
'***************************************
SUB PLAYPLAYERDYING
    IF PLAYFX = 0 THEN
        EXIT SUB
    END IF

    SOUND 0, 1, 15, 0
    ENVELOPE 0, 0, 0, 15, 10
    LFO 0, 13, 15, 4, 10
    LFO WAVE 0, 0, 1, 0, 1
    PLAY 0, 60, 1
END SUB

'***************************************
'PLAY THE THUNDER SOUND
'***************************************
SUB PLAYTHUNDERSOUND
    SOUND 0, 3, 15, 0
    ENVELOPE 0, 0, 2, 15, 10
    LFO 0, 10, 12, 14, 8
    LFO WAVE 0, 3, 0, 0, 0
    PLAY 0, 60, 1
END SUB

'LEVELS DATA, WHERE:
'0 = WALL
'1 = WATER
'2 = EARTH (TYPE 1)
'3 = EARTH (TYPE 2)
'4 = EARTH (TYPE 3)
'5 = EARTH (TYPE 4)
'6 = GRASS (TYPE 1)
'7 = GRASS (TYPE 2)
'8 = GRASS (TYPE 3)
'9 = GRASS (TYPE 4)
'ITEMS DATA
'0  = NO ITEM
'1  = KEY
'2  = DOOR
'3  = ROCK (LEVEL MAY CONTAIN UNTIL 10 ROCKS MAX)
'4  = BARRIER SWITCH (ONE MAX PER LEVEL)
'5  = BARRIER, HORIZONTAL ITEM
'6  = BARRIER, VERTICAL ITEM
'7  = BARRIER, LEFT TOP CORNER
'8  = BARRIER, RIGHT TOP CORNER
'9  = BARRIER, LEFT BOTTOM CORNER
'10 = BARRIER, RIGHT TOP CORNER
'11 = FIRE SWITCH (ONE MAX PER LEVEL)
'12 = FIRE
'13 = TIME STOP RING
'14 = INVINCIBILITY RING
'15 = SPEED UP RING
'16 = GUN
'17 = COIN (LEVEL MAY CONTAIN UNTIL 10 COINS MAX)
'18 = EXTRA-LIVE (LEVEL MAY CONTAIN ONLY ONE)
'19 = CHEST (LEFT-TOP POSITION, WILL OCCUPY 4 CELLS)

LEVEL1:
    'LEVEL DATA
    DATA 2, 3, 3, 2, 2, 4, 5, 2, 5, 4
    DATA 5, 6, 9, 8, 7, 7, 8, 9, 6, 5
    DATA 4, 7, 6, 6, 8, 7, 6, 6, 7, 3
    DATA 4, 6, 7, 7, 8, 8, 7, 7, 7, 3
    DATA 2, 9, 8, 6, 7, 9, 8, 6, 7, 2
    DATA 3, 7, 6, 9, 8, 6, 7, 7, 6, 2
    DATA 3, 8, 7, 8, 7, 6, 8, 8, 7, 3
    DATA 2, 8, 6, 6, 7, 7, 6, 6, 7, 2
    DATA 2, 7, 8, 7, 6, 6, 6, 8, 6, 4
    DATA 3, 2, 2, 3, 5, 5, 4, 2, 4, 5

    'ITEMS DATA
    DATA 0, 0, 0, 0, 0, 0, 0, 0,  0,  0
    DATA 0, 0, 0, 0, 0, 0, 0, 0,  0,  0
    DATA 0, 0, 0, 0, 0, 0, 0, 1,  0,  0
    DATA 0, 0, 0, 0, 0, 0, 0, 0,  0,  0
    DATA 0, 0, 0, 0, 0, 0, 0, 0,  0,  0
    DATA 0, 0, 0, 0, 0, 0, 0, 0,  0,  0
    DATA 0, 0, 0, 0, 0, 0, 0, 0,  17, 0
    DATA 0, 0, 2, 0, 0, 0, 0, 17, 17, 0
    DATA 0, 0, 0, 0, 0, 0, 0, 0,  0,  0
    DATA 0, 0, 0, 0, 0, 0, 0, 0,  0,  0

    'PLAYER START POSITION AND DIRECTION
    DATA 1, 1, 3

    'LEVEL TIME
    DATA 30

    'ENEMIES COUNT (MAX 9 BY LEVEL)
    DATA 0

LEVEL2:
    'LEVEL DATA
    DATA 1, 1, 1, 1, 1, 1, 1, 1, 9, 4
    DATA 1, 1, 1, 1, 1, 1, 1, 1, 1, 7
    DATA 1, 1, 1, 1, 1, 1, 1, 1, 1, 1
    DATA 1, 1, 2, 4, 2, 3, 3, 1, 1, 1
    DATA 1, 1, 5, 9, 7, 9, 5, 1, 1, 1
    DATA 1, 1, 2, 7, 8, 6, 4, 1, 1, 1
    DATA 1, 1, 3, 6, 9, 7, 2, 1, 1, 1
    DATA 1, 1, 2, 5, 5, 3, 4, 1, 1, 1
    DATA 7, 1, 1, 1, 1, 1, 1, 1, 1, 1
    DATA 3, 6, 1, 1, 1, 1, 1, 1, 1, 1

    'ITEMS DATA
    DATA 0, 0,  0, 0, 0, 0, 0,  0, 0,  0
    DATA 0, 17, 0, 0, 0, 0, 0,  0, 0,  0
    DATA 0, 0,  0, 0, 0, 0, 0,  0, 0,  0
    DATA 0, 0,  0, 0, 0, 0, 17, 0, 0,  0
    DATA 0, 0,  0, 0, 3, 0, 0,  0, 0,  0
    DATA 0, 0,  0, 3, 1, 3, 0,  0, 0,  0
    DATA 0, 0,  0, 0, 3, 0, 0,  0, 0,  0
    DATA 0, 0,  0, 0, 0, 0, 0,  0, 0,  0
    DATA 0, 0,  0, 0, 0, 0, 0,  0, 17, 0
    DATA 2, 0,  0, 0, 0, 0, 0,  0, 0,  0

    'PLAYER START POSITION AND DIRECTION
    DATA 9, 0, 3

    'LEVEL TIME
    DATA 30

    'ENEMIES COUNT
    DATA 1

    'ENEMIES START POSITION, DIR AND TYPE. LAST VALUE IS FOR SPIRIT,
    '0 = CW, 1 = CCW, FOR OTHER MONSTERS SET IT TO 0
    DATA 6, 7, 0, 4, 0

LEVEL3:
    'LEVEL DATA
    DATA 7, 8, 7, 1, 1, 4, 5, 2, 5, 4
    DATA 8, 6, 9, 1, 1, 2, 8, 9, 6, 5
    DATA 9, 7, 6, 1, 1, 2, 6, 6, 7, 3
    DATA 1, 1, 1, 1, 1, 3, 5, 4, 3, 3
    DATA 1, 1, 1, 1, 1, 0, 0, 0, 0, 0
    DATA 3, 4, 5, 5, 2, 1, 1, 1, 1, 1
    DATA 3, 8, 7, 6, 4, 1, 1, 1, 1, 1
    DATA 2, 8, 6, 6, 4, 1, 1, 6, 7, 6
    DATA 2, 7, 8, 7, 3, 1, 1, 8, 6, 7
    DATA 3, 2, 2, 3, 5, 1, 1, 6, 8, 6

    'ITEMS DATA
    DATA 0, 0,  0, 0,  0, 0, 0, 0, 0, 0
    DATA 0, 2,  0, 0,  0, 0, 0, 0, 0, 0
    DATA 0, 0,  0, 0,  0, 0, 0, 0, 0, 0
    DATA 0, 0,  0, 0,  0, 0, 0, 0, 0, 0
    DATA 0, 0,  0, 0,  0, 0, 0, 0, 0, 0
    DATA 0, 0,  0, 0,  0, 0, 0, 0, 0, 0
    DATA 0, 17, 0, 0,  0, 0, 0, 0, 0, 0
    DATA 0, 0,  0, 0,  0, 0, 0, 0, 0, 0
    DATA 0, 17, 0, 17, 0, 0, 0, 0, 1, 0
    DATA 0, 0,  0, 0,  0, 0, 0, 0, 0, 0

    'PLAYER START POSITION AND DIRECTION
    DATA 7, 2, 4

    'LEVEL TIME
    DATA 30

    'ENEMIES COUNT
    DATA 2

    'ENEMIES START POSITION, DIR AND TYPE. LAST VALUE IS FOR SPIRIT,
    '0 = CW, 1 = CCW, FOR OTHER MONSTERS SET IT TO 0
    DATA 7, 7, 0, 3, 0
    DATA 6, 9, 0, 4, 3

LEVEL4:
    'LEVEL DATA
    DATA 2, 3, 2, 0, 2, 4, 5, 2, 5, 4
    DATA 5, 6, 7, 0, 7, 7, 8, 9, 6, 5
    DATA 4, 7, 0, 0, 0, 0, 0, 6, 7, 3
    DATA 4, 6, 7, 7, 8, 8, 7, 7, 7, 3
    DATA 0, 0, 0, 0, 0, 0, 0, 6, 7, 2
    DATA 3, 7, 6, 9, 8, 6, 7, 7, 6, 2
    DATA 3, 8, 7, 8, 7, 6, 8, 8, 7, 3
    DATA 2, 8, 6, 6, 7, 7, 6, 6, 7, 2
    DATA 2, 7, 8, 7, 6, 6, 6, 8, 6, 4
    DATA 3, 2, 2, 3, 5, 5, 4, 2, 4, 5

    'ITEMS DATA
    DATA 0,  0, 0,  0,  17, 0,  12, 0, 0, 0
    DATA 0,  0, 11, 0,  1,  0,  12, 0, 0, 0
    DATA 0,  0, 0,  0,  0,  0,  0,  0, 0, 0
    DATA 0,  0, 0,  0,  0,  0,  4,  0, 0, 0
    DATA 0,  0, 0,  0,  0,  0,  0,  0, 0, 0
    DATA 18, 0, 0,  0,  0,  0,  0,  0, 0, 0
    DATA 0,  0, 0,  0,  0,  0,  0,  0, 0, 0
    DATA 0,  0, 2,  0,  0,  17, 0,  7, 5, 5
    DATA 0,  0, 0,  0,  0,  0,  0,  6, 0, 0
    DATA 0,  0, 0,  17, 0,  0,  0,  6, 0, 0

    'PLAYER START POSITION AND DIRECTION
    DATA 1, 1, 3

    'LEVEL TIME
    DATA 30

    'ENEMIES COUNT (MAX 9 BY LEVEL)
    DATA 1

    'ENEMIES START POSITION, DIR AND TYPE. LAST VALUE IS FOR SPIRIT,
    '0 = CW, 1 = CCW, FOR OTHER MONSTERS SET IT TO 0
    DATA 9, 9, 0, 1, 0

LEVEL5:
    'LEVEL DATA
    DATA 2, 0, 3, 2, 2, 4, 5, 2, 5, 4
    DATA 5, 0, 9, 0, 7, 7, 0, 0, 0, 0
    DATA 4, 0, 6, 0, 8, 7, 6, 6, 7, 3
    DATA 4, 0, 7, 0, 8, 8, 7, 7, 7, 3
    DATA 2, 0, 8, 0, 7, 9, 0, 0, 0, 0
    DATA 3, 0, 6, 0, 8, 6, 7, 7, 6, 2
    DATA 3, 0, 7, 0, 7, 6, 8, 8, 7, 3
    DATA 2, 0, 6, 0, 7, 7, 0, 0, 0, 5
    DATA 2, 0, 8, 0, 6, 6, 6, 8, 6, 4
    DATA 3, 2, 2, 0, 5, 5, 4, 2, 4, 5

    'ITEMS DATA
    DATA 0,  0, 0,  0, 0,  0,  0,  0,  0,  0
    DATA 0,  0, 0,  0, 0,  0,  0,  0,  0,  0
    DATA 0,  0, 17, 0, 0,  0,  6,  0,  0,  1
    DATA 0,  0, 0,  0, 0,  0,  6,  0,  0,  0
    DATA 0,  0, 0,  0, 0,  0,  0,  0,  0,  0
    DATA 0,  0, 0,  0, 0,  0,  0,  0,  0,  4
    DATA 17, 0, 0,  0, 0,  0,  0,  0,  17, 0
    DATA 0,  0, 0,  0, 0,  12, 0,  0,  0,  0
    DATA 0,  0, 0,  0, 12, 2,  12, 0,  0,  0
    DATA 0,  0, 0,  0, 0,  12, 0,  0,  0,  11

    'PLAYER START POSITION AND DIRECTION
    DATA 0, 0, 3

    'LEVEL TIME
    DATA 30

    'ENEMIES COUNT (MAX 9 BY LEVEL)
    DATA 1

    'ENEMIES START POSITION, DIR AND TYPE. LAST VALUE IS FOR SPIRIT,
    '0 = CW, 1 = CCW, FOR OTHER MONSTERS SET IT TO 0
    DATA 9, 9, 0, 2, 0

LEVEL6:
    'LEVEL DATA
    DATA 2, 0, 3, 1, 2, 4, 5, 2, 5, 4
    DATA 5, 0, 0, 1, 1, 7, 8, 9, 6, 5
    DATA 1, 1, 1, 1, 1, 7, 6, 0, 7, 3
    DATA 4, 1, 1, 1, 1, 1, 7, 0, 7, 3
    DATA 2, 1, 1, 1, 1, 1, 1, 0, 7, 2
    DATA 3, 7, 1, 1, 1, 1, 1, 0, 6, 2
    DATA 3, 8, 1, 1, 1, 1, 8, 0, 7, 3
    DATA 2, 8, 6, 1, 1, 7, 6, 0, 7, 2
    DATA 0, 0, 0, 1, 1, 6, 6, 8, 6, 4
    DATA 7, 6, 6, 1, 5, 5, 4, 2, 4, 5

    'ITEMS DATA
    DATA 14, 0, 17, 0, 0, 0, 0,  0,  0, 0
    DATA 0,  0, 0,  0, 0, 0, 0,  0,  0, 0
    DATA 0,  0, 0,  0, 0, 0, 0,  1,  0, 0
    DATA 0,  0, 0,  0, 0, 0, 0,  0,  0, 0
    DATA 0,  0, 3,  3, 3, 3, 3,  0,  1, 0
    DATA 0,  0, 3,  0, 3, 0, 17, 0,  0, 0
    DATA 0,  0, 0,  0, 0, 0, 0,  0,  0, 0
    DATA 0,  0, 0,  0, 0, 0, 0,  0,  0, 17
    DATA 0,  0, 0,  0, 0, 0, 0,  0,  0, 0
    DATA 0,  2, 0,  0, 0, 0, 0,  0,  0, 0

    'PLAYER START POSITION AND DIRECTION
    DATA 8, 1, 3

    'LEVEL TIME
    DATA 30

    'ENEMIES COUNT (MAX 9 BY LEVEL)
    DATA 3

    'ENEMIES START POSITION, DIR AND TYPE. LAST VALUE IS FOR SPIRIT,
    '0 = CW, 1 = CCW, FOR OTHER MONSTERS SET IT TO 0
    DATA 9, 9, 0, 3, 0
    DATA 6, 9, 0, 4, 3
    DATA 5, 5, 0, 2, 3

LEVEL7:
    'LEVEL DATA
    DATA 2, 3, 3, 2, 2, 4, 5, 2, 5, 4
    DATA 5, 6, 9, 0, 7, 0, 8, 9, 6, 5
    DATA 4, 1, 0, 0, 0, 0, 0, 0, 7, 3
    DATA 4, 6, 1, 7, 1, 8, 1, 7, 7, 3
    DATA 2, 9, 0, 0, 0, 0, 0, 0, 7, 2
    DATA 3, 7, 6, 1, 8, 6, 7, 1, 6, 2
    DATA 3, 8, 0, 0, 0, 0, 0, 0, 7, 3
    DATA 2, 8, 0, 6, 0, 7, 0, 6, 7, 2
    DATA 2, 7, 8, 7, 6, 6, 6, 8, 1, 4
    DATA 3, 2, 1, 0, 5, 0, 4, 2, 4, 5

    'ITEMS DATA
    DATA 0, 0, 0, 0,  0,  0,  0,  0, 0, 0
    DATA 0, 0, 0, 0,  18, 0,  0,  0, 0, 0
    DATA 0, 0, 0, 0,  0,  0,  0,  0, 0, 0
    DATA 0, 0, 0, 0,  13, 0,  0,  0, 0, 0
    DATA 0, 0, 0, 0,  0,  0,  0,  0, 0, 0
    DATA 0, 0, 0, 0,  0,  0,  17, 0, 0, 0
    DATA 0, 0, 0, 0,  0,  0,  0,  0, 0, 0
    DATA 0, 0, 0, 17, 0,  17, 0,  2, 0, 0
    DATA 0, 0, 0, 0,  3,  0,  0,  0, 0, 0
    DATA 0, 0, 0, 0,  1,  0,  0,  0, 0, 0

    'PLAYER START POSITION AND DIRECTION
    DATA 1, 1, 3

    'LEVEL TIME
    DATA 25

    'ENEMIES COUNT (MAX 9 BY LEVEL)
    DATA 0

LEVEL8:
    'LEVEL DATA
    DATA 6, 7, 0, 2, 2, 4, 5, 2, 5, 4
    DATA 5, 0, 1, 1, 0, 0, 0, 0, 0, 8
    DATA 1, 0, 1, 0, 0, 7, 1, 1, 0, 3
    DATA 1, 0, 7, 0, 8, 6, 0, 1, 0, 8
    DATA 1, 0, 8, 0, 7, 9, 0, 1, 0, 7
    DATA 1, 0, 6, 0, 8, 6, 0, 7, 0, 8
    DATA 8, 0, 7, 0, 0, 0, 0, 8, 0, 3
    DATA 1, 0, 1, 6, 7, 7, 6, 1, 0, 6
    DATA 1, 0, 0, 0, 0, 0, 0, 0, 0, 4
    DATA 1, 1, 1, 3, 5, 1, 1, 1, 4, 1

    'ITEMS DATA
    DATA 0,  1, 0, 0, 0,  0,  0, 0,  0, 17
    DATA 0,  0, 0, 0, 0,  0,  0, 0,  0, 0
    DATA 17, 0, 0, 0, 0,  0,  0, 0,  0, 0
    DATA 0,  0, 0, 0, 18, 3,  0, 0,  0, 0
    DATA 0,  0, 0, 0, 0,  0,  0, 0,  0, 0
    DATA 0,  0, 0, 0, 2,  0,  0, 0,  0, 0
    DATA 0,  0, 0, 0, 0,  0,  0, 0,  0, 0
    DATA 0,  0, 0, 0, 0,  15, 0, 17, 0, 0
    DATA 0,  0, 0, 0, 0,  0,  0, 0,  0, 0
    DATA 0,  0, 0, 0, 0,  0,  0, 0,  0, 0

    'PLAYER START POSITION AND DIRECTION
    DATA 2, 1, 1

    'LEVEL TIME
    DATA 25

    'ENEMIES COUNT (MAX 9 BY LEVEL)
    DATA 0

LEVEL9:
    'LEVEL DATA
    DATA 2, 3, 3, 2, 2, 4, 5, 2, 5, 4
    DATA 5, 6, 9, 8, 7, 7, 8, 9, 6, 5
    DATA 4, 7, 6, 6, 8, 7, 6, 6, 7, 3
    DATA 4, 6, 7, 7, 8, 8, 7, 7, 7, 3
    DATA 2, 9, 8, 6, 7, 9, 8, 6, 7, 2
    DATA 3, 7, 6, 9, 8, 6, 7, 7, 6, 2
    DATA 3, 8, 7, 8, 7, 6, 8, 8, 7, 3
    DATA 2, 8, 6, 6, 7, 7, 6, 6, 7, 2
    DATA 2, 7, 8, 7, 6, 6, 6, 8, 6, 4
    DATA 3, 2, 2, 3, 5, 5, 4, 2, 4, 5

    'ITEMS DATA
    DATA 7, 5,  8,  12, 4,  17, 12, 7, 5,  8
    DATA 6, 0,  6,  0,  12, 12, 0,  6, 2,  6
    DATA 9, 5,  10, 0,  0,  0,  0,  9, 5,  10
    DATA 0, 0,  0,  0,  0,  0,  0,  0, 0,  0
    DATA 0, 0,  0,  0,  0,  0,  0,  0, 11, 0
    DATA 0, 17, 0,  0,  0,  0,  0,  0, 0,  0
    DATA 0, 0,  0,  0,  0,  0,  0,  0, 0,  0
    DATA 7, 5,  8,  0,  0,  0,  0,  7, 5,  8
    DATA 6, 1,  6,  0,  12, 12, 0,  6, 0,  6
    DATA 9, 5,  10, 12, 17, 16, 12, 9, 5,  10

    'PLAYER START POSITION AND DIRECTION
    DATA 4, 5, 3

    'LEVEL TIME
    DATA 20

    'ENEMIES COUNT (MAX 9 BY LEVEL)
    DATA 2

    'ENEMIES START POSITION, DIR AND TYPE. LAST VALUE IS FOR SPIRIT,
    '0 = CW, 1 = CCW, FOR OTHER MONSTERS SET IT TO 0
    DATA 1, 1, 3, 1, 0
    DATA 8, 8, 1, 3, 3

LEVEL10:
    'LEVEL DATA
    DATA 2, 3, 3, 0, 2, 4, 5, 2, 5, 4
    DATA 5, 6, 9, 8, 7, 0, 8, 9, 0, 5
    DATA 4, 0, 6, 0, 8, 7, 0, 6, 7, 0
    DATA 4, 6, 7, 7, 8, 8, 7, 7, 7, 3
    DATA 2, 0, 8, 6, 0, 9, 8, 0, 7, 2
    DATA 3, 7, 6, 9, 8, 6, 7, 7, 6, 0
    DATA 3, 8, 0, 8, 7, 0, 8, 8, 7, 3
    DATA 0, 0, 6, 6, 0, 7, 6, 6, 7, 2
    DATA 2, 7, 8, 7, 6, 6, 6, 8, 6, 0
    DATA 3, 2, 2, 3, 5, 5, 0, 2, 4, 5

    'ITEMS DATA
    DATA 0,  0, 0, 0, 0, 0, 1, 0,  0, 0
    DATA 0,  0, 0, 0, 0, 0, 0, 0,  0, 0
    DATA 0,  0, 0, 0, 0, 0, 0, 17, 0, 0
    DATA 0,  0, 0, 0, 0, 0, 0, 0,  0, 0
    DATA 0,  0, 0, 0, 0, 0, 0, 0,  0, 0
    DATA 17, 0, 0, 0, 0, 0, 0, 0,  0, 0
    DATA 0,  0, 0, 0, 0, 0, 0, 0,  0, 0
    DATA 0,  0, 2, 0, 0, 0, 0, 17, 0, 0
    DATA 0,  0, 0, 0, 0, 0, 0, 0,  0, 0
    DATA 0,  0, 0, 0, 0, 0, 0, 0,  0, 0

    'PLAYER START POSITION AND DIRECTION
    DATA 1, 1, 3

    'LEVEL TIME
    DATA 20

    'ENEMIES COUNT (MAX 9 BY LEVEL)
    DATA 1

    'ENEMIES START POSITION, DIR AND TYPE. LAST VALUE IS FOR SPIRIT,
    '0 = CW, 1 = CCW, FOR OTHER MONSTERS SET IT TO 0
    DATA 8, 8, 3, 2, 0

LEVEL11:
    'LEVEL DATA
    DATA 2, 3, 3, 2, 2, 4, 5, 2, 5, 4
    DATA 5, 6, 9, 8, 7, 7, 8, 9, 6, 5
    DATA 4, 7, 6, 6, 8, 7, 6, 6, 7, 3
    DATA 4, 6, 7, 7, 8, 8, 7, 7, 7, 3
    DATA 2, 9, 8, 6, 7, 9, 8, 6, 7, 2
    DATA 3, 7, 6, 9, 8, 6, 7, 7, 6, 2
    DATA 3, 8, 7, 8, 7, 6, 8, 8, 7, 3
    DATA 2, 8, 6, 6, 7, 7, 6, 6, 7, 2
    DATA 2, 7, 8, 7, 6, 6, 6, 8, 6, 4
    DATA 3, 2, 2, 3, 5, 5, 4, 2, 4, 5

    'ITEMS DATA
    DATA 17, 6, 0,  0,  0,  0,  0,  0,  6,  1
    DATA 5, 10, 0,  7,  5,  5,  0,  0,  9,  5
    DATA 0, 0,  7,  10, 18, 0,  0,  0,  0,  0
    DATA 5, 5,  10, 7,  5,  5,  8,  7,  8,  0
    DATA 0, 0,  0,  9,  5,  8,  6,  17, 6,  0
    DATA 0, 0,  0,  0,  4,  6,  6,  17, 6,  0
    DATA 0, 5,  5,  7,  5,  10, 6,  9,  10, 0
    DATA 0, 0,  0,  9,  5,  5,  10, 0,  0,  0
    DATA 5, 8,  0,  0,  0,  0,  0,  0,  7,  5
    DATA 2, 6,  0,  0,  7,  5,  5,  8,  6,  13

    'PLAYER START POSITION AND DIRECTION
    DATA 2, 1, 3

    'LEVEL TIME
    DATA 15

    'ENEMIES COUNT (MAX 9 BY LEVEL)
    DATA 0

LEVEL12:
    'LEVEL DATA
    DATA 2, 3, 3, 2, 2, 4, 5, 2, 5, 4
    DATA 5, 6, 9, 8, 7, 7, 8, 9, 6, 5
    DATA 4, 7, 8, 0, 0, 0, 0, 8, 7, 3
    DATA 4, 6, 0, 7, 8, 8, 7, 0, 7, 3
    DATA 2, 9, 0, 6, 7, 9, 8, 6, 7, 2
    DATA 3, 7, 0, 9, 8, 6, 7, 7, 6, 2
    DATA 3, 8, 0, 8, 7, 6, 8, 0, 7, 3
    DATA 2, 8, 6, 0, 0, 0, 0, 7, 7, 2
    DATA 2, 7, 8, 7, 6, 6, 6, 8, 6, 4
    DATA 3, 2, 2, 3, 5, 5, 4, 2, 4, 5

    'ITEMS DATA
    DATA 0,  0,  0,  0,  0,  0,  0, 0,  0, 0
    DATA 0,  0,  0,  0,  0,  0,  0, 0,  0, 0
    DATA 0,  11, 0,  0,  0,  0,  0, 16, 0, 0
    DATA 0,  0,  0,  17, 0,  13, 0, 0,  0, 0
    DATA 0,  0,  0,  0,  19, 0,  0, 12, 0, 0
    DATA 0,  0,  0,  0,  0,  0,  0, 12, 0, 0
    DATA 0,  0,  0,  14, 0,  0,  0, 0,  0, 0
    DATA 0,  0,  15, 0,  0,  0,  0, 17, 0, 0
    DATA 0,  0,  0,  0,  0,  0,  0, 0,  0, 0
    DATA 17, 0,  0,  0,  0,  0,  0, 0,  0, 0

    'PLAYER START POSITION AND DIRECTION
    DATA 9, 9, 1

    'LEVEL TIME
    DATA 25

    'ENEMIES COUNT (MAX 9 BY LEVEL)
    DATA 4
    
    'ENEMIES START POSITION, DIR AND TYPE. LAST VALUE IS FOR SPIRIT,
    '0 = CW, 1 = CCW, FOR OTHER MONSTERS SET IT TO 0
    DATA 1, 1, 3, 4, 1
    DATA 8, 8, 3, 4, 0
    DATA 9, 0, 3, 4, 0
    DATA 0, 9, 3, 4, 1

#1:MAIN PALETTES
003F2A15002F0B0700382410002E0804
003F3A1B001A3E20003D2F0B003E3830

#2:MAIN CHARACTERS
00000000000000000000000000000000
FF81BDA5A5BD81FF017F475F5F7F7FFF
0000000000000000FFFFFFFFFFFFFFFF
0000042000100000FFFFFFFFFFFFFFFF
0010042000140000FFFFFFDFFFFBFFFF
0054042A00548200FFFBFFD5FFFB7FFF
3C56D5D5D5D5D5D5003C7E7E7E7A7E7E
3C7EFFFFFFFFE7FF003C7E7E7E7E7E42
0040A0BFA54500000000000000000000
182456C7D54E341800182C3B7F361C18
FF8199A5A59981FF017F675F5F7F7FFF
FF8199BDBD9981FF017F67475F7F7FFF
000099DBDB9900000000FF2424FF0000
3C18003C3C00183C24243C24243C2424
0000040D1D3C00180000070A12233C24
000020B0B83C00180000E05048C43C24
18003C1D0D040000243C23120A070000
18003CB8B0200000243CC44850E00000
FFD5ABD5ABD5ABFF017F7F7F7F7F7FFF
1800182442422418183C000000000000
00003F00202040400040007F60E0C0C0
18101010101010001818181818181818
10183C3C3C3C18181800282828281800
10385A5A5A5A1C1818246C6C6C6C3800
006CBEDE7C381000006CFEBE5C381000
FFEDB7DBEDB7DBFF00375B6D375B6DFF
FFB7DBEDB7DBEDFF005B6D375B6D37FF
FFDBEDB7DBEDB7FF006D375B6D375BFF
03060C3C64C41C100002080420401400
070C081A16F222640408001002D00024
031F316644CC88180211002400440008
00000000000000000000000000000000
FFC0C0C0C0C3FFFFFF7F7F7F7F7F7E02
FF03030303C3FFFFFFFEFEFEFEFE7E40
037F7F7F7F7F7FFFFCFFFFFFFFFFFF02
C0FEFEFEFEFEFEFF3FFFFFFFFFFFFF40
070C1810101C1D100003070F0F03020F
F0180C040464640C00E0F0F8F89898F0
070C1810101C1D100003070F0F03020F
F0180C040464640C00E0F0F8F89898F0
00000000000000000000000000000000
00000000000000000000000000000000
00000000000000000000000000000000
00000000000000000000000000000000
00000000000000000000000000000000
00000000000000000000000000000000
00000000000000000000000000000000
00000000000000000000000000000000
C3C0C0C0C0F0FF007F7F7F7F7F7F0F60
C3030303030FFF00FEFEFEFEFEFEF006
0000000000097D5F0000000000005224
0000000000F0DC7C0000000000902492
180A0F00040300000705000503000000
3CB8F00040800000C040004080000000
180A0F00000403000705000005030000
3CB8F00000408000C040000040800000
00000000000000000000000000000000
00000000000000000000000000000000
00000000000000000000000000000000
00000000000000000000000000000000
00000000000000000000000000000000
00000000000000000000000000000000
00000000000000000000000000000000
00000000000000000000000000000000
00183800003818001C2677FFFF77261C
0000246666000000183C7EBD99FF7E3C
0C1E7BDFDF7B1E0C00000C60600C0000
183C247EFFDB7E3C0018180024240000
60785FFEDC7830209044300132042850
183FEB7E3E1C0C040182549540221008
0C62F1F0F0F1620C7C9E6F0F0F6F9E7C
3C7E7E3C8181422442A5A5C3FFFF7E3C
910018BC3D180089914A248241245289
2480193C3C9801242494410240822924
4801983C3C1980124829824002419412
04161C7AF63C5A30041A22448A426628
000814363C70100000081C2A44483000
000018382C1800000000182434080000
000000C03F3F000000003F3FFF3F0000
080830303030303010103C3C3C3C3C3C
00101840401810001C2E77BFBF772E1C
001800662400000018247EBDDBFF7E3C
00101840401810001C2E77BBAF772E1C
001800662400000018247EB5DBEF7E3C
00101840401810001C2E57BBAF732E0C
001800662400000018245EB4DBEB7E3C
0010184040181000142E56BBAF332E0C
001800662400000018205EB45BEB7E1C
0010180040181000142C56BBAE332E08
000800662400000018205EB45BEA3E14
0010180040181000102454BB2E332408
000800662400000010205EB4196A1C14
0010180040181000102454922C132408
000800662400000010204AB4096A1404
00001800401810001020541224122408
000800262400000000204AB4012A1400
00001000001810000020541204122008
00000026040000000020423401281400
00000000001800000020441004122008
00000004040000000020421401280400
00000000001000000020040004102008
00000004000000000000420401280000
00000000001000000020000004100000
00000004000000000000400400080000
00000000001000000000000000100000
00000004000000000000000400000000
18EC4E21214EEC1818F4723F3F72F418
42665A81E766241842667EFF995A3C18
182C4EE1E14E2C18183472FFFF723418
183C5A81E7662418183C7EFF995A3C18
18245ABDBD5A2418183C66C3C3663C18
00000000000000000000000000000000
00000000660018003C7EFFFF997E2418
0000002466001800007EFFDBBD7E2418
00000024660018000000FFDBBD7E2418
0000002466001800000000DBBD7E2418
000000006600180000000000BD7E2418
000000000000180000000000007E2418
00000000000018000000000000002418
00000000000000000000000000000018
00246666662400003C7EFF99BD7E3C18
00246600000000003C7EFFFFFF7E3C18
00246666662400183C7EFF99BD7E3C00
00000066662418003C7EFF99BD7E2418
00000000660018003C7EFFFFBD7E2418
00000000662400003C7EFFFF997E3C18
00181C02021C18003864EEFDFDEE6438
78FCFCFC780000EE064B4A02067FFFEE
00DD000048E900000022494949E90000
00AB0A0021EF0000000030AA29EF0000
00370000121700000008121212170000
00561000405E000000806456545E0000
005A0200497D00000004484A497D0000
00B60400023E00000040A0B4223E0000
005A0200517D00000004505A517D0000
00FCA40024360000000000B424360000
00FB100095CB00000004859595CB0000
00EB220039AF00000004083B39AF0000
00000000000000000000000000000000
00000000000000000000000000000000
00000000000000000000000000000000
00000000000000000000000000000000
00000000000000000000000000000000
00000000000000000000000000000000
00000066662400003C7EFF99BD7E3C18
07070000000101010000010101010101
F7F7000000BEB6B60000B6B6BEBEB6B6
FFFF000000C0F0F00000C0E0E0C0F0F0
FFFF000000ECCFCF0000CCCCECECCFCF
FFFF000000DFD9D90000DBDBDFDFD9D9
FFFF00000036B2BE000030303636B2BE
FFFF000000CDFDFD0000CDCDCDCDFDFD
FFFF000000B6B7B70000B6B7B7B6B7B7
F3F300000037B7B30000333B3B37B7B3
00000000000000000000000000000000
00000000000000000000000000000000
00000000000000000000000000000000
00000000000000000000000000000000
00000000000000000000000000000000
00000000000000000000000000000000
38367E717A747800384E818F868C7800
07070000000000000000000000000000
FFFF0000000000000000000000000000
FFFF0000006F6C6C00006D6D6F6F6C6C
FFFF00000098DEDE0000989C9C98DEDE
FFFF000000F8DBDB0000DBDBF8F8DBDB
FBFB000000DBDFDF00001B1BDBDBDFDF
FFFF0000007C666600006C6C7C7C6666
FFFF000000C0F0F00000C0E0E0C0F0F0
FFFF0000000000000000000000000000

#15:MAIN THEME
0E00D03008FFCC0058288084002F8000
12008060080F50000100C80008040000
2F00508E181CFF003800606000000000
21004068120B30002400418A10372000
0800000F000000000800000F00000000
0800000F000000000800000F00000000
0800000F000000000800FBDF128FF000
1F0000DF14FDA4000F0000DF13FFA400
808103030419C0404040401B9C40401B
1C40401B1F40401E1FC0401E1D224040
202340402140C0402426C04024254040
40404040404040404040404040404040
40404040404040404040404040404040
40404040404040404040404040404040
40404040404040404040404040404040
40404040404040404040404040404040
40404040404040404040404040404040
40404040404040404040404040404040
40404040404040404040404040404040
40404040404040404040404040404040
40404040404040404040404040404040
40404040404040404040404040404040
40404040404040404040404040404040
40404040404040404040404040404040
2608000000002D080000000032080000
00002608000000002D08000000003208
000000002608000000002D0800000000
3208000000002608000000002D080000
00003208000000002208000000002908
000000002408000000002B0800000000
39080000000000000000000000000000
00000000000000000000000000000000
00000000000000000000000000000000
00000000000000000000000000000000
00000000000000003508000000000000
00000000300800000000000000000000
190F0000000000000000000000000000
00000000000000000000000000000000
00000000000000000000000000000000
1B0F0000000000000000000000000000
00000000000000000000000000000000
00000000180F00000000000000000000
3E08000000003E08003E08003E080000
00003E08003E08003E08000000003E08
003E08003E08000000003E08003E0800
3E08000000003E08003E08003E080000
00003E08003E08003A08000000003A08
003C08000000003C08003C08003E0800
2B1F0000000000000000000000000037
1F00000000000000000000000000341F
00000000000000000000000000321F00
341F00321F0000000000000000000000
0000301F00321F00301F000000000000
00000000000000000000000000000000
1B2FE81B2F000000001B2F001C2F0000
00001B2F001B2F00000000202F001B2F
001B2F001E2F001B2F001C2F001B2F00
1B2F001B2F000000001B2F001C2F0000
00001B2F001B2F00000000202F001B2F
001B2F001E2F001B2F001C2F001B2F00
337800000000000000FF000000000000
00002E7800000000000000FF00000000
00000000337800000000000000000000
31780000000030780000000000000000
00002E7800000000000000FF00000000
000000002C7800000000000000000000
190F0000000000000000000000000000
0000000000000000FF00000000000000
00000000000000000000000000000000
190F0000000000000000000000000000
0000000000000000FF00000000000000
00000000000000000000000000000000
4278003F78003A78003678003378002E
78002A7800277800FF00000000000000
00000000000000000000000000000000
00000000000000000000000000000000
00000000000000000000000000000000
00000000000000000000000000000000
1E2F001E2F001E2F00000000192F0000
0000192F001E2F000000001F2F000000
001F2F000000001F2F000000001F2F00
1E2F001E2F001E2F00000000192F0000
0000192F001E2F000000001F2F000000
001F2F000000001F2F001A2F001C2F00
36780000000000000037780000000000
00003678000000000000003778000000
00000000367800000000FF0000000000
2A78000000000000002B780000000000
00002C78000000000000002D78000000
000000002E78000000002F7800000000
2E7800000000000000FF000000000000
00002A7800000000000000FF00000000
00000000257800000000000000000000
277800000000000000000000FF000000
00000000002C78000000000000002D78
00000000317800000000FF0000000000
36780000000000000037780000000000
00003678000000000000003778000000
00000000367800000000FF0000000000
2A78000000000000002B780000000000
00003078000000000000002F78000000
000000002E78000000002D7800000000
1E2F00000000192F000000001E2F0000
0000192F001C2F000000001C2F001B2F
00000000192F00000000172F00000000
152F00152F00000000172F00172F0000
0000192F00192F000000001C2F001C2F
000000001B2F00000000192F00000000
36780000000000000038780000000000
0000397800000000000000FF00000000
00000000000000000000000000000000
34780000000000000033780000000000
00003178000000000000002F78000000
00000000317800000000FF0000000000
36780000000000000038780000000000
0000397800000000000000000000FF00
00000000000000000000000000000000
2D78000000000000002F780000000000
00003178000000000000003478000000
00000000317800000000FF0000000000
33780000000000000000000000000000
0000000000000000000000FF00000000
00000000000000000000000000000000
00000000000000000000000000000000
00000000000000000000000000000000
00000000000000000000000000000000
1B2F001B2F000000001B2F001C2F0000
00001B2F001B2F00000000202F001B2F
000000001C2F000000001C2F00000000
1B2F001B2F00000000162F00162F0000
0000172F00172F00000000122F00122F
00000000122F00000000122F00000000
1B2F001B2F000000000000001B2F0000
00000000000000001B2F000000000000
000000001B2F00000000000000000000
122F00122F000000000000000F2F0000
00000000000000001B2F000F2F000000
000000001B2F000F2F00000000000000
1B0FD000000000000000000000000000
0000000000000000120F000000000000
00000000000000000000000000000000
190F0000000000000000000000000000
0000000000000000140F000000000000
00000000000000000000FF0000000000
2A7800000000000000000000FF000000
00000000000000002E78000000000000
00000000FF0000000000000000000000
2C780000000000000000000025780000
00000000000000002778000000000000
00000000FF0000000000000000000000
2E7800000000000000000000FF000000
00000000000000003178000000000000
00000000FF0000000000000000000000
3678000000000000000000003A780000
00000000000000003378000000000000
00000000FF0000000000000000000000
416F00000000356F000000003C6F0000
0000416F00000000000000FF00000000
00000000000000000000000000000000
436F00000000376F00000000446F0000
0000466F00000000000000FF00000000
00000000000000000000000000000000
3D6F00000000316F00000000FF000000
00003D6F00000000316F00000000FF00
00000000000000000000000000000000
436F00000000436F00000000446F0000
0000436F000000003F6F000000000000
00FF0000000000000000000000000000
1C0F0100000200000100000200000100
00020000010000020000000000000000
01000002000001000002000001000000
00000100000200000100000200000100
0002000001000002200F000000000000
010000021B0F01000002000001000000
241F000000000000000000000000001C
1F00000000000000000000000000181F
000000000000000000000000002D1F00
301F002D1F0000000000000000000000
00002B1F002D1F002B1F030000000000
00000000000000000000000000000000
251801291A02251C01251C02291C0125
1C02291A012518020000000000002518
01291A02251C01251A02291801000000
271801271A022C1C01271C022C1C012C
1C02271A012C18020000000000002718
012C1A02271C01271A022C1801000000
262F00000000000000000000322F0000
0000000000000000262F000000000000
00000000322F00000000000000000000
262F00000000000000000000322F0000
0000000000000000262F000000000000
00000000322F00000000000000000000
342F00000000000000352F00352F0000
0000000000000000000000000000372F
00000000392F00000000000000000000
342F00000000372F00000000352F0000
0000000000000000322F000000000000
00000000000000000000000000000000
2921000000002A22000000002E230000
00002924000000002A25000000002E26
000000002927000000002A2800000000
2E2900000000292A000000002A2B0000
00002E2C00000000292D000000002A2E
000000002E2F00000000292F00000000
212F000000000000000000002D2F0000
0000000000000000212F000000000000
000000002D2F00000000000000000000
212F000000000000000000002D2F0000
0000000000000000212F000000000000
000000002D2F00000000000000000000
2D2F000000002D2F000000002D2F0000
0000000000000000372F00000000342F
00000000352F00000000000000000000
2D2F0000000000000000000000000000
00000000000000000000000000000000
00000000000000000000000000000000
2A2F000000002E2F00000000292F0000
00002A2F000000002E2F00000000292F
000000002A2F000000002E2F00000000
272F00000000292F000000002C2F0000
0000272F00000000292F000000002C2F
00000000272F00000000292F00000000
2C2F00000000272F00000000292E0000
00002C2D00000000272C00000000292B
000000002C2A00000000272A00000000
2928000000002C270000000027260000
00002925000000002C24000000002723
000000002922000000002C2100FF0000
00000000000000000000000000000000
00000000000000000000000000000000
00000000000000000000000000000000
00000000000000000000000000000000
00000000000000002734000000000000
00000000000000000000000000000000
00000000000000000000000000000000
00000000000000000000000000000000
00000000000000000000000000000000
25340000000000000000000000000000
00000000000000000000000000000000
00000000000000000000000000000000
2D31A200000000000000000000000000
00000000000000000000000000000000
000000000000000000000000A2000000
00000000000000000000000000000000
00000000000000000000000000000000
00000000000000000000000000FF0000
2934000000000000000000002B340000
00002C34000000003534000000003434
00000000333400000000323400000000
31340000000000000000000000000000
00000000000000000000000000000000
00000000000000000000000000000000
1C1F00000000211F00000000281F0000
0000231F00000000241F00000000201F
00000000211F000000001C1F00000000
1C1F00000000211D00000000281B0000
00002319000000002417000000002015
000000002113000000001C1100FF0000

