#include <dos.h>
#include <alloc.h>
#include <stdio.h>
#include <conio.h>
#include <wgt.h>
#include <scroll.h>

// WordUp Graphics Toolkit Scrolling Demo
// PACMAN!


void checkpos(void);

int spx,spy;
int pacanim,pacdir;
int ox,oy;

wgtmap mymap;			// our world map

int kbdon[35]={0,0,0,0,0};	// our keyboard on/off array;
int kbdscanlist[35]={72,80,75,77,1};	// our keyboard scan codes;
// You must have the above two if you want the keyboard interrupt 

color palette[256];		// our palette of colours

block blocks[201];		// our blocks for the map
block sprites[201];		// our sprites 


int bonus,traptime[5];
int killtime[5];
int i;
int pacspeed=8,ghostspeed=8;
int moved[5],movedir[5];
int bluetime;

void moveghost(int);

void main(void)
{
vga256();
wloadsprites(&palette,"pacman.spr",blocks);    	// load blocks
wloadsprites(&palette,"pac.spr",sprites);    	// load sprites

mymap=wloadmap("pacman.wmp");		// load our world map


winitscroll(10,10);				// make a 12x10 box
						// for the scrolling

wnormscreen();					// go back to normal screen
wcls(0);					// clear it
wbutt(1,1,318,198);

wshowwindow(0,0,mymap);			// start looking at world
						// at 0,0
installkbd();					// start new keyboard interrupt

numsprites=5;
spr[0].on=1; spr[0].x=16; spr[0].y=16; spr[0].num=1;

spr[1].on=1; spr[1].x=16; spr[1].y=16; spr[1].num=21;
spr[2].on=1; spr[2].x=16; spr[2].y=16; spr[2].num=22;
spr[3].on=1; spr[3].x=16; spr[3].y=16; spr[3].num=23;
spr[4].on=1; spr[4].x=16; spr[4].y=16; spr[4].num=24;
for (i=1; i<5; i++) moved[i]=0;
pacanim=1;


do
{
spx=0;
spy=0;
ox=spr[0].x;
oy=spr[0].y;

if (kbdon[2]==1)		// Pressing left
  {
  spr[0].x-=pacspeed;
  checkpos();
  pacdir=2;
  }
else if (kbdon[3]==1)	// Pressing right
  {
  spr[0].x+=pacspeed;
  checkpos();
  pacdir=0;
  }
else if (kbdon[0]==1)		// Pressing up
  {
  spr[0].y-=pacspeed;
  checkpos();
  pacdir=1;
  }
else if (kbdon[1]==1)	// Pressing down
  {
  spr[0].y+=pacspeed;
  checkpos();
  pacdir=3;
  }

    if (bluetime>0)
    bluetime--;

for (i=1; i<5; i++)
 {
 if (traptime[i]==0)
   {
   moveghost(i);
 if (bluetime>0)
    spr[i].num=25;
 if ((bluetime==1) | ((bluetime<40) & (bluetime % 2==1)))
    spr[i].num=20+i;
 if ((soverlap(i,0)==1) & (traptime[i]==0))
   {
   if (bluetime>0)
     {
     spr[i].num=27+bonus;
     bonus++;
     traptime[i]=100;
     }
   }
  }
  else traptime[i]--;
 if (traptime[i]==1)
    {
    spr[i].x=256;
    spr[i].y=256;
    bonus=0;
}
 }


pacanim++;
if (pacanim>5)
  pacanim=1;
spr[0].num=pacanim+(pacdir*5);


if (spr[0].x-worldx<windowmaxx/2-1)
   spx=-pacspeed;
else if (spr[0].x-worldx>windowmaxx/2+1)
   spx=pacspeed;
if (spr[0].y-worldy<windowmaxy/2-1)
   spy=-pacspeed;
else if (spr[0].y-worldy>windowmaxy/2+1)
   spy=pacspeed;

nosound();
wscrollwindow(spx,spy,mymap);	// update the scrolling window
wshowsprites();
wcopyscroll(80,15);
} while (kbdon[4] !=1);			// until ESC is pressed

uninstallkbd();
wendscroll();
wfreesprites(blocks);
wfreesprites(sprites);
wfreemap(mymap);
textmode(C80);
}

void checkpos(void)
{
int hit=0;

  i=wgetworldblock(spr[0].x,spr[0].y,mymap);
  if (i<12)
    hit=1;
  i=wgetworldblock(spr[0].x+15,spr[0].y,mymap);
  if (i<12)
    hit=1;
  i=wgetworldblock(spr[0].x,spr[0].y+15,mymap);
  if (i<12)
    hit=1;
  i=wgetworldblock(spr[0].x+15,spr[0].y+15,mymap);
  if (i<12)
    hit=1;
  i=wgetworldblock(spr[0].x+7,spr[0].y+7,mymap);
  if (i>=13)
    {
    sound(500);
    wputworldblock(spr[0].x+7,spr[0].y+7,12,mymap);
    }
  if (i>13)
     {
     bluetime+=150;
     }

  if (hit==1)
     {
     spr[0].x=ox;
     spr[0].y=oy;                   
     }
  }


void moveghost(int numb)
{
int gox,goy,hit=0,j;

gox=spr[numb].x;
goy=spr[numb].y;

moveagain:
;
if (moved[numb]==0)
   movedir[numb]=(rand() % 5)+1;

   if (movedir[numb]==1)
   spr[numb].x+=ghostspeed;
   else if (movedir[numb]==2)
   spr[numb].x-=ghostspeed;
   else if (movedir[numb]==3)
   spr[numb].y+=ghostspeed;
   else if (movedir[numb]==4)
   spr[numb].y-=ghostspeed;

   moved[numb]+=ghostspeed;
   if (moved[numb]>=16)
     moved[numb]=0;

 if (spr[numb].x<0)
    spr[numb].x=0;
else if (spr[numb].x>(mapwidth-1)*16)
    spr[numb].x=(mapwidth-1)*16;
 if (spr[numb].y<0)
    spr[numb].y=0;
else if (spr[numb].y>(mapheight-1)*16)
    spr[numb].y=(mapheight-1)*16;

  j=wgetworldblock(spr[numb].x,spr[numb].y,mymap);
  if (j<12)
    hit=1;
  j=wgetworldblock(spr[numb].x+15,spr[numb].y,mymap);
  if (j<12)
    hit=1;
  j=wgetworldblock(spr[numb].x,spr[numb].y+15,mymap);
  if (j<12)
    hit=1;
  j=wgetworldblock(spr[numb].x+15,spr[numb].y+15,mymap);
  if (j<12)
    hit=1;
  if (hit==1)
     {
     spr[numb].x=gox;
     spr[numb].y=goy;
     moved[numb]=0;
     }
}
