PROGRAM HEROQUEST(INPUT,OUTPUT);


USES GRAPH,CRT;

CONST
 NUMTX=14;
 NUMTY=12;
 PLACEX=0;
 PLACEY=0;


TYPE
 GRAPHICS=ARRAY[-10..125] OF POINTER;
 DUNGEON=RECORD
    TILES:ARRAY[1..100,1..100] OF SHORTINT;
    VISIBLE:ARRAY[1..100,1..100] OF BOOLEAN;
    ROOM:ARRAY[1..100,1..100] OF SHORTINT;
    TRAP:ARRAY[1..100,1..100] OF SHORTINT;


   END;

 ITEMRECORD=RECORD
     EQUIPPED:BOOLEAN;
     NAME:STRING[15];
     ID:BYTE;
     SLOTS:ARRAY[1..8]OF SHORTINT;
  END;


 CHESTRECORD=RECORD

   ITEM:ARRAY[1..5]OF ITEMRECORD;
   X,Y:SHORTINT;
   NUM:SHORTINT;
   OPEN:BOOLEAN;
 END;


 ROOMREC=RECORD

   ENTERED:BOOLEAN;
 END;

 ROOMARRAY=ARRAY[1..50] OF ROOMREC;


 CHARSHEET=RECORD
   ITEMS:ARRAY[0..10] OF ITEMRECORD;
   HITPOINTS:INTEGER;
   MAXHP:INTEGER;
   GOLD:INTEGER;
   CHARID:INTEGER;
   XPOS,YPOS,SX,SY,XOLD,YOLD:INTEGER;
   FACING:INTEGER;
   INVINCE:BYTE;
   AC:INTEGER;
   NAME:STRING[15];
   NUMITEMS:BYTE;
   READY:BYTE;
   WORN:BYTE;
   SHIELD:BYTE;
   ALIVE:BOOLEAN;
   EXP:INTEGER;
   KEYS:BYTE;
   OLDT,NEWT:INTEGER;
   MAGIC:BOOLEAN;
   SPEED:BYTE;
   RSPEED:BYTE;
   SDELAY:BYTE;
   INACTIVE:BYTE;
   LEVEL:INTEGER;
   SP:INTEGER;
   POISON:BOOLEAN;
   EXIT:BOOLEAN;
 END;

 MARECORD=RECORD
   ATTACK:SHORTINT;
   LONG:BOOLEAN;
   APIC1,APIC2,APIC3,APIC4:BYTE;
   TOA:SHORTINT;
   DTYPE:BYTE;
 END;

 ATTACKARRAY=ARRAY[1..5]OF MARECORD;


 MONSTERSHEET=RECORD
   NAME:STRING[12];
   LEVEL:INTEGER;
   CHARID:INTEGER;
   XPOS,YPOS,SX,SY,XOLD,YOLD:INTEGER;
   FACING:INTEGER;
   ACTIVE:BOOLEAN;
   HITPOINTS:INTEGER;
   AC:INTEGER;
   SPEED:SHORTINT;
   ATTACKI:SHORTINT;
   XS,YS:BYTE;{LAST SEEN}
   EXP:INTEGER;
   OLDT,NEWT:INTEGER;
   DELAY:SHORTINT;
   ATYPE:ATTACKARRAY;
   HOSTILE:BOOLEAN;
   ONUM:BYTE;
   NUMAT:BYTE;
   NUMTYPE:BYTE;

   REG:BOOLEAN;
   LASTCHANCE:BOOLEAN;

 END;


 CHARARRAY=ARRAY[1..4] OF CHARSHEET;
 MONSTERARRAY=ARRAY[1..80] OF MONSTERSHEET;


VAR
 J,M:INTEGER;
 GD,GM:INTEGER;
 X,Y:INTEGER;
 TILE:GRAPHICS;
 MAP:DUNGEON;
 CSX:INTEGER;
 CSY:INTEGER;
 COMMAND:CHAR;
 PAGE:INTEGER;
 PAGE2:INTEGER;
 FIN:TEXT;
 FOUT:TEXT;
 MAPNAME:STRING;
 XMAX,YMAX:INTEGER;
 CIMAGE:INTEGER;
 PLAYER:CHARARRAY;
 GX,GY,GXO,GYO,GXS,GYS:INTEGER;
 ROOM:ROOMARRAY;
 NUMROOMS:INTEGER;
 WAIT:CHAR;
 MONSTER:MONSTERARRAY;
 NUMMON:INTEGER;
 MMOVE:INTEGER;
 DIE1:BYTE;
 CLEAR:BOOLEAN;
 NUMPLAYERS:INTEGER;
 CHEST:ARRAY[1..10] OF CHESTRECORD;
 NUMCHEST:BYTE;
 MOVED:BOOLEAN;
 INSCOPE:BOOLEAN;
 STEP:BOOLEAN;
 XW,YW:INTEGER;
 FTALK:TEXT;
 MAM:BYTE;
 LEFT:BOOLEAN;
 ALLDEAD:BOOLEAN;
 FQUEST:TEXT;
 SEESOMEBODY:BOOLEAN;



PROCEDURE LOADMAP;
 VAR
  new:char;
  CH:INTEGER;
   BEGIN
     NUMROOMS:=0;
     Assign(FIN,'KEEP.MAP');
     Reset(FIN);

     READ(FIN,XMAX);
     READLN(FIN,YMAX);
     FOR y:=1 TO YMAX DO
      BEGIN
       FOR x:=1 TO XMAX DO
        BEGIN
         read(FIN,CH);
         MAP.TILES[X,Y]:=CH;
         CASE CH OF
                               { .ATYPE[1]}

          17..18:BEGIN

                  NUMMON:=NUMMON+1;
                  MONSTER[NUMMON].CHARID:=17;
                  MONSTER[NUMMON].XPOS:=X;
                  MONSTER[NUMMON].YPOS:=Y;
                  MONSTER[NUMMON].XOLD:=X;
                  MONSTER[NUMMON].YOLD:=Y;
                  MONSTER[NUMMON].SX:=((MONSTER[NUMMON].XPOS-1) DIV NUMTX)+1;
                  MONSTER[NUMMON].SY:=((MONSTER[NUMMON].YPOS-1) DIV NUMTY)+1;
                  MONSTER[NUMMON].FACING:=1;
                  MONSTER[NUMMON].ACTIVE:=FALSE;
                  MONSTER[NUMMON].HITPOINTS:=RANDOM(8)+1;
                  MONSTER[NUMMON].AC:=3;
                  MONSTER[NUMMON].ATYPE[1].ATTACK:=4;
                  MONSTER[NUMMON].ATYPE[1].LONG:=TRUE;
                  MONSTER[NUMMON].SPEED:=6;
                  MONSTER[NUMMON].EXP:=5;
                  MONSTER[NUMMON].OLDT:=0;
                  MONSTER[NUMMON].NEWT:=0;
                  MONSTER[NUMMON].DELAY:=0;
                  MONSTER[NUMMON].HOSTILE:=TRUE;
                  MONSTER[NUMMON].ONUM:=NUMMON;
                  MONSTER[NUMMON].NUMAT:=1;
                  MONSTER[NUMMON].ATYPE[1].DTYPE:=1;
                  MONSTER[NUMMON].LEVEL:=1;
                  MONSTER[NUMMON].NAME:='THIEF';
                  MONSTER[NUMMON].ATYPE[1].TOA:=1;
                  MONSTER[NUMMON].NUMTYPE:=1;

                  MONSTER[NUMMON].ATYPE[1].APIC1:=112;
                  MONSTER[NUMMON].ATYPE[1].APIC2:=113;
                  MONSTER[NUMMON].ATYPE[1].APIC3:=114;
                  MONSTER[NUMMON].ATYPE[1].APIC4:=115;





                 END;

          33..34:BEGIN

                  NUMMON:=NUMMON+1;
                  MONSTER[NUMMON].CHARID:=18;
                  MONSTER[NUMMON].XPOS:=X;
                  MONSTER[NUMMON].YPOS:=Y;
                  MONSTER[NUMMON].XOLD:=X;
                  MONSTER[NUMMON].YOLD:=Y;
                  MONSTER[NUMMON].SX:=((MONSTER[NUMMON].XPOS-1) DIV NUMTX)+1;
                  MONSTER[NUMMON].SY:=((MONSTER[NUMMON].YPOS-1) DIV NUMTY)+1;
                  MONSTER[NUMMON].FACING:=1;
                  MONSTER[NUMMON].ACTIVE:=FALSE;
                  MONSTER[NUMMON].HITPOINTS:=RANDOM(16)+1;
                  MONSTER[NUMMON].AC:=3;
                  MONSTER[NUMMON].ATYPE[1].ATTACK:=6;
                  MONSTER[NUMMON].ATYPE[1].LONG:=FALSE;
                  MONSTER[NUMMON].SPEED:=6;
                  MONSTER[NUMMON].EXP:=25;
                  MONSTER[NUMMON].OLDT:=0;
                  MONSTER[NUMMON].NEWT:=0;
                  MONSTER[NUMMON].DELAY:=0;
                  MONSTER[NUMMON].HOSTILE:=TRUE;
                  MONSTER[NUMMON].ONUM:=NUMMON;
                  MONSTER[NUMMON].NUMAT:=1;
                  MONSTER[NUMMON].ATYPE[1].DTYPE:=1;
                  MONSTER[NUMMON].LEVEL:=2;
                  MONSTER[NUMMON].NUMTYPE:=1;
                  MONSTER[NUMMON].NAME:='WOLF';






                 END;
            48..49:BEGIN

                  NUMMON:=NUMMON+1;
                  MONSTER[NUMMON].CHARID:=8;
                  MONSTER[NUMMON].XPOS:=X;
                  MONSTER[NUMMON].YPOS:=Y;
                  MONSTER[NUMMON].XOLD:=X;
                  MONSTER[NUMMON].YOLD:=Y;
                  MONSTER[NUMMON].SX:=((MONSTER[NUMMON].XPOS-1) DIV NUMTX)+1;
                  MONSTER[NUMMON].SY:=((MONSTER[NUMMON].YPOS-1) DIV NUMTY)+1;
                  MONSTER[NUMMON].FACING:=1;
                  MONSTER[NUMMON].ACTIVE:=FALSE;
                  MONSTER[NUMMON].HITPOINTS:=RANDOM(16)+1;;
                  MONSTER[NUMMON].AC:=3;
                  MONSTER[NUMMON].ATYPE[1].ATTACK:=6;
                  MONSTER[NUMMON].ATYPE[1].LONG:=FALSE;
                  MONSTER[NUMMON].SPEED:=6;
                  MONSTER[NUMMON].EXP:=75;
                  MONSTER[NUMMON].OLDT:=0;
                  MONSTER[NUMMON].NEWT:=0;
                  MONSTER[NUMMON].DELAY:=0;
                  MONSTER[NUMMON].HOSTILE:=TRUE;
                  MONSTER[NUMMON].ONUM:=NUMMON;
                  MONSTER[NUMMON].NUMAT:=1;
                  MONSTER[NUMMON].ATYPE[1].DTYPE:=3;
                  MONSTER[NUMMON].LEVEL:=2;
                  MONSTER[NUMMON].NUMTYPE:=1;
                  MONSTER[NUMMON].NAME:='GIANT FROG';





                 END;

          50..51:BEGIN

                  NUMMON:=NUMMON+1;
                  MONSTER[NUMMON].CHARID:=21;
                  MONSTER[NUMMON].XPOS:=X;
                  MONSTER[NUMMON].YPOS:=Y;
                  MONSTER[NUMMON].XOLD:=X;
                  MONSTER[NUMMON].YOLD:=Y;
                  MONSTER[NUMMON].SX:=((MONSTER[NUMMON].XPOS-1) DIV NUMTX)+1;
                  MONSTER[NUMMON].SY:=((MONSTER[NUMMON].YPOS-1) DIV NUMTY)+1;
                  MONSTER[NUMMON].FACING:=1;
                  MONSTER[NUMMON].ACTIVE:=FALSE;
                  MONSTER[NUMMON].HITPOINTS:=RANDOM(40)+1;;
                  MONSTER[NUMMON].AC:=6;
                  MONSTER[NUMMON].ATYPE[1].ATTACK:=12;
                  MONSTER[NUMMON].ATYPE[1].LONG:=TRUE;
                  MONSTER[NUMMON].SPEED:=6;
                  MONSTER[NUMMON].EXP:=300;
                  MONSTER[NUMMON].OLDT:=0;
                  MONSTER[NUMMON].NEWT:=0;
                  MONSTER[NUMMON].DELAY:=0;
                  MONSTER[NUMMON].HOSTILE:=TRUE;
                  MONSTER[NUMMON].ONUM:=NUMMON;
                  MONSTER[NUMMON].NUMAT:=2;
                  MONSTER[NUMMON].ATYPE[1].DTYPE:=1;
                  MONSTER[NUMMON].LEVEL:=5;
                  MONSTER[NUMMON].ATYPE[1].TOA:=1;
                  MONSTER[NUMMON].ATYPE[1].APIC1:=84;
                  MONSTER[NUMMON].ATYPE[1].APIC2:=84;
                  MONSTER[NUMMON].ATYPE[1].APIC3:=84;
                  MONSTER[NUMMON].ATYPE[1].APIC4:=84;
                  MONSTER[NUMMON].NUMTYPE:=1;
                  MONSTER[NUMMON].NAME:='STONE GOLEM';




               END;

           92..93:BEGIN

                  NUMMON:=NUMMON+1;
                  MONSTER[NUMMON].CHARID:=19;
                  MONSTER[NUMMON].XPOS:=X;
                  MONSTER[NUMMON].YPOS:=Y;
                  MONSTER[NUMMON].XOLD:=X;
                  MONSTER[NUMMON].YOLD:=Y;
                  MONSTER[NUMMON].SX:=((MONSTER[NUMMON].XPOS-1) DIV NUMTX)+1;
                  MONSTER[NUMMON].SY:=((MONSTER[NUMMON].YPOS-1) DIV NUMTY)+1;
                  MONSTER[NUMMON].FACING:=1;
                  MONSTER[NUMMON].ACTIVE:=FALSE;
                  MONSTER[NUMMON].HITPOINTS:=RANDOM(40)+1;;
                  MONSTER[NUMMON].AC:=5;
                  MONSTER[NUMMON].ATYPE[1].ATTACK:=8;
                  MONSTER[NUMMON].ATYPE[1].LONG:=FALSE;
                  MONSTER[NUMMON].SPEED:=6;
                  MONSTER[NUMMON].EXP:=175;
                  MONSTER[NUMMON].OLDT:=0;
                  MONSTER[NUMMON].NEWT:=0;
                  MONSTER[NUMMON].DELAY:=0;
                  MONSTER[NUMMON].HOSTILE:=TRUE;
                  MONSTER[NUMMON].ONUM:=NUMMON;
                  MONSTER[NUMMON].NUMAT:=2;
                  MONSTER[NUMMON].ATYPE[1].DTYPE:=1;
                  MONSTER[NUMMON].LEVEL:=5;
                  MONSTER[NUMMON].NUMTYPE:=1;
                  MONSTER[NUMMON].NAME:='OWL BEAR';





               END;

           94:BEGIN

                  NUMMON:=NUMMON+1;
                  MONSTER[NUMMON].CHARID:=20;
                  MONSTER[NUMMON].XPOS:=X;
                  MONSTER[NUMMON].YPOS:=Y;
                  MONSTER[NUMMON].XOLD:=X;
                  MONSTER[NUMMON].YOLD:=Y;
                  MONSTER[NUMMON].SX:=((MONSTER[NUMMON].XPOS-1) DIV NUMTX)+1;
                  MONSTER[NUMMON].SY:=((MONSTER[NUMMON].YPOS-1) DIV NUMTY)+1;
                  MONSTER[NUMMON].FACING:=1;
                  MONSTER[NUMMON].ACTIVE:=FALSE;
                  MONSTER[NUMMON].HITPOINTS:=RANDOM(80)+1;;
                  MONSTER[NUMMON].AC:=3;
                  MONSTER[NUMMON].ATYPE[1].ATTACK:=24;
                  MONSTER[NUMMON].ATYPE[1].LONG:=FALSE;
                  MONSTER[NUMMON].SPEED:=6;
                  MONSTER[NUMMON].EXP:=1600;
                  MONSTER[NUMMON].OLDT:=0;
                  MONSTER[NUMMON].NEWT:=0;
                  MONSTER[NUMMON].DELAY:=0;
                  MONSTER[NUMMON].HOSTILE:=TRUE;
                  MONSTER[NUMMON].ONUM:=NUMMON;
                  MONSTER[NUMMON].NUMAT:=1;
                  MONSTER[NUMMON].ATYPE[1].DTYPE:=1;
                  MONSTER[NUMMON].LEVEL:=10;
                  MONSTER[NUMMON].NUMTYPE:=1;
                  MONSTER[NUMMON].NAME:='BLACK PUDDING';





               END;

          27..30:BEGIN

                  NUMMON:=NUMMON+1;
                  MONSTER[NUMMON].CHARID:=4;
                  MONSTER[NUMMON].XPOS:=X;
                  MONSTER[NUMMON].YPOS:=Y;
                  MONSTER[NUMMON].XOLD:=X;
                  MONSTER[NUMMON].YOLD:=Y;
                  MONSTER[NUMMON].SX:=((MONSTER[NUMMON].XPOS-1) DIV NUMTX)+1;
                  MONSTER[NUMMON].SY:=((MONSTER[NUMMON].YPOS-1) DIV NUMTY)+1;
                  MONSTER[NUMMON].FACING:=1;
                  MONSTER[NUMMON].ACTIVE:=FALSE;
                  MONSTER[NUMMON].HITPOINTS:=RANDOM(40)+1;;
                  MONSTER[NUMMON].AC:=8;
                  MONSTER[NUMMON].ATYPE[1].ATTACK:=3;
                  MONSTER[NUMMON].ATYPE[1].LONG:=FALSE;
                  MONSTER[NUMMON].SPEED:=6;
                  MONSTER[NUMMON].EXP:=300;
                  MONSTER[NUMMON].OLDT:=0;
                  MONSTER[NUMMON].NEWT:=0;
                  MONSTER[NUMMON].DELAY:=0;
                  MONSTER[NUMMON].HOSTILE:=TRUE;
                  MONSTER[NUMMON].ONUM:=NUMMON;
                  MONSTER[NUMMON].NUMAT:=1;
                  MONSTER[NUMMON].ATYPE[1].DTYPE:=5;
                  MONSTER[NUMMON].LEVEL:=5;
                  MONSTER[NUMMON].NUMTYPE:=1;
                  MONSTER[NUMMON].NAME:='RUST MONSTER';





                 END;
           31..32:BEGIN

                  NUMMON:=NUMMON+1;
                  MONSTER[NUMMON].CHARID:=5;
                  MONSTER[NUMMON].XPOS:=X;
                  MONSTER[NUMMON].YPOS:=Y;
                  MONSTER[NUMMON].XOLD:=X;
                  MONSTER[NUMMON].YOLD:=Y;
                  MONSTER[NUMMON].SX:=((MONSTER[NUMMON].XPOS-1) DIV NUMTX)+1;
                  MONSTER[NUMMON].SY:=((MONSTER[NUMMON].YPOS-1) DIV NUMTY)+1;
                  MONSTER[NUMMON].FACING:=1;
                  MONSTER[NUMMON].ACTIVE:=FALSE;
                  MONSTER[NUMMON].HITPOINTS:=RANDOM(8)+1;;
                  MONSTER[NUMMON].AC:=4;
                  MONSTER[NUMMON].ATYPE[1].ATTACK:=6;
                  MONSTER[NUMMON].ATYPE[1].LONG:=FALSE;
                  MONSTER[NUMMON].SPEED:=6;
                  MONSTER[NUMMON].OLDT:=0;
                  MONSTER[NUMMON].NEWT:=0;
                  MONSTER[NUMMON].DELAY:=0;
                  MONSTER[NUMMON].HOSTILE:=TRUE;
                  MONSTER[NUMMON].ONUM:=NUMMON;
                  MONSTER[NUMMON].NUMAT:=1;
                  MONSTER[NUMMON].ATYPE[1].DTYPE:=1;
                  MONSTER[NUMMON].LEVEL:=1;
                  MONSTER[NUMMON].NUMTYPE:=1;
                  MONSTER[NUMMON].NAME:='ORC';

                 END;

          38..41:BEGIN
                  NUMMON:=NUMMON+1;
                  MONSTER[NUMMON].CHARID:=6;
                  MONSTER[NUMMON].XPOS:=X;
                  MONSTER[NUMMON].YPOS:=Y;
                  MONSTER[NUMMON].XOLD:=X;
                  MONSTER[NUMMON].YOLD:=Y;
                  MONSTER[NUMMON].SX:=((MONSTER[NUMMON].XPOS-1) DIV NUMTX)+1;
                  MONSTER[NUMMON].SY:=((MONSTER[NUMMON].YPOS-1) DIV NUMTY)+1;
                  MONSTER[NUMMON].FACING:=1;
                  MONSTER[NUMMON].ACTIVE:=FALSE;
                  MONSTER[NUMMON].HITPOINTS:=RANDOM(16)+1;;
                  MONSTER[NUMMON].AC:=2;
                  MONSTER[NUMMON].ATYPE[1].ATTACK:=6;
                  MONSTER[NUMMON].ATYPE[1].LONG:=FALSE;
                  MONSTER[NUMMON].SPEED:=4;
                  MONSTER[NUMMON].EXP:=20;
                  MONSTER[NUMMON].OLDT:=0;
                  MONSTER[NUMMON].NEWT:=0;
                  MONSTER[NUMMON].DELAY:=0;
                  MONSTER[NUMMON].HOSTILE:=TRUE;
                  MONSTER[NUMMON].ONUM:=NUMMON;
                  MONSTER[NUMMON].NUMAT:=1;
                  MONSTER[NUMMON].ATYPE[1].DTYPE:=1;
                  MONSTER[NUMMON].LEVEL:=2;
                  MONSTER[NUMMON].NUMTYPE:=1;
                  MONSTER[NUMMON].NAME:='ZOMBIE';

                 END;
          44..47:BEGIN
                  NUMMON:=NUMMON+1;
                  MONSTER[NUMMON].CHARID:=7;
                  MONSTER[NUMMON].XPOS:=X;
                  MONSTER[NUMMON].YPOS:=Y;
                  MONSTER[NUMMON].XOLD:=X;
                  MONSTER[NUMMON].YOLD:=Y;
                  MONSTER[NUMMON].SX:=((MONSTER[NUMMON].XPOS-1) DIV NUMTX)+1;
                  MONSTER[NUMMON].SY:=((MONSTER[NUMMON].YPOS-1) DIV NUMTY)+1;
                  MONSTER[NUMMON].FACING:=1;
                  MONSTER[NUMMON].ACTIVE:=FALSE;
                 MONSTER[NUMMON].HITPOINTS:=RANDOM(40)+1;;
                  MONSTER[NUMMON].AC:=4;
                  MONSTER[NUMMON].ATYPE[1].ATTACK:=6;
                  MONSTER[NUMMON].ATYPE[1].LONG:=TRUE;
                  MONSTER[NUMMON].ATYPE[1].TOA:=1;

                  MONSTER[NUMMON].ATYPE[1].APIC1:=85;
                  MONSTER[NUMMON].ATYPE[1].APIC2:=110;
                  MONSTER[NUMMON].ATYPE[1].APIC3:=86;
                  MONSTER[NUMMON].ATYPE[1].APIC4:=111;
                  MONSTER[NUMMON].SPEED:=6;
                  MONSTER[NUMMON].EXP:=275;
                  MONSTER[NUMMON].OLDT:=0;
                  MONSTER[NUMMON].NEWT:=0;
                  MONSTER[NUMMON].DELAY:=0;
                  MONSTER[NUMMON].HOSTILE:=TRUE;
                  MONSTER[NUMMON].ONUM:=NUMMON;
                  MONSTER[NUMMON].NUMAT:=1;
                  MONSTER[NUMMON].ATYPE[1].DTYPE:=1;
                  MONSTER[NUMMON].LEVEL:=5;
                  MONSTER[NUMMON].NUMTYPE:=1;
                  MONSTER[NUMMON].NAME:='MINATAUR';
                 END;

          52:BEGIN
                  NUMMON:=NUMMON+1;
                  MONSTER[NUMMON].CHARID:=9;
                  MONSTER[NUMMON].XPOS:=X;
                  MONSTER[NUMMON].YPOS:=Y;
                  MONSTER[NUMMON].XOLD:=X;
                  MONSTER[NUMMON].YOLD:=Y;
                  MONSTER[NUMMON].SX:=((MONSTER[NUMMON].XPOS-1) DIV NUMTX)+1;
                  MONSTER[NUMMON].SY:=((MONSTER[NUMMON].YPOS-1) DIV NUMTY)+1;
                  MONSTER[NUMMON].FACING:=1;
                  MONSTER[NUMMON].ACTIVE:=FALSE;
                  MONSTER[NUMMON].HITPOINTS:=RANDOM(36)+1;;
                  MONSTER[NUMMON].AC:=4;
                  MONSTER[NUMMON].ATYPE[1].ATTACK:=6;
                  MONSTER[NUMMON].ATYPE[1].LONG:=TRUE;
                  MONSTER[NUMMON].ATYPE[1].TOA:=1;

                  MONSTER[NUMMON].ATYPE[1].APIC1:=84;
                  MONSTER[NUMMON].ATYPE[1].APIC2:=84;
                  MONSTER[NUMMON].ATYPE[1].APIC3:=84;
                  MONSTER[NUMMON].ATYPE[1].APIC4:=84;

                  MONSTER[NUMMON].SPEED:=6;
                  MONSTER[NUMMON].EXP:=200;
                  MONSTER[NUMMON].OLDT:=0;
                  MONSTER[NUMMON].NEWT:=0;
                  MONSTER[NUMMON].DELAY:=0;
                  MONSTER[NUMMON].HOSTILE:=TRUE;
                  MONSTER[NUMMON].ONUM:=NUMMON;
                  MONSTER[NUMMON].NUMAT:=10;
                  MONSTER[NUMMON].ATYPE[1].DTYPE:=1;
                  MONSTER[NUMMON].LEVEL:=4;
                  MONSTER[NUMMON].NUMTYPE:=4;

                  MONSTER[NUMMON].ATYPE[2].ATTACK:=6;
                  MONSTER[NUMMON].ATYPE[2].LONG:=TRUE;
                  MONSTER[NUMMON].ATYPE[2].APIC1:=105;
                  MONSTER[NUMMON].ATYPE[2].APIC2:=122;
                  MONSTER[NUMMON].ATYPE[2].APIC3:=105;
                  MONSTER[NUMMON].ATYPE[2].APIC4:=122;
                  MONSTER[NUMMON].ATYPE[2].TOA:=1;
                  MONSTER[NUMMON].ATYPE[2].DTYPE:=2;

                  MONSTER[NUMMON].ATYPE[3].ATTACK:=6;
                  MONSTER[NUMMON].ATYPE[3].LONG:=TRUE;
                  MONSTER[NUMMON].ATYPE[3].APIC1:=95;
                  MONSTER[NUMMON].ATYPE[3].APIC2:=95;
                  MONSTER[NUMMON].ATYPE[3].APIC3:=95;
                  MONSTER[NUMMON].ATYPE[3].APIC4:=95;
                  MONSTER[NUMMON].ATYPE[3].TOA:=2;
                  MONSTER[NUMMON].ATYPE[3].DTYPE:=1;

                  MONSTER[NUMMON].ATYPE[4].ATTACK:=6;
                  MONSTER[NUMMON].ATYPE[4].LONG:=TRUE;
                  MONSTER[NUMMON].ATYPE[4].APIC1:=124;
                  MONSTER[NUMMON].ATYPE[4].APIC2:=125;
                  MONSTER[NUMMON].ATYPE[4].APIC3:=124;
                  MONSTER[NUMMON].ATYPE[4].APIC4:=125;
                  MONSTER[NUMMON].ATYPE[4].TOA:=2;
                  MONSTER[NUMMON].ATYPE[4].DTYPE:=1;


                  MONSTER[NUMMON].NAME:='BEHOLDER';
                 END;

          42,11:BEGIN
                 NUMCHEST:=NUMCHEST+1;
                 CHEST[NUMCHEST].X:=X;
                 CHEST[NUMCHEST].Y:=Y;
               END;

          74..77:BEGIN
                  NUMMON:=NUMMON+1;
                  MONSTER[NUMMON].CHARID:=10;
                  MONSTER[NUMMON].XPOS:=X;
                  MONSTER[NUMMON].YPOS:=Y;
                  MONSTER[NUMMON].XOLD:=X;
                  MONSTER[NUMMON].YOLD:=Y;
                  MONSTER[NUMMON].SX:=((MONSTER[NUMMON].XPOS-1) DIV NUMTX)+1;
                  MONSTER[NUMMON].SY:=((MONSTER[NUMMON].YPOS-1) DIV NUMTY)+1;
                  MONSTER[NUMMON].FACING:=1;
                  MONSTER[NUMMON].ACTIVE:=FALSE;
                  MONSTER[NUMMON].HITPOINTS:=RANDOM(8)+1;;
                  MONSTER[NUMMON].AC:=4;
                  MONSTER[NUMMON].ATYPE[1].ATTACK:=6;
                  MONSTER[NUMMON].ATYPE[1].LONG:=FALSE;
                  MONSTER[NUMMON].SPEED:=6;
                  MONSTER[NUMMON].EXP:=5;
                  MONSTER[NUMMON].OLDT:=0;
                  MONSTER[NUMMON].NEWT:=0;
                  MONSTER[NUMMON].DELAY:=0;
                  MONSTER[NUMMON].HOSTILE:=TRUE;
                  MONSTER[NUMMON].ONUM:=NUMMON;
                  MONSTER[NUMMON].NUMAT:=1;
                  MONSTER[NUMMON].ATYPE[1].DTYPE:=1;
                  MONSTER[NUMMON].LEVEL:=1;
                  MONSTER[NUMMON].NUMTYPE:=1;
                  MONSTER[NUMMON].NAME:='GOBLIN';
                 END;

          78..81:BEGIN
                  NUMMON:=NUMMON+1;
                  MONSTER[NUMMON].CHARID:=11;
                  MONSTER[NUMMON].XPOS:=X;
                  MONSTER[NUMMON].YPOS:=Y;
                  MONSTER[NUMMON].XOLD:=X;
                  MONSTER[NUMMON].YOLD:=Y;
                  MONSTER[NUMMON].SX:=((MONSTER[NUMMON].XPOS-1) DIV NUMTX)+1;
                  MONSTER[NUMMON].SY:=((MONSTER[NUMMON].YPOS-1) DIV NUMTY)+1;
                  MONSTER[NUMMON].FACING:=1;
                  MONSTER[NUMMON].ACTIVE:=FALSE;
                  MONSTER[NUMMON].HITPOINTS:=RANDOM(24)+1;;
                  MONSTER[NUMMON].AC:=7;
                  MONSTER[NUMMON].ATYPE[1].ATTACK:=6;
                  MONSTER[NUMMON].ATYPE[1].LONG:=TRUE;
                  MONSTER[NUMMON].ATYPE[1].APIC1:=84;
                  MONSTER[NUMMON].ATYPE[1].APIC2:=84;
                  MONSTER[NUMMON].ATYPE[1].APIC3:=84;
                  MONSTER[NUMMON].ATYPE[1].APIC4:=84;
                  MONSTER[NUMMON].ATYPE[1].TOA:=2;
                  MONSTER[NUMMON].ATYPE[1].DTYPE:=2;

                  MONSTER[NUMMON].SPEED:=6;
                  MONSTER[NUMMON].EXP:=310;
                  MONSTER[NUMMON].OLDT:=0;
                  MONSTER[NUMMON].NEWT:=0;
                  MONSTER[NUMMON].DELAY:=0;
                  MONSTER[NUMMON].HOSTILE:=TRUE;
                  MONSTER[NUMMON].ONUM:=NUMMON;
                  MONSTER[NUMMON].NUMAT:=1;

                  MONSTER[NUMMON].LEVEL:=3;
                  MONSTER[NUMMON].NUMTYPE:=1;
                  MONSTER[NUMMON].NAME:='ZORN';
                 END;

          82:BEGIN
                  NUMMON:=NUMMON+1;
                  MONSTER[NUMMON].CHARID:=12;
                  MONSTER[NUMMON].XPOS:=X;
                  MONSTER[NUMMON].YPOS:=Y;
                  MONSTER[NUMMON].XOLD:=X;
                  MONSTER[NUMMON].YOLD:=Y;
                  MONSTER[NUMMON].SX:=((MONSTER[NUMMON].XPOS-1) DIV NUMTX)+1;
                  MONSTER[NUMMON].SY:=((MONSTER[NUMMON].YPOS-1) DIV NUMTY)+1;
                  MONSTER[NUMMON].FACING:=1;
                  MONSTER[NUMMON].ACTIVE:=FALSE;
                  MONSTER[NUMMON].HITPOINTS:=1;
                  MONSTER[NUMMON].AC:=0;
                  MONSTER[NUMMON].ATYPE[1].ATTACK:=3;
                  MONSTER[NUMMON].ATYPE[1].LONG:=FALSE;
                  MONSTER[NUMMON].SPEED:=1;
                  MONSTER[NUMMON].EXP:=10;
                  MONSTER[NUMMON].OLDT:=0;
                  MONSTER[NUMMON].NEWT:=0;
                  MONSTER[NUMMON].DELAY:=0;
                  MONSTER[NUMMON].HOSTILE:=TRUE;
                  MONSTER[NUMMON].ONUM:=NUMMON;
                  MONSTER[NUMMON].NUMAT:=1;
                  MONSTER[NUMMON].ATYPE[1].DTYPE:=1;
                  MONSTER[NUMMON].LEVEL:=1;
                  MONSTER[NUMMON].NUMTYPE:=1;
                  MONSTER[NUMMON].NAME:='GREEN SLIME';

                 END;
          83:BEGIN
                  NUMMON:=NUMMON+1;
                  MONSTER[NUMMON].CHARID:=13;
                  MONSTER[NUMMON].XPOS:=X;
                  MONSTER[NUMMON].YPOS:=Y;
                  MONSTER[NUMMON].XOLD:=X;
                  MONSTER[NUMMON].YOLD:=Y;
                  MONSTER[NUMMON].SX:=((MONSTER[NUMMON].XPOS-1) DIV NUMTX)+1;
                  MONSTER[NUMMON].SY:=((MONSTER[NUMMON].YPOS-1) DIV NUMTY)+1;
                  MONSTER[NUMMON].FACING:=1;
                  MONSTER[NUMMON].ACTIVE:=FALSE;
                  MONSTER[NUMMON].HITPOINTS:=1;
                  MONSTER[NUMMON].AC:=0;
                  MONSTER[NUMMON].ATYPE[1].ATTACK:=3;
                  MONSTER[NUMMON].ATYPE[1].LONG:=FALSE;
                  MONSTER[NUMMON].SPEED:=1;
                  MONSTER[NUMMON].EXP:=10;
                  MONSTER[NUMMON].OLDT:=0;
                  MONSTER[NUMMON].NEWT:=0;
                  MONSTER[NUMMON].DELAY:=0;
                  MONSTER[NUMMON].HOSTILE:=TRUE;
                  MONSTER[NUMMON].ONUM:=NUMMON;
                  MONSTER[NUMMON].NUMAT:=1;
                  MONSTER[NUMMON].ATYPE[1].DTYPE:=1;
                  MONSTER[NUMMON].LEVEL:=1;
                  MONSTER[NUMMON].NUMTYPE:=1;
                  MONSTER[NUMMON].NAME:='BLUE SLIME';
                 END;

          { 92..95:BEGIN
                  NUMMON:=NUMMON+1;
                  MONSTER[NUMMON].CHARID:=14;
                  MONSTER[NUMMON].XPOS:=X;
                  MONSTER[NUMMON].YPOS:=Y;
                  MONSTER[NUMMON].XOLD:=X;
                  MONSTER[NUMMON].YOLD:=Y;
                  MONSTER[NUMMON].SX:=((MONSTER[NUMMON].XPOS-1) DIV NUMTX)+1;
                  MONSTER[NUMMON].SY:=((MONSTER[NUMMON].YPOS-1) DIV NUMTY)+1;
                  MONSTER[NUMMON].FACING:=1;
                  MONSTER[NUMMON].ACTIVE:=FALSE;
                  MONSTER[NUMMON].HITPOINTS:=2;
                  MONSTER[NUMMON].AC:=2;
                  MONSTER[NUMMON].ATTACK:=3;
                  MONSTER[NUMMON].LONG:=TRUE;
                  MONSTER[NUMMON].APIC1:=106;
                  MONSTER[NUMMON].APIC2:=107;
                  MONSTER[NUMMON].APIC3:=108;
                  MONSTER[NUMMON].APIC4:=109;
                  MONSTER[NUMMON].TOA:=2;

                  MONSTER[NUMMON].SPEED:=6;
                  MONSTER[NUMMON].EXP:=10;
                  MONSTER[NUMMON].OLDT:=0;
                  MONSTER[NUMMON].NEWT:=0;
                  MONSTER[NUMMON].DELAY:=0;
                  MONSTER[NUMMON].HOSTILE:=FALSE;
                  MONSTER[NUMMON].ONUM:=NUMMON;
                  MONSTER[NUMMON].NUMAT:=1;
                  MONSTER[NUMMON].DTYPE:=1;
                 END;}

            96:BEGIN
                  NUMMON:=NUMMON+1;
                  MONSTER[NUMMON].CHARID:=15;
                  MONSTER[NUMMON].XPOS:=X;
                  MONSTER[NUMMON].YPOS:=Y;
                  MONSTER[NUMMON].XOLD:=X;
                  MONSTER[NUMMON].YOLD:=Y;
                  MONSTER[NUMMON].SX:=((MONSTER[NUMMON].XPOS-1) DIV NUMTX)+1;
                  MONSTER[NUMMON].SY:=((MONSTER[NUMMON].YPOS-1) DIV NUMTY)+1;
                  MONSTER[NUMMON].FACING:=1;
                  MONSTER[NUMMON].ACTIVE:=FALSE;
                  MONSTER[NUMMON].HITPOINTS:=4;
                  MONSTER[NUMMON].AC:=0;
                  MONSTER[NUMMON].ATYPE[1].ATTACK:=3;
                  MONSTER[NUMMON].ATYPE[1].LONG:=FALSE;
                  MONSTER[NUMMON].ATYPE[1].APIC1:=36;
                  MONSTER[NUMMON].ATYPE[1].APIC2:=36;
                  MONSTER[NUMMON].SPEED:=6;
                  MONSTER[NUMMON].EXP:=10;
                  MONSTER[NUMMON].OLDT:=0;
                  MONSTER[NUMMON].NEWT:=0;
                  MONSTER[NUMMON].DELAY:=0;
                  MONSTER[NUMMON].HOSTILE:=TRUE;
                  MONSTER[NUMMON].ONUM:=NUMMON;
                  MONSTER[NUMMON].NUMAT:=1;
                  MONSTER[NUMMON].ATYPE[1].DTYPE:=1;
                  MONSTER[NUMMON].LEVEL:=1;
                  MONSTER[NUMMON].NUMTYPE:=1;
                  MONSTER[NUMMON].NAME:='INSECT SWARM';
                 END;

          97,123:BEGIN
                  NUMMON:=NUMMON+1;
                  MONSTER[NUMMON].CHARID:=16;
                  MONSTER[NUMMON].XPOS:=X;
                  MONSTER[NUMMON].YPOS:=Y;
                  MONSTER[NUMMON].XOLD:=X;
                  MONSTER[NUMMON].YOLD:=Y;
                  MONSTER[NUMMON].SX:=((MONSTER[NUMMON].XPOS-1) DIV NUMTX)+1;
                  MONSTER[NUMMON].SY:=((MONSTER[NUMMON].YPOS-1) DIV NUMTY)+1;
                  MONSTER[NUMMON].FACING:=1;
                  MONSTER[NUMMON].ACTIVE:=FALSE;
                  MONSTER[NUMMON].HITPOINTS:=RANDOM(24)+1;;
                  MONSTER[NUMMON].AC:=4;
                  MONSTER[NUMMON].ATYPE[1].ATTACK:=3;
                  MONSTER[NUMMON].ATYPE[1].LONG:=TRUE;
                  MONSTER[NUMMON].ATYPE[1].APIC1:=84;
                  MONSTER[NUMMON].ATYPE[1].APIC2:=84;
                  MONSTER[NUMMON].ATYPE[1].APIC3:=84;
                  MONSTER[NUMMON].ATYPE[1].APIC4:=84;
                  MONSTER[NUMMON].ATYPE[1].TOA:=1;

                  MONSTER[NUMMON].SPEED:=6;
                  MONSTER[NUMMON].EXP:=310;
                  MONSTER[NUMMON].OLDT:=0;
                  MONSTER[NUMMON].NEWT:=0;
                  MONSTER[NUMMON].DELAY:=0;
                  MONSTER[NUMMON].HOSTILE:=TRUE;
                  MONSTER[NUMMON].ONUM:=NUMMON;
                  MONSTER[NUMMON].NUMAT:=1;
                  MONSTER[NUMMON].ATYPE[1].DTYPE:=1;
                  MONSTER[NUMMON].REG:=TRUE;
                  MONSTER[NUMMON].LEVEL:=3;
                  MONSTER[NUMMON].NUMTYPE:=1;
                  MONSTER[NUMMON].NAME:='TROLL';
                 END;
            98,99:BEGIN
                  NUMMON:=NUMMON+1;
                  MONSTER[NUMMON].CHARID:=22;
                  MONSTER[NUMMON].XPOS:=X;
                  MONSTER[NUMMON].YPOS:=Y;
                  MONSTER[NUMMON].XOLD:=X;
                  MONSTER[NUMMON].YOLD:=Y;
                  MONSTER[NUMMON].SX:=((MONSTER[NUMMON].XPOS-1) DIV NUMTX)+1;
                  MONSTER[NUMMON].SY:=((MONSTER[NUMMON].YPOS-1) DIV NUMTY)+1;
                  MONSTER[NUMMON].FACING:=1;
                  MONSTER[NUMMON].ACTIVE:=FALSE;
                  MONSTER[NUMMON].HITPOINTS:=RANDOM(80)+1;;
                  MONSTER[NUMMON].AC:=8;
                  MONSTER[NUMMON].ATYPE[1].ATTACK:=24;
                  MONSTER[NUMMON].ATYPE[1].LONG:=TRUE;
                  MONSTER[NUMMON].ATYPE[1].APIC1:=84;
                  MONSTER[NUMMON].ATYPE[1].APIC2:=84;
                  MONSTER[NUMMON].ATYPE[1].APIC3:=84;
                  MONSTER[NUMMON].ATYPE[1].APIC4:=84;
                  MONSTER[NUMMON].ATYPE[1].TOA:=1;

                  MONSTER[NUMMON].SPEED:=6;
                  MONSTER[NUMMON].EXP:=2500;
                  MONSTER[NUMMON].OLDT:=0;
                  MONSTER[NUMMON].NEWT:=0;
                  MONSTER[NUMMON].DELAY:=0;
                  MONSTER[NUMMON].HOSTILE:=TRUE;
                  MONSTER[NUMMON].ONUM:=NUMMON;
                  MONSTER[NUMMON].NUMAT:=1;
                  MONSTER[NUMMON].ATYPE[1].DTYPE:=1;
                  MONSTER[NUMMON].REG:=FALSE;
                  MONSTER[NUMMON].LEVEL:=10;
                  MONSTER[NUMMON].NUMTYPE:=1;
                  MONSTER[NUMMON].NAME:='EFREETI';
                 END;

        100,101:BEGIN
                  NUMMON:=NUMMON+1;
                  MONSTER[NUMMON].CHARID:=23;
                  MONSTER[NUMMON].XPOS:=X;
                  MONSTER[NUMMON].YPOS:=Y;
                  MONSTER[NUMMON].XOLD:=X;
                  MONSTER[NUMMON].YOLD:=Y;
                  MONSTER[NUMMON].SX:=((MONSTER[NUMMON].XPOS-1) DIV NUMTX)+1;
                  MONSTER[NUMMON].SY:=((MONSTER[NUMMON].YPOS-1) DIV NUMTY)+1;
                  MONSTER[NUMMON].FACING:=1;
                  MONSTER[NUMMON].ACTIVE:=FALSE;
                  MONSTER[NUMMON].HITPOINTS:=RANDOM(56)+1;;
                  MONSTER[NUMMON].AC:=6;
                  MONSTER[NUMMON].ATYPE[1].ATTACK:=16;
                  MONSTER[NUMMON].ATYPE[1].LONG:=TRUE;
                  MONSTER[NUMMON].ATYPE[1].APIC1:=84;
                  MONSTER[NUMMON].ATYPE[1].APIC2:=84;
                  MONSTER[NUMMON].ATYPE[1].APIC3:=84;
                  MONSTER[NUMMON].ATYPE[1].APIC4:=84;
                  MONSTER[NUMMON].ATYPE[1].TOA:=1;

                  MONSTER[NUMMON].SPEED:=6;
                  MONSTER[NUMMON].EXP:=900;
                  MONSTER[NUMMON].OLDT:=0;
                  MONSTER[NUMMON].NEWT:=0;
                  MONSTER[NUMMON].DELAY:=0;
                  MONSTER[NUMMON].HOSTILE:=TRUE;
                  MONSTER[NUMMON].ONUM:=NUMMON;
                  MONSTER[NUMMON].NUMAT:=1;
                  MONSTER[NUMMON].ATYPE[1].DTYPE:=1;
                  MONSTER[NUMMON].REG:=FALSE;
                  MONSTER[NUMMON].LEVEL:=7;
                  MONSTER[NUMMON].NUMTYPE:=1;
                  MONSTER[NUMMON].NAME:='DJINNI';
                 END;





          END;





        END;


       READLN(FIN);
      END;
     READLN(FIN);

     FOR y:=1 TO YMAX DO
      BEGIN
       FOR x:=1 TO XMAX DO
        BEGIN
         read(FIN,CH);
         IF CH> NUMROOMS THEN
           NUMROOMS:=CH;
         MAP.ROOM[X,Y]:=CH;
         MAP.VISIBLE[X,Y]:=FALSE;
        END;


       READLN(FIN);
      END;

      READLN(FIN);

      FOR y:=1 TO YMAX DO
      BEGIN
       FOR x:=1 TO XMAX DO
        BEGIN
         read(FIN,CH);
         MAP.TRAP[X,Y]:=CH;
        END;


       READLN(FIN);
      END;

     CLOSE(FIN);

     ASSIGN(FIN,'DARK.TR');
     RESET(FIN);
     FOR X:=1 TO NUMCHEST DO
      BEGIN
      { READLN(FIN,CHEST[X].GOLD);}
       READLN(FIN,CHEST[X].NUM);
       CHEST[X].OPEN:=FALSE;
       J:=X;
       FOR Y:=1 TO CHEST[X].NUM DO
           BEGIN

            READLN(FIN,CHEST[X].ITEM[Y].NAME);
            READLN(FIN,CHEST[X].ITEM[Y].ID);
            READLN(FIN,CHEST[X].ITEM[Y].SLOTS[1]);
            READLN(FIN,CHEST[X].ITEM[Y].SLOTS[2]);
            READLN(FIN,CHEST[X].ITEM[Y].SLOTS[3]);
            READLN(FIN,CHEST[X].ITEM[Y].SLOTS[4]);
            READLN(FIN,CHEST[X].ITEM[Y].SLOTS[5]);
            READLN(FIN,CHEST[X].ITEM[Y].SLOTS[6]);
            READLN(FIN,CHEST[X].ITEM[Y].SLOTS[7]);
            READLN(FIN,CHEST[X].ITEM[Y].SLOTS[8]);


           END;
      END;
     CLOSE(FIN);




     Assign(FIN,'DARK.MES');
     Reset(FIN);

     Assign(FTALK,'DARK.TLK');
     Reset(FTALK);


     FOR X:=1 TO NUMROOMS DO
       BEGIN
         ROOM[X].ENTERED:=FALSE;
       END;





   END;

PROCEDURE LOSEITEM(J,POINT:INTEGER);
 VAR
  A:INTEGER;
 BEGIN
   PLAYER[J].NUMITEMS:=PLAYER[J].NUMITEMS-1;
    FOR A:=POINT TO PLAYER[J].NUMITEMS  DO
       PLAYER[J].ITEMS[A]:=PLAYER[J].ITEMS[A+1];

   IF POINT<PLAYER[J].READY THEN
       PLAYER[J].READY:=PLAYER[J].READY-1;
   IF POINT<PLAYER[J].WORN THEN
       PLAYER[J].WORN:=PLAYER[J].WORN-1;
   IF POINT<PLAYER[J].SHIELD THEN
       PLAYER[J].SHIELD:=PLAYER[J].SHIELD-1;



 END;


PROCEDURE PLAYERTEXT;
 VAR
  B:INTEGER;
  BEGIN
   FOR B:=1 TO NUMPLAYERS DO
     BEGIN
      IF B=J THEN
       BEGIN
        IF PLAYER[J].ALIVE THEN
        SETCOLOR(1)
       END
      ELSE
        SETCOLOR(15);
        OUTTEXTXY(470,15+(12*B-1),PLAYER[B].NAME);
     END;
     SETCOLOR(15);
  END;

PROCEDURE PLAYERSTATUS;

 VAR
  B:INTEGER;
  HP:STRING[3];
  BEGIN
   BAR(585,26,628,100);
   FOR B:=1 TO NUMPLAYERS DO
     BEGIN

     IF PLAYER[B].ALIVE=FALSE THEN
      BEGIN
         MOVETO(585,15+(12*B-1)) ;
         OUTTEXT('DEAD');
      END
     ELSE
       IF PLAYER[B].HITPOINTS>0 THEN
        BEGIN
         STR(PLAYER[B].HITPOINTS,HP);
         OUTTEXTXY(585,15+(12*B-1),HP);
        END;

     IF PLAYER[B].ALIVE=TRUE THEN
      BEGIN

         IF PLAYER[B].INACTIVE>0 THEN
          BEGIN
           MOVETO(585,15+(12*B-1)) ;
           OUTTEXT('  S');
          END;
         IF PLAYER[B].POISON=TRUE THEN
          BEGIN
           MOVETO(585,15+(12*B-1)) ;
           OUTTEXT('   P');
          END;
         IF PLAYER[B].INVINCE>0 THEN
          BEGIN
           MOVETO(585,15+(12*B-1)) ;
           OUTTEXT('    I');
          END;


      END;



     END;
  END;


PROCEDURE MOVESALLOWED(XPOS,YPOS:INTEGER;VAR ALLOWED:BOOLEAN);
  BEGIN
    CASE MAP.TILES[XPOS,YPOS] OF
      -1,0,91,43,-3:ALLOWED:=TRUE
     ELSE
       ALLOWED:=FALSE;
    END;
  END;





PROCEDURE PRINTSTRING(MESSAGE:STRING;WAIT:BOOLEAN);
 VAR
  XLEN:INTEGER;
  WL:INTEGER;
  TYPESTRING:ARRAY[1..15] OF CHAR ;
  SP:BYTE;
  A:CHAR;
  BEGIN

      IF WAIT THEN
      BEGIN
       M:=0;
        REPEAT
         M:=M+1;
         
        UNTIL (MESSAGE[M]='.')OR (MESSAGE[M]='?');
       MESSAGE[M]:=' ';
       MESSAGE:=MESSAGE+' <SPACE>.';
      END;

      X:=485;
      Y:=160;
      M:=0;
      XLEN:=0;



      REPEAT
       WL:=0;
       REPEAT
        M:=M+1;
        WL:=WL+1;
        TYPESTRING[WL]:=MESSAGE[M];

       UNTIL (MESSAGE[M]=' ') OR (MESSAGE[M]='.')OR (MESSAGE[M]='?');








        IF  (XLEN+WL>17) THEN
         BEGIN
          Y:=Y+10;
          X:=485;
          XLEN:=0;
         END;

         XLEN:=XLEN+WL;

        FOR SP:=1 TO WL DO
        BEGIN

         OUTTEXTXY(X,Y,TYPESTRING[SP]);
         X:=X+8;
        END;

      UNTIL (MESSAGE[M]='.')OR (MESSAGE[M]='?');

    IF WAIT=TRUE THEN
     REPEAT
      A:=READKEY;
     UNTIL A=' '
    ELSE
     REPEAT
     UNTIL KEYPRESSED;


     BAR(485,160,625,300);
 END;



PROCEDURE LOADPIC(FILENAME:STRING;VAR POINT:POINTER);
 VAR
  J:INTEGER;
  K:INTEGER;
  TC:CHAR;
  WIDTH:INTEGER;
  HEIGHT:INTEGER;
  NUM:INTEGER;
  SIZE:INTEGER;
  FIN:TEXT;


   BEGIN

    Assign(FIN,FILENAME);
    Reset(FIN);
    Read(FIN,Tc);
    Width := Ord(Tc);
    Read(FIN,Tc);
    Height := Ord(Tc);
    For J := 1 to Height Do
      Begin
        For K := 1 to Width  Do
          Begin
            Read(FIN,Tc);
            Num := Ord(Tc);
            if num<>0 then
            PutPixel(K,J,Num);
          End;
      End;
    CLOSE(FIN);
    Size := ImageSize(1,1,Width,HEIGHt);

     GetMem(POINT,Size);
     GetImage(1,1,Width,Height,POINT^);
     CLEARDEVICE;
  End;

PROCEDURE LOADGRAPHICS;
 VAR
  LOAD:INTEGER;
  GL:TEXT;
  FILENAME:STRING[15];



  BEGIN
   ASSIGN(GL,'GRAPHIC.GAM');
   RESET(GL);
   LOAD:=-9;
   REPEAT
     READLN(GL,FILENAME);
     LOADPIC(FILENAME,TILE[LOAD]);
     LOAD:=LOAD+1;
   UNTIL EOF(GL);
   CLOSE(GL);


END;


PROCEDURE GETCIMAGE(FACING,CHARID:INTEGER);
  BEGIN
    CASE CHARID OF
       1:BEGIN
           CASE FACING OF
              1:CIMAGE:=15;
              2:CIMAGE:=16;
              3:CIMAGE:=16;
              4:CIMAGE:=15;
            END;
         END;

       2:BEGIN
          CASE FACING OF
            1:CIMAGE:=19;
            2:CIMAGE:=20;
            3:CIMAGE:=21;
            4:CIMAGE:=22;
          END;
         END;
       3:BEGIN
          CASE FACING OF
            1:CIMAGE:=23;
            2:CIMAGE:=24;
            3:CIMAGE:=25;
            4:CIMAGE:=26;
          END;
         END;
       4:BEGIN
          CASE FACING OF
            1:CIMAGE:=29;
            2:CIMAGE:=27;
            3:CIMAGE:=29;
            4:CIMAGE:=29;
          END;
         END;
       5:BEGIN
          CASE FACING OF
            1:CIMAGE:=31;
            2:CIMAGE:=31;
            3:CIMAGE:=32;
            4:CIMAGE:=32;
          END;
         END;
       6:BEGIN
          CASE FACING OF
            1:CIMAGE:=38;
            2:CIMAGE:=39;
            3:CIMAGE:=40;
            4:CIMAGE:=41;
          END;
         END;
       7:BEGIN
          CASE FACING OF
            1:CIMAGE:=44;
            2:CIMAGE:=45;
            3:CIMAGE:=46;
            4:CIMAGE:=47;
          END;
         END;
       8:BEGIN
          CASE FACING OF
            1:CIMAGE:=48;
            2:CIMAGE:=49;
            3:CIMAGE:=49;
            4:CIMAGE:=48;
          END;
         END;
       9:BEGIN
          CASE FACING OF
            1:CIMAGE:=52;
            2:CIMAGE:=52;
            3:CIMAGE:=52;
            4:CIMAGE:=52;
          END;
         END;
       10:BEGIN
          CASE FACING OF
            1:CIMAGE:=74;
            2:CIMAGE:=75;
            3:CIMAGE:=76;
            4:CIMAGE:=77;
          END;
         END;
       11:BEGIN
          CASE FACING OF
            1:CIMAGE:=78;
            2:CIMAGE:=79;
            3:CIMAGE:=80;
            4:CIMAGE:=81;
          END;
         END;
       12:BEGIN
          CASE FACING OF
            1:CIMAGE:=82;
            2:CIMAGE:=82;
            3:CIMAGE:=82;
            4:CIMAGE:=82;
          END;
         END;
       13:BEGIN
          CASE FACING OF
            1:CIMAGE:=83;
            2:CIMAGE:=83;
            3:CIMAGE:=83;
            4:CIMAGE:=83;
          END;
         END;
       14:BEGIN
          CASE FACING OF
            1:CIMAGE:=92;
            2:CIMAGE:=93;
            3:CIMAGE:=94;
            4:CIMAGE:=95;
          END;
         END;
       15:BEGIN
          CASE FACING OF
            1:CIMAGE:=96;
            2:CIMAGE:=96;
            3:CIMAGE:=96;
            4:CIMAGE:=96;
          END;
         END;
        16:BEGIN
          CASE FACING OF
            1:CIMAGE:=97;
            2:CIMAGE:=123;
            3:CIMAGE:=123;
            4:CIMAGE:=97;
          END;
         END;
       17:BEGIN
          CASE FACING OF
             1:CIMAGE:=17;
             2:CIMAGE:=18;
             3:CIMAGE:=18;
             4:CIMAGE:=17;
           END;
        END;
       18:BEGIN
          CASE FACING OF
             1:CIMAGE:=33;
             2:CIMAGE:=33;
             3:CIMAGE:=34;
             4:CIMAGE:=34;
           END;
        END;
       19:BEGIN
          CASE FACING OF
             1:CIMAGE:=92;
             2:CIMAGE:=93;
             3:CIMAGE:=93;
             4:CIMAGE:=92;
           END;
        END;
       20:BEGIN
          CASE FACING OF
             1:CIMAGE:=94;
             2:CIMAGE:=94;
             3:CIMAGE:=94;
             4:CIMAGE:=94;
           END;
        END;

       21:BEGIN
          CASE FACING OF
             1:CIMAGE:=50;
             2:CIMAGE:=51;
             3:CIMAGE:=51;
             4:CIMAGE:=50;
           END;
        END;
      22:BEGIN
          CASE FACING OF
             1:CIMAGE:=98;
             2:CIMAGE:=99;
             3:CIMAGE:=99;
             4:CIMAGE:=98;
           END;
        END;
      23:BEGIN
          CASE FACING OF
             1:CIMAGE:=100;
             2:CIMAGE:=101;
             3:CIMAGE:=101;
             4:CIMAGE:=100;
           END;
         END;
      24:BEGIN
           CASE FACING OF
             1:CIMAGE:=53;
             2:CIMAGE:=53;
             3:CIMAGE:=53;
             4:CIMAGE:=53;
           END;
        END;







     END;
 END;



PROCEDURE PUTTILES(VAR XPOS,YPOS,XOLD,YOLD,SX,SY,FACING,CHARID,NEWT,OLDT:INTEGER);
VAR
 SCOPECHANGE:BOOLEAN;
 XTILE,YTILE:INTEGER;
 BEGIN
   SCOPECHANGE:=FALSE;
   IF (CSX<>SX) OR (CSY<>SY) THEN
      BEGIN
        IF PAGE=0 THEN
          PAGE:=1
        ELSE
          PAGE:=0;

        SETACTIVEPAGE(PAGE);
        SCOPECHANGE:=TRUE;
        PLAYERTEXT;
        PLAYERSTATUS;
        CSX:=SX;
        CSY:=SY;

        BAR(30,25,450,325);
         FOR X:=1 TO NUMTX DO
          FOR Y:=1 TO NUMTY DO
           BEGIN
             XTILE:=X+((SX-1)*NUMTX);
             YTILE:=Y+((SY-1)*NUMTY);
             IF (XTILE<=XMAX) AND (YTILE<=YMAX) AND (MAP.VISIBLE[XTILE,YTILE]=TRUE) THEN
              BEGIN
               PUTIMAGE(30*(X+PLACEX),25*(Y+PLACEY),TILE[MAP.TILES[XTILE,YTILE]]^,NORMALPUT);
               
              END;

            { ELSE
              PUTIMAGE(30*(X+PLACEX),25*(Y+PLACEY),TILE[0]^,NORMALPUT);}
          END;

        SETVISUALPAGE(PAGE);

      END;

       IF (YOLD) > ((SY-1)*NUMTY) THEN
       IF (YOLD) < ((SY)*NUMTY)+1 THEN
       IF (XOLD) > ((SX-1)*NUMTX) THEN
       IF (XOLD) < ((SX)*NUMTX)+1 THEN
       BEGIN
        X:=((XOLD+PLACEX)-((CSX-1)*NUMTX))*30;
        Y:=((YOLD+PLACEY)-((CSY-1)*NUMTY))*25;
        PUTIMAGE(X,Y,TILE[OLDT]^,NORMALPUT);


       END;

      MAP.TILES[XOLD,YOLD]:=OLDT;
      GETCIMAGE(FACING,CHARID);
      X:=((XPOS+PLACEX)-((CSX-1)*NUMTX))*30;
      Y:=((YPOS+PLACEY)-((CSY-1)*NUMTY))*25;

      PUTIMAGE(X,Y,TILE[CIMAGE]^,NORMALPUT);




      MAP.TILES[XPOS,YPOS]:=CIMAGE;


END;

PROCEDURE MOVESIGHT;
   BEGIN
     COMMAND:=READKEY;
     GXO:=GX;
     GYO:=GY;
     CASE COMMAND OF
      '8':IF GY>1 THEN
          BEGIN
           GY:=GY-1;
           IF (GY) < ((CSY-1)*NUMTY)+1 THEN
              GYS:=GYS-1;

          END;

      '2':IF GY<YMAX THEN
          BEGIN
           GY:=GY+1;
           IF (GY) > ((CSY)*NUMTY) THEN
              GYS:=GYS+1;
          END;
      '4':IF GX>1 THEN
          BEGIN
           GX:=GX-1;
           IF (GX) < ((CSX-1)*NUMTX)+1 THEN
             GXS:=GXS-1;
          END;
      '6':IF GX<XMAX THEN
          BEGIN
           GX:=GX+1;
           IF (GX) > ((CSX)*NUMTX) THEN
              GXS:=GXS+1;
          END;
      END;
  END;

PROCEDURE GUNSIGHT;
VAR
 SCOPECHANGE:BOOLEAN;
 XTILE,YTILE:INTEGER;
 BEGIN

   SCOPECHANGE:=FALSE;
   IF (CSX<>GXS) OR (CSY<>GYS) THEN
      BEGIN
        IF PAGE=0 THEN
          PAGE:=1
        ELSE
          PAGE:=0;

        SETACTIVEPAGE(PAGE);
        SCOPECHANGE:=TRUE;
        CSX:=GXS;
        CSY:=GYS;
        BAR(30,25,450,325);
         FOR X:=1 TO NUMTX DO
          FOR Y:=1 TO NUMTY DO
           BEGIN
             XTILE:=X+((GXS-1)*NUMTX);
             YTILE:=Y+((GYS-1)*NUMTY);
             IF (XTILE<=XMAX) AND (YTILE<=YMAX) AND (MAP.VISIBLE[XTILE,YTILE]=TRUE) THEN
              PUTIMAGE(30*(X+PLACEX),25*(Y+PLACEY),TILE[MAP.TILES[XTILE,YTILE]]^,NORMALPUT);
          END;

        SETVISUALPAGE(PAGE);

      END;

     IF SCOPECHANGE=FALSE THEN
       BEGIN
        X:=((GXO+PLACEX)-((CSX-1)*NUMTX))*30;
        Y:=((GYO+PLACEY)-((CSY-1)*NUMTY))*25;
        PUTIMAGE(X,Y,TILE[35]^,XORPUT);
       END;

      X:=((GX+PLACEX)-((CSX-1)*NUMTX))*30;
      Y:=((GY+PLACEY)-((CSY-1)*NUMTY))*25;
      PUTIMAGE(X,Y,TILE[35]^,XORPUT);

END;

PROCEDURE HIT;
 VAR
   COUNT:SHORTINT;
  BEGIN


   SOUND(50);
   DELAY(40);
   SOUND(70);
   DELAY(80);
   SOUND(40);
   DELAY(60);
   FOR COUNT:=1 TO 50 DO
                BEGIN
                 SOUND(2*COUNT);
                 DELAY(5);
                END;

                SOUND(60);
                DELAY(15);
                SOUND(50);
                DELAY(15);
                SOUND(20);
                DELAY(15);
                SOUND(70);
                DELAY(15);
                SOUND(50);
                DELAY(15);
                SOUND(30);
                DELAY(15);
                SOUND(20);
                DELAY(15);
   NOSOUND;

  END;

PROCEDURE MISS;
 BEGIN

   SOUND(200);
   DELAY(20);
   SOUND(150);
   DELAY(20);
   SOUND(200);
   DELAY(20);
   NOSOUND;


 END;


PROCEDURE MONSTERHIT(DAMAGE,HITMON:INTEGER);
 VAR
  MCHECK:SHORTINT;
        BEGIN
              HIT;


                MONSTER[HITMON].HITPOINTS:= MONSTER[HITMON].HITPOINTS-DAMAGE;
                IF MONSTER[HITMON].DELAY>0 THEN
                  MONSTER[HITMON].HITPOINTS:=0;
                 IF MONSTER[HITMON].HITPOINTS<=0 THEN
                  BEGIN
                   PLAYER[J].EXP:=PLAYER[J].EXP+MONSTER[HITMON].EXP;
                   X:=((Gx+PLACEX)-((CSX-1)*NUMTX))*30;
                   Y:=((GY+PLACEY)-((CSY-1)*NUMTY))*25;
                   IF (GY) > ((CSY-1)*NUMTY) THEN
                   IF (GY) < ((CSY)*NUMTY)+1 THEN
                   IF (GX) > ((CSX-1)*NUMTX) THEN
                   IF (GX) < ((CSX)*NUMTX)+1 THEN

                     PUTIMAGE(X,Y,TILE[-1]^,normalput);
                     IF MONSTER[HITMON].OLDT<>91 THEN
                        MAP.TILES[GX,GY]:=-1
                     ELSE
                        MAP.TILES[GX,GY]:=91;
                  { NUMMON:=NUMMON-1;

                   FOR MCHECK:=HITMON TO NUMMON DO
                      MONSTER[MCHECK]:=MONSTER[MCHECK+1];}
                  END;
         END;

PROCEDURE INITSIGHT(XPOS,YPOS,XOLD,YOLD,SX,SY:INTEGER);
 BEGIN
   GX:=XPOS;
   GY:=YPOS;
   GXO:=XOLD;
   GYO:=YOLD;
   GXS:=SX;
   GYS:=SY;



  END;

 PROCEDURE COMMANDSIGHT(XPOS,YPOS,XOLD,YOLD,SX,SY:INTEGER);

  BEGIN

   INITSIGHT(XPOS,YPOS,XOLD,YOLD,SX,SY);

   X:=((GX+PLACEX)-((CSX-1)*NUMTX))*30;
   Y:=((GY+PLACEY)-((CSY-1)*NUMTY))*25;
   PUTIMAGE(X,Y,TILE[35]^,XORPUT);

   REPEAT
    GUNSIGHT;
    MOVESIGHT;
   UNTIL COMMAND='A';

   X:=((GX+PLACEX)-((CSX-1)*NUMTX))*30;
   Y:=((GY+PLACEY)-((CSY-1)*NUMTY))*25;
   PUTIMAGE(X,Y,TILE[35]^,XORPUT);
  END;

PROCEDURE WHICHMONSTER(VAR HITMON:BYTE);
 VAR
   MCHECK:BYTE;

   BEGIN
    FOR MCHECK:=1 TO NUMMON DO
      IF (MONSTER[MCHECK].XPOS=GX) AND
      (MONSTER[MCHECK].YPOS=GY) THEN
       HITMON:=MCHECK;
   END;

PROCEDURE SEEIFHIT(LEVEL,AC,PDAMAGE:INTEGER;VAR DAMAGE:INTEGER);
 VAR
  LT:TEXT;
  L,A:INTEGER;
  NTH:INTEGER;


      BEGIN

        Assign(LT,'HITTABLE.DAT');
        Reset(LT);

        DAMAGE:=0;

        FOR A:=1 TO AC DO
         BEGIN
          READLN(LT);
         END;

        FOR L:=1 TO LEVEL  DO
          READ(LT,NTH);

        DIE1:=RANDOM(20)+1;
         IF DIE1>=NTH THEN
           DAMAGE:=RANDOM(PDAMAGE)+1;

        CLOSE(LT);




      END;

PROCEDURE KILLCHAR(ATTACKID,DAMAGE,XW,YW,DTYPE:INTEGER);
 VAR
  MCHECK:BYTE;

           BEGIN
             HIT;


             IF PLAYER[ATTACKID].INVINCE=0 THEN
              CASE DTYPE OF
              1: BEGIN
               PLAYER[ATTACKID].HITPOINTS:=PLAYER[ATTACKID].HITPOINTS-DAMAGE;
               PLAYERSTATUS;
                IF PLAYER[ATTACKID].HITPOINTS<1 THEN
                 BEGIN
                  PLAYER[ATTACKID].ALIVE:=FALSE;
                  X:=((xw+PLACEX)-((CSX-1)*NUMTX))*30;
                  Y:=((YW+PLACEY)-((CSY-1)*NUMTY))*25;
                  IF (YW) > ((CSY-1)*NUMTY) THEN
                  IF (YW) < ((CSY)*NUMTY)+1 THEN
                  IF (XW) > ((CSX-1)*NUMTX) THEN
                  IF (XW) < ((CSX)*NUMTX)+1 THEN
                    PUTIMAGE(X,Y,TILE[91]^,normalput);

                  {NUMPLAYERS:=NUMPLAYERS-1;}
                  MAP.TILES[XW,YW]:=91;
                  FOR MCHECK:=1 TO PLAYER[ATTACKID].NUMITEMS DO
                      PLAYER[ATTACKID].ITEMS[MCHECK].EQUIPPED:=FALSE;

                  PLAYER[ATTACKID].AC:=0;
                  PLAYER[ATTACKID].SHIELD:=0;
                  PLAYER[ATTACKID].READY:=0;
                  PLAYER[ATTACKID].WORN:=0;



                   IF PLAYER[ATTACKID].GOLD>0 THEN
                    BEGIN
                     PLAYER[ATTACKID].NUMITEMS:=PLAYER[ATTACKID].NUMITEMS+1;
                     PLAYER[ATTACKID].ITEMS[PLAYER[ATTACKID].NUMITEMS].NAME:='GOLD';
                     PLAYER[ATTACKID].ITEMS[PLAYER[ATTACKID].NUMITEMS].ID:=9;
                     PLAYER[ATTACKID].ITEMS[PLAYER[ATTACKID].NUMITEMS].SLOTS[1]:=
                     PLAYER[ATTACKID].GOLD;
                     PLAYER[ATTACKID].ITEMS[PLAYER[ATTACKID].NUMITEMS].EQUIPPED:=FALSE;
                     PLAYER[ATTACKID].GOLD:=0;
                    END;

                   IF PLAYER[ATTACKID].KEYS>0 THEN
                    BEGIN
                     PLAYER[ATTACKID].NUMITEMS:=PLAYER[ATTACKID].NUMITEMS+1;
                     PLAYER[ATTACKID].ITEMS[PLAYER[ATTACKID].NUMITEMS].NAME:='KEYS';
                     PLAYER[ATTACKID].ITEMS[PLAYER[ATTACKID].NUMITEMS].ID:=10;
                     PLAYER[ATTACKID].ITEMS[PLAYER[ATTACKID].NUMITEMS].EQUIPPED:=FALSE;
                     PLAYER[ATTACKID].ITEMS[PLAYER[ATTACKID].NUMITEMS].SLOTS[1]:=
                     PLAYER[ATTACKID].KEYS;

                     PLAYER[ATTACKID].KEYS:=0;
                   END;

                 END;
                END;

               2:BEGIN

                  PLAYER[ATTACKID].INACTIVE:=5;
                  PLAYERSTATUS;

                 END;
               3:BEGIN
                  PLAYER[ATTACKID].POISON:=TRUE;
                 END;

               5:IF PLAYER[ATTACKID].READY<>0 THEN
                 BEGIN
                 IF PLAYER[ATTACKID].ITEMS[PLAYER[ATTACKID].READY].SLOTS[8]=1 THEN
                  BEGIN
                   LOSEITEM(ATTACKID,PLAYER[ATTACKID].READY);
                   PLAYER[ATTACKID].READY:=0;
                   PRINTSTRING('YOUR WEAPON CRUMBLES TO DUST.',TRUE);
                  END
                 END
                ELSE
                 IF PLAYER[ATTACKID].SHIELD<>0 THEN
                 BEGIN
                 IF PLAYER[ATTACKID].ITEMS[PLAYER[ATTACKID].SHIELD].SLOTS[8]=1 THEN
                   BEGIN
                   PLAYER[ATTACKID].AC:=PLAYER[ATTACKID].AC-PLAYER[ATTACKID].ITEMS[PLAYER[ATTACKID].SHIELD].SLOTS[1];
                   LOSEITEM(ATTACKID,PLAYER[ATTACKID].SHIELD);
                   PLAYER[ATTACKID].SHIELD:=0;
                   PRINTSTRING('YOUR SHIELD CRUMBLES TO DUST.',TRUE);
                  END
                 END
                ELSE
                  IF PLAYER[ATTACKID].WORN<>0 THEN
                  BEGIN
                  IF PLAYER[ATTACKID].ITEMS[PLAYER[ATTACKID].WORN].SLOTS[8]=1 THEN
                   BEGIN
                   PLAYER[ATTACKID].AC:=PLAYER[ATTACKID].AC-PLAYER[ATTACKID].ITEMS[PLAYER[ATTACKID].WORN].SLOTS[1];
                   LOSEITEM(ATTACKID,PLAYER[ATTACKID].WORN);
                   PLAYER[ATTACKID].WORN:=0;
                   PRINTSTRING('YOUR ARMOR CRUMBLES TO DUST.',TRUE);
                  END
                 END;
              END;
            END;

PROCEDURE SPOTCHAR(XP,YP,SX,SY:INTEGER);
 BEGIN
   GX:=XP;
   GY:=YP;
   GXS:=SX;
   GYS:=SY;


   IF (GY) > ((SY-1)*NUMTY) THEN
   IF (GY) < ((SY)*NUMTY)+1 THEN
   IF (GX) > ((SX-1)*NUMTX) THEN
   IF (GX) < ((SX)*NUMTX)+1 THEN
    BEGIN
     X:=((GX+PLACEX)-((CSX-1)*NUMTX))*30;
     Y:=((GY+PLACEY)-((CSY-1)*NUMTY))*25;
     PUTIMAGE(X,Y,TILE[35]^,XORPUT);
     DELAY(500);
     X:=((GX+PLACEX)-((CSX-1)*NUMTX))*30;
     Y:=((GY+PLACEY)-((CSY-1)*NUMTY))*25;
     PUTIMAGE(X,Y,TILE[35]^,XORPUT);
    END;
 END;



PROCEDURE ATTACK(XPOS,YPOS,XOLD,YOLD,SX,SY,I1,I2,I3,I4,TOA,HOM:INTEGER;VAR HITSOMETHING:BOOLEAN);
 VAR
  XT,YT:INTEGER;
  XA,YA:INTEGER;

  XW1,YW1:INTEGER;
  XW2,YW2:INTEGER;
  REALX,REALY:REAL;
  SLOPEX:REAL;
  SLOPEY:REAL;
  DGX,DGY:INTEGER;
  DISTANCE:REAL;
  DRATIO:REAL;
  ROTATE:BOOLEAN;
  COUNT:INTEGER;
  XL,YL:SHORTINT;
  SI:INTEGER;
  DARRAY:ARRAY[1..4] OF REAL;
  ROTATE2:BOOLEAN;
  POINT:POINTER;

  SIZE:INTEGER;

      BEGIN
             IF HOM<=0 THEN
              BEGIN
               GX:=GX+RANDOM(2)+1;
               GY:=GY+RANDOM(2)+1;
              END;

               XT:=GX;
               YT:=GY;
               XA:=XPOS;
               YA:=YPOS;

               REALX:=((XA+PLACEX)-((CSX-1)*NUMTX))*30+10;
               REALY:=((YA+PLACEY)-((CSY-1)*NUMTY))*25+10;

               DGX :=((XT+PLACEX)-((CSX-1)*NUMTX))*30+10;
               DGY :=((YT+PLACEY)-((CSY-1)*NUMTY))*25+10;

               DISTANCE:=SQRT( SQR(DGX-REALX) + SQR(DGY-REALY));
               DRATIO:=(DISTANCE / 11)+1;

               SLOPEX:=(DGX-REALX) / DRATIO;
               SLOPEY:=(DGY-REALY) / DRATIO;


               HITSOMETHING:=FALSE;
               COUNT:=-1;

              IF TOA=2 THEN
               BEGIN
                 DARRAY[1]:=DGX-REALX;
                 DARRAY[2]:=DGY-REALY;
                 DARRAY[3]:=DARRAY[1];
                 DARRAY[4]:=DARRAY[2];
                 DARRAY[1]:=ABS(DARRAY[1]);
                 DARRAY[2]:=ABS(DARRAY[2]);
                 IF DARRAY[1]<DARRAY[2] THEN
                   BEGIN
                     IF DARRAY[4]>=0 THEN
                       SI:=I3
                     ELSE
                       SI:=I1;
                   END
                else
                 IF DARRAY[1]>DARRAY[2] THEN
                   BEGIN
                     IF DARRAY[3]>=0 THEN
                       SI:=I2
                     ELSE
                       SI:=I4;
                   END
                 else
                   si:=I1;
               END;

              REPEAT
               COUNT:=COUNT+1;
               REALX:=REALX+ SLOPEX;
               REALY:=REALY+ SLOPEY;

               X:=ROUND(REALX);
               Y:=ROUND(REALY);





               XW:=(X) DIV 30-PLACEX+NUMTX*(CSX-1);

               YW:=(Y) DIV 25-PLACEY+NUMTY*(CSY-1);

               XW2:=(X+10) DIV 30-PLACEX+NUMTX*(CSX-1);

               YW2:=(Y+10) DIV 25-PLACEY+NUMTY*(CSY-1);

               XW1:=(X-10) DIV 30-PLACEX+NUMTX*(CSX-1);

               YW1:=(Y-10) DIV 25-PLACEY+NUMTY*(CSY-1);






               CASE MAP.TILES[XW,YW] OF
                   1..10,56..60,87..90,116,117,-2,-9..-4:HITSOMETHING:=TRUE;
               END;



               IF (YW) > ((CSY-1)*NUMTY) THEN
               IF (YW) < ((CSY)*NUMTY)+1 THEN
               IF (XW) > ((CSX-1)*NUMTX) THEN
               IF (XW) < ((CSX)*NUMTX)+1 THEN
               IF (YW2) > ((CSY-1)*NUMTY) THEN
               IF (YW2) < ((CSY)*NUMTY)+1 THEN
               IF (XW2) > ((CSX-1)*NUMTX) THEN
               IF (XW2) < ((CSX)*NUMTX)+1 THEN
               IF (YW1) > ((CSY-1)*NUMTY) THEN
               IF (YW1) < ((CSY)*NUMTY)+1 THEN
               IF (XW1) > ((CSX-1)*NUMTX) THEN
               IF (XW1) < ((CSX)*NUMTX)+1 THEN
               BEGIN
                Size := ImageSize(X-15,Y-15,X+15,Y+15);
               GetMem(POINT,Size);
               GetImage(X-15,Y-15,X+15,Y+15,POINT^);
               IF TOA=1 THEN
               BEGIN

                IF COUNT DIV 2=0 THEN
                  PUTIMAGE(X-5,Y-5,TILE[I1]^,NORMALPUT);

                IF COUNT DIV 2=1 THEN
                  PUTIMAGE(X-5,Y,TILE[I2]^,NORMALPUT);
                IF COUNT DIV 2=2 THEN
                  PUTIMAGE(X-5,Y-5,TILE[I3]^,NORMALPUT);
                IF COUNT DIV 2=3 THEN
                  PUTIMAGE(X-10,Y,TILE[I4]^,NORMALPUT);

                 IF COUNT >6  THEN
                   COUNT:=-1;



               IF (XW=XT) AND (YW=YT) THEN
                 DELAY(250)
               ELSE
                 DELAY(50);
                 PUTIMAGE(X-15,Y-15,POINT^,NORMALPUT);

               END
             ELSE
               BEGIN
                 PUTIMAGE(X-5,Y-5,TILE[SI]^,NORMALPUT);
                 DELAY(50);
                 PUTIMAGE(X-15,Y-15,POINT^,NORMALPUT);
               END;


              FREEMEM(POINT,SIZE);
           END;


              UNTIL ((XW=XT) AND   (YW=YT) ) OR
                   (HITSOMETHING)   ;

    END;


PROCEDURE SEARCHFORTRAPS(XPOS,YPOS,SX,SY:INTEGER);
 VAR
  XTILE,YTILE:INTEGER;
  SLOPEY,SLOPEX:INTEGER;
  HIT:BOOLEAN;
  XGRAPH,YGRAPH:INTEGER;
  XGTILE,YGTILE:INTEGER;
  XCHECK,YCHECK:INTEGER;
  XPUT,YPUT:INTEGER;
  SEARCH:INTEGER;

  BEGIN

       FOR X:=1 TO NUMTX DO
          FOR Y:=1 TO NUMTY DO
           BEGIN
             XTILE:=X+((SX-1)*NUMTX);
             YTILE:=Y+((SY-1)*NUMTY);
             IF (XTILE<=XMAX) AND (YTILE<=YMAX) AND (MAP.TRAP[XTILE,YTILE]<>0) THEN
              BEGIN
                SLOPEX:=XTILE-XPOS;
                SLOPEY:=YTILE-YPOS;
                XGRAPH:=((XPOS+PLACEX)-((SX-1)*NUMTX))*30+15;
                YGRAPH:=((YPOS+PLACEY)-((SY-1)*NUMTY))*25+10;
                XGTILE :=((XTILE+PLACEX)-((SX-1)*NUMTX))*30+15;
                YGTILE :=((YTILE+PLACEY)-((SY-1)*NUMTY))*25+10;
                HIT:=FALSE;

                REPEAT
                  XGRAPH:=XGRAPH+SLOPEX;
                  YGRAPH:=YGRAPH+SLOPEY;

                   XCHECK:=(XGRAPH) DIV 30-PLACEX+NUMTX*(SX-1);
                   YCHECK:=(YGRAPH) DIV 25-PLACEY+NUMTY*(SY-1);
                   IF MAP.VISIBLE[XCHECK,YCHECK]=TRUE THEN
                   IF MAP.TRAP[XCHECK,YCHECK]<>0 THEN
                   IF (YCHECK) > ((SY-1)*NUMTY) THEN
                   IF (YCHECK) < ((SY)*NUMTY)+1 THEN
                   IF (XCHECK) > ((SX-1)*NUMTX) THEN
                   IF (XCHECK) < ((SX)*NUMTX)+1 THEN
                      BEGIN

                        XPUT:=((XCHECK+PLACEX)-((SX-1)*NUMTX))*30;
                        YPUT:=((YCHECK+PLACEY)-((SY-1)*NUMTY))*25;
                        PUTIMAGE(XPUT,YPUT,TILE[37]^,ORPUT);


                      END;



                   CASE MAP.TILES[XCHECK,YCHECK] OF
                     1..10,56..60,87..90,-2,-4..-9:HIT:=TRUE;
                   END;



                UNTIL (HIT=TRUE)  OR ((XGRAPH<XGTILE+10)
                      AND (XGRAPH>XGTILE-10) AND(YGRAPH<YGTILE+10) AND (YGRAPH>YGTILE-10)  );

              END;

          END;


END;

PROCEDURE VISIBILITY(XPOS,YPOS,SX,SY:INTEGER);
 VAR
  XTILE,YTILE:INTEGER;
  SLOPEY,SLOPEX:INTEGER;
  HIT:BOOLEAN;
  XGRAPH,YGRAPH:INTEGER;
  XGTILE,YGTILE:INTEGER;
  XCHECK,YCHECK:INTEGER;
  XPUT,YPUT:INTEGER;
  SEARCH:INTEGER;
  BEGIN

       FOR X:=1 TO NUMTX DO
          FOR Y:=1 TO NUMTY DO
           BEGIN
             XTILE:=X+((SX-1)*NUMTX);
             YTILE:=Y+((SY-1)*NUMTY);
             IF (XTILE<=XMAX) AND (YTILE<=YMAX) AND (MAP.VISIBLE[XTILE,YTILE]=FALSE) THEN
              BEGIN
                SLOPEX:=XTILE-XPOS;
                SLOPEY:=YTILE-YPOS;
                XGRAPH:=((XPOS+PLACEX)-((SX-1)*NUMTX))*30+15;
                YGRAPH:=((YPOS+PLACEY)-((SY-1)*NUMTY))*25+10;
                XGTILE :=((XTILE+PLACEX)-((SX-1)*NUMTX))*30+15;
                YGTILE :=((YTILE+PLACEY)-((SY-1)*NUMTY))*25+10;
                HIT:=FALSE;

                REPEAT
                  XGRAPH:=XGRAPH+SLOPEX;
                  YGRAPH:=YGRAPH+SLOPEY;

                   XCHECK:=(XGRAPH) DIV 30-PLACEX+NUMTX*(SX-1);
                   YCHECK:=(YGRAPH) DIV 25-PLACEY+NUMTY*(SY-1);
                   IF MAP.VISIBLE[XCHECK,YCHECK]=FALSE THEN
                   IF (YCHECK) > ((SY-1)*NUMTY) THEN
                   IF (YCHECK) < ((SY)*NUMTY)+1 THEN
                   IF (XCHECK) > ((SX-1)*NUMTX) THEN
                   IF (XCHECK) < ((SX)*NUMTX)+1 THEN

                   BEGIN
                        XPUT:=((XCHECK+PLACEX)-((SX-1)*NUMTX))*30;
                        YPUT:=((YCHECK+PLACEY)-((SY-1)*NUMTY))*25;
                        PUTIMAGE(XPUT,YPUT,TILE[MAP.TILES[XCHECK,YCHECK]]^,NORMALPUT);


                        MAP.VISIBLE[XCHECK,YCHECK]:=TRUE;
                         CASE MAP.TILES[XCHECK,YCHECK] OF
                         17,18,33,34,48..51,92..94,27..30,31..34,38..41,44..47,52,74..77,78..83,92..97,123,98..101:
                         FOR SEARCH:=1 TO NUMMON DO
                               BEGIN
                                 IF(MONSTER[SEARCH].XPOS=XCHECK) AND (MONSTER[SEARCH].YPOS=YCHECK) THEN
                                   BEGIN

                                     MONSTER[SEARCH].ACTIVE:=TRUE;
                                     MONSTER[SEARCH].ATTACKI:=J;
                                     MONSTER[SEARCH].XS:=PLAYER[J].XPOS;
                                     MONSTER[SEARCH].YS:=PLAYER[J].YPOS;
                                     MONSTER[SEARCH].LASTCHANCE:=TRUE;

                                   END;

                                   END;

                      END;

                    END;


                   CASE MAP.TILES[XCHECK,YCHECK] OF
                     1..10,56..60,87..90,-4,-5,-6,-7,-8,-9:HIT:=TRUE;
                   END;



                UNTIL (HIT=TRUE) OR ((XGRAPH<XGTILE+10) AND (XGRAPH>XGTILE-10) AND(YGRAPH<YGTILE+10) AND (YGRAPH>YGTILE-10)  );

              END;

          END;


END;

PROCEDURE TRAPSOUND;
 BEGIN
    SOUND(300);
    DELAY(15);
    SOUND(200);
    DELAY(10);
    NOSOUND;
 END;

PROCEDURE LONGTRAP(XPOS,YPOS,SX,SY,I1,I2,I3,I4,PDAMAGE,TOA,TNUM:INTEGER);
  VAR
   FREEX,PX:BYTE;
   FREEY,PY:BYTE;
   HOLD:REAL;
   HITSOMETHING:BOOLEAN;
   DAMAGE:INTEGER;
   DISTANCE:REAL;
     BEGIN
          MAP.TRAP[XPOS,YPOS]:=0;
          HOLD:=1000;
          FOR FREEX:=1 TO XMAX DO
           FOR FREEY:=1 TO YMAX DO
             IF (MAP.TRAP[FREEX,FREEY]=TNUM) THEN
               BEGIN
                DISTANCE:=SQRT(SQR((FREEX-PLAYER[J].XPOS))+SQR((FREEY-PLAYER[J].YPOS)));
                 IF HOLD>DISTANCE THEN
                  BEGIN
                   HOLD:=DISTANCE;
                   PX:=FREEX;
                   PY:=FREEY;
                  END;
               END;
          TRAPSOUND;
          SPOTCHAR(PLAYER[J].XPOS,PLAYER[J].YPOS,PLAYER[J].SX,PLAYER[J].SY);
          SEEIFHIT(5,PLAYER[J].AC,PDAMAGE,DAMAGE);
          ATTACK(PX,PY,PX,PY,PLAYER[J].SX,PLAYER[J].SY,I1,I2,I3,I4,TOA,DAMAGE,HITSOMETHING);
          IF (HITSOMETHING=FALSE) AND (DAMAGE>0)  THEN
            KILLCHAR(J,DAMAGE,PLAYER[J].XPOS,PLAYER[J].YPOS,1);
          MAP.TRAP[PX,PY]:=0;
       END;

PROCEDURE TELEPORT(XPOS,YPOS,SX,SY,PX,PY:INTEGER);

 BEGIN
  BEGIN
                 PLAYER[J].OLDT:=PLAYER[J].NEWT;
                 PLAYER[J].NEWT:=MAP.TILES[PX,PY];

                 PLAYER[J].XOLD:=XPOS;
                 PLAYER[J].YOLD:=YPOS;
                 PLAYER[J].XPOS:=PX;
                 PLAYER[J].YPOS:=PY;



                 PLAYER[J].SX:=((PLAYER[J].XPOS-1) DIV NUMTX)+1;
                 PLAYER[J].SY:=((PLAYER[J].YPOS-1) DIV NUMTY)+1;

                END;

            PX:=10;
            PY:=0;

            REPEAT
             PX:=PX-1;
             PY:=PY+1;
             SOUND(PX);
             DELAY(5);
             SOUND(PY);
             DELAY(5);




            UNTIL  (PY>100);

            NOSOUND;


            PUTTILES(PLAYER[J].XPOS,PLAYER[J].YPOS,PLAYER[J].XOLD,PLAYER[J].YOLD,
            PLAYER[J].SX,PLAYER[J].SY,PLAYER[J].FACING,PLAYER[J].CHARID
            ,PLAYER[J].NEWT,PLAYER[J].OLDT);
            VISIBILITY(PLAYER[J].XPOS,PLAYER[J].YPOS,PLAYER[J].SX,PLAYER[J].SY);
     END;


PROCEDURE HITTRAP(XPOS,YPOS,SX,SY:INTEGER);

  VAR
   FREEX,PX:BYTE;
   FREEY,PY:BYTE;
   HOLD:REAL;
   HITSOMETHING:BOOLEAN;
   DAMAGE:INTEGER;
   DISTANCE:REAL;

  BEGIN
   CASE MAP.TRAP[XPOS,YPOS] OF
     1:BEGIN
        MAP.TRAP[XPOS,YPOS]:=0;
        TRAPSOUND;
        PRINTSTRING('YOU HAVE TRIGERED A POISON NEEDLE TRAP ....',TRUE);


       END;
     2:BEGIN
        MAP.TRAP[XPOS,YPOS]:=0;
        TRAPSOUND;
        PRINTSTRING('HOT OIL FALLS FROM THE DUNGEON CEILING AND IT HURTS REALLY REALLY BAD IS BURNING YOU LIKE NAPALM.',TRUE);
       END;
     3:BEGIN
        MAP.TRAP[XPOS,YPOS]:=0;
        TRAPSOUND;
        PRINTSTRING('SPIKES EJECT FROM THE DUNGEON FLOOR....',TRUE);

       END;
     4:BEGIN
        MAP.TRAP[XPOS,YPOS]:=0;
        TRAPSOUND;
        PRINTSTRING('A VOLT OF ELECTRICITY SURGES THREW THE DOOR .',TRUE);

       END;
     5:BEGIN
        MAP.TRAP[XPOS,YPOS]:=0;


         PX:=0;
         PY:=0;
         FOR FREEX:=XPOS-1 TO XPOS+1 DO
           FOR FREEY:=YPOS-1 TO YPOS+1 DO
           IF MAP.TILES[FREEX,FREEY]=0 THEN
             BEGIN
              PX:=FREEX;
              PY:=FREEY;

              NUMMON:=NUMMON+1;
              MONSTER[NUMMON].CHARID:=13;
              MONSTER[NUMMON].XPOS:=PX;
              MONSTER[NUMMON].YPOS:=PY;
              MONSTER[NUMMON].XOLD:=PX;
              MONSTER[NUMMON].YOLD:=PY;
              MONSTER[NUMMON].SX:=((MONSTER[NUMMON].XPOS-1) DIV NUMTX)+1;
              MONSTER[NUMMON].SY:=((MONSTER[NUMMON].YPOS-1) DIV NUMTY)+1;
              MONSTER[NUMMON].FACING:=1;
              MONSTER[NUMMON].ACTIVE:=TRUE;
              MONSTER[NUMMON].HITPOINTS:=1;
              MONSTER[NUMMON].AC:=0;
              MONSTER[NUMMON].ATYPE[1].ATTACK:=3;
              MONSTER[NUMMON].ATYPE[1].LONG:=FALSE;
              MONSTER[NUMMON].SPEED:=1;
              MONSTER[NUMMON].ATTACKI:=J;
              MONSTER[NUMMON].XS:=PLAYER[J].XPOS;
              MONSTER[NUMMON].YS:=PLAYER[J].YPOS;
              MONSTER[NUMMON].OLDT:=0;
              MONSTER[NUMMON].NEWT:=0;
              MONSTER[NUMMON].DELAY:=0;
              MONSTER[NUMMON].REG:=FALSE;
              GETCIMAGE(MONSTER[NUMMON].FACING,MONSTER[NUMMON].CHARID);
              X:=((PX+PLACEX)-((CSX-1)*NUMTX))*30;
              Y:=((PY+PLACEY)-((CSY-1)*NUMTY))*25;
              IF (PY) > ((CSY-1)*NUMTY) THEN
              IF (PY) < ((CSY)*NUMTY)+1 THEN
              IF (PX) > ((CSX-1)*NUMTX) THEN
              IF (PX) < ((CSX)*NUMTX)+1 THEN
               PUTIMAGE(X,Y,TILE[CIMAGE]^,NORMALPUT);
              MAP.TILES[PX,PY]:=CIMAGE;



             END;
           PRINTSTRING('SLIME OZZIESS OUT OF NEARBY TILES.',TRUE);

       END;

      6:BEGIN
         MAP.TRAP[XPOS,YPOS]:=0;
         X:=((XPOS-1+PLACEX)-((CSX-1)*NUMTX))*30;
         Y:=((YPOS+PLACEY)-((CSY-1)*NUMTY))*25;
         PUTIMAGE(X,Y,TILE[89]^,NORMALPUT);
              MAP.TILES[XPOS-1,YPOS]:=89;
         PRINTSTRING('THE DOOR SLAMS SHUTBEHIND YOU.',TRUE);
        END;
      7:BEGIN
         MAP.TRAP[XPOS,YPOS]:=0;
         X:=((XPOS+1+PLACEX)-((CSX-1)*NUMTX))*30;
         Y:=((YPOS+PLACEY)-((CSY-1)*NUMTY))*25;
         PUTIMAGE(X,Y,TILE[89]^,NORMALPUT);
              MAP.TILES[XPOS+1,YPOS]:=89;
         PRINTSTRING('THE DOOR SLAMS SHUTBEHIND YOU.',TRUE);
        END;
       8:BEGIN
         MAP.TRAP[XPOS,YPOS]:=0;
         X:=((XPOS+PLACEX)-((CSX-1)*NUMTX))*30;
         Y:=((YPOS-1+PLACEY)-((CSY-1)*NUMTY))*25;
         PUTIMAGE(X,Y,TILE[90]^,NORMALPUT);
              MAP.TILES[XPOS,YPOS-1]:=90;
         PRINTSTRING('THE DOOR SLAMS SHUTBEHIND YOU.',TRUE);
        END;
      9:BEGIN
         MAP.TRAP[XPOS,YPOS]:=0;
         X:=((XPOS+PLACEX)-((CSX-1)*NUMTX))*30;
         Y:=((YPOS+1+PLACEY)-((CSY-1)*NUMTY))*25;
         PUTIMAGE(X,Y,TILE[89]^,NORMALPUT);
              MAP.TILES[XPOS,YPOS+1]:=90;
         PRINTSTRING('THE DOOR SLAMS SHUT BEHIND YOU.',TRUE);
        END;
      10:BEGIN
         MAP.TRAP[XPOS,YPOS]:=0;
          FOR PX:=1 TO XMAX DO
            FOR PY:=1 TO YMAX DO
              IF (MAP.TRAP[PX,PY]=10) AND (PX<>XPOS) AND (PY<>YPOS) THEN
               BEGIN
                TELEPORT(XPOS,YPOS,SX,SY,PX,PY);
                MAP.TRAP[XPOS,YPOS]:=0;
                MAP.TRAP[XPOS,YPOS]:=0;
               END;


         END;
      11:BEGIN
          LONGTRAP(XPOS,YPOS,SX,SY,85,86,110,111,4,1,11);
         END;

      12:BEGIN
          LONGTRAP(XPOS,YPOS,SX,SY,106,107,108,109,4,2,12);
         END;
      13:BEGIN
          LONGTRAP(XPOS,YPOS,SX,SY,112,113,114,115,4,1,13);
         END;

      14:BEGIN
          LONGTRAP(XPOS,YPOS,SX,SY,84,84,84,84,4,1,14);
         END;
















   END;
  END;


PROCEDURE CURSOR(VAR POINT,OLDPOINT:BYTE;VAR DOOR:CHAR;MAX:INTEGER);

  BEGIN

   REPEAT
     OLDPOINT:=POINT;
     PUTIMAGE(470,158+(10*POINT),TILE[36]^,XORPUT);
     DOOR:=READKEY;
     CASE DOOR OF
       '8':BEGIN
            POINT:=POINT-1;
            IF POINT=0 THEN
              POINT:=MAX;
           END;
       '2':BEGIN
            POINT:=POINT+1;
            IF POINT>MAX THEN
              POINT:=1;
           END;
    END;
    PUTIMAGE(470,158+(10*OLDPOINT),TILE[36]^,XORPUT);

   UNTIL (DOOR=' ') OR (DOOR='Q');
  END;


PROCEDURE VIEWCHARACTER;
 VAR
  ISTG:STRING[5];
 BEGIN
  OUTTEXTXY(485,172,PLAYER[J].NAME);
  MOVETO(485,182);
  OUTTEXT('HEALTH:');
  STR(PLAYER[J].HITPOINTS,ISTG);
  OUTTEXTXY(550,182,ISTG);

  MOVETO(485,192);
  OUTTEXT('DEFENCE:');
  STR(PLAYER[J].AC,ISTG);
  OUTTEXTXY(550,192,ISTG);

  MOVETO(485,202);
  OUTTEXT('GOLD:');
  STR(PLAYER[J].GOLD,ISTG);
  OUTTEXTXY(550,202,ISTG);

  MOVETO(485,212);
  OUTTEXT('EXP:');
  STR(PLAYER[J].EXP,ISTG);
  OUTTEXTXY(550,212,ISTG);

  MOVETO(485,222);
  OUTTEXT('KEYS:');
  STR(PLAYER[J].KEYS,ISTG);
  OUTTEXTXY(550,222,ISTG);


  WAIT:=READKEY;
  BAR(485,150,625,300);

 END;

 PROCEDURE SPELLSOUND;
 VAR
  PX,PY:INTEGER;
  BEGIN
    PX:=500;
    PY:=400;

    REPEAT
    PX:=PX-1;
    PY:=PY+1;
    SOUND(PX);
    DELAY(5);
    SOUND(PY);
    DELAY(5);




   UNTIL  (PY>500);

   NOSOUND;
  END;



 PROCEDURE ATTACKSEQ(XPOS,YPOS,SX,SY,PDAMAGE:INTEGER;VAR HITMON:BYTE;
                VAR HITSOMETHING:BOOLEAN;VAR DAMAGE:INTEGER;I1,I2,I3,I4,TOA:BYTE);
    BEGIN
     COMMANDSIGHT(XPOS,YPOS,XPOS,YPOS,SX,SY);
     HITMON:=0;
     WHICHMONSTER(HITMON);
     IF HITMON<>0 THEN
       SEEIFHIT(5,MONSTER[HITMON].AC,PDAMAGE,DAMAGE);

     ATTACK(XPOS,YPOS,XPOS,YPOS,SX,SY,I1,I2,I3,I4,TOA,DAMAGE,HITSOMETHING);


     IF (HITSOMETHING=FALSE) AND (DAMAGE>=1) AND (HITMON<>0) THEN
       MONSTERHIT(DAMAGE,HITMON)
      ELSE
       MISS;
    END;


 PROCEDURE MAGICMISSILE(XPOS,YPOS,SX,SY:INTEGER);
  VAR
   HITMON:BYTE;
   HITSOMETHING:BOOLEAN;
   DAMAGE:INTEGER;


    BEGIN

     PRINTSTRING('MAGIC MISSILE.',FALSE);
     PRINTSTRING('DIRECTION -?',FALSE);
     ATTACKSEQ(XPOS,YPOS,SX,SY,6,HITMON,HITSOMETHING,DAMAGE,106,107,108,109,2);


   END;

  PROCEDURE FIREBALL(XPOS,YPOS,SX,SY:INTEGER);
  VAR
   HITMON:BYTE;
   HITSOMETHING:BOOLEAN;
   DAMAGE:INTEGER;


    BEGIN

     PRINTSTRING('FIRE BALL.',FALSE);
     PRINTSTRING('DIRECTION -?',FALSE);
     ATTACKSEQ(XPOS,YPOS,SX,SY,10,HITMON,HITSOMETHING,DAMAGE,103,104,118,119,2);


   END;

  PROCEDURE ICEBALL(XPOS,YPOS,SX,SY:INTEGER);
  VAR
   HITMON:BYTE;
   HITSOMETHING:BOOLEAN;
   DAMAGE:INTEGER;


    BEGIN

     PRINTSTRING('ICE BALL.',FALSE);
     PRINTSTRING('DIRECTION -?',FALSE);
     ATTACKSEQ(XPOS,YPOS,SX,SY,200,HITMON,HITSOMETHING,DAMAGE,95,95,95,95,2);


   END;

  PROCEDURE KILL(XPOS,YPOS,SX,SY:INTEGER);
  VAR
   HITMON:BYTE;
   HITSOMETHING:BOOLEAN;
   DAMAGE:INTEGER;


    BEGIN

     PRINTSTRING('KILL.',FALSE);
     PRINTSTRING('DIRECTION -?',FALSE);
     ATTACKSEQ(XPOS,YPOS,SX,SY,200,HITMON,HITSOMETHING,DAMAGE,84,84,84,84,2);


   END;


PROCEDURE LIGHTING(XPOS,YPOS,SX,SY:INTEGER);
  VAR
   HITMON:BYTE;
   HITSOMETHING:BOOLEAN;
   DAMAGE:INTEGER;


    BEGIN

     PRINTSTRING('LIGHTING BOLT.',FALSE);
     PRINTSTRING('DIRECTION -?',FALSE);
     ATTACKSEQ(XPOS,YPOS,SX,SY,10,HITMON,HITSOMETHING,DAMAGE,124,125,124,125,2);


   END;


  PROCEDURE VIEW(XPOS,YPOS,SX,SY:INTEGER);
    BEGIN

      COMMANDSIGHT(XPOS,YPOS,XPOS,YPOS,SX,SY);
      SPELLSOUND;
      VISIBILITY(GX,GY,GXS,GYS);

    END;

  PROCEDURE SLEEP(XPOS,YPOS,SX,SY:INTEGER);
   VAR
    HITMON:BYTE;
    HITSOMETHING:BOOLEAN;
    DAMAGE:INTEGER;
    BEGIN

     COMMANDSIGHT(XPOS,YPOS,XPOS,YPOS,SX,SY);
     HITMON:=0;
     WHICHMONSTER(HITMON);

     ATTACK(XPOS,YPOS,XPOS,YPOS,SX,SY,84,84,84,84,1,1,HITSOMETHING);


     IF (HITSOMETHING=FALSE) AND (DAMAGE>=1) AND (HITMON<>0) THEN
       BEGIN
         MONSTER[HITMON].DELAY:=MONSTER[HITMON].DELAY+5;
         SPELLSOUND;

       END
      ELSE
       MISS;


   END;

  PROCEDURE HEAL(XPOS,YPOS,SX,SY,MHP,TYP:INTEGER);
   VAR
    HITMON:BYTE;
    HITSOMETHING:BOOLEAN;
    DAMAGE:INTEGER;
    CCHECK:SHORTINT;
    P:SHORTINT;
    BEGIN

     COMMANDSIGHT(XPOS,YPOS,XPOS,YPOS,SX,SY);

     ATTACK(XPOS,YPOS,XPOS,YPOS,SX,SY,105,122,105,122,1,1,HITSOMETHING);
      P:=0;
      FOR CCHECK:=1 TO NUMPLAYERS DO
      IF (PLAYER[CCHECK].XPOS=XW) AND
      (PLAYER[CCHECK].YPOS=YW) THEN
       P:=CCHECK;


     IF (HITSOMETHING=FALSE) AND(P<>0) THEN
       BEGIN
         PLAYER[P].HITPOINTS:=PLAYER[P].HITPOINTS+MHP;
          IF PLAYER[P].HITPOINTS>PLAYER[P].MAXHP THEN
             PLAYER[P].HITPOINTS:=PLAYER[P].MAXHP;
          IF TYP=1 THEN
             PLAYER[P].POISON:=FALSE;

         SPELLSOUND;
         PLAYERSTATUS;
       END
      ELSE
       MISS;


   END;

  PROCEDURE INVINCIBILITY(XPOS,YPOS,SX,SY:INTEGER);
   VAR
    HITMON:BYTE;
    HITSOMETHING:BOOLEAN;
    DAMAGE:INTEGER;
    CCHECK:SHORTINT;
    P:SHORTINT;
    BEGIN

     COMMANDSIGHT(XPOS,YPOS,XPOS,YPOS,SX,SY);

     ATTACK(XPOS,YPOS,XPOS,YPOS,SX,SY,105,122,105,122,1,1,HITSOMETHING);
      P:=0;
      FOR CCHECK:=1 TO NUMPLAYERS DO
      IF (PLAYER[CCHECK].XPOS=XW) AND
      (PLAYER[CCHECK].YPOS=YW) THEN
       P:=CCHECK;


     IF (HITSOMETHING=FALSE) AND(P<>0) THEN
       BEGIN
         PLAYER[P].INVINCE:=PLAYER[P].INVINCE+5;
         SPELLSOUND;
         PLAYERSTATUS;
       END
      ELSE
       MISS;


   END;

 PROCEDURE ALIVE(XPOS,YPOS,SX,SY:INTEGER);
   VAR
    HITMON:BYTE;
    HITSOMETHING:BOOLEAN;
    DAMAGE:INTEGER;
    CCHECK:SHORTINT;
    P,LL:SHORTINT;
    BEGIN

     COMMANDSIGHT(XPOS,YPOS,XPOS,YPOS,SX,SY);

     ATTACK(XPOS,YPOS,XPOS,YPOS,SX,SY,105,122,105,122,1,1,HITSOMETHING);
      P:=0;
      FOR CCHECK:=1 TO NUMPLAYERS DO
      IF (PLAYER[CCHECK].XPOS=XW) AND
      (PLAYER[CCHECK].YPOS=YW) THEN
       P:=CCHECK;

     IF (HITSOMETHING=FALSE) THEN
       BEGIN
         PLAYER[P].HITPOINTS:=PLAYER[P].HITPOINTS+5;
          IF PLAYER[P].HITPOINTS>PLAYER[P].MAXHP THEN
             PLAYER[P].HITPOINTS:=PLAYER[P].MAXHP;
         PLAYER[P].ALIVE:=TRUE;
         PLAYER[P].POISON:=FALSE;
         SPELLSOUND;
         PLAYERSTATUS;
{         MAP.TILES[PLAYER[P].XOLD,PLAYER[PYOLD]:=OLDT;}
         GETCIMAGE(PLAYER[P].FACING,PLAYER[P].CHARID);
         X:=((PLAYER[P].XPOS+PLACEX)-((CSX-1)*NUMTX))*30;
         Y:=((PLAYER[P].YPOS+PLACEY)-((CSY-1)*NUMTY))*25;
         PUTIMAGE(X,Y,TILE[CIMAGE]^,NORMALPUT);
         MAP.TILES[PLAYER[P].XPOS,PLAYER[P].YPOS]:=CIMAGE;
         FOR LL:=1 TO PLAYER[P].NUMITEMS DO
           BEGIN
             IF PLAYER[P].ITEMS[LL].ID=9 THEN
               BEGIN
                PLAYER[P].GOLD:=PLAYER[P].GOLD+PLAYER[P].ITEMS[LL].SLOTS[1];
                LOSEITEM(P,LL);
               END;
              IF PLAYER[P].ITEMS[LL].ID=10 THEN
               BEGIN
                PLAYER[P].KEYS:=PLAYER[P].KEYS+PLAYER[P].ITEMS[LL].SLOTS[1];
                LOSEITEM(P,LL);
               END;
          END;

       END
      ELSE
       MISS;




   END;

  PROCEDURE DESTROYWALL(XPOS,YPOS,SX,SY:INTEGER);
   VAR
    HITSOMETHING:BOOLEAN;
    DAMAGE:INTEGER;
    BEGIN

     COMMANDSIGHT(XPOS,YPOS,XPOS,YPOS,SX,SY);

     ATTACK(XPOS,YPOS,XPOS,YPOS,SX,SY,103,104,103,104,1,1,HITSOMETHING);


     IF (HITSOMETHING=TRUE) THEN
       BEGIN
         CASE MAP.TILES[XW,YW] OF
            1..10,56..60,87..90:HITSOMETHING:=FALSE;
         END;
         IF HITSOMETHING=FALSE THEN
          BEGIN
           HIT;
           X:=((XW+PLACEX)-((CSX-1)*NUMTX))*30;
           Y:=((YW+PLACEY)-((CSY-1)*NUMTY))*25;
           IF (Yw) > ((CSY-1)*NUMTY) THEN
           IF (YW) < ((CSY)*NUMTY)+1 THEN
           IF (XW) > ((CSX-1)*NUMTX) THEN
           IF (XW) < ((CSX)*NUMTX)+1 THEN
           PUTIMAGE(X,Y,TILE[0]^,NORMALPUT);
           MAP.TILES[XW,YW]:=0;
          END;

       END
      ELSE
       MISS;


   END;

PROCEDURE AWAKEN(XPOS,YPOS,SX,SY:INTEGER);
 VAR
  A:INTEGER;
  HITSOMETHING:BOOLEAN;

  BEGIN
   COMMANDSIGHT(XPOS,YPOS,XPOS,YPOS,SX,SY);
  ATTACK(XPOS,YPOS,XPOS,YPOS,SX,SY,105,122,105,122,1,1,HITSOMETHING);

  IF HITSOMETHING=FALSE THEN
   BEGIN
    FOR A:=1 TO NUMPLAYERS DO
      IF (GX=PLAYER[A].XPOS) AND (GY=PLAYER[A].YPOS) THEN
          BEGIN
           SPELLSOUND;
           PLAYER[A].INACTIVE:=0;
           PLAYERSTATUS;
          END;
   END
  ELSE
   MISS;

END;

PROCEDURE SPEED(XPOS,YPOS,SX,SY:INTEGER);
 VAR
  A:INTEGER;
  HITSOMETHING:BOOLEAN;

  BEGIN
   COMMANDSIGHT(XPOS,YPOS,XPOS,YPOS,SX,SY);
  ATTACK(XPOS,YPOS,XPOS,YPOS,SX,SY,105,122,105,122,1,1,HITSOMETHING);

  IF HITSOMETHING=FALSE THEN
   BEGIN
    FOR A:=1 TO NUMPLAYERS DO
      IF (GX=PLAYER[A].XPOS) AND (GY=PLAYER[A].YPOS) THEN
          BEGIN
           SPELLSOUND;
           PLAYER[A].SPEED:=PLAYER[A].RSPEED+6;
           PLAYER[A].SDELAY:=5;
          END;
   END
  ELSE
   MISS;

END;




PROCEDURE WALLFIRE(XPOS,YPOS,SX,SY:INTEGER);
 VAR
  FX:INTEGER;
  XA:ARRAY[1..8]OF INTEGER;
  YA:ARRAY[1..8]OF INTEGER;
  DAMAGE:INTEGER;

  HITMON:BYTE;

  BEGIN
   XA[1]:=XPOS;
   XA[2]:=XPOS-1;
   XA[3]:=XPOS-1;
   XA[4]:=XPOS-1;
   XA[5]:=XPOS;
   XA[6]:=XPOS+1;
   XA[7]:=XPOS+1;
   XA[8]:=XPOS+1;

   YA[1]:=YPOS-1;
   YA[2]:=YPOS-1;
   YA[3]:=YPOS;
   YA[4]:=YPOS+1;
   YA[5]:=YPOS+1;
   YA[6]:=YPOS+1;
   YA[7]:=YPOS;
   YA[8]:=YPOS-1;



   FOR FX:=1 TO 8 DO
      BEGIN
        GX:=XA[FX];
        GY:=YA[FX];
        HITMON:=0;
        WHICHMONSTER(HITMON);
        IF HITMON<>0 THEN
         SEEIFHIT(5,MONSTER[HITMON].AC,10,DAMAGE);
        IF (DAMAGE>=1) AND (HITMON<>0) THEN
         MONSTERHIT(DAMAGE,HITMON)
        ELSE
         MISS;
        X:=((XA[FX]+PLACEX)-((CSX-1)*NUMTX))*30;
        Y:=((YA[FX]+PLACEY)-((CSY-1)*NUMTY))*25;

        IF (YA[FX]) > ((CSY-1)*NUMTY) THEN
        IF (YA[FX]) < ((CSY)*NUMTY)+1 THEN
        IF (XA[FX]) > ((CSX-1)*NUMTX) THEN
        IF (XA[FX]) < ((CSX)*NUMTX)+1 THEN
        BEGIN
          PUTIMAGE(X,Y,TILE[120]^,NORMALPUT);
          DELAY(150);
          PUTIMAGE(X,Y,TILE[121]^,NORMALPUT);
          DELAY(150);
         END;
       END;

    FOR FX:=1 TO 8 DO
      BEGIN
        X:=((XA[FX]+PLACEX)-((CSX-1)*NUMTX))*30;
        Y:=((YA[FX]+PLACEY)-((CSY-1)*NUMTY))*25;
        IF (YA[FX]) > ((CSY-1)*NUMTY) THEN
        IF (YA[FX]) < ((CSY)*NUMTY)+1 THEN
        IF (XA[FX]) > ((CSX-1)*NUMTX) THEN
        IF (XA[FX]) < ((CSX)*NUMTX)+1 THEN
        PUTIMAGE(X,Y,TILE[MAP.TILES[XA[FX],YA[FX]]]^,NORMALPUT);
        DELAY(50);
       END;

   END;

PROCEDURE MULTIPLE(XPOS,YPOS,SX,SY,SOK,PDAMAGE,I1,I2,I3,I4,TOA:INTEGER);
 VAR
   FX,FY:INTEGER;
   HITMON:BYTE;
   HITSOMETHING:BOOLEAN;
   DAMAGE:INTEGER;
           BEGIN
              FOR FX:=-3 TO 3 DO
               FOR FY :=-3 TO 3 DO
               BEGIN
                GX:=XPOS+FX;
                GY:=YPOS+FY;
                HITMON:=0;
                WHICHMONSTER(HITMON);
                IF HITMON<>0 THEN
                 BEGIN
                  IF SOK=1 THEN
                   SEEIFHIT(5,MONSTER[HITMON].AC,PDAMAGE,DAMAGE)
                  ELSE
                    DAMAGE:=1;

                  ATTACK(XPOS,YPOS,XPOS,YPOS,SX,SY,I1,I2,I3,I4,TOA,DAMAGE,HITSOMETHING);


                 IF (HITSOMETHING=FALSE) AND (DAMAGE>=1) AND (HITMON<>0) THEN
                  BEGIN
                   IF SOK=1 THEN
                    MONSTERHIT(DAMAGE,HITMON);
                   IF SOK=2 THEN
                    BEGIN
                     MONSTER[HITMON].DELAY:=5;
                     SPELLSOUND;
                    END;

                  END
                 ELSE
                 MISS;
                END;
             END;
           END;




 PROCEDURE GETSPELL(LEVEL,SPELL:BYTE;XPOS,YPOS,SX,SY:INTEGER);

  VAR
   P:SHORTINT;

  BEGIN
   CASE LEVEL OF
      1:CASE SPELL OF
            1:BEGIN
                  MAGICMISSILE(XPOS,YPOS,SX,SY);
                END;
            2:BEGIN
                 PRINTSTRING('MAGIC EYE.',FALSE);
                 VIEW(XPOS,YPOS,SX,SY);
                END;
            3:BEGIN
                 PRINTSTRING('SLEEP.',FALSE);
                 SLEEP(XPOS,YPOS,SX,SY);
               END;
            4:BEGIN
                 PRINTSTRING('CURE POISON.',FALSE);
                 HEAL(XPOS,YPOS,SX,SY,0,1);
              END;

        END;
       2:CASE SPELL OF
            1:BEGIN
                  FIREBALL(XPOS,YPOS,SX,SY);
                END;
            2:BEGIN
                  PRINTSTRING('DESTROY WALL.',FALSE);
                  DESTROYWALL(XPOS,YPOS,SX,SY);
                END;

            3:BEGIN
                  PRINTSTRING('HEAL LIGHT WOUNDS.',FALSE);
                  HEAL(XPOS,YPOS,SX,SY,5,0);
                END;
            4:BEGIN
                 WALLFIRE(XPOS,YPOS,SX,SY);
                END;
            5:BEGIN
                SPEED(XPOS,YPOS,SX,SY);
              END;
            6:BEGIN
                  ICEBALL(XPOS,YPOS,SX,SY);
              END;


         END;
      3:CASE SPELL OF
         1:BEGIN
            AWAKEN(XPOS,YPOS,SX,SY);
           END;

         2:BEGIN
            LIGHTING(XPOS,YPOS,SX,SY);
           END;
         3:BEGIN
             COMMANDSIGHT(XPOS,YPOS,XPOS,YPOS,SX,SY);
             IF (MAP.TILES[GX,GY]=0) OR (MAP.TILES[GX,GY]=-3) THEN
               TELEPORT(XPOS,YPOS,SX,SY,GX,GY);

           END;
         4:BEGIN
             MULTIPLE(XPOS,YPOS,SX,SY,2,0,105,122,105,122,1);
           END;
        END;
      4:CASE SPELL OF
         1:BEGIN
            ALIVE(XPOS,YPOS,SX,SY);
           END;
         2:BEGIN
            HEAL(XPOS,YPOS,SX,SY,100,0);
           END;
         3:BEGIN
            INVINCIBILITY(XPOS,YPOS,SX,SY);

           END;
         4:BEGIN
            KILL(XPOS,YPOS,SX,SY);
           END;
         5:BEGIN
             MULTIPLE(XPOS,YPOS,SX,SY,1,100,84,84,84,84,2);
           END;
        END;

    END;
  END;




PROCEDURE TALK(XPT,YPT:INTEGER);
 VAR
  MESSAGE:STRING;
  C:INTEGER;
  T:INTEGER;
 BEGIN


      T:=0;
      RESET(FTALK);
      FOR C:=1 TO NUMMON DO
      IF (MONSTER[C].XPOS=XPT) AND
      (MONSTER[C].YPOS=YPT) THEN
       T:=MONSTER[C].ONUM;


      IF T<>0 THEN
       BEGIN
        FOR C:=1 TO T DO
         READLN(FTALK);


        READLN(FTALK,MESSAGE);

        PRINTSTRING(MESSAGE,TRUE);
       END
    ELSE
    PRINTSTRING('NO RESPONCE.',TRUE);

 END;

PROCEDURE WRITEFILE(VAR ST:TEXT;VAR B:BYTE);
 VAR
  SPELLSTRING:STRING[15];

  BEGIN
     B:=0;
     REPEAT
       B:=B+1;
       READLN(ST,SPELLSTRING);
       OUTTEXTXY(495,160+(10*B),SPELLSTRING);

     UNTIL EOF(ST);
     CLOSE(ST);

  END;


PROCEDURE MUSIC(XPOS,YPOS,SX,SY,POINT:INTEGER);
 VAR
  KEY:CHAR;
  HOLD:CHAR;
  BASE:INTEGER;
  DIF:INTEGER;
  DEL:INTEGER;
  SONG:BYTE;
  FSONG:TEXT;
  SLEN:BYTE;
  A:INTEGER;
  CORRECT:BOOLEAN;
  PSONG:ARRAY[1..20] OF CHAR;
  SSONG:ARRAY[1..20] OF CHAR;
  NUMKEYS:BYTE;
  ST:TEXT;
  NUMSONGS:BYTE;
  OP,P:BYTE;

  BEGIN
  Assign(ST,'SONG.TXT');
  Reset(ST);
  WRITEFILE(ST,NUMSONGS);
  P:=1;
  CURSOR(P,OP,HOLD,NUMSONGS);
  SONG:=P;

  BAR(470,150,625,300);

  CASE SONG OF
   1:BEGIN
        PRINTSTRING('ELVIN LORE.',FALSE);
        Assign(FSONG,'EL.SNG');
        Reset(FSONG);
        READLN(FSONG,SLEN);
        FOR A:=1 TO SLEN DO
         READLN(FSONG,SSONG[A]);
       END;
  END;




  BASE:=PLAYER[J].ITEMS[POINT].SLOTS[1]*10;
  DIF:=PLAYER[J].ITEMS[POINT].SLOTS[2];
  DEL:=PLAYER[J].ITEMS[POINT].SLOTS[3]*10;
  X:=PLAYER[J].ITEMS[POINT].SLOTS[3];
  NUMKEYS:=0;
   REPEAT
    NUMKEYS:=NUMKEYS+1;
    KEY:=READKEY;
    PSONG[NUMKEYS]:=KEY;
    CASE KEY OF
      '1':SOUND(BASE+(DIF*1));
      '2':SOUND(BASE+(DIF*2));
      '3':SOUND(BASE+(DIF*3));
      '4':SOUND(BASE+(DIF*4));
      '5':SOUND(BASE+(DIF*5));
      '6':SOUND(BASE+(DIF*6));
      '7':SOUND(BASE+(DIF*7));
      '8':SOUND(BASE+(DIF*8));
      '9':SOUND(BASE+(DIF*9));
    END;
    DELAY(DEL);
    NOSOUND;

   UNTIL (KEY='Q')OR (NUMKEYS=SLEN) ;
   CORRECT:=TRUE;
   A:=0;
   IF NUMKEYS=SLEN THEN
      REPEAT
        A:=A+1;
        IF PSONG[A]<>SSONG[A] THEN
         CORRECT:=FALSE;


      UNTIL (CORRECT=FALSE) OR (A=SLEN);

  IF (A=SLEN) AND (CORRECT=TRUE) THEN
    CASE SONG OF
     1: HEAL(XPOS,YPOS,SX,SY,5,0);
    END;



 END;

PROCEDURE HEALPOTION(POINT:INTEGER);
VAR A:INTEGER;
 BEGIN
   PLAYER[J].HITPOINTS:=PLAYER[J].HITPOINTS+PLAYER[J].ITEMS[POINT].SLOTS[1];
   IF PLAYER[J].HITPOINTS>PLAYER[J].MAXHP THEN
      PLAYER[J].HITPOINTS:=PLAYER[J].MAXHP;
   SPELLSOUND;
   PLAYERSTATUS;


 END;

PROCEDURE SPEEDPOTION(POINT:INTEGER);
VAR A:INTEGER;
 BEGIN

   SPELLSOUND;


 END;

PROCEDURE FIREPOTION(XPOS,YPOS,SX,SY,POINT:INTEGER);
 VAR
  A:INTEGER;
  HITMON:BYTE;
  HITSOMETHING:BOOLEAN;
  DAMAGE:INTEGER;
  BEGIN
   PRINTSTRING('SPIT.',FALSE);
   PRINTSTRING('DIRECTION -?',FALSE);
   ATTACKSEQ(XPOS,YPOS,SX,SY,20,HITMON,HITSOMETHING,DAMAGE,103,104,118,119,2);

  END;


PROCEDURE USE(XPOS,YPOS,SX,SY,POINT:INTEGER);
 VAR
  A:INTEGER;
 BEGIN
   CASE PLAYER[J].ITEMS[POINT].ID OF
     13:MUSIC(XPOS,YPOS,SX,SY,POINT);
     14:HEALPOTION(POINT);
     15:FIREPOTION(XPOS,YPOS,SX,SY,POINT);
     16:BEGIN
         VIEW(XPOS,YPOS,SX,SY);


        END;
     17:SPEEDPOTION(POINT);
     18:BEGIN
         PLAYER[J].POISON:=TRUE;
         HIT;
         PLAYERSTATUS;
        END;
     19:BEGIN
         PLAYER[J].POISON:=FALSE;
         SPELLSOUND;
         PLAYERSTATUS;
        END;



   END;

  CASE PLAYER[J].ITEMS[POINT].ID OF
    14,15,16,17,18,19:BEGIN
                  LOSEITEM(J,POINT);


                END;
              END;



 END;
PROCEDURE MOVESOUND;
 BEGIN
  SOUND(100);
  DELAY(5);
  SOUND(200);
  DELAY(5);
  SOUND(100);
  DELAY(5);
  NOSOUND;
 END;



PROCEDURE GETLS(VAR LEVEL,SPELL:BYTE);
 VAR
  POINT,OLDPOINT:BYTE;
  CC:CHAR;
  ST:TEXT;
  B:BYTE;
  SPELLSTRING:STRING[15];

    BEGIN

     Assign(ST,'SPELL.TXT');
     Reset(ST);

     WRITEFILE(ST,B);
     POINT:=1;
     CURSOR(POINT,OLDPOINT,CC,B);
     LEVEL:=POINT;

     BAR(470,150,625,300);

     CASE LEVEL OF
       1:Assign(ST,'LV1.TXT');
       2:Assign(ST,'LV2.TXT');
       3:Assign(ST,'LV3.TXT');
       4:ASSIGN(ST,'LV4.TXT');

     END;
     RESET(ST);

     WRITEFILE(ST,B);
     POINT:=1;
     CURSOR(POINT,OLDPOINT,CC,B);
     SPELL:=POINT;

     BAR(470,150,625,300);
   END;

PROCEDURE EXIT(XOLD,YOLD,SX,SY,OLDT:INTEGER;VAR EXIT:BOOLEAN);

  BEGIN
   EXIT:=TRUE;
   X:=((XOLD+PLACEX)-((CSX-1)*NUMTX))*30;
   Y:=((YOLD+PLACEY)-((CSY-1)*NUMTY))*25;
   PUTIMAGE(X,Y,TILE[OLDT]^,NORMALPUT);
   MAP.TILES[XOLD,YOLD]:=OLDT;
   SOUND(300);
   DELAY(50);
   SOUND(400);
   DELAY(30);
   NOSOUND;
  END;

 

PROCEDURE MOVE(VAR XPOS,YPOS,XOLD,YOLD,SX,SY,FACING,NEWT,OLDT:INTEGER);
 VAR
  DIR:INTEGER;
  DOOR:CHAR;
  A,B:BYTE;
  CON:STRING[5];
  FCHEST:INTEGER;
  CODE:INTEGER;
  VALUE:INTEGER;
  POINT:BYTE;
  OLDPOINT:BYTE;
  EQUIP:BOOLEAN;
  ALREADY:BOOLEAN;
  ALLOWED:BOOLEAN;
  ATTACKSTRING:STRING[35];
  HITMON:BYTE;
  DAMAGE:INTEGER;
  HITSOMETHING:BOOLEAN;
  LEVEL:BYTE;
  SPELL:BYTE;
  OK:BOOLEAN;




   BEGIN
     COMMAND:=READKEY;
     XOLD:=XPOS;
     YOLD:=YPOS;
     OLDT:=NEWT;
     CASE COMMAND OF
      '8':
          IF (YPOS=1) THEN
           EXIT(XOLD,YOLD,SX,SY,OLDT,PLAYER[J].EXIT)
          ELSE
          IF MMOVE>=1 THEN
           BEGIN
            MOVESALLOWED(XPOS,YPOS-1,ALLOWED);
            IF ALLOWED=TRUE THEN
            BEGIN
              MOVESOUND;
             MMOVE:=MMOVE-1;
             FACING:=1;
             YPOS:=YPOS-1;
             IF (YPOS) < ((CSY-1)*NUMTY)+1 THEN
                SY:=SY-1;
             NEWT:=MAP.TILES[XPOS,YPOS];
            END;
           END;
      '2':IF (YPOS=YMAX) THEN
            EXIT(XOLD,YOLD,SX,SY,OLDT,PLAYER[J].EXIT)
          ELSE
          IF MMOVE>=1 THEN
          BEGIN
            MOVESALLOWED(XPOS,YPOS+1,ALLOWED);
            IF ALLOWED=TRUE THEN
             BEGIN
               MOVESOUND;
              MMOVE:=MMOVE-1;
              FACING:=3;
              YPOS:=YPOS+1;
              IF (YPOS) > ((CSY)*NUMTY) THEN
               SY:=SY+1;
              NEWT:=MAP.TILES[XPOS,YPOS];
            END;
          END;
      '4':IF (XPOS=1) THEN
            EXIT(XOLD,YOLD,SX,SY,OLDT,PLAYER[J].EXIT)
          ELSE
          IF MMOVE>=1 THEN
          BEGIN
            MOVESALLOWED(XPOS-1,YPOS,ALLOWED);
             IF ALLOWED=TRUE THEN
              BEGIN
                 MOVESOUND;
                MMOVE:=MMOVE-1;
                FACING:=4;
                XPOS:=XPOS-1;
                IF (XPOS) < ((CSX-1)*NUMTX)+1 THEN
                SX:=SX-1;
                NEWT:=MAP.TILES[XPOS,YPOS];
              END;
           END;
      '6':IF (XPOS=XMAX) THEN
           EXIT(XOLD,YOLD,SX,SY,OLDT,PLAYER[J].EXIT)
          ELSE
          IF MMOVE>=1 THEN
          BEGIN
            MOVESALLOWED(XPOS+1,YPOS,ALLOWED);
             IF ALLOWED=TRUE THEN
              BEGIN
               MOVESOUND;
               MMOVE:=MMOVE-1;
               FACING:=2;
               XPOS:=XPOS+1;
               IF (XPOS) > ((CSX)*NUMTX) THEN
                SX:=SX+1;
              NEWT:=MAP.TILES[XPOS,YPOS];
             END;
          END;


      'O':
          BEGIN
           PRINTSTRING('OPEN- DIRECTION?',FALSE);
           DOOR:=READKEY;

           CASE DOOR OF

           '8':IF (MAP.TILES[XPOS,YPOS-1]=90) THEN
                 PRINTSTRING('LOCKED.',FALSE)
               ELSE
               BEGIN
                IF (MAP.TILES[XPOS,YPOS-1]=10) OR (MAP.TILES[XPOS,YPOS-1]=87)
                   OR (MAP.TILES[XPOS,YPOS-1]=117) THEN
                  BEGIN
                   MAP.TILES[XPOS,YPOS-1]:=0;
                   X:=((XPOS+PLACEX)-((CSX-1)*NUMTX))*30;
                   Y:=((YPOS+PLACEY-1)-((CSY-1)*NUMTY))*25;
                   IF (YPOS) > ((CSY-1)*NUMTY)+1 THEN
                     PUTIMAGE(X,Y,TILE[0{9}]^,NORMALPUT);
                  IF MAP.TRAP[XPOS,YPOS-1]<>0 THEN
                     HITTRAP(XPOS,YPOS-1,SX,SY);
                  END;

                IF (MAP.TILES[XPOS,YPOS-1]=11) OR (MAP.TILES[XPOS,YPOS-1]=42) THEN

                  BEGIN


                   IF MAP.TILES[XPOS,YPOS-1]=11 THEN
                    MAP.TILES[XPOS,YPOS-1]:=62;
                   IF MAP.TILES[XPOS,YPOS-1]=42 THEN
                    MAP.TILES[XPOS,YPOS-1]:=61;

                   X:=((XPOS+PLACEX)-((CSX-1)*NUMTX))*30;
                   Y:=((YPOS+PLACEY-1)-((CSY-1)*NUMTY))*25;
                   IF (YPOS) > ((CSY-1)*NUMTY)+1 THEN
                     PUTIMAGE(X,Y,TILE[MAP.TILES[XPOS,YPOS-1]]^,NORMALPUT);
                   IF MAP.TRAP[XPOS,YPOS-1]<>0 THEN
                     HITTRAP(XPOS,YPOS-1,SX,SY);


                  END;



               END;

           '2':IF (MAP.TILES[XPOS,YPOS+1]=90) THEN
                 PRINTSTRING('LOCKED.',FALSE)
               ELSE
               BEGIN
                IF (MAP.TILES[XPOS,YPOS+1]=10) OR (MAP.TILES[XPOS,YPOS+1]=87)
                    OR (MAP.TILES[XPOS,YPOS+1]=117)THEN
                  BEGIN
                   MAP.TILES[XPOS,YPOS+1]:=0;
                   X:=((XPOS+PLACEX)-((CSX-1)*NUMTX))*30;
                   Y:=((YPOS+PLACEY+1)-((CSY-1)*NUMTY))*25;
                   IF (YPOS) < ((CSY)*NUMTY) THEN
                    PUTIMAGE(X,Y,TILE[0{9}]^,NORMALPUT);
                   IF MAP.TRAP[XPOS,YPOS+1]<>0 THEN
                     HITTRAP(XPOS,YPOS+1,SX,SY);

                  END;

                IF (MAP.TILES[XPOS,YPOS+1]=11) OR (MAP.TILES[XPOS,YPOS+1]=42) THEN
                  BEGIN


                   IF MAP.TILES[XPOS,YPOS+1]=11 THEN
                    MAP.TILES[XPOS,YPOS+1]:=62;
                   IF MAP.TILES[XPOS,YPOS+1]=42 THEN
                    MAP.TILES[XPOS,YPOS+1]:=61;

                   X:=((XPOS+PLACEX)-((CSX-1)*NUMTX))*30;
                   Y:=((YPOS+PLACEY+1)-((CSY-1)*NUMTY))*25;
                   IF (YPOS) < ((CSY)*NUMTY) THEN
                     PUTIMAGE(X,Y,TILE[MAP.TILES[XPOS,YPOS+1]]^,NORMALPUT);
                   IF MAP.TRAP[XPOS,YPOS+1]<>0 THEN
                     HITTRAP(XPOS,YPOS+1,SX,SY);

                  END;
               END;
           '4':IF (MAP.TILES[XPOS-1,YPOS]=89) THEN
                 PRINTSTRING('LOCKED.',FALSE)
               ELSE
               BEGIN
                IF (MAP.TILES[XPOS-1,YPOS]=8) OR  (MAP.TILES[XPOS-1,YPOS]=88)
                   OR (MAP.TILES[XPOS-1,YPOS]=116)THEN

                  BEGIN
                   MAP.TILES[XPOS-1,YPOS]:=0;
                   X:=((XPOS+PLACEX-1)-((CSX-1)*NUMTX))*30;
                   Y:=((YPOS+PLACEY)-((CSY-1)*NUMTY))*25;
                   IF (XPOS) > ((CSX-1)*NUMTX)+1 THEN
                    PUTIMAGE(X,Y,TILE[0{7}]^,NORMALPUT);
                   IF MAP.TRAP[XPOS-1,YPOS]<>0 THEN
                    HITTRAP(XPOS-1,YPOS,SX,SY);
                  END;

                IF (MAP.TILES[XPOS-1,YPOS]=11) OR (MAP.TILES[XPOS-1,YPOS]=42) THEN
                  BEGIN


                   IF MAP.TILES[XPOS-1,YPOS]=11 THEN
                    MAP.TILES[XPOS-1,YPOS]:=62;
                   IF MAP.TILES[XPOS-1,YPOS]=42 THEN
                    MAP.TILES[XPOS-1,YPOS]:=61;

                   X:=((XPOS+PLACEX-1)-((CSX-1)*NUMTX))*30;
                   Y:=((YPOS+PLACEY)-((CSY-1)*NUMTY))*25;
                   IF (XPOS) > ((CSX-1)*NUMTX)+1 THEN
                     PUTIMAGE(X,Y,TILE[MAP.TILES[XPOS-1,YPOS]]^,NORMALPUT);
                   IF MAP.TRAP[XPOS-1,YPOS]<>0 THEN
                     HITTRAP(XPOS-1,YPOS,SX,SY);


                  END;
               END;
           '6':IF MAP.TILES[XPOS+1,YPOS]=89 THEN
                 PRINTSTRING('LOCKED.',FALSE)
               ELSE
               BEGIN
                IF (MAP.TILES[XPOS+1,YPOS]=8)OR  (MAP.TILES[XPOS+1,YPOS]=88)
                   OR (MAP.TILES[XPOS+1,YPOS]=116) THEN
                  BEGIN
                   MAP.TILES[XPOS+1,YPOS]:=0;
                   X:=((XPOS+PLACEX+1)-((CSX-1)*NUMTX))*30;
                   Y:=((YPOS+PLACEY)-((CSY-1)*NUMTY))*25;
                   IF (XPOS) < ((CSX)*NUMTX) THEN
                     PUTIMAGE(X,Y,TILE[0{7}]^,NORMALPUT);
                   IF MAP.TRAP[XPOS+1,YPOS]<>0 THEN
                    HITTRAP(XPOS+1,YPOS,SX,SY);
                  END;
                IF (MAP.TILES[XPOS+1,YPOS]=11) OR (MAP.TILES[XPOS+1,YPOS]=42) THEN
                  BEGIN
                   IF MAP.TILES[XPOS+1,YPOS]=11 THEN
                    MAP.TILES[XPOS+1,YPOS]:=62;
                   IF MAP.TILES[XPOS+1,YPOS]=42 THEN
                    MAP.TILES[XPOS+1,YPOS]:=61;

                   X:=((XPOS+PLACEX+1)-((CSX-1)*NUMTX))*30;
                   Y:=((YPOS+PLACEY)-((CSY-1)*NUMTY))*25;
                   IF (XPOS) < ((CSX)*NUMTX) THEN
                     PUTIMAGE(X,Y,TILE[MAP.TILES[XPOS+1,YPOS]]^,NORMALPUT);
                   IF MAP.TRAP[XPOS+1,YPOS]<>0 THEN
                     HITTRAP(XPOS+1,YPOS,SX,SY);


                  END;

               END;



            END;
           END;
        'J':IF MMOVE>=1 THEN
             BEGIN
             IF PLAYER[J].KEYS=0 THEN
              PRINTSTRING('YOU DO NOT HAVE A KEY.',FALSE)
             ELSE
               BEGIN
               PRINTSTRING('UNLOCK- DIRECTION?',FALSE);
               MMOVE:=MMOVE-1;
               DOOR:=READKEY;
               CASE DOOR OF
                '8':BEGIN
                     IF (MAP.TILES[XPOS,YPOS-1]=90) THEN
                     BEGIN
                      MAP.TILES[XPOS,YPOS-1]:=10;
                       X:=((XPOS+PLACEX)-((CSX-1)*NUMTX))*30;
                       Y:=((YPOS+PLACEY-1)-((CSY-1)*NUMTY))*25;
                      IF (YPOS) > ((CSY-1)*NUMTY)+1 THEN
                       PUTIMAGE(X,Y,TILE[10{9}]^,NORMALPUT);
                      {IF MAP.TRAP[XPOS,YPOS-1]<>0 THEN
                       HITTRAP(XPOS,YPOS-1);}
                       PLAYER[J].KEYS:=PLAYER[J].KEYS-1;
                     END;
                    END;
                 '2':BEGIN
                      IF (MAP.TILES[XPOS,YPOS+1]=90) THEN
                      BEGIN
                       MAP.TILES[XPOS,YPOS+1]:=10;
                        X:=((XPOS+PLACEX)-((CSX-1)*NUMTX))*30;
                        Y:=((YPOS+PLACEY+1)-((CSY-1)*NUMTY))*25;
                       IF (YPOS) < ((CSY)*NUMTY) THEN
                        PUTIMAGE(X,Y,TILE[10{9}]^,NORMALPUT);
                       {IF MAP.TRAP[XPOS,YPOS-1]<>0 THEN
                        HITTRAP(XPOS,YPOS-1);}
                        PLAYER[J].KEYS:=PLAYER[J].KEYS-1;
                      END;
                     END;
                  '4':BEGIN
                       IF (MAP.TILES[XPOS-1,YPOS]=89) THEN
                       BEGIN
                        MAP.TILES[XPOS-1,YPOS]:=8;
                         X:=((XPOS+PLACEX-1)-((CSX-1)*NUMTX))*30;
                         Y:=((YPOS+PLACEY)-((CSY-1)*NUMTY))*25;
                        IF (XPOS) > ((CSX-1)*NUMTX)+1 THEN
                         PUTIMAGE(X,Y,TILE[8{9}]^,NORMALPUT);
                        {IF MAP.TRAP[XPOS,YPOS-1]<>0 THEN
                         HITTRAP(XPOS,YPOS-1);}
                         PLAYER[J].KEYS:=PLAYER[J].KEYS-1;
                       END;
                      END;
                   '6':BEGIN
                        IF (MAP.TILES[XPOS+1,YPOS]=89) THEN
                        BEGIN
                         MAP.TILES[XPOS+1,YPOS]:=8;
                          X:=((XPOS+PLACEX+1)-((CSX-1)*NUMTX))*30;
                          Y:=((YPOS+PLACEY)-((CSY-1)*NUMTY))*25;
                         IF (XPOS) < ((CSX)*NUMTX) THEN
                          PUTIMAGE(X,Y,TILE[8{9}]^,NORMALPUT);
                         {IF MAP.TRAP[XPOS,YPOS-1]<>0 THEN
                          HITTRAP(XPOS,YPOS-1);}
                          PLAYER[J].KEYS:=PLAYER[J].KEYS-1;
                        END;
                       END;
                END;
               END;
             END;

        'R':IF MMOVE>=3 THEN
             BEGIN

               IF PLAYER[J].NUMITEMS=0 THEN
                  BEGIN
                   PRINTSTRING('YOU HAVE NOTHING TO READY.',FALSE);
                  END

                  ELSE
                    BEGIN
                      MMOVE:=MMOVE-3;
                      PRINTSTRING('READY- EQUIPMENT.',FALSE);
                     FOR B:=1 TO PLAYER[J].NUMITEMS DO
                       BEGIN
                        OUTTEXTXY(495,160+(10*B),PLAYER[J].ITEMS[B].NAME);
                        IF PLAYER[J].ITEMS[B].EQUIPPED=TRUE THEN
                          BEGIN
                           MOVETO(480,160+(10*B));
                           OUTTEXT('*');
                          END;
                       END;

                       POINT:=1;
                       REPEAT

                        CURSOR(POINT,OLDPOINT,DOOR,PLAYER[J].NUMITEMS);


                       IF DOOR=' ' THEN
                       BEGIN
                        IF PLAYER[J].ITEMS[POINT].EQUIPPED=TRUE THEN
                           BEGIN
                             IF PLAYER[J].ITEMS[POINT].ID=3 THEN
                               BEGIN
                                PLAYER[J].AC:=PLAYER[J].AC-PLAYER[J].ITEMS[PLAYER[J].WORN].SLOTS[1];
                                PLAYER[J].WORN:=0;
                               END;

                             IF ((PLAYER[J].ITEMS[POINT].ID=1) OR (PLAYER[J].ITEMS[POINT].ID=2)
                                 OR (PLAYER[J].ITEMS[POINT].ID=5)  OR (PLAYER[J].ITEMS[POINT].ID=6)) THEN

                               BEGIN
                                PLAYER[J].READY:=0;
                               END;

                             IF (PLAYER[J].ITEMS[POINT].ID=4)  THEN
                              BEGIN
                               PLAYER[J].SHIELD:=0;
                               PLAYER[J].AC:=PLAYER[J].AC-PLAYER[J].ITEMS[POINT].SLOTS[1];
                              END;

                             IF (PLAYER[J].ITEMS[POINT].ID=11)  THEN
                              BEGIN
                               PLAYER[J].AC:=PLAYER[J].AC-PLAYER[J].ITEMS[POINT].SLOTS[1];
                              END;





                             PLAYER[J].ITEMS[POINT].EQUIPPED:=FALSE;
                             BAR(480,161+(9*POINT),486,171+(9*POINT));
                           END
                        ELSE
                           BEGIN
                             EQUIP:=FALSE;
                             IF (PLAYER[J].ITEMS[POINT].ID=3) AND (PLAYER[J].WORN=0) THEN
                              BEGIN
                               PLAYER[J].WORN:=POINT;
                               PLAYER[J].AC:=PLAYER[J].AC+PLAYER[J].ITEMS[POINT].SLOTS[1];
                               EQUIP:=TRUE;
                              END;

                             IF ((PLAYER[J].ITEMS[POINT].ID=1) OR (PLAYER[J].ITEMS[POINT].ID=2)
                             OR (PLAYER[J].ITEMS[POINT].ID=5)OR (PLAYER[J].ITEMS[POINT].ID=6))
                             AND (PLAYER[J].READY=0) THEN
                             BEGIN
                               PLAYER[J].READY:=POINT;
                               EQUIP:=TRUE;
                             END;

                             IF ((PLAYER[J].ITEMS[POINT].ID=4)) AND (PLAYER[J].SHIELD=0) THEN
                              BEGIN
                               PLAYER[J].SHIELD:=POINT;
                               EQUIP:=TRUE;
                               PLAYER[J].AC:=PLAYER[J].AC+PLAYER[J].ITEMS[POINT].SLOTS[1];
                              END;


                             IF ((PLAYER[J].ITEMS[POINT].ID=11))  THEN
                              BEGIN
                               ALREADY:=FALSE;
                               FOR A:=1 TO PLAYER[J].NUMITEMS DO
                                IF (PLAYER[J].ITEMS[A].ID=11) AND (PLAYER[J].ITEMS[A].EQUIPPED=TRUE) THEN
                                  ALREADY:=TRUE;

                                  IF NOT(ALREADY) THEN
                                   BEGIN
                                    EQUIP:=TRUE;
                                    PLAYER[J].AC:=PLAYER[J].AC+PLAYER[J].ITEMS[POINT].SLOTS[1];
                                   END;
                             END;

                             IF EQUIP=TRUE THEN
                              BEGIN
                               PLAYER[J].ITEMS[POINT].EQUIPPED:=TRUE;
                               MOVETO(480,160+(10*POINT));
                               OUTTEXT('* ');
                              END;

                           END;
                         END;
                      UNTIL DOOR='Q';
                   END;
                  BAR(470,150,625,300);
            END;

        'T':IF MMOVE>=1 THEN
            BEGIN
             DOOR:=READKEY;
             MMOVE:=MMOVE-1;
             CASE DOOR OF
              '8':TALK(XPOS,YPOS-1);
              '2':TALK(XPOS,YPOS+1);
              '4':TALK(XPOS-1,YPOS);
              '6':TALK(XPOS+1,YPOS);
             END;
            END;


        'G':IF MMOVE>=1 THEN
            BEGIN
             MMOVE:=MMOVE-1;
             PRINTSTRING('TAKE- DIRECTION?',FALSE);
             DOOR:=READKEY;
             FCHEST:=0;
             CASE DOOR OF
                '8':
                    IF (MAP.TILES[XPOS,YPOS-1]=62) OR (MAP.TILES[XPOS,YPOS-1]=61) THEN
                       BEGIN
                        FOR A:=1 TO NUMCHEST DO
                         IF (CHEST[A].X=XPOS) AND (CHEST[A].Y=YPOS-1) THEN
                          FCHEST:=A;
                       END;

                '2':
                    IF (MAP.TILES[XPOS,YPOS+1]=62) OR (MAP.TILES[XPOS,YPOS+1]=61) THEN
                       BEGIN
                        FOR A:=1 TO NUMCHEST DO
                         IF (CHEST[A].X=XPOS) AND (CHEST[A].Y=YPOS+1) THEN
                          FCHEST:=A;
                       END;

                '4':
                    IF (MAP.TILES[XPOS-1,YPOS]=62) OR (MAP.TILES[XPOS-1,YPOS]=61) THEN
                       BEGIN
                        FOR A:=1 TO NUMCHEST DO
                         IF (CHEST[A].X=XPOS-1) AND (CHEST[A].Y=YPOS) THEN
                           FCHEST:=A;
                       END;

                '6':
                    IF (MAP.TILES[XPOS+1,YPOS]=62) OR (MAP.TILES[XPOS+1,YPOS]=61) THEN
                       BEGIN
                        FOR A:=1 TO NUMCHEST DO
                         IF (CHEST[A].X=XPOS+1) AND (CHEST[A].Y=YPOS) THEN
                           FCHEST:=A;
                       END;

             END;

             IF FCHEST<>0 THEN
               BEGIN

               IF (CHEST[FCHEST].NUM<=0) THEN
                BEGIN
                 PRINTSTRING('EMPTY.',FALSE);
                END;

             POINT:=1;
             REPEAT
               IF CHEST[FCHEST].NUM>0 THEN
                BEGIN


                 FOR B:=1 TO CHEST[FCHEST].NUM DO
                     BEGIN
                        OUTTEXTXY(495,160+(10*B),CHEST[FCHEST].ITEM[B].NAME);
                     END;

                       
                        CURSOR(POINT,OLDPOINT,DOOR,CHEST[FCHEST].NUM);


                      IF DOOR=' ' THEN
                       BEGIN
                        IF CHEST[FCHEST].ITEM[POINT].ID=9 THEN
                          PLAYER[J].GOLD:=PLAYER[J].GOLD+CHEST[FCHEST].ITEM[POINT].SLOTS[1]
                        ELSE
                          IF CHEST[FCHEST].ITEM[POINT].ID=10 THEN
                           PLAYER[J].KEYS:=PLAYER[J].KEYS+CHEST[FCHEST].ITEM[POINT].SLOTS[1]
                          ELSE
                           BEGIN
                            PLAYER[J].NUMITEMS:=PLAYER[J].NUMITEMS+1;
                            PLAYER[J].ITEMS[PLAYER[J].NUMITEMS]:=CHEST[FCHEST].ITEM[POINT];
                           END;

                          CHEST[FCHEST].NUM:=CHEST[FCHEST].NUM-1;
                          FOR A:=POINT TO CHEST[FCHEST].NUM DO
                           CHEST[FCHEST].ITEM[A]:=CHEST[FCHEST].ITEM[A+1];
                       END;


                    BAR(485,160,625,300);

                    IF POINT=CHEST[FCHEST].NUM+1 THEN
                       POINT:=POINT-1;


                END;
               UNTIL (DOOR='Q') OR (CHEST[FCHEST].NUM=0);
               END;


            END;

        'B':IF MMOVE>=1 THEN
            BEGIN
             PRINTSTRING('TAKE- DIRECTION?',FALSE);
             DOOR:=READKEY;
             FCHEST:=0;
             MMOVE:=MMOVE-1;
             CASE DOOR OF
                '8':
                    {IF (MAP.TILES[XPOS,YPOS-1]=91) THEN}
                       BEGIN
                        FOR A:=1 TO NUMPLAYERS DO
                         IF (PLAYER[A].XPOS=XPOS) AND (PLAYER[A].YPOS=YPOS-1) THEN
                           FCHEST:=A;
                       END;

                '2':
                    {IF (MAP.TILES[XPOS,YPOS+1]=91) THEN}
                      BEGIN
                        FOR A:=1 TO NUMPLAYERS DO
                         IF (PLAYER[A].XPOS=XPOS) AND (PLAYER[A].YPOS=YPOS+1) THEN
                           FCHEST:=A;
                       END;

                '4':
                    {IF (MAP.TILES[XPOS-1,YPOS]=91) THEN}
                      BEGIN
                        FOR A:=1 TO NUMPLAYERS DO
                         IF (PLAYER[A].XPOS=XPOS-1) AND (PLAYER[A].YPOS=YPOS) THEN
                           FCHEST:=A;
                       END;

                '6':
                    {IF (MAP.TILES[XPOS+1,YPOS]=91) THEN}
                      BEGIN
                        FOR A:=1 TO NUMPLAYERS DO
                         IF (PLAYER[A].XPOS=XPOS+1) AND (PLAYER[A].YPOS=YPOS) THEN
                           FCHEST:=A;
                       END;

             END;



             IF FCHEST<>0 THEN
              BEGIN
               IF (PLAYER[FCHEST].NUMITEMS<=0) THEN
                BEGIN
                 PRINTSTRING('NOTHING ON BODY.',FALSE);
                END;

             POINT:=1;
             REPEAT
               IF PLAYER[FCHEST].NUMITEMS>0 THEN
                BEGIN


                 FOR B:=1 TO PLAYER[FCHEST].NUMITEMS DO
                     BEGIN
                        OUTTEXTXY(495,160+(10*B),PLAYER[FCHEST].ITEMS [B].NAME);
                     END;



                        CURSOR(POINT,OLDPOINT,DOOR,PLAYER[FCHEST].NUMITEMS);


                      IF DOOR=' ' THEN
                       BEGIN
                        IF PLAYER[FCHEST].ITEMS[POINT].ID=9 THEN
                          PLAYER[J].GOLD:=PLAYER[J].GOLD+PLAYER[FCHEST].ITEMS[POINT].SLOTS[1]
                        ELSE
                          IF PLAYER[FCHEST].ITEMS[POINT].ID=10 THEN
                           PLAYER[J].KEYS:=PLAYER[J].KEYS+PLAYER[FCHEST].ITEMS[POINT].SLOTS[1]
                        ELSE
                         BEGIN
                          IF PLAYER[FCHEST].ITEMS[POINT].EQUIPPED<>TRUE THEN
                           BEGIN
                            PLAYER[J].NUMITEMS:=PLAYER[J].NUMITEMS+1;
                            PLAYER[J].ITEMS[PLAYER[J].NUMITEMS]:=PLAYER[FCHEST].ITEMS[POINT];
                           END;
                         END;

                          IF PLAYER[FCHEST].ITEMS[POINT].EQUIPPED<>TRUE THEN
                           BEGIN
                            PLAYER[FCHEST].NUMITEMS:=PLAYER[FCHEST].NUMITEMS-1;
                            FOR A:=POINT TO PLAYER[FCHEST].NUMITEMS  DO
                             PLAYER[FCHEST].ITEMS[A]:=PLAYER[FCHEST].ITEMS[A+1];
                           END;


                       END;


                    BAR(485,160,625,300);
                     IF POINT=PLAYER[FCHEST].NUMITEMS+1 THEN
                       POINT:=POINT-1;


                END;
               UNTIL (DOOR='Q') OR (PLAYER[FCHEST].NUMITEMS=0);
               END;


            END;

       'U':IF MMOVE>=3 THEN
            BEGIN
             FOR B:=1 TO PLAYER[J].NUMITEMS DO
                     BEGIN
                        OUTTEXTXY(495,160+(10*B),PLAYER[J].ITEMS [B].NAME);
                     END;


             POINT:=1;
             CURSOR(POINT,OLDPOINT,DOOR,PLAYER[J].NUMITEMS);
             BAR(485,160,625,300);
             USE(XPOS,YPOS,SX,SY,POINT);
             MMOVE:=MMOVE-3;
           END;


       'C':IF MMOVE>=3 THEN
           IF PLAYER[J].MAGIC=FALSE THEN
             PRINTSTRING('NOT A MAGIC USER.',FALSE)
           ELSE
             BEGIN

              GETLS(LEVEL,SPELL);

              OK:=FALSE;
              CASE LEVEL OF
                1:IF PLAYER[J].SP>=10 THEN
                   BEGIN
                    OK:=TRUE;
                    PLAYER[J].SP:=PLAYER[J].SP-10;
                   END;
                2:IF PLAYER[J].SP>=20 THEN
                   BEGIN
                    OK:=TRUE;
                    PLAYER[J].SP:=PLAYER[J].SP-20;
                   END;
                3:IF PLAYER[J].SP>=30 THEN
                   BEGIN
                    OK:=TRUE;
                    PLAYER[J].SP:=PLAYER[J].SP-30;
                   END;
                4:IF PLAYER[J].SP>=40 THEN
                   BEGIN
                    OK:=TRUE;
                    PLAYER[J].SP:=PLAYER[J].SP-40;
                   END;

                END;


               IF OK THEN
                BEGIN
                 GETSPELL(LEVEL,SPELL,XPOS,YPOS,SX,SY);
                 MMOVE:=MMOVE-3;
                END
              ELSE
               PRINTSTRING('NOT ENOUGH SPELL POINTS.',FALSE);

            END;






        'A':IF MMOVE>=3 THEN
            BEGIN
             MMOVE:=MMOVE-3;
             ATTACKSTRING:='ATTACK- '+PLAYER[J].ITEMS[PLAYER[J].READY].NAME+' DIRECTION?';
             PRINTSTRING(ATTACKSTRING,FALSE);
             COMMANDSIGHT(XPOS,YPOS,XOLD,YOLD,SX,SY);
             HITMON:=0;
             WHICHMONSTER(HITMON);
             IF HITMON<>0 THEN
              SEEIFHIT(PLAYER[J].LEVEL,MONSTER[HITMON].AC,PLAYER[J].ITEMS[PLAYER[J].READY].SLOTS[1],DAMAGE);

              IF PLAYER[J].ITEMS[PLAYER[J].READY].ID=1 THEN
              BEGIN
               HITSOMETHING:=TRUE;
               IF ((SQR(GX-XPOS) =1)OR (SQR(GX-XPOS) =0)) AND
                  ((SQR(GY-YPOS) =1)OR (SQR(GY-YPOS) =0)) THEN
                   HITSOMETHING:=FALSE;
              END;

             IF PLAYER[J].ITEMS[PLAYER[J].READY].ID=2 THEN
               BEGIN
                ATTACK(XPOS,YPOS,XOLD,YOLD,SX,SY,PLAYER[J].ITEMS[PLAYER[J].READY].SLOTS[2]
                ,PLAYER[J].ITEMS[PLAYER[J].READY].SLOTS[3],PLAYER[J].ITEMS[PLAYER[J].READY].SLOTS[4],
                PLAYER[J].ITEMS[PLAYER[J].READY].SLOTS[5],PLAYER[J].ITEMS[PLAYER[J].READY].SLOTS[6],DAMAGE,HITSOMETHING);

                 PLAYER[J].NUMITEMS:=PLAYER[J].NUMITEMS-1;

                   FOR A:=PLAYER[J].READY TO PLAYER[J].NUMITEMS DO
                      PLAYER[J].ITEMS[A]:=PLAYER[J].ITEMS[A+1];
                PLAYER[J].READY:=0;
               END;


             IF PLAYER[J].ITEMS[PLAYER[J].READY].ID=5 THEN
               BEGIN
                ALLOWED:=FALSE;
                FOR A:=1 TO PLAYER[J].NUMITEMS DO
                 IF (PLAYER[J].ITEMS[A].ID=12) AND (ALLOWED=FALSE)THEN
                     IF PLAYER[J].ITEMS[A].SLOTS[1]>0 THEN
                      BEGIN
                       PLAYER[J].ITEMS[A].SLOTS[1]:=PLAYER[J].ITEMS[A].SLOTS[1]-1;
                       ALLOWED:=TRUE;
                       B:=A;
                      END;


               IF ALLOWED THEN
                 BEGIN
                  ATTACK(XPOS,YPOS,XOLD,YOLD,SX,SY,PLAYER[J].ITEMS[PLAYER[J].READY].SLOTS[2]
                  ,PLAYER[J].ITEMS[PLAYER[J].READY].SLOTS[3],PLAYER[J].ITEMS[PLAYER[J].READY].SLOTS[4],
                  PLAYER[J].ITEMS[PLAYER[J].READY].SLOTS[5],PLAYER[J].ITEMS[PLAYER[J].READY].SLOTS[6],DAMAGE,HITSOMETHING);


                  IF PLAYER[J].ITEMS[B].SLOTS[1]=0 THEN
                   BEGIN
                    PLAYER[J].NUMITEMS:=PLAYER[J].NUMITEMS-1;

                     FOR A:=B TO PLAYER[J].NUMITEMS DO
                        PLAYER[J].ITEMS[A]:=PLAYER[J].ITEMS[A+1];
                    PLAYER[J].READY:=0;
                   END;
                 END;
              END;

            IF PLAYER[J].ITEMS[PLAYER[J].READY].ID=6 THEN
               BEGIN
               IF PLAYER[J].ITEMS[PLAYER[J].READY].SLOTS[7]>0 THEN
                 BEGIN
                  ATTACK(XPOS,YPOS,XOLD,YOLD,SX,SY,PLAYER[J].ITEMS[PLAYER[J].READY].SLOTS[2]
                  ,PLAYER[J].ITEMS[PLAYER[J].READY].SLOTS[3],PLAYER[J].ITEMS[PLAYER[J].READY].SLOTS[4],
                  PLAYER[J].ITEMS[PLAYER[J].READY].SLOTS[5],PLAYER[J].ITEMS[PLAYER[J].READY].SLOTS[6],DAMAGE,HITSOMETHING);

                  PLAYER[J].ITEMS[PLAYER[J].READY].SLOTS[7]:=
                  PLAYER[J].ITEMS[PLAYER[J].READY].SLOTS[7]-1;

                   END
               ELSE
                 PRINTSTRING('RECHARGE.',FALSE);

               END;




              MONSTER[HITMON].HOSTILE:=TRUE;

              IF (HITSOMETHING=FALSE) AND (DAMAGE>=1) AND (HITMON<>0) THEN
                MONSTERHIT(DAMAGE,HITMON)
               ELSE
                MISS;


           END;


        'V':VIEWCHARACTER;
        'S':IF MMOVE>=4 THEN
            BEGIN
             MMOVE:=MMOVE-4;
             PRINTSTRING('SEARCH- ALL DIRECTION?',FALSE);
             SEARCHFORTRAPS(XPOS,YPOS,SX,SY);
            END;
        'L':IF PLAYER[J].NUMITEMS>0 THEN
            BEGIN
            POINT:=1;
            REPEAT
             FOR B:=1 TO PLAYER[J].NUMITEMS DO
                       BEGIN
                        OUTTEXTXY(495,160+(10*B),PLAYER[J].ITEMS[B].NAME);
                        IF PLAYER[J].ITEMS[B].EQUIPPED=TRUE THEN
                          BEGIN
                           MOVETO(480,160+(10*B));
                           OUTTEXT('*');
                          END;
                       END;



                       CURSOR(POINT,OLDPOINT,DOOR,PLAYER[J].NUMITEMS);
                       IF (DOOR=' ') AND (PLAYER[J].ITEMS[POINT].EQUIPPED<>TRUE) THEN
                          BEGIN
                           LOSEITEM(J,POINT);
                           IF POINT=PLAYER[J].NUMITEMS+1 THEN
                              POINT:=POINT-1;
                          END;
                       BAR(470,160,625,300);
           UNTIL (DOOR='Q') OR (PLAYER[J].NUMITEMS=0);
            END;

    'D':
      BEGIN
        IF MMOVE>=3 THEN
        PRINTSTRING('DISARM- DIRECTION?',FALSE);
        MMOVE:=MMOVE-3;
        DOOR:=READKEY;
           CASE DOOR OF
           '8':BEGIN
                IF MAP.TRAP[XPOS,YPOS-1]<>0 THEN
                  BEGIN
                    MAP.TRAP[XPOS,YPOS-1]:=0;
                   X:=((XPOS+PLACEX)-((CSX-1)*NUMTX))*30;
                   Y:=((YPOS+PLACEY-1)-((CSY-1)*NUMTY))*25;
                   IF (YPOS) > ((CSY-1)*NUMTY)+1 THEN
                     PUTIMAGE(X,Y,TILE[MAP.TILES[PLAYER[J].XPOS,PLAYER[J].YPOS-1]]^,NORMALPUT);
                  END;
               END;
           '2':BEGIN
                IF MAP.TRAP[XPOS,YPOS+1]<>0 THEN
                  BEGIN
                   MAP.TRAP[XPOS,YPOS+1]:=0;
                   X:=((XPOS+PLACEX)-((CSX-1)*NUMTX))*30;
                   Y:=((YPOS+PLACEY+1)-((CSY-1)*NUMTY))*25;
                   IF (YPOS) < ((CSY)*NUMTY) THEN
                    PUTIMAGE(X,Y,TILE[MAP.TILES[PLAYER[J].XPOS,PLAYER[J].YPOS+1]]^,NORMALPUT);
                  END;
               END;
           '4':BEGIN
                IF MAP.TRAP[XPOS-1,YPOS]<>0 THEN
                  BEGIN
                MAP.TRAP[XPOS-1,YPOS]:=0;
                   X:=((XPOS+PLACEX-1)-((CSX-1)*NUMTX))*30;
                   Y:=((YPOS+PLACEY)-((CSY-1)*NUMTY))*25;
                   IF (XPOS) > ((CSX-1)*NUMTX)+1 THEN
                    PUTIMAGE(X,Y,TILE[MAP.TILES[PLAYER[J].XPOS-1,PLAYER[J].YPOS]]^,NORMALPUT);
                  END;
               END;
           '6':BEGIN
                 IF MAP.TRAP[XPOS+1,YPOS]<>0 THEN
                  BEGIN
                   MAP.TRAP[XPOS+1,YPOS]:=0;
                   X:=((XPOS+PLACEX+1)-((CSX-1)*NUMTX))*30;
                   Y:=((YPOS+PLACEY)-((CSY-1)*NUMTY))*25;
                   IF (XPOS) < ((CSX)*NUMTX) THEN
                     PUTIMAGE(X,Y,TILE[MAP.TILES[PLAYER[J].XPOS+1,PLAYER[J].YPOS]]^,NORMALPUT);
                  END;
               END;



            END;
           END;


    END;


  END;

PROCEDURE MESSAGE;
 VAR
  MESSAGE:STRING;
  C:INTEGER;
 BEGIN


      
      ROOM[MAP.ROOM[PLAYER[J].XPOS,PLAYER[J].YPOS]].ENTERED:=TRUE;
      RESET(FIN);
      FOR C:=1 TO MAP.ROOM[PLAYER[J].XPOS,PLAYER[J].YPOS] DO
       READLN(FIN);


      READLN(FIN,MESSAGE);

      PRINTSTRING(MESSAGE,TRUE);

 END;







PROCEDURE LOS(XM,YM,XP,YP,SX,SY:INTEGER);
  VAR
  XT,YT:INTEGER;
  XA,YA:INTEGER;
  XW,YW:INTEGER;
  REALX,REALY:REAL;
  SLOPEX:REAL;
  SLOPEY:REAL;
  DGX,DGY:INTEGER;
  HITSOMETHING:BOOLEAN;
  DISTANCE:REAL;
  DRATIO:REAL;
  MCHECK:INTEGER;
  HITMON:BYTE;

  BEGIN
             CLEAR:=TRUE;
             GX:=XP;
             GY:=YP;


             GXS:=SX;
             GYS:=SY;
             X:=((GX+PLACEX)-((CSX-1)*NUMTX))*30;
             Y:=((GY+PLACEY)-((CSY-1)*NUMTY))*25;




             X:=((GX+PLACEX)-((CSX-1)*NUMTX))*30;
             Y:=((GY+PLACEY)-((CSY-1)*NUMTY))*25;


            XT:=GX;
            YT:=GY;
            XA:=XM;
            YA:=YM;

            REALX:=((XA+PLACEX)-((CSX-1)*NUMTX))*30+10;
            REALY:=((YA+PLACEY)-((CSY-1)*NUMTY))*25+10;

            DGX :=((XT+PLACEX)-((CSX-1)*NUMTX))*30+10;
            DGY :=((YT+PLACEY)-((CSY-1)*NUMTY))*25+10;

            DISTANCE:=SQRT( SQR(DGX-REALX) + SQR(DGY-REALY));
            DRATIO:=(DISTANCE / 5)+1;

            SLOPEX:=(DGX-REALX) / DRATIO;
            SLOPEY:=(DGY-REALY) / DRATIO;


            HITSOMETHING:=FALSE;

           REPEAT

            REALX:=REALX+ SLOPEX;
            REALY:=REALY+ SLOPEY;

            X:=ROUND(REALX);
            Y:=ROUND(REALY);


            XW:=(X) DIV 30-PLACEX+NUMTX*(CSX-1);

            YW:=(Y) DIV 25-PLACEY+NUMTY*(CSY-1);

            CASE MAP.TILES[XW,YW] OF
                1..10,56..60,87..90,-9..-4:BEGIN
                       HITSOMETHING:=TRUE;
                       CLEAR:=FALSE;
                      END;
            END;










           UNTIL ((XW=XT) AND   (YW=YT) ) OR
                 (HITSOMETHING)   ;
  END;







PROCEDURE MOVEMONSTER(VAR XPOS,YPOS,XOLD,YOLD,SX,SY,FACING,NEWT,OLDT:INTEGER);
 VAR
  DISTANCE:REAL;
  LOOP:INTEGER;
  HOLD:REAL;
  ATTACKID:INTEGER;
  ALLOWED:BOOLEAN;
  DAMAGE:INTEGER;
  DX,DY:INTEGER;
  HITSOMETHING:BOOLEAN;
  CA:BYTE;

   BEGIN
    XOLD:=XPOS;
    YOLD:=YPOS;
    OLDT:=NEWT;
    MOVED:=FALSE;
    HOLD:=1000;
    ATTACKID:=0;
    CA:=RANDOM(MONSTER[J].NUMTYPE)+1;
    FOR LOOP :=1 TO NUMPLAYERS DO
      BEGIN
       DISTANCE:=SQRT(SQR((XPOS-PLAYER[LOOP].XPOS))+SQR((YPOS-PLAYER[LOOP].YPOS)));
       IF DISTANCE<HOLD THEN
         BEGIN

          LOS(XPOS,YPOS,PLAYER[LOOP].XPOS,PLAYER[LOOP].YPOS,SX,SY);
            IF CLEAR=TRUE THEN
             IF PLAYER[LOOP].ALIVE THEN
              IF PLAYER[LOOP].EXIT=FALSE THEN
              BEGIN
               HOLD:=DISTANCE;
               ATTACKID:=LOOP;
               MONSTER[J].XS:=PLAYER[ATTACKID].XPOS;
               MONSTER[J].YS:=PLAYER[ATTACKID].YPOS;
               MONSTER[J].ATTACKI:=ATTACKID;
              END;
         END;
       END;



     IF ((SQR(PLAYER[ATTACKID].XPOS-XPOS) =1)OR (SQR(PLAYER[ATTACKID].XPOS-XPOS) =0)) AND
        ((SQR(PLAYER[ATTACKID].YPOS-YPOS) =1)OR (SQR(PLAYER[ATTACKID].YPOS-YPOS) =0)) THEN
       BEGIN
        IF PLAYER[ATTACKID].ALIVE THEN
        IF MAM>0 THEN
        BEGIN
           MAM:=MAM-1;
           SPOTCHAR(PLAYER[ATTACKID].XPOS,PLAYER[ATTACKID].YPOS,SX,SY);
           X:=((PLAYER[ATTACKID].XPOS+PLACEX)-((CSX-1)*NUMTX))*30;
           Y:=((PLAYER[ATTACKID].YPOS+PLACEY)-((CSY-1)*NUMTY))*25;
           SEEIFHIT(MONSTER[J].LEVEL,PLAYER[ATTACKID].AC,MONSTER[J].ATYPE[CA].ATTACK,DAMAGE);
           IF DAMAGE>0 THEN
             BEGIN
                KILLCHAR(ATTACKID,DAMAGE,PLAYER[ATTACKID].XPOS,PLAYER[ATTACKID].YPOS,MONSTER[J].ATYPE[CA].DTYPE);

             END
           ELSE
             BEGIN
              MISS;
             END;
        END;
       END
    ELSE
     IF MAM>0 THEN
     BEGIN
      LOS(XPOS,YPOS,PLAYER[ATTACKID].XPOS,PLAYER[ATTACKID].YPOS,SX,SY);
       IF MONSTER[J].ATYPE[CA].LONG=TRUE THEN
        IF CLEAR=TRUE THEN
         IF PLAYER[ATTACKID].ALIVE THEN
          BEGIN
           MAM:=MAM-1;
           SPOTCHAR(PLAYER[ATTACKID].XPOS,PLAYER[ATTACKID].YPOS,SX,SY);
           SEEIFHIT(MONSTER[J].LEVEL,PLAYER[ATTACKID].AC,MONSTER[J].ATYPE[CA].ATTACK,DAMAGE);
           ATTACK(XPOS,YPOS,XOLD,YOLD,SX,SY,MONSTER[J].ATYPE[CA].APIC1,MONSTER[J].ATYPE[CA].APIC2
           ,MONSTER[J].ATYPE[CA].APIC3,MONSTER[J].ATYPE[CA].APIC4,MONSTER[J].ATYPE[CA].TOA,DAMAGE,HITSOMETHING);
           IF (HITSOMETHING=FALSE) AND (DAMAGE>0)  THEN
            KILLCHAR(ATTACKID,DAMAGE,PLAYER[ATTACKID].XPOS,PLAYER[ATTACKID].YPOS,MONSTER[J].ATYPE[CA].DTYPE)
           ELSE
            MISS;
          END;
     END;


     IF ATTACKID=0 THEN
       BEGIN
        {IF (DX=MONSTER[J].XS) AND (DY=MONSTER[J].YS) THEN
         BEGIN
          DX:=PLAYER[MONSTER[J].ATTACKI].XPOS;
          DY:=PLAYER[MONSTER[J].ATTACKI].YPOS;
          MONSTER[J].XS:=DX;
          MONSTER[J].YS:=DY;
         END
        ELSE
         BEGIN}
          DX:=MONSTER[J].XS;
          DY:=MONSTER[J].YS;


       END
     ELSE
      BEGIN
       DX:=PLAYER[ATTACKID].XPOS;
       DY:=PLAYER[ATTACKID].YPOS;
       MONSTER[J].ATTACKI:=ATTACKID;
      END;


      IF (YPOS>1) THEN
      IF MAP.VISIBLE[XPOS,YPOS-1] THEN
       BEGIN
        MOVESALLOWED(XPOS,YPOS-1,ALLOWED);
        IF ALLOWED=TRUE THEN
        IF DY<YPOS THEN
          BEGIN
           FACING:=1;
           YPOS:=YPOS-1;
           IF (YPOS) < ((CSY-1)*NUMTY)+1 THEN
              SY:=SY-1;
            MOVED:=TRUE;
           NEWT:=MAP.TILES[XPOS,YPOS];
          END;
        END;


       IF (YPOS<YMAX) THEN
       IF MAP.VISIBLE[XPOS,YPOS+1] THEN
        BEGIN
         MOVESALLOWED(XPOS,YPOS+1,ALLOWED);
         IF ALLOWED=TRUE THEN
        IF DY>YPOS THEN
           BEGIN
            FACING:=3;
            YPOS:=YPOS+1;
            IF (YPOS) > ((CSY)*NUMTY) THEN
               SY:=SY+1;
              MOVED:=TRUE;
            NEWT:=MAP.TILES[XPOS,YPOS];
           END;
         END;

        IF (XPOS>1)  THEN
         IF MAP.VISIBLE[XPOS-1,YPOS] THEN
          BEGIN
           MOVESALLOWED(XPOS-1,YPOS,ALLOWED);
           IF ALLOWED=TRUE THEN
           IF DX<XPOS THEN
            BEGIN
             FACING:=4;
             XPOS:=XPOS-1;
             IF (XPOS) < ((CSX-1)*NUMTX)+1 THEN
               SX:=SX-1;
             MOVED:=TRUE;
             NEWT:=MAP.TILES[XPOS,YPOS];
            END;
          END;

        IF (XPOS<XMAX) THEN
         IF MAP.VISIBLE[XPOS+1,YPOS] THEN
         BEGIN
          MOVESALLOWED(XPOS+1,YPOS,ALLOWED);
          IF ALLOWED=TRUE THEN
          IF DX>XPOS THEN
           BEGIN
            FACING:=2;
            XPOS:=XPOS+1;
            IF (XPOS) > ((CSX)*NUMTX) THEN
               SX:=SX+1;
            MOVED:=TRUE;
            NEWT:=MAP.TILES[XPOS,YPOS];
           END;
         END;

         IF MOVED=TRUE THEN
           MOVESOUND;

  END;


 PROCEDURE MOVENICE(VAR XPOS,YPOS,XOLD,YOLD,SX,SY,FACING,NEWT,OLDT:INTEGER);
 VAR
  DISTANCE:REAL;
  LOOP:INTEGER;
  HOLD:REAL;
  ATTACKID:INTEGER;
  ALLOWED:BOOLEAN;
  DAMAGE:INTEGER;
  DX,DY:INTEGER;
  HITSOMETHING:BOOLEAN;
  RD:INTEGER;

   BEGIN
    XOLD:=XPOS;
    YOLD:=YPOS;
    OLDT:=NEWT;
    MOVED:=FALSE;
    RANDOMIZE;
    RD:= RANDOM(4)+1;


    CASE RD OF

     1: IF (YPOS>1) THEN
       BEGIN
        MOVESALLOWED(XPOS,YPOS-1,ALLOWED);
        IF ALLOWED=TRUE THEN

          BEGIN
           FACING:=1;
           YPOS:=YPOS-1;
           IF (YPOS) < ((CSY-1)*NUMTY)+1 THEN
              SY:=SY-1;
            MOVED:=TRUE;
           NEWT:=MAP.TILES[XPOS,YPOS];
          END;
        END;


     2:  IF (YPOS<YMAX) THEN
        BEGIN
         MOVESALLOWED(XPOS,YPOS+1,ALLOWED);
         IF ALLOWED=TRUE THEN

           BEGIN
            FACING:=3;
            YPOS:=YPOS+1;
            IF (YPOS) > ((CSY)*NUMTY) THEN
               SY:=SY+1;
              MOVED:=TRUE;
            NEWT:=MAP.TILES[XPOS,YPOS];
           END;
         END;

     3:   IF (XPOS>1)  THEN
          BEGIN
           MOVESALLOWED(XPOS-1,YPOS,ALLOWED);
           IF ALLOWED=TRUE THEN
           BEGIN
             FACING:=4;
             XPOS:=XPOS-1;
             IF (XPOS) < ((CSX-1)*NUMTX)+1 THEN
               SX:=SX-1;
             MOVED:=TRUE;
             NEWT:=MAP.TILES[XPOS,YPOS];
            END;
          END;

     4:   IF (XPOS<XMAX) THEN
         BEGIN
          MOVESALLOWED(XPOS+1,YPOS,ALLOWED);
          IF ALLOWED=TRUE THEN

           BEGIN
            FACING:=2;
            XPOS:=XPOS+1;
            IF (XPOS) > ((CSX)*NUMTX) THEN
               SX:=SX+1;
            MOVED:=TRUE;
            NEWT:=MAP.TILES[XPOS,YPOS];
           END;
         END;
    END;
         IF MOVED=TRUE THEN
           MOVESOUND;

  END;

PROCEDURE SLEEPSEQ(XPOS,YPOS,SX,SY:INTEGER);
 BEGIN
       X:=((XPOS+PLACEX)-((SX-1)*NUMTX))*30;
       Y:=((YPOS+PLACEY)-((SY-1)*NUMTY))*25;
       FOR DIE1 :=1 TO 2 DO
       BEGIN
         PUTIMAGE(X,Y,TILE[102]^,ORPUT);
         DELAY(500);
         PUTIMAGE(X,Y,TILE[MAP.TILES[XPOS,YPOS]]^,NORMALPUT);
         DELAY(500);
       END;
 END;


PROCEDURE DELAYCOUNTERS;
  BEGIN
   IF PLAYER[J].SDELAY>0 THEN
     BEGIN
      PLAYER[J].SDELAY:=PLAYER[J].SDELAY-1;
       IF PLAYER[J].SDELAY=0 THEN
          PLAYER[J].SPEED:=PLAYER[J].RSPEED;
     END;

    IF PLAYER[J].INVINCE>0 THEN
      PLAYER[J].INVINCE:=PLAYER[J].INVINCE-1;

   IF PLAYER[J].INACTIVE>0 THEN
    IF PLAYER[J].ALIVE=TRUE THEN
     BEGIN
      PLAYER[J].INACTIVE:=PLAYER[J].INACTIVE-1;
      PUTTILES(PLAYER[J].XPOS,PLAYER[J].YPOS,PLAYER[J].XOLD,PLAYER[J].YOLD,
       PLAYER[J].SX,PLAYER[J].SY,PLAYER[J].FACING,PLAYER[J].CHARID
       ,PLAYER[J].NEWT,PLAYER[J].OLDT);
      SLEEPSEQ(PLAYER[J].XPOS,PLAYER[J].YPOS,PLAYER[J].SX,PLAYER[J].SY);
     END;

   IF PLAYER[J].ALIVE=TRUE THEN
    IF PLAYER[J].POISON=TRUE THEN
      KILLCHAR(J,1,PLAYER[J].XPOS,PLAYER[J].YPOS,1)




 END;


PROCEDURE DRAWBOARDER;


 BEGIN
  SETCOLOR(15);
  LINE(29,24,29,326);
  LINE(29,24,629{481},24);
  LINE(29,326,629{481},326);
  LINE(451,24,451,326);

  LINE(19,14,19,336);
  LINE(19,14,639{491},14);
  LINE(19,336,639{491},336);
  LINE(461,24,461,326);

  LINE(639,14,639,336);
  LINE(629,24,629,326);


  LINE(461,130,629,130);
  LINE(461,140,629,140);

  SETCOLOR(0);



  LINE(452,24,460,24);
  LINE(452,24,460,24);

  LINE(452,326,460,326);
  LINE(452,326,460,326);

  LINE(461,131,461,139);
  LINE(629,131,629,139);



  SETCOLOR(15);




  SETFILLSTYLE(1,1);
  FLOODFILL(20,15,15);
  SETFILLSTYLE(1,0);




 END;

PROCEDURE ANYBODYTHERE;
 VAR
  LOOP:INTEGER;

  BEGIN
   SEESOMEBODY:=FALSE;
   FOR LOOP :=1 TO NUMPLAYERS DO
      BEGIN
          LOS(MONSTER[J].XPOS,MONSTER[J].YPOS,PLAYER[LOOP].XPOS,PLAYER[LOOP].YPOS,MONSTER[J].SX,MONSTER[J].SY);
            IF CLEAR=TRUE THEN
             IF PLAYER[LOOP].ALIVE THEN
              IF PLAYER[LOOP].EXIT=FALSE THEN
              BEGIN
               SEESOMEBODY:=TRUE;
               MONSTER[J].LASTCHANCE:=TRUE;
              END;
       END;

   IF (SEESOMEBODY=FALSE) AND (MONSTER[J].LASTCHANCE=TRUE) THEN
      IF ((MONSTER[J].XPOS)<>(MONSTER[J].XS)) OR ((MONSTER[J].YPOS)<>(MONSTER[J].YS)) THEN
       BEGIN
        SEESOMEBODY:=TRUE;
        MONSTER[J].LASTCHANCE:=FALSE;
       END;


  END;


PROCEDURE ENDING;
 VAR
  BANDIT:ARRAY[1..10]OF INTEGER;
  MISSION,NUMBANDIT,REWARD,L:INTEGER;
  ENDSTRING:STRING;
  GOOP:INTEGER;
  ALLDEAD:BOOLEAN;
 BEGIN
  Assign(FQUEST,'KEEP.QST');
  Reset(FQUEST);
  READLN(FQUEST,MISSION);

  CASE MISSION OF
    1:BEGIN
       READLN(FQUEST,NUMBANDIT);
       FOR GOOP:=1 TO NUMBANDIT DO
         READLN(FQUEST,BANDIT[GOOP]);
       READLN(FQUEST,REWARD);
       ALLDEAD:=TRUE;
       FOR GOOP:=1 TO NUMBANDIT DO
        IF MONSTER[BANDIT[GOOP]].HITPOINTS>0 THEN
          ALLDEAD:=FALSE;

       IF ALLDEAD THEN
           READLN(FQUEST,ENDSTRING)
       ELSE
        BEGIN
         READLN(FQUEST);
         READLN(FQUEST,ENDSTRING);
        END;

       PRINTSTRING(ENDSTRING,TRUE);

       IF ALLDEAD THEN
         FOR L:=1 TO NUMPLAYERS DO
           PLAYER[J].GOLD:=PLAYER[J].GOLD+100;

      END;

   END;
  END;




BEGIN
 NUMMON:=0;
 NUMCHEST:=0;
 LOADMAP;
 GD:=EGA;GM:=1; INITGRAPH(GD,GM, ' ');
 SETACTIVEPAGE(0);
 SETVISUALPAGE(1);

 LOADGRAPHICS;
{ SETVISUALPAGE(0);
 SETTEXTSTYLE(2,0,5);}
 SETFILLSTYLE(1,0);



 CSX:=2;
 CSY:=2;
 FOR J:=1 TO NUMMON DO
   BEGIN
    MONSTER[J].LEVEL:=1;
   END;





 PLAYER[1].SX:=3;
 PLAYER[1].SY:=4;
 PLAYER[1].YPOS:=48;
 PLAYER[1].XPOS:=34;
 PLAYER[1].YOLD:=48;
 PLAYER[1].XOLD:=34;
 PLAYER[1].FACING:=2;
 PLAYER[1].CHARID:=1;
 PLAYER[1].HITPOINTS:=12;
 PLAYER[1].NUMITEMS:=0;
 PLAYER[1].READY:=0;
 PLAYER[1].NAME:='ELRON';






 PLAYER[2].SX:=3;
 PLAYER[2].SY:=4;
 PLAYER[2].YPOS:=48;
 PLAYER[2].XPOS:=35;
 PLAYER[2].YOLD:=48;
 PLAYER[2].XOLD:=35;
 PLAYER[2].FACING:=2;
 PLAYER[2].CHARID:=2;

 PLAYER[2].HITPOINTS:=12;
 PLAYER[2].NUMITEMS:=0;
 PLAYER[2].READY:=0;
 PLAYER[2].NAME:='MERLIN';
 PLAYER[2].MAGIC:=TRUE;
 PLAYER[2].SP:=1000;




 PLAYER[3].SX:=3;
 PLAYER[3].SY:=4;
 PLAYER[3].YPOS:=48;
 PLAYER[3].XPOS:=36;
 PLAYER[3].YOLD:=48;
 PLAYER[3].XOLD:=36;
 PLAYER[3].FACING:=2;
 PLAYER[3].CHARID:=24;
 PLAYER[3].HITPOINTS:=12;

 PLAYER[3].READY:=0;
 PLAYER[3].NUMITEMS:=0;
 PLAYER[3].NAME:='ODIN';


 PLAYER[4].SX:=3;
 PLAYER[4].SY:=4;
 PLAYER[4].YPOS:=48;
 PLAYER[4].XPOS:=37;
 PLAYER[4].YOLD:=48;
 PLAYER[4].XOLD:=37;
 PLAYER[4].FACING:=2;
 PLAYER[4].CHARID:=5;
 PLAYER[4].HITPOINTS:=12;

 PLAYER[4].READY:=0;
 PLAYER[4].NUMITEMS:=0;
 PLAYER[4].NAME:='SKREECH';


 FOR J:=1 TO 4 DO
  BEGIN
   PLAYER[J].ITEMS[0].ID:=1;
   PLAYER[J].ITEMS[0].NAME:='FIST';
   PLAYER[J].ITEMS[0].SLOTS[1]:=1;
   PLAYER[J].ITEMS[0].SLOTS[8]:=0;

   PLAYER[J].WORN:=0;
   PLAYER[J].AC:=0;
   PLAYER[J].SHIELD:=0;
   PLAYER[J].GOLD:=0;
   PLAYER[J].ALIVE:=TRUE;
   PLAYER[J].EXP:=0;
   PLAYER[J].KEYS:=0;
   PLAYER[J].OLDT:=MAP.TILES[PLAYER[J].XPOS,PLAYER[J].YPOS];
   PLAYER[J].NEWT:=MAP.TILES[PLAYER[J].XPOS,PLAYER[J].YPOS];;
   PLAYER[J].MAGIC:=FALSE;
   PLAYER[J].SPEED:=6;
   PLAYER[J].RSPEED:=6;
   PLAYER[J].SDELAY:=0;
   PLAYER[J].INVINCE:=0;
   PLAYER[J].INACTIVE:=0;
   PLAYER[J].LEVEL:=2;
   PLAYER[J].MAXHP:=12;
   PLAYER[J].POISON:=FALSE;
   GETCIMAGE(1,player[j].charid);
   MAP.TILES[player[j].XPOS,player[j].ypos]:=CIMAGE;
   PLAYER[J].EXIT:=FALSE;



  END;

FOR J:=1 TO NUMMON DO
 BEGIN
   FOR X:=-1 TO 1 DO
    FOR Y:=-1 TO 1 DO
      IF (MAP.TILES[MONSTER[J].XPOS+X,MONSTER[J].YPOS+Y]=0)  OR (MAP.TILES[MONSTER[J].XPOS+X,MONSTER[J].YPOS+Y]=-3) THEN
          BEGIN
           MONSTER[J].OLDT:=MAP.TILES[MONSTER[J].XPOS+X,MONSTER[J].YPOS+Y];
           MONSTER[J].NEWT:=MAP.TILES[MONSTER[J].XPOS+X,MONSTER[J].YPOS+Y];
           BREAK;
          END;
 END;


PLAYER[2].MAGIC:=TRUE;

 NUMPLAYERS:=4;


 SETACTIVEPAGE(0);
 SETVISUALPAGE(1);
 DRAWBOARDER;

 SETACTIVEPAGE(1);
 SETVISUALPAGE(0);
 DRAWBOARDER;


 PAGE:=0;

J:=1;
 PLAYERTEXT;
 PLAYERSTATUS;
 STEP:=TRUE;


REPEAT

 FOR J:=1 TO NUMPLAYERS DO
 BEGIN
  DELAYCOUNTERS;

  IF PLAYER[J].ALIVE=TRUE THEN
  IF PLAYER[J].INACTIVE=0 THEN
  IF PLAYER[J].EXIT=FALSE THEN
   BEGIN

    PLAYERTEXT;
    PLAYERSTATUS;
    MMOVE:=PLAYER[J].SPEED;
   REPEAT





   PUTTILES(PLAYER[J].XPOS,PLAYER[J].YPOS,PLAYER[J].XOLD,PLAYER[J].YOLD,
            PLAYER[J].SX,PLAYER[J].SY,PLAYER[J].FACING,PLAYER[J].CHARID
            ,PLAYER[J].NEWT,PLAYER[J].OLDT);



   VISIBILITY(PLAYER[J].XPOS,PLAYER[J].YPOS,PLAYER[J].SX,PLAYER[J].SY);


     IF (MAP.ROOM[PLAYER[J].XPOS,PLAYER[J].YPOS]<>0)
      AND (ROOM[MAP.ROOM[PLAYER[J].XPOS,PLAYER[J].YPOS]].ENTERED=FALSE) THEN
        MESSAGE;



    IF MAP.TRAP[PLAYER[J].XPOS,PLAYER[J].YPOS]<>0 THEN
     HITTRAP(PLAYER[J].XPOS,PLAYER[J].YPOS,PLAYER[J].SX,PLAYER[J].SY);

   IF PLAYER[J].ALIVE THEN
    MOVE(PLAYER[J].XPOS,PLAYER[J].YPOS,PLAYER[J].XOLD,PLAYER[J].YOLD,
      PLAYER[J].SX,PLAYER[J].SY,PLAYER[J].FACING,PLAYER[J].NEWT,PLAYER[J].OLDT);







{   IF STEP=TRUE THEN
    STEP:=FALSE
   ELSE
     STEP:=TRUE;}


 UNTIL (COMMAND='E') OR NOT(PLAYER[J].ALIVE)OR (PLAYER[J].EXIT=TRUE);
END;
END;

   FOR J:=1 TO NUMMON DO
   IF MONSTER[J].ACTIVE=TRUE THEN
   IF MONSTER[J].HITPOINTS>0 THEN
    BEGIN

    ANYBODYTHERE;
    IF SEESOMEBODY THEN

    BEGIN

    IF MONSTER[J].DELAY>0 THEN
      BEGIN
       MONSTER[J].DELAY:=MONSTER[J].DELAY-1;
       PUTTILES(MONSTER[J].XPOS,MONSTER[J].YPOS,MONSTER[J].XPOS,MONSTER[J].YPOS,
             MONSTER[J].SX,MONSTER[J].SY,MONSTER[J].FACING,MONSTER[J].CHARID
             ,MONSTER[J].NEWT,MONSTER[J].OLDT);
       SLEEPSEQ(MONSTER[J].XPOS,MONSTER[J].YPOS,MONSTER[J].SX,MONSTER[J].SY);
      END;





     IF MONSTER[J].DELAY= 0 THEN
     BEGIN

      MAM:=MONSTER[J].NUMAT;
      MMOVE:=0;
       PUTTILES(MONSTER[J].XPOS,MONSTER[J].YPOS,MONSTER[J].XPOS,MONSTER[J].YPOS,
             MONSTER[J].SX,MONSTER[J].SY,MONSTER[J].FACING,MONSTER[J].CHARID
             ,MONSTER[J].NEWT,MONSTER[J].OLDT);
       IF MONSTER[J].REG= TRUE THEN
      BEGIN
        MONSTER[J].HITPOINTS:=MONSTER[J].HITPOINTS+2;
        PRINTSTRING('THE TROLL REGENERATES.',FALSE);
      END;

      REPEAT



       IF MONSTER[J].HOSTILE=TRUE THEN
        MOVEMONSTER(MONSTER[J].XPOS,MONSTER[J].YPOS,MONSTER[J].XOLD,MONSTER[J].YOLD,
         MONSTER[J].SX,MONSTER[J].SY,MONSTER[J].FACING,MONSTER[J].NEWT,MONSTER[J].OLDT)
       ELSE
        MOVENICE(MONSTER[J].XPOS,MONSTER[J].YPOS,MONSTER[J].XOLD,MONSTER[J].YOLD,
         MONSTER[J].SX,MONSTER[J].SY,MONSTER[J].FACING,MONSTER[J].NEWT,MONSTER[J].OLDT);

      IF MOVED=TRUE THEN
         PUTTILES(MONSTER[J].XPOS,MONSTER[J].YPOS,MONSTER[J].XOLD,MONSTER[J].YOLD,
             MONSTER[J].SX,MONSTER[J].SY,MONSTER[J].FACING,MONSTER[J].CHARID
             ,MONSTER[J].NEWT,MONSTER[J].OLDT );




       MMOVE:=MMOVE+1;
      IF MOVED THEN
       DELAY(100);
      UNTIL MMOVE=MONSTER[J].SPEED;

     END;
    END;
   END;



  LEFT:=FALSE;
  J:=0;
  REPEAT
   BEGIN
    J:=J+1;
    IF (PLAYER[J].ALIVE=TRUE)THEN
      IF (PLAYER[J].EXIT=FALSE) THEN
        LEFT:=FALSE
      ELSE
       LEFT:=TRUE;

   END;
  UNTIL  (J=NUMPLAYERS)OR (LEFT=FALSE);

  ALLDEAD:=TRUE;
  FOR J:=1 TO NUMPLAYERS DO
     IF PLAYER[J].ALIVE=TRUE THEN
      ALLDEAD:=FALSE;


UNTIL LEFT OR ALLDEAD ;

ENDING;



END.






