#include "ScriptUtils.h"

#include <crtdbg.h>
#include <string.h>
#include <stdlib.h>

/*
	Misn17Mission
*/

static void GetRidOfSomeScrap(void);

class Misn17Mission {
public:
	Misn17Mission(void);
	~Misn17Mission();

	bool Load(void);
	bool PostLoad(void);
	bool Save(void);

	void Update(void);

	void AddObject(Handle h);
		
private:
	void Setup(void);
	void Execute(void);

	VECTOR_3D nearDeathPos;
	VECTOR_3D nearBuildPos;
	char takeThisPath[30];

	// bools
	union {
		struct {
			bool
				missionstart, hasOrder, healthCreated, moveHealth, buildFriend, 
				b_last;
		};
		bool b_array[5];
	};

	// floats
	union {
		struct {
			float
				damagecheck1, buildDelay,
				f_last;
		};
		float f_array[2];
	};

	// handles
	union {
		struct {
			Handle
				buildSite1, buildSite2, buildSite3, buildSite4, buildSite5, ip1, ip2, ip3, ip4,
				buildSite6, badman1, friend1, startFromHere,
				h_last;
		};
		Handle h_array[13];
	};

	// integers
	union {
		struct {
			int
				hint, minecount, crit, deathCount,
				i_last;
		};
		int i_array[4];
	};
};

bool missionSave;
Misn17Mission *mission;

void Misn17Mission::Setup(void)
{
	/*
		Initialize variables
	*/
	buildSite1 = 0; 
	buildSite2 = 0; 
	buildSite3 = 0; 
	buildSite4 = 0; 
	buildSite5 = 0;
	buildSite6 = 0;
	startFromHere = 0;
	badman1 = 0;
	deathCount = 0;
	ip1 = 0; 
	ip2 = 0;
	ip3 = 0;
	ip4 = 0;
	friend1 = 0;
	buildFriend = false;
}

void Misn17Mission::AddObject(Handle h)
{
}

void addObjective(int count) { 
		
		//PurgeItem("misn1701.otf");
		FILE *fd=fopen("addon\\misn1701.otf","w+");
		fprintf(fd,"You have killed %d enemies.",count);
		fclose(fd);
		ClearObjectives();
		AddObjective("misn1701.otf", WHITE);

}



void Misn17Mission::Execute(void)
{/*
	if	(missionstart == false)
	{
		buildSite1 = GetHandle ("spawn1");
		buildSite2 = GetHandle ("spawn2");
		buildSite3 = GetHandle ("spawn3");
		buildSite4 = GetHandle ("svmuf");
		buildSite5 = GetHandle ("svRecycler");
		buildSite6 = GetHandle ("avRecycler");
		ip1 = BuildObject("svtank", 2, buildSite5);
		strcpy( takeThisPath, "pathToBase");
		SetObjectiveOn(ip1);
		missionstart = true;
		hasOrder = false;
		healthCreated = false;
		moveHealth = false;
	}	

	//Choose where we will build something and what path it will need to take	
	if ((missionstart == true) && (!IsAlive(ip1)))
	{	int randomLocation = rand()%4;
		int randomPathPoint = rand()%2;
		SetObjectiveOff(ip1);
		switch (randomLocation) {
		case 0:
			startFromHere = buildSite1;
			strcpy( takeThisPath, "spawn1ToBase");
			break;
		case 1:
			startFromHere = buildSite2;
			strcpy( takeThisPath, "spawn2ToBase");
				break;
		case 2:
			startFromHere = buildSite3;
			strcpy( takeThisPath, "spawn3ToBase");
				break;
		case 3:
			startFromHere = buildSite4;
			strcpy( takeThisPath, "mufToBase");
				break;
		case 4:
			startFromHere = buildSite5;
			strcpy( takeThisPath, "pathToBase");
				break;
		}
	
		//Choose what to build and build it at the random location determined above
		int randomNumber = rand()%6;
		switch (randomNumber) {
		case 0:
			ip1 = BuildObject("svtank", 2, startFromHere);
				break;
		case 1:
			ip1 = BuildObject("svfigh", 2, startFromHere);
			//ip4 = BuildObject("svfigh", 2, startFromHere);
				break;
		case 2:
			ip1 = BuildObject("svrckt", 2, startFromHere);
				break;
		case 3:
			ip1 = BuildObject("svhraz", 2, startFromHere);
				break;
		case 4:
			ip1 = BuildObject("hvsav", 2, startFromHere);
				break;
		case 5:
			ip1 = BuildObject("hvsat", 2, startFromHere);
				break;
		}
		healthCreated = true;
		hasOrder = false;
		buildDelay = (GetTime( ) + 7.0f);
		deathCount += 1;
		addObjective(deathCount);
		
	}

	//Give the guy the order

	if (hasOrder == false) {
		Goto(ip1, takeThisPath);
		hasOrder = true;
		SetObjectiveOn(ip1);
		}

	//Get the position on the guy when he is close to death
	if (hasOrder == true)
	{
		damagecheck1 = GetHealth(ip1);
		if ((damagecheck1 < 0.05f) && (healthCreated == false))
		{	
			nearDeathPos=GetPosition(ip1);  
		}	
		
	}

	//Build health after the guy has died
	if ((healthCreated == true) && (buildDelay < GetTime()))
	{
#if 0
		AiPath *path;
		path=AiPath::Find("ammo");
		path->points[0].x=nearDeathPos.x;
		path->points[0].z=nearDeathPos.z;
		ip2 = BuildObject("apammo", 1, "ammo");
		path->points[0].x=nearDeathPos.x+3;
		path->points[0].z=nearDeathPos.z;
		ip3 = BuildObject("aprepa", 1, "ammo");
#else
		VECTOR_3D pos = nearDeathPos;
		ip2 = BuildObject("apammo", 1, pos);
		pos.x += 3;
		ip3 = BuildObject("aprepa", 1, pos);
#endif
		healthCreated = false;
	}	

	switch (deathCount) {
	case 0: 
		if (buildFriend == false) {
			nearBuildPos = GetPosition(buildSite6);
#if 0
			AiPath *path;
			path=AiPath::Find("ammo");
			path->points[0].x=nearBuildPos.x+50;
			path->points[0].z=nearBuildPos.z-50;
			friend1 = BuildObject("avartl", 1, "ammo");
#else
			VECTOR_3D pos = nearBuildPos;
			pos.x += 50;
			pos.z -= 50;
			friend1 = BuildObject("avartl", 1, pos);
#endif
			buildFriend = true;
			AudioMessage("avartlvg.wav");
			ClearObjectives();
			AddObjective("misn1702.otf", WHITE);
			AudioMessage("avartlvc.wav");
			break;
			}
		
	}

*/
//This is the end of Misn17 Execute	
}



Misn17Mission::Misn17Mission(void)
{
}

Misn17Mission::~Misn17Mission()
{
}

bool Misn17Mission::Load(void)
{
	if (missionSave) {
		int i;

		// init bools
		int b_count = &b_last - b_array;
		_ASSERTE(b_count == SIZEOF(b_array));
		for (i = 0; i < b_count; i++)
			b_array[i] = false;

		// init floats
		int f_count = &f_last - f_array;
		_ASSERTE(f_count == SIZEOF(f_array));
		for (i = 0; i < f_count; i++)
			f_array[i] = 99999.0f;

		// init handles
		int h_count = &h_last - h_array;
		_ASSERTE(h_count == SIZEOF(h_array));
		for (i = 0; i < h_count; i++)
			h_array[i] = 0;

		// init ints
		int i_count = &i_last - i_array;
		_ASSERTE(i_count == SIZEOF(i_array));
		for (i = 0; i < i_count; i++)
			i_array[i] = 0;

		Setup();
		return true;
	}

	bool ret = true;

	// bools
	int b_count = &b_last - b_array;
	_ASSERTE(b_count == SIZEOF(b_array));
	ret = ret && in(b_array, sizeof(b_array));

	// floats
	int f_count = &f_last - f_array;
	_ASSERTE(f_count == SIZEOF(f_array));
	ret = ret && in(f_array, sizeof(f_array));

	// Handles
	int h_count = &h_last - h_array;
	_ASSERTE(h_count == SIZEOF(h_array));
	ret = ret && in(h_array, sizeof(h_array));

	// ints
	int i_count = &i_last - i_array;
	_ASSERTE(i_count == SIZEOF(i_array));
	ret = ret && in(i_array, sizeof(i_array));

	return ret;
}

bool Misn17Mission::PostLoad(void)
{
	if (missionSave)
		return true;

	bool ret = true;

	int h_count = &h_last - h_array;
	for (int i = 0; i < h_count; i++)
		h_array[i] = ConvertHandle(h_array[i]);

	return ret;
}

bool Misn17Mission::Save(void)
{
	if (missionSave)
		return true;

	bool ret = true;

	// bools
	int b_count = &b_last - b_array;
	_ASSERTE(b_count == SIZEOF(b_array));
	ret = ret && out(b_array, sizeof(b_array), "b_array");

	// floats
	int f_count = &f_last - f_array;
	_ASSERTE(f_count == SIZEOF(f_array));
	ret = ret && out(f_array, sizeof(f_array), "f_array");

	// Handles
	int h_count = &h_last - h_array;
	_ASSERTE(h_count == SIZEOF(h_array));
	ret = ret && out(h_array, sizeof(h_array), "h_array");

	// ints
	int i_count = &i_last - i_array;
	_ASSERTE(i_count == SIZEOF(i_array));
	ret = ret && out(i_array, sizeof(i_array), "i_array");

	return ret;
}

void Misn17Mission::Update(void)
{
	Execute();
}

bool Save(bool misnSave)
{
	missionSave = misnSave;
	return mission->Save();
}

bool Load(bool misnSave)
{
	mission = new Misn17Mission();
	missionSave = misnSave;
	return mission->Load();
}

bool PostLoad(bool misnSave)
{
	missionSave = misnSave;
	return mission->PostLoad();
}

void AddObject(Handle h)
{
	mission->AddObject(h);
}

void Update(void)
{
	mission->Update();
}

void PostRun(void)
{
	delete mission;
}

static MisnExport misnExport;
MisnImport misnImport;

MisnExport * __cdecl GetMisnAPI(MisnImport *import)
{
	misnImport = *import;
	misnExport.misnImport = &misnImport;
	misnExport.Save = Save;
	misnExport.Load = Load;
	misnExport.PostLoad = PostLoad;
	misnExport.AddObject = AddObject;
	misnExport.Update = Update;
	misnExport.PostRun = PostRun;
	return &misnExport;
}

