/*
 *  - Large view of the world
 */


#include <stdio.h>
#include "igui.hpp"
#include "../ithelib.h"
#include "../console.h"
#include "../core.hpp"
#include "../gamedata.h"
#include "../object.hpp"
#include "../oscli.h"
#include "../init.h"
#include "menusys.h"

// defines

//#define PATHBUILDER
#define MAX_PATH_SQUARES 4096
#define MicroX 512
#define MicroY 288

// variables

static int pmx=0,pmy=0,path1x=0,path1y=0;
static int SafetyCatch=1,ShowSolid=0,ShowEggs=0;
static int CN_Id,CS_Id,CE_Id,CW_Id;
static char ConnNstr[]="None  ";
static char ConnSstr[]="None  ";
static char ConnWstr[]="None  ";
static char ConnEstr[]="None  ";

extern int focus,BM_Id;
extern int L_bgtile;
//static int PathMode=0;

extern long M_core;     // Total amount of core, from memory.cc
extern int s_proj;      // Flag, are sprites being displayed?
extern int l_proj;      // Flag, are layers being displayed?

// functions

extern int ReadMap(int x,int y);
extern void WriteMap(int x,int y, int tile);
extern void Toolbar();
extern void (*EdUpdateFunc)(void);
extern void DrawMap(int x,int y,char s_proj,char l_proj,char f_proj);

static void OneToOne();
static void PanMap();
static void PanUp();
static void PanDown();
static void PanLeft();
static void PanRight();
static void SetL();
static void SetM();
static void Spray();
static void GoMap();
static void Nothing();

static void Connections();
static void Connections_Update();
static void ConnN();
static void ConnS();
static void ConnE();
static void ConnW();
static void Finish();
static void PathMaker();
extern void PathMe();

// GoFocal - The menu tab function.  This is called from the toolbar

void BM_GoFocal()
{
int temp;               // Used to get button handles

if(focus==4)            // Make sure we don't redraw if the user clicks again
	return;

focus=4;                // This is now the focus
Toolbar();              // Build up the menu system again from scratch
IG_SetFocus(BM_Id);     // And make the button stick inwards

// Add Panning buttons

IG_TextButton(516,104,__up,PanUp,NULL,NULL);         // Pan up button
IG_TextButton(500,128,__left,PanLeft,NULL,NULL);     // Pan left button
IG_TextButton(532,128,__right,PanRight,NULL,NULL);   // Pan right button
IG_TextButton(516,150,__down,PanDown,NULL,NULL);     // Pan down button

temp = IG_ToggleButton(500,256,"Can Edit ",Nothing,NULL,NULL,&SafetyCatch);
IG_SetInText(temp,"Read-Only");

temp = IG_ToggleButton(500,224,"Normal View  ",Nothing,NULL,NULL,&ShowSolid);
IG_SetInText(temp,"Solid Objects");

temp = IG_ToggleButton(500,192,"Don't show eggs",Nothing,NULL,NULL,&ShowEggs);
IG_SetInText(temp,"Display eggs   ");

// Set up Map windows

IG_BlackPanel(MicroX-2,MicroY-2,68,68);

if(curmap->w>=384 || curmap->h>=384)
    {
    IG_BlackPanel(62,62,386,386);
    PanMap();
    IG_AddKey(KEY_UP,PanUp);
    IG_AddKey(KEY_DOWN,PanDown);
    IG_AddKey(KEY_LEFT,PanLeft);
    IG_AddKey(KEY_RIGHT,PanRight);
    }
else
    OneToOne();

EdUpdateFunc=NULL;

IG_Region(64,64,384,384,SetL,SetM,GoMap);

IG_TextButton(496,384,"Connections",Connections,NULL,NULL);

#ifdef PATHBUILDER
temp = IG_TextButton(496,416,"PathMaker",PathMaker,NULL,NULL);
#endif

}

void OneToOne()
{
int temp,cx,cy,div,rx,ry,blockx,blocky,blockw,blockh;
OBJECT *ob;
IG_BlackPanel(62,62,386,386);

for(cy=0;cy<curmap->h;cy++)
	for(cx=0;cx<curmap->w;cx++)
		{
		temp=ReadMap(cx,cy);
		if(temp==RANDOM_TILE)
			putpixel(swapscreen,cx+64,cy+64,ITG_BLUE);
		else
			putpixel(swapscreen,cx+64,cy+64,TIlist[temp].form->seq[0]->thumbcol);
		}

if(ShowSolid || ShowEggs)
	for(cy=0;cy<curmap->h;cy++)
		for(cx=0;cx<curmap->w;cx++)
			{
			ob=GetRawObjectBase(cx,cy);
			for(;ob;ob=ob->next)
				{
				if(ShowSolid && ob->flags.solid)
					if(ob->flags.large)
						{
						if(ob->curdir > CHAR_D) //(U,D,L,R) > D = L,R
							{
							blockx=ob->hblock[BLK_X];
							blocky=ob->hblock[BLK_Y];
							blockw=ob->hblock[BLK_W];
							blockh=ob->hblock[BLK_H];
							}
						else
							{
							blockx=ob->vblock[BLK_X];
							blocky=ob->vblock[BLK_Y];
							blockw=ob->vblock[BLK_W];
							blockh=ob->vblock[BLK_H];
							}
						rectfill(swapscreen,cx+64+blockx,cy+64+blocky,cx+64+blockx+(blockw-1),cy+64+blocky+(blockh-1),ITG_BLUE);
						}
					else
						putpixel(swapscreen,cx+64,cy+64,ITG_BLUE);
				// Show eggs
				if(ShowEggs)
					if(!istricmp_fuzzy(ob->name,"egg*"))
						putpixel(swapscreen,cx+64,cy+64,ITG_YELLOW);
				}
			}


div = curmap->w>>6; //div64
rx=0;
ry=0;
for(cy=0;cy<64;cy++)
	{
	for(cx=0;cx<64;cx++)
		{
		temp = ReadMap(rx,ry);
		if(temp==RANDOM_TILE)
			putpixel(swapscreen,MicroX+cx,MicroY+cy,ITG_BLUE);
		else
			putpixel(swapscreen,MicroX+cx,MicroY+cy,TIlist[temp].form->seq[0]->thumbcol);
		rx+=div;
		}
	rx=0;
	ry+=div;
	}
}

void PanMap()
{
int temp,cx,cy,cw,ch,div,rx,ry,blockx,blocky,blockw,blockh;
OBJECT *ob;

if(pmx+384 > curmap->w)
	pmx = (curmap->w-384);
if(pmy+384 > curmap->h)
	pmy = (curmap->h-384);
if(pmx < 0)
	pmx = 0;
if(pmy < 0)
	pmy = 0;

cw=curmap->w;
if(cw>384)
	cw=384;
ch=curmap->h;
if(ch>384)
	ch=384;

for(cy=0;cy<ch;cy++)
	for(cx=0;cx<cw;cx++)
		{
		temp=ReadMap(cx+pmx,cy+pmy);
		if(temp==RANDOM_TILE)
			putpixel(swapscreen,cx+64,cy+64,ITG_BLUE);
		else
			putpixel(swapscreen,cx+64,cy+64,TIlist[temp].form->seq[0]->thumbcol);
		}

if(ShowSolid || ShowEggs)
	for(cy=0;cy<ch;cy++)
		for(cx=0;cx<cw;cx++)
			{
			ob=GetRawObjectBase(cx+pmx,cy+pmy);
			for(;ob;ob=ob->next)
				{
				if(ShowSolid && ob->flags.solid)
					if(ob->flags.large)
						{
						if(ob->curdir > CHAR_D) //(U,D,L,R) > D = L,R
							{
							blockx=ob->hblock[BLK_X];
							blocky=ob->hblock[BLK_Y];
							blockw=ob->hblock[BLK_W];
							blockh=ob->hblock[BLK_H];
							}
						else
							{
							blockx=ob->vblock[BLK_X];
							blocky=ob->vblock[BLK_Y];
							blockw=ob->vblock[BLK_W];
							blockh=ob->vblock[BLK_H];
							}
						rectfill(swapscreen,cx+64+blockx,cy+64+blocky,cx+64+blockx+(blockw-1),cy+64+blocky+(blockh-1),ITG_BLUE);
						}
					else
						putpixel(swapscreen,cx+64,cy+64,ITG_BLUE);
				// Show eggs
				if(ShowEggs)
					if(!istricmp_fuzzy(ob->name,"egg*"))
						putpixel(swapscreen,cx+64,cy+64,ITG_YELLOW);
				}
			}

// Path point

if(path1x)
	if(path1y)
		if(path1x-pmx>0)
			if(path1y-pmy>0)
				if((path1x-pmx)+64<384)
					if((path1y-pmy)+64<384)
						{
						circlefill(swapscreen,(path1x-pmx)+64,(path1y-pmy)+64,3,ITG_RED);
						}

div = curmap->w>>6; // div64
rx=0;
ry=0;
for(cy=0;cy<64;cy++)
	{
	for(cx=0;cx<64;cx++)
		{
		temp = ReadMap(rx,ry);
		if(temp==RANDOM_TILE)
			putpixel(swapscreen,MicroX+cx,MicroY+cy,ITG_BLUE);
		else
			putpixel(swapscreen,MicroX+cx,MicroY+cy,TIlist[temp].form->seq[0]->thumbcol);
		rx+=div;
		}
	rx=0;
	ry+=div;
	}
}

void PanUp()
{
pmy-=16;
PanMap();
}

void PanDown()
{
pmy+=16;
PanMap();
}

void PanLeft()
{
pmx-=16;
PanMap();
}

void PanRight()
{
pmx+=16;
PanMap();
}

void SetL()
{
int hx,hy,xx,yy,nodraw=0,col,div;
static int lastx=666,lasty=666;

/*
if(PathMode)
	{
	PathMe();
//	PathMode=0;
	return;
	}
*/

if(SafetyCatch)
	return;

hx = (x-64)+pmx;
hy = (y-64)+pmy;

nodraw=0;
if(hx==lastx && hy==lasty)
	nodraw=1;
lastx=hx;lasty=hy;

if(L_bgtile==RANDOM_TILE)
	col=ITG_BLUE;
else
	col=TIlist[L_bgtile].form->seq[0]->thumbcol;

if(hx>(curmap->w-8))
	hx=(curmap->w-8);
if(hy>(curmap->h-8))
	hy=(curmap->h-8);

for(xx=0;xx<8;xx++)
	for(yy=0;yy<8;yy++)
		{
		WriteMap(hx+xx,hy+yy,L_bgtile);
		if(x+xx<448 && y+yy<448)
			putpixel(swapscreen,x+xx,y+yy,col);
		}
div=curmap->w>>6; // divide by 64
putpixel(swapscreen,MicroX+(hx/div),MicroY+(hy/div),col);
}

void SetM()
{
int hx,hy,xx,yy,nodraw=0,col,div;
static int lastx=666,lasty=666;

if(SafetyCatch)
	return;

hx = (x-64)+pmx;
hy = (y-64)+pmy;

nodraw=0;
if(hx==lastx && hy==lasty)
	nodraw=1;
lastx=hx;lasty=hy;

if(L_bgtile==RANDOM_TILE)
	col=ITG_BLUE;
else
	col=TIlist[L_bgtile].form->seq[0]->thumbcol;

if(hx>(curmap->w-32))
	hx=(curmap->w-32);
if(hy>(curmap->h-32))
	hy=(curmap->h-32);

for(xx=0;xx<32;xx++)
	for(yy=0;yy<32;yy++)
		{
		WriteMap(hx+xx,hy+yy,L_bgtile);
		if(x+xx<448 && y+yy<448)
			putpixel(swapscreen,x+xx,y+yy,col);
		}
div=curmap->w>>6; // divide by 64
putpixel(swapscreen,MicroX+(hx/div),MicroY+(hy/div),col);
}

void GoMap()
{
mapx = (x-64)+pmx;
mapy = (y-64)+pmy;
}

void Spray()
{
int hx,hy,xx,yy,nodraw=0,col;
static int lastx=666,lasty=666;

if(SafetyCatch)
	return;

hx = (x-64)+pmx;
hy = (y-64)+pmy;

nodraw=0;
if(hx==lastx && hy==lasty)
	nodraw=1;
lastx=hx;lasty=hy;

if(L_bgtile==RANDOM_TILE)
	col=ITG_BLUE;
else
	col=TIlist[L_bgtile].form->seq[0]->thumbcol;

if(hx>(curmap->w-8))
	hx=(curmap->w-8);
if(hy>(curmap->h-8))
	hy=(curmap->h-8);

for(xx=0;xx<8;xx++)
	for(yy=0;yy<8;yy++)
		{
		if(rand()%100>95)
			{
			WriteMap(hx+xx,hy+yy,L_bgtile);
			if(x+xx<448 && y+yy<448)
				putpixel(swapscreen,x+xx,y+yy,col);
			}
		}
//div=curmap->w>>6; // divide by 64
//putpixel(swapscreen,MicroX+(hx/div),MicroY+(hy/div),col);
}

void Nothing()
{
PanMap();
}





void Connections()
{
focus=0;
IG_KillAll();

DrawScreenBox3D(128,128,384,320);

setcolor(ITG_WHITE);
DrawScreenText(144,160,"Map to the North");
CN_Id = IG_InputButton(280,152,ConnNstr,ConnN,NULL,NULL);
DrawScreenText(144,192,"Map to the South:");
CS_Id = IG_InputButton(280,184,ConnSstr,ConnS,NULL,NULL);
DrawScreenText(144,224,"Map to the East:");
CE_Id = IG_InputButton(280,216,ConnEstr,ConnE,NULL,NULL);
DrawScreenText(144,256,"Map to the West:");
CW_Id = IG_InputButton(280,248,ConnWstr,ConnW,NULL,NULL);

IG_TextButton(160,288,"Finish",Finish,NULL,NULL);
IG_AddKey(KEY_ESC,Finish);     // ESC to quit this menu
//IG_AddKey(KEY_F10,Snap);           // Add key binding for shift-F10

Connections_Update();
IG_WaitForRelease();
}

void Connections_Update()
{
if(curmap->con_n)
	sprintf(ConnNstr,"%6d",curmap->con_n);
else
	strcpy(ConnNstr,"None  ");
IG_UpdateText(CN_Id,ConnNstr);

if(curmap->con_s)
	sprintf(ConnSstr,"%6d",curmap->con_s);
else
	strcpy(ConnSstr,"None  ");
IG_UpdateText(CS_Id,ConnSstr);

if(curmap->con_e)
	sprintf(ConnEstr,"%6d",curmap->con_e);
else
	strcpy(ConnEstr,"None  ");
IG_UpdateText(CE_Id,ConnEstr);

if(curmap->con_w)
	sprintf(ConnWstr,"%6d",curmap->con_w);
else
	strcpy(ConnWstr,"None  ");
IG_UpdateText(CW_Id,ConnWstr);

IG_WaitForRelease();
}

void ConnN()
{
int ret;

ret=0;
ret=InputIntegerValueP(-1,-1,0,9999,curmap->con_n,"Enter map number ");
if(ret<0)
	return;

if(ret==mapnumber)
	if(!Confirm(-1,-1,"That's this map.","Are you sure you want to link this map to itself?"))
		return;

curmap->con_n=ret;
Connections_Update();
}

void ConnS()
{
int ret;

ret=0;
ret=InputIntegerValueP(-1,-1,0,9999,curmap->con_s,"Enter map number ");
if(ret<0)
	return;

if(ret==mapnumber)
	if(!Confirm(-1,-1,"That's this map.","Are you sure you want to link this map to itself?"))
		return;

curmap->con_s=ret;
Connections_Update();
}

void ConnE()
{
int ret;

ret=0;
ret=InputIntegerValueP(-1,-1,0,9999,curmap->con_e,"Enter map number ");
if(ret<0)
	return;

if(ret==mapnumber)
	if(!Confirm(-1,-1,"That's this map.","Are you sure you want to link this map to itself?"))
		return;

curmap->con_e=ret;
Connections_Update();
}

void ConnW()
{
int ret;

ret=0;
ret=InputIntegerValueP(-1,-1,0,9999,curmap->con_w,"Enter map number ");
if(ret<0)
	return;

if(ret==mapnumber)
	if(!Confirm(-1,-1,"That's this map.","Are you sure you want to link this map to itself?"))
		return;

curmap->con_w=ret;
Connections_Update();

}

void Finish()
{
IG_WaitForRelease();
BM_GoFocal();
}

void PathMaker()
{
//PathMode=1;
}


