int WINAPI WinMain(HINSTANCE hInstance,
                   HINSTANCE hPrevInstance,
                   LPSTR cmdLine,
                   int cmdShow)
{

    //Set our window settings
    const int windowWidth = 1024;
    const int windowHeight = 768;
    const int windowBPP = 16;
	float spawnTime= 3.0f;
	float curSpawnTime = 0.0f;
	int enemyNumber = 0;
	int enemiesPast = 0;
	float starSpawnTime = 0.5f;
	float curStarSpawnTime = 0.0f;
	bool camType = true;
	bool musicOn = true;
    //This is our window
	static cWNDManager* pgmWNDMgr = cWNDManager::getInstance();

	// This is the input manager
	static cInputMgr* theInputMgr = cInputMgr::getInstance();

	// This is the Font manager
	static cFontMgr* theFontMgr = cFontMgr::getInstance();

	// This is the sound manager
	static cSoundMgr* theSoundMgr = cSoundMgr::getInstance();
	
	//The example OpenGL code
    windowOGL theOGLWnd;

    //Attach our example to our window
	pgmWNDMgr->attachOGLWnd(&theOGLWnd);

	// Attach the keyboard manager
	pgmWNDMgr->attachInputMgr(theInputMgr);


    //Attempt to create the window
	if (!pgmWNDMgr->createWND(windowWidth, windowHeight, windowBPP))
    {
        //If it fails

        MessageBox(NULL, "Unable to create the OpenGL Window", "An error occurred", MB_ICONERROR | MB_OK);
		pgmWNDMgr->destroyWND(); //Reset the display and exit
        return 1;
    }

	if (!theOGLWnd.initOGL(windowWidth, windowHeight)) //Initialize our example
    {
        MessageBox(NULL, "Could not initialize the application", "An error occurred", MB_ICONERROR | MB_OK);
		pgmWNDMgr->destroyWND(); //Reset the display and exit
        return 1;
    }

	// Create Texture map
	cTexture tardisTexture;
	tardisTexture.createTexture("Models/tardis.png");
	cTexture spaceShipTexture;
	spaceShipTexture.createTexture("Models/SpaceShip/sh3.jpg");
	cTexture laserTexture;
	laserTexture.createTexture("Models/Laser/Red.png");
	cTexture starTexture;
	starTexture.createTexture("Models/Star/StarTex.png");
	cTexture playerTex;
	playerTex.createTexture("Models/Player/Grey.png");
	cTexture expTex;
	expTex.createTexture("Models/Explosion/Explosion.png");

	// the starfield
	//cStarfield theStarField(starTexture.getTexture(), glm::vec3(50.0f, 50.0f, 50.0f));

	// Create Materials for lights
	cMaterial sunMaterial(lightColour4(0.0f, 0.0f, 0.0f, 1.0f), lightColour4(1.0f, 1.0f, 1.0f, 1.0f), lightColour4(1.0f, 1.0f, 1.0f, 1.0f), lightColour4(0, 0, 0, 1.0f), 5.0f);

	// Create Light
	cLight sunLight(GL_LIGHT0, lightColour4(0, 0, 0, 1), lightColour4(1, 1, 1, 1), lightColour4(1, 1, 1, 1), glm::vec4(0, 0, 20, 1),
		glm::vec3(0.0, 0.0, 1.0), 0.0f, 180.0f, 1.0f, 0.0f, 0.0f);
	cLight lfLight(GL_LIGHT1, lightColour4(0, 0, 0, 1), lightColour4(1, 1, 1, 1), lightColour4(1, 1, 1, 1), glm::vec4(30, 0, 100, 1),
		glm::vec3(0.0, 0.0, 1.0), 0.0f, 180.0f, 1.0f, 0.0f, 0.0f);
	cLight rfLight(GL_LIGHT2, lightColour4(0, 0, 0, 1), lightColour4(1, 1, 1, 1), lightColour4(1, 1, 1, 1), glm::vec4(-30, 0, 100, 1),
		glm::vec3(0.0, 0.0, 1.0), 0.0f, 180.0f, 1.0f, 0.0f, 0.0f);
	cLight cbLight(GL_LIGHT3, lightColour4(0, 0, 0, 1), lightColour4(1, 1, 1, 1), lightColour4(1, 1, 1, 1), glm::vec4(0, 0, -100, 1),
		glm::vec3(0.0, 0.0, 1.0), 0.0f, 180.0f, 1.0f, 0.0f, 0.0f);
	//Define Ambient light for scene
	GLfloat g_Ambient[] = { 0.2, 0.2, 0.2, 1.0 };
	glLightModelfv(GL_LIGHT_MODEL_AMBIENT, g_Ambient);

	// load game fonts
	// Load Fonts
	LPCSTR gameFonts[3] = {"Fonts/JustinFont12Bold.ttf" };

	theFontMgr->addFont("ftFont", gameFonts[0], 24);

	// load game sounds
	// Load Sound
	LPCSTR gameSounds[3] = { "Audio/music.wav", "Audio/shoot.wav", "Audio/boom.wav" };

	theSoundMgr->add("Theme", gameSounds[0]);
	theSoundMgr->add("Shot", gameSounds[1]);
	theSoundMgr->add("Explosion", gameSounds[2]);

	// Create a camera
	cCamera theCamera;
	theCamera.setTheCameraPos(glm::vec3(0.0f, 0.0f, 75.0f));
	theCamera.setTheCameraLookAt(glm::vec3(0.0f, 0.0f, 0.0f));
	theCamera.setTheCameraUpVector(glm::vec3(0.0f, 1.0f, 0.0f)); // pointing upwards in world space
	theCamera.setTheCameraAspectRatio(windowWidth, windowHeight);
	theCamera.setTheProjectionMatrix(45.0f, theCamera.getTheCameraAspectRatio(), 0.1f, 300.0f);
	theCamera.update();

	//Create second camera
	cCamera thirdPersCamera;
	thirdPersCamera.setTheCameraPos(glm::vec3(0.0f, -65.0f, 20.0f));
	thirdPersCamera.setTheCameraLookAt(glm::vec3(0.0f, 0.0f, 0.0f));
	thirdPersCamera.setTheCameraUpVector(glm::vec3(0.0f, -1.0f, 0.0f)); // pointing upwards in world space
	thirdPersCamera.setTheCameraAspectRatio(windowWidth, windowHeight);
	thirdPersCamera.setTheProjectionMatrix(25.0f, thirdPersCamera.getTheCameraAspectRatio(), 0.1f, 300.0f);

	//Clear key buffers
	theInputMgr->clearBuffers(theInputMgr->KEYS_DOWN_BUFFER | theInputMgr->KEYS_PRESSED_BUFFER);

	// Model
	cModelLoader tardisMdl;
	tardisMdl.loadModel("Models/Player/thePlayer.obj", playerTex); // Player

	cModelLoader spaceShipMdl;
	spaceShipMdl.loadModel("Models/Enemy/newEnemy.obj", starTexture); // Enemy
	
	cModelLoader theLaser;
	theLaser.loadModel("Models/Laser/Laser.obj", laserTexture);

	cModelLoader star;
	star.loadModel("Models/Star/StarModelNew.obj", starTexture);

	cModelLoader explosion;
	explosion.loadModel("Models/Explosion/Explosion.obj", expTex);

	cPlayer thePlayer;
	thePlayer.initialise(glm::vec3(0, -20, -20), 180.0f, glm::vec3(1, 1, 1), glm::vec3(0, 0, 0), 5.0f, true);
	thePlayer.setMdlDimensions(tardisMdl.getModelDimensions());
	thePlayer.attachInputMgr(theInputMgr);
	thePlayer.attachSoundMgr(theSoundMgr);
	thePlayer.setScale(glm::vec3(0.15, 0.15, 0.15));
	thePlayer.setSpeed(20.0f);

	float tCount = 0.0f;
	string outputMsg;

	theSoundMgr->getSnd("Theme")->playAudio(1);

	std::vector<cLaser*> laserList;
	std::vector<cLaser*>::iterator index;
	std::vector<cStar*> starList;
	std::vector<cStar*>::iterator starIndex;

   //This is the mainloop, we render frames until isRunning returns false
	while (pgmWNDMgr->isWNDRunning())
    {
		pgmWNDMgr->processWNDEvents(); //Process any window events

        //We get the time that passed since the last frame
		float elapsedTime = pgmWNDMgr->getElapsedSeconds();
		
		// Lab code goes here
		glClear(GL_COLOR_BUFFER_BIT | GL_DEPTH_BUFFER_BIT);
		theOGLWnd.initOGL(windowWidth,windowHeight);

		glMatrixMode(GL_MODELVIEW);
		glLoadIdentity();

		if (camType == true)
		{
			glLoadMatrixf((GLfloat*)&theCamera.getTheViewMatrix());
			theCamera.update();
		}
		else
		{
			//Position third person camera behind player
			glm::vec3 newCamPos;
			newCamPos.x = thePlayer.getPosition().x;
			newCamPos.y = -70.0f;
			newCamPos.z = 5.0f;
			thirdPersCamera.setTheCameraPos(newCamPos);

			//calc where third person camera should be looking
			glm::vec3 newCamLookPos;
			newCamLookPos.x = thePlayer.getPosition().x;
			newCamLookPos.y = 0;
			newCamLookPos.z = 0;
			thirdPersCamera.setTheCameraLookAt(newCamLookPos);
			//update third person camera
			glLoadMatrixf((GLfloat*)&thirdPersCamera.getTheViewMatrix());
			thirdPersCamera.update();
		}


		sunMaterial.useMaterial();
		sunLight.lightOn();
		lfLight.lightOn();
		rfLight.lightOn();
		cbLight.lightOn();

		if (gameState == 0)
		{
		
			/*
			==============================================================
			| Enemy Update and Render
			==============================================================
			*/

			for (vector<cEnemy*>::iterator enemyIterator = theEnemy.begin(); enemyIterator != theEnemy.end(); ++enemyIterator)
			{
				if ((*enemyIterator)->isActive())
				{
					if ((*enemyIterator)->getPosition().y <= -25.0f)
					{
						// if enemy has gone past player "delete"
						(*enemyIterator)->setIsActive(false);
						// increment enemies gone past screen
						enemiesPast++;
					}
					(*enemyIterator)->update(elapsedTime);
					spaceShipMdl.renderMdl((*enemyIterator)->getPosition(), (*enemyIterator)->getRotation(), (*enemyIterator)->getScale());
				}
			}


			/*
			==============================================================
			| Stars Update and Render
			==============================================================
			*/

			for (vector<cStar*>::iterator starsIterator = theStars.begin(); starsIterator != theStars.end(); ++starsIterator)
			{
				if ((*starsIterator)->isActive())
				{
					star.renderMdl((*starsIterator)->getPosition(), (*starsIterator)->getRotation(), (*starsIterator)->getScale());
					(*starsIterator)->update(elapsedTime);
				}
			}

			/*
			==============================================================
			| Explosions Update and Render
			==============================================================
			*/

			for (vector<cExploison*>::iterator expIterator = theExplosions.begin(); expIterator != theExplosions.end(); ++expIterator)
			{
				if ((*expIterator)->isActive())
				{
					explosion.renderMdl((*expIterator)->getPosition(), (*expIterator)->getRotation(), (*expIterator)->getScale());
					(*expIterator)->update(elapsedTime);
				}
			}


			/*
			==============================================================
			| Player Update and Render
			==============================================================
			*/
			tardisMdl.renderMdl(thePlayer.getPosition(), thePlayer.getRotation(), thePlayer.getScale());
			thePlayer.update(elapsedTime);


			/*
			==============================================================
			| Laser Update and Render
			==============================================================
			*/
			for (vector<cLaser*>::iterator laserIterartor = theTardisLasers.begin(); laserIterartor != theTardisLasers.end(); ++laserIterartor)
			{
				if ((*laserIterartor)->isActive())
				{
					theLaser.renderMdl((*laserIterartor)->getPosition(), (*laserIterartor)->getRotation(), (*laserIterartor)->getScale());
					(*laserIterartor)->update(elapsedTime);
				}
			}




			if (gameState == 0) //only do if game state is zero (play)
			{
				/*
				==============================================================
				| Enemy Spawning
				==============================================================
				*/
				if (curSpawnTime > spawnTime)
				{
					//generate number of enemies to spawn
					int numSpawns = (((float)rand()) / (float)RAND_MAX) * (5.0F);
					for (int i = 0; i < numSpawns; i++)
					{
						//Spawn
						theEnemy.push_back(new cEnemy);
						int enemyNumber = theEnemy.size() - 1;
						theEnemy[enemyNumber]->initialise();
						theEnemy[enemyNumber]->setMdlDimensions(spaceShipMdl.getModelDimensions());
						theEnemy[enemyNumber]->setScale(glm::vec3(5, 5, 5));
					}
					curSpawnTime = 0.0f;
				}
				else
				{
					curSpawnTime += 0.01;
				}
				/*
				==============================================================
				| Star Spawning
				==============================================================
				*/
				if (curStarSpawnTime > starSpawnTime)
				{
					//generate number of enemies to spawn
					int numSpawns = (((float)rand()) / (float)RAND_MAX) * (10.0F);
					for (int i = 0; i < numSpawns; i++)
					{
						//Spawn Star
						theStars.push_back(new cStar);
						int starNumber = theStars.size() - 1;
						float randX = rand() % (int)((50 - -50) + 1) + -50;
						float randY = rand() % (int)((25 - 20) + 1) + 20;
						float randZ = rand() % (int)((30 - -30) + 1) + -30;
						glm::vec3 starPos = glm::vec3(randX, randY, randZ);
						theStars[starNumber]->initialise(starPos, 180.0f, glm::vec3(1, 1, 1), glm::vec3(0, -1, 0), 5.0f, true);
					}
					curStarSpawnTime = 0.0f;
				}
				else
				{
					curStarSpawnTime += 0.01;
				}
			
			}

			/*
			==============================================================
			| Player Wrapping
			==============================================================
			*/
			if (thePlayer.getPosition().x < -32)
			{
				glm::vec3 playPos;
				playPos.x = thePlayer.getPosition().x + 64;
				playPos.y = thePlayer.getPosition().y;
				playPos.z = thePlayer.getPosition().z;
				thePlayer.setPosition(playPos);
			}
			else if (thePlayer.getPosition().x > 32)
			{
				glm::vec3 playPos;
				playPos.x = thePlayer.getPosition().x - 64;
				playPos.y = thePlayer.getPosition().y;
				playPos.z = thePlayer.getPosition().z;
				thePlayer.setPosition(playPos);
			}
			/*
			==============================================================
			| Game Over
			==============================================================
			*/
			//Lose
			if (enemiesPast >= 5)
			{
				GameOver(1);
			}
			//Win
			if (tCount >= 60)
			{
				GameOver(2);
			}
					/*
		==============================================================
		| CAMERA SWITCHING
		==============================================================
		*/
			if (camType == true && theInputMgr->isKeyDown(0x43))
			{
				camType = false;
			}
			else if (camType == false && theInputMgr->isKeyDown(0x43))
			{
				camType = true;
			}
		}

		/*
		==============================================================
		| RESTART
		==============================================================
		*/
		if (theInputMgr->isKeyDown(VK_RETURN) && gameState != 0)
		{
			gameState = 0;
			enemiesPast = 0;
			thePlayer.score = 0;
			tCount = 0;
		}

		/*
		==============================================================
		| SOUND TOGGLE
		==============================================================
		*/
		if (theInputMgr->isKeyDown(0x4D) && music == true)
		{
			music = false;
			theSoundMgr->getSnd("Theme")->stopAudio();
		}
		else if (theInputMgr->isKeyDown(0x4D) && music == false)
		{
			music = true;
			theSoundMgr->getSnd("Theme")->playAudio(1);
		}
		/*
		==============================================================
		| GUI
		==============================================================
		*/
		glPushMatrix();
		theOGLWnd.setOrtho2D(windowWidth, windowHeight);
		string scoreString = "YOU SCORED : " + to_string(thePlayer.score);
		string inGameScoreString = "SCORE : " + to_string(thePlayer.score);
		string timeString = "Time : " + (to_string((int)tCount) + " s");
		string laserChargeString = "Laser Charge : " + (to_string((int)thePlayer.charge));
		string soundOnOff;
		if (music == true)
		{
			soundOnOff = "SOUND : ON";
		}
		else
		{
			soundOnOff = "SOUND : OFF";
		}
		switch (gameState)
		{
		case (0) :
			//GAME GUI
			outputMsg = "Enemies Through : " + to_string(enemiesPast); // convert float to string
			theFontMgr->getFont("ftFont")->printText(soundOnOff.c_str(), FTPoint(10, 35, 0.0f), colour3f(255.0f, 255.0f, 255.0f));
			theFontMgr->getFont("ftFont")->printText(outputMsg.c_str(), FTPoint(750, 35, 0.0f), colour3f(255.0f, 255.0f, 255.0f)); // uses c_str to convert string to LPCSTR
			theFontMgr->getFont("ftFont")->printText(timeString.c_str(), FTPoint(0, 760, 0.0f), colour3f(255.0f, 255.0f, 255.0f)); // uses c_str to convert string to LPCSTR
			theFontMgr->getFont("ftFont")->printText(laserChargeString.c_str(), FTPoint(770, 760, 0.0f), colour3f(255.0f, 255.0f, 255.0f)); // uses c_str to convert string to LPCSTR
			theFontMgr->getFont("ftFont")->printText(inGameScoreString.c_str(), FTPoint(450, 35, 0.0f), colour3f(255.0f, 255.0f, 255.0f)); // uses c_str to convert string to LPCSTR
			break;
		case (1) :
			//GAME OVER GUI
			theFontMgr->getFont("ftFont")->printText("GAME OVER", FTPoint(450, 384, 0.0f), colour3f(255.0f, 255.0f, 255.0f));
			theFontMgr->getFont("ftFont")->printText("PRESS ENTER TO RESTART", FTPoint(370, 484, 0.0f), colour3f(255.0f, 255.0f, 255.0f));
			break;
		case (2) :
			//WIN GUI
			theFontMgr->getFont("ftFont")->printText("YOU WIN", FTPoint(450, 300, 0.0f), colour3f(255.0f, 255.0f, 255.0f));
			theFontMgr->getFont("ftFont")->printText(scoreString.c_str(), FTPoint(415, 400, 0.0f), colour3f(255.0f, 255.0f, 255.0f));
			theFontMgr->getFont("ftFont")->printText("PRESS ENTER TO PLAY AGAIN", FTPoint(350, 500, 0.0f), colour3f(255.0f, 255.0f, 255.0f));
			break;
		case (3) :
			//MAIN GAME SCREEN GUI
			theFontMgr->getFont("ftFont")->printText("SPACE DEFENCE", FTPoint(425, 200, 0.0f), colour3f(255.0f, 255.0f, 255.0f));
			theFontMgr->getFont("ftFont")->printText("DONT LET MORE THAN FIVE ENEMIES PAST FOR 60 SECONDS", FTPoint(190, 300, 0.0f), colour3f(255.0f, 255.0f, 255.0f));
			theFontMgr->getFont("ftFont")->printText("PRESS ENTER TO START", FTPoint(380, 400, 0.0f), colour3f(255.0f, 255.0f, 255.0f));
			theFontMgr->getFont("ftFont")->printText("C SWITCHES CAMERA, M ENABLES/DISABLES MUSIC", FTPoint(220, 500, 0.0f), colour3f(255.0f, 255.0f, 255.0f));
			break;

		}
		glPopMatrix();
		pgmWNDMgr->swapBuffers();
		tCount += elapsedTime;
		//Clear key buffers
		theInputMgr->clearBuffers(theInputMgr->KEYS_DOWN_BUFFER | theInputMgr->KEYS_PRESSED_BUFFER);

	}
	theOGLWnd.shutdown(); //Free any resources
	pgmWNDMgr->destroyWND(); //Destroy the program window

    return 0; //Return success
}
Beispiel #2
0
int WINAPI WinMain(HINSTANCE hInstance,
	HINSTANCE hPrevInstance,
	LPSTR cmdLine,
	int cmdShow)
{

	//Set our window settings
	const int windowWidth = 1024;
	const int windowHeight = 768;
	const int windowBPP = 16;

	//Make a variable like intitialModelRotation

	

	//This is our window
	static cWNDManager* pgmWNDMgr = cWNDManager::getInstance();

	// This is the input manager
	static cInputMgr* theInputMgr = cInputMgr::getInstance();

	// This is the Font manager
	static cFontMgr* theFontMgr = cFontMgr::getInstance();

	// This is the sound manager
	static cSoundMgr* theSoundMgr = cSoundMgr::getInstance();

	//The example OpenGL code
	windowOGL theOGLWnd;

	//Attach our example to our window
	pgmWNDMgr->attachOGLWnd(&theOGLWnd);

	//Adding Spheres for the solar system (Sun, Planet, moon)
	cSphere theSun(4, 40, 40);
	cSphere thePlanet(3, 30, 30);
	cSphere theMoon(1, 20, 20);

	// Attach the keyboard manager
	pgmWNDMgr->attachInputMgr(theInputMgr);

	//Attempt to create the window
	if (!pgmWNDMgr->createWND(windowWidth, windowHeight, windowBPP))
	{
		//If it fails

		MessageBox(NULL, "Unable to create the OpenGL Window", "An error occurred", MB_ICONERROR | MB_OK);
		pgmWNDMgr->destroyWND(); //Reset the display and exit
		return 1;
	}

	if (!theOGLWnd.initOGL(windowWidth, windowHeight)) //Initialize our example
	{
		MessageBox(NULL, "Could not initialize the application", "An error occurred", MB_ICONERROR | MB_OK);
		pgmWNDMgr->destroyWND(); //Reset the display and exit
		return 1;
	}

	// Create Texture map for models
	cTexture spaceShipTexture;
	spaceShipTexture.createTexture("Models/SpaceFighter/mat_ship.png");
	cTexture spaceGateTexture;
	spaceGateTexture.createTexture("Models/SpaceGate/mat_gate.png");
	cTexture spaceStationTexture;
	spaceStationTexture.createTexture("Models/SpaceStation/mat_stat.png");
	cTexture spaceSatelliteTexture;
	spaceSatelliteTexture.createTexture("Models/SpaceSatellite/mat_sate.png");


	cTexture laserTexture;
	laserTexture.createTexture("Models/laser.tga");
	cTexture starTexture;
	starTexture.createTexture("Images/star.png");

	//Adding textures for the star system

	cTexture planetTexture;
	planetTexture.createTexture("Images/ice.png");

	cTexture sunTexture;
	sunTexture.createTexture("Images/Sun.png");

	cTexture moonTexture;
	moonTexture.createTexture("Images/Moon.png");

	// the starfield
	cStarfield theStarField(starTexture.getTexture(), glm::vec3(50.0f, 50.0f, 50.0f));

	//Initialization of the planet and sun
	theSun.initialise(sunTexture.getTexture(), glm::vec3(0, 0, 40), glm::vec3(0, 0, 0));
	thePlanet.initialise(planetTexture.getTexture(), glm::vec3(10, 0, 20), glm::vec3(0, 0, 0));
	float planetRotSpeed = 3.0f;
	GLfloat planetOrbit = 0.0f;

	//Initialization of the moon of the planet
	theMoon.initialise(moonTexture.getTexture(), glm::vec3(10, 5, 8), glm::vec3(0, 0, 0));
	float moonRotSpeed = 5.0f;
	GLfloat moonOrbit = 0.0f;

	// Create Materials for lights
	cMaterial sunMaterial(lightColour4(0.0f, 0.0f, 0.0f, 1.0f), lightColour4(1.0f, 1.0f, 1.0f, 1.0f), lightColour4(1.0f, 1.0f, 1.0f, 1.0f), lightColour4(0, 0, 0, 1.0f), 5.0f);
	cMaterial planetMaterial(lightColour4(0.2f, 0.2f, 0.2f, 1.0f), lightColour4(1.0f, 1.0f, 1.0f, 1.0f), lightColour4(1.0f, 1.0f, 1.0f, 1.0f), lightColour4(0, 0, 0, 1.0f), 50.0f);
	cMaterial moonMaterial(lightColour4(0.1f, 0.1f, 0.1f, 1.0f), lightColour4(1.0f, 1.0f, 1.0f, 1.0f), lightColour4(0.2f, 0.2f, 0.2f, 1.0f), lightColour4(0, 0, 0, 1.0f), 10.0f);

	// Create Light where the sun to act as a light source for the scene
	cLight sunLight(GL_LIGHT0, lightColour4(0, 0, 0, 1), lightColour4(1, 1, 1, 1), lightColour4(1, 1, 1, 1), glm::vec4(0, 0, 20, 1),
		glm::vec3(0.0, 0.0, 1.0), 0.0f, 180.0f, 1.0f, 0.0f, 0.0f);
	cLight lfLight(GL_LIGHT1, lightColour4(0, 0, 0, 1), lightColour4(1, 1, 1, 1), lightColour4(1, 1, 1, 1), glm::vec4(30, 0, 100, 1),
		glm::vec3(0.0, 0.0, 1.0), 0.0f, 180.0f, 1.0f, 0.0f, 0.0f);
	cLight rfLight(GL_LIGHT2, lightColour4(0, 0, 0, 1), lightColour4(1, 1, 1, 1), lightColour4(1, 1, 1, 1), glm::vec4(-30, 0, 100, 1),
		glm::vec3(0.0, 0.0, 1.0), 0.0f, 180.0f, 1.0f, 0.0f, 0.0f);
	cLight cbLight(GL_LIGHT3, lightColour4(0, 0, 0, 1), lightColour4(1, 1, 1, 1), lightColour4(1, 1, 1, 1), glm::vec4(0, 0, -100, 1),
		glm::vec3(0.0, 0.0, 1.0), 0.0f, 180.0f, 1.0f, 0.0f, 0.0f);

	//Define Ambient light for scene
	GLfloat g_Ambient[] = { 0.2, 0.2, 0.2, 1.0 };
	glLightModelfv(GL_LIGHT_MODEL_AMBIENT, g_Ambient);

	// Load Fonts
	LPCSTR gameFonts[3] = { "Fonts/digital-7.ttf", "Fonts/space age.ttf", "Fonts/doctor_who.ttf" };

	theFontMgr->addFont("SevenSeg", gameFonts[0], 24);
	theFontMgr->addFont("Space", gameFonts[1], 12);
	theFontMgr->addFont("DrWho", gameFonts[2], 48);

	// Load Sound for main theme and sounds					
	LPCSTR gameSounds[4] = { "Audio/Breaking Ground.wav", "Audio/shot007.wav", "Audio/explosion2.wav", "Audio/engine_2.wav" };

	theSoundMgr->add("Theme", gameSounds[0]);
	theSoundMgr->add("Shot", gameSounds[1]);
	theSoundMgr->add("Explosion", gameSounds[2]);
	theSoundMgr->add("Engine", gameSounds[3]);

	//Clear key buffers
	theInputMgr->clearBuffers(theInputMgr->KEYS_DOWN_BUFFER | theInputMgr->KEYS_PRESSED_BUFFER);


	// Model Loaders, object is assigned along with its texture
	cModelLoader spaceShipMdl;
	spaceShipMdl.loadModel("Models/SpaceFighter/spaceship01.obj",spaceShipTexture);

	cModelLoader spaceGateMdl;
	spaceGateMdl.loadModel("Models/SpaceGate/gate.obj", spaceGateTexture);

	cModelLoader spaceGateMdl1;
	spaceGateMdl1.loadModel("Models/SpaceGate/gate.obj", spaceGateTexture);

	cModelLoader spaceGateMdl2;
	spaceGateMdl2.loadModel("Models/SpaceGate/gate.obj", spaceGateTexture);

	cModelLoader spaceStation;
	spaceStation.loadModel("Models/SpaceStation/station.obj", spaceStationTexture);

	cModelLoader spaceSatellite;
	spaceSatellite.loadModel("Models/SpaceSatellite/satellite.obj", spaceSatelliteTexture);

	cModelLoader theLaser;
	theLaser.loadModel("Models/laser.obj", laserTexture);

	/*for (int loop = 0; loop < 5; loop++)
	{
		theEnemy.push_back(new cEnemy);
		theEnemy[loop]->randomise();
		theEnemy[loop]->setMdlDimensions(spaceShipMdl.getModelDimensions());
		theEnemy[loop]->setScale(glm::vec3(5, 5, 5));
	}*/

	// Player initizlation, the two managers (Input and Sound) are attached to allow key inputs to control the player, sound associated with player.
	cPlayer thePlayer;
	thePlayer.initialise(glm::vec3(1, 0, 70), 90.0f, glm::vec3(0.002, 0.002, 0.002), glm::vec3(0, 0,0), 1.0f, true);
	//thePlayer.setRotation(mdlRotation.x = 5);
	//thePlayer.setMdlDimensions(tardisMdl.getModelDimensions());
	thePlayer.setMdlDimensions(spaceShipMdl.getModelDimensions());
	thePlayer.attachInputMgr(theInputMgr);
	thePlayer.attachSoundMgr(theSoundMgr);

	// First three models are created, intially there was going to be 3 gates to travel too like racing but this was scrapped
	cEnemy gate;
	gate.initialise(glm::vec3(1, 0, 60), 0.0f, glm::vec3(0.02, 0.02, 0.02), glm::vec3(0, 0, 0), 1.0f, true);
	gate.setMdlDimensions(spaceGateMdl.getModelDimensions());

	cEnemy gate1;
	gate1.initialise(glm::vec3(10, 0, 60), 0.0f, glm::vec3(0.02, 0.02, 0.02), glm::vec3(0, 0, 0), 1.0f, true);
	gate1.setMdlDimensions(spaceGateMdl1.getModelDimensions());

	cEnemy gate2;
	gate2.initialise(glm::vec3(20, 0, 60), 0.0f, glm::vec3(0.02, 0.02, 0.02), glm::vec3(0, 0, 0), 1.0f, true);
	gate2.setMdlDimensions(spaceGateMdl2.getModelDimensions());

	// A space station model, a larger example of model loading
	cEnemy station;
	station.initialise(glm::vec3(1, 0, 50), 0.0f, glm::vec3(0.02, 0.02, 0.02), glm::vec3(0, 0, 0), 1.0f, true);
	station.setMdlDimensions(spaceStation.getModelDimensions());

	// A satellite model initialization
	cEnemy satellite;
	satellite.initialise(glm::vec3(10, 0, 50), 0.0f, glm::vec3(0.002, 0.002, 0.002), glm::vec3(0, 0, 0), 1.0f, true);
	satellite.setMdlDimensions(spaceSatellite.getModelDimensions());

	//This creates the camera based on the cCamera class, its here that initial parameters are set like position and lookat
	cCamera theCamera;
	theCamera.setTheCameraPos(glm::vec3(thePlayer.getPosition().x, thePlayer.getPosition().y, 3.0f + thePlayer.getPosition().z));
	theCamera.setTheCameraLookAt(glm::vec3(thePlayer.getPosition().x, thePlayer.getPosition().y ,0.0f));
	theCamera.setTheCameraUpVector(glm::vec3(0.0f, 1.0f, 0.0f)); // pointing upwards in world space
	theCamera.setTheCameraAspectRatio(windowWidth, windowHeight);
	theCamera.setTheProjectionMatrix(45.0f, theCamera.getTheCameraAspectRatio(), 0.1f, 300.0f);
	theCamera.update();

	float tCount = 0.0f;

	//Outputmsg that can be passed to displaying text in the scene
	string outputMsg;

	// Starts the theme music and plays it in a loop
	theSoundMgr->getSnd("Theme")->playAudio(AL_LOOPING);

	// List and index for the lasers fired from player is declared here
	std::vector<cLaser*> laserList;
	std::vector<cLaser*>::iterator index;

	//Declaration of Variables for Fog
	GLuint filter;
	GLuint fogMode[] = { GL_EXP, GL_EXP2, GL_LINEAR };
	GLuint fogfilter = 0;
	GLfloat fogcolour[4] = { 0.5f, 0.5f, 0.5f, 1.0f };


	//This is the mainloop, we render frames until isRunning returns false
	while (pgmWNDMgr->isWNDRunning())
	{
		//Enter code here about what to render, create a variable that is boolean or int, render title scene if 0, render game scene if 1 and end scene if is 2
		//This may require some experimentation to succed like is it here where the code changes or 2 lines down after the elapsed time 
		pgmWNDMgr->processWNDEvents(); //Process any window events

		//We get the time that passed since the last frame
		float elapsedTime = pgmWNDMgr->getElapsedSeconds();

		glClear(GL_COLOR_BUFFER_BIT | GL_DEPTH_BUFFER_BIT);
		theOGLWnd.initOGL(windowWidth, windowHeight);

		glMatrixMode(GL_MODELVIEW);
		glLoadIdentity();
		glLoadMatrixf((GLfloat*)&theCamera.getTheViewMatrix());

		//Fog Code
		
		glClearColor(0.0f, 0.0f, 0.0f, 1.0f);
		glFogi(GL_FOG_MODE, fogMode[fogfilter]);
		glFogfv(GL_FOG_COLOR, fogcolour);
		glFogf(GL_FOG_DENSITY, 0.05f);
		glHint(GL_FOG_HINT, GL_DONT_CARE);
		glFogf(GL_FOG_START, 1.0f);
		glFogf(GL_FOG_END, 5.0f);
		
		//Enable Fog

		glEnable(GL_FOG);

		//This allows the toggling of the main theme playing ON/OFF
		if (thePlayer.soundToggle == false)
		{
			//theSoundMgr->getSnd("Theme")->playAudio(AL_LOOPING);
		}
		if (thePlayer.soundToggle == true)
		{
			theSoundMgr->getSnd("Theme")->stopAudio();
		
		}

		// Code that switches between the player 3rd person view and set view 
		if (thePlayer.cameraSwitch == true)
		{
			// Set view
			outputMsg = to_string(thePlayer.cameraSwitch);
			theCamera.setTheCameraPos(glm::vec3(10.0f, 3.0f, 70.0f));
			theCamera.setTheCameraLookAt(glm::vec3(0.0f, 0.0f, 0.0f));
			theCamera.update();
		}

		if (thePlayer.cameraSwitch == false)
		{
			// return back to third person view
		outputMsg = to_string(thePlayer.cameraSwitch);
		theCamera.setTheCameraPos(glm::vec3(thePlayer.getPosition().x, thePlayer.getPosition().y, 3.0f + thePlayer.getPosition().z));
		theCamera.setTheCameraLookAt(glm::vec3(thePlayer.getPosition().x, thePlayer.getPosition().y, 0.0f));
		theCamera.update();
		}
	
		// render the Starfield
		theStarField.render(0.0f);

		//Rendering and setup of the star system planet,moon and sun
		theSun.prepare(0.0f);
		sunMaterial.useMaterial();
		sunLight.lightOn();
		lfLight.lightOn();
		rfLight.lightOn();
		cbLight.lightOn();
		theSun.render(theSun.getRotAngle());
	
		// Planets's orbit
		glPushMatrix();
		thePlanet.setRotAngle(thePlanet.getRotAngle() + (planetRotSpeed*elapsedTime));
		thePlanet.prepare(thePlanet.getRotAngle()); //Do any pre-rendering logic
		planetMaterial.useMaterial();				// Set the material for use
		thePlanet.render(thePlanet.getRotAngle()); //Render the scene

		// Moon's orbit
		glPushMatrix();
		theMoon.setRotAngle(theMoon.getRotAngle() + (moonRotSpeed*elapsedTime));
		theMoon.prepare(rotationAngle);
		moonMaterial.useMaterial();
		theMoon.render(theMoon.getRotAngle());
		glPopMatrix();
		glPopMatrix();
		glPopMatrix();
		
		for (vector<cEnemy*>::iterator enemyIterator = theEnemy.begin(); enemyIterator != theEnemy.end(); ++enemyIterator)
		{
			if ((*enemyIterator)->isActive())
			{
				spaceShipMdl.renderMdl((*enemyIterator)->getPosition(), (*enemyIterator)->getRotation(), (*enemyIterator)->getScale());
				(*enemyIterator)->update(elapsedTime);
			}
		}

		//Model Rendering for the spacegates, player fighter, satellite and station.
		spaceShipMdl.renderMdl(thePlayer.getPosition(), thePlayer.getRotation(), thePlayer.getScale());
		spaceGateMdl.renderMdl(gate.getPosition(), gate.getRotation(), gate.getScale());
		spaceGateMdl1.renderMdl(gate1.getPosition(), gate1.getRotation(), gate1.getScale());
		spaceGateMdl2.renderMdl(gate2.getPosition(), gate2.getRotation(), gate2.getScale());
		spaceStation.renderMdl(station.getPosition(), station.getRotation(), station.getScale());
		spaceSatellite.renderMdl(satellite.getPosition(), satellite.getRotation(), satellite.getScale());

		thePlayer.update(elapsedTime);

		for (vector<cLaser*>::iterator laserIterartor = theLasers.begin(); laserIterartor != theLasers.end(); ++laserIterartor)
		{
			if ((*laserIterartor)->isActive())
			{
				theLaser.renderMdl((*laserIterartor)->getPosition(), (*laserIterartor)->getRotation(), (*laserIterartor)->getScale());
				(*laserIterartor)->update(elapsedTime);
			}
		}
		//outputMsg = to_string(theEnemy.size()); // convert float to string

		glPushMatrix();
		theOGLWnd.setOrtho2D(windowWidth, windowHeight);

		//Generate the text overlay on screen
		theFontMgr->getFont("DrWho")->printText("Space Game", FTPoint(10, 35, 0.0f), colour3f(0.0f, 255.0f, 0.0f));
		theFontMgr->getFont("Space")->printText("C & V = camera", FTPoint(830, 35, 0.0f), colour3f(255.0f, 255.0f, 255.0f)); // uses c_str to convert string to LPCSTR
		theFontMgr->getFont("Space")->printText("E & R = Sound ON/OFF", FTPoint(830, 45, 0.0f), colour3f(255.0f, 255.0f, 255.0f));
		glPopMatrix();

		
		pgmWNDMgr->swapBuffers();

		tCount += elapsedTime;

		//Clear key buffers
		theInputMgr->clearBuffers(theInputMgr->KEYS_DOWN_BUFFER | theInputMgr->KEYS_PRESSED_BUFFER);
	}
	theOGLWnd.shutdown(); //Free any resources
	pgmWNDMgr->destroyWND(); //Destroy the program window

	return 0; //Return success
}