Files
PlanetFleet/game.cpp
T

189 lines
4.8 KiB
C++

#include "game.h"
#include "player.h"
#include "projectile.h"
#include "gameManager.h"
#include "activeGameState.h"
#include "inGameAppState.h"
#include "concreteGuiManager.h"
#include "defConfigs.h"
#include <assetManager.h>
#include <particleEmitter.h>
#include <stateManager.h>
#include <solUtil.h>
#include <SFML/Audio.hpp>
namespace battleship{
using namespace std;
using namespace vb01;
using namespace gameBase;
static Game *game = nullptr;
Game* Game::getSingleton(){
if(!game)
game = new Game();
return game;
}
void Game::resetLuaGameObjects(){
sol::state_view SOL_LUA_VIEW = generateView();
SOL_LUA_VIEW.script("game.players = {}");
for(int i = 0; i < players.size(); i++)
SOL_LUA_VIEW["game"]["players"][i + 1] = players[i];
for(int i = 0; i < players.size(); i++)
if(players[i]->isCpuPlayer()){
string plStr = "game.players[" + to_string(i + 1) + "]";
SOL_LUA_VIEW.script("executeBtNode(" + plStr + ", " + plStr + ".behaviour)");
}
}
void Game::endGame(bool victory){
ended = true;
StateManager *sm = GameManager::getSingleton()->getStateManager();
sm->dettachAppState(sm->getAppStateByType(AppStateType::ACTIVE_STATE));
togglePause();
string endGameScreen = (victory ? "victory.lua" : "defeat.lua");
ConcreteGuiManager::getSingleton()->readLuaScreenScript(endGameScreen);
}
void Game::update(){
resetLuaGameObjects();
int numPlayersWithUnits = 0;
for(int i = 0; i < players.size(); i++){
players[i]->update();
if(players[i]->getNumUnits() > 0)
numPlayersWithUnits++;
}
ActiveGameState *activeState = (ActiveGameState*)GameManager::getSingleton()->getStateManager()->getAppStateByType(AppStateType::ACTIVE_STATE);
Player *mainPlayer = (activeState ? activeState->getPlayer() : nullptr);
if(mainPlayer && !ended){
int numMainPlayerUnits = mainPlayer->getNumUnits();
if(numMainPlayerUnits > 0 && numPlayersWithUnits == 1)
endGame(true);
else if(numMainPlayerUnits == 0)
endGame(false);
}
for(int i = 0; i < fx.size(); i++){
if(getTime() - fx[i].initTime > fx[i].vfxTime)
removeFx(i, true);
if(getTime() - fx[i].initTime > fx[i].sfxTime)
removeFx(i, false);
}
}
//TODO remove the bool flag
void Game::removeFx(int id, bool vfx){
const sf::SoundBuffer *buffer = fx[id].sfx->getBuffer();
if(!vfx){
fx[id].sfx->stop();
delete fx[id].sfx;
delete buffer;
fx.erase(fx.begin() + id);
}
if(fx[id].peNode && vfx){
Root::getSingleton()->getRootNode()->dettachChild(fx[id].peNode);
delete fx[id].peNode;
fx[id].peNode = nullptr;
}
}
void Game::removeAllElements(){
resetLuaGameObjects();
while(!players.empty()){
delete players[0];
players.erase(players.begin());
}
ended = false;
paused = false;
}
void Game::togglePause(){
GameManager *gm = GameManager::getSingleton();
ConcreteGuiManager *guiManager = ConcreteGuiManager::getSingleton();
ActiveGameState *activeState = ((InGameAppState*)gm->getStateManager()->getAppStateByType(AppStateType::IN_GAME_STATE))->getActiveState();
if (!paused) {
gm->getStateManager()->dettachAppState(activeState);
guiManager->readLuaScreenScript("gamePaused.lua", activeState->getButtons());
}
else {
for(string f : configData::scripts)
generateView().script_file(gm->getPath() + f);
guiManager->readLuaScreenScript("inGame.lua", activeState->getButtons());
AssetManager::getSingleton()->load(gm->getPath() + (string)generateView()["modelPrefix"], true);
for(Player *p : Game::getSingleton()->getPlayers())
for(Unit *u : p->getUnits())
u->reinit();
gm->getStateManager()->attachAppState(activeState);
}
paused = !paused;
}
void Game::explode(Vector3 pos, int damage, float radius, sf::Sound *explosionSfx){
if(!(damage == 0 || radius == 0))
for(Player *pl : players){
for(Unit *un : pl->getUnits()){
float distance = un->getPos().getDistanceFrom(pos);
if(distance < radius)
un->takeDamage(int(damage * (1.f - distance / radius)));
}
}
Root *root = Root::getSingleton();
const int numFrames = 1;
string p[numFrames];
for(int i = 0; i < numFrames; i++)
p[i] = GameManager::getSingleton()->getPath() + "Textures/Explosion/explosion07.png";
Texture *tex = new Texture(p, numFrames, false);
Material *mat = new Material(root->getLibPath() + "particle");
mat->addTexUniform("tex", tex, true);
ParticleEmitter *pe = new ParticleEmitter(1);
pe->setMaterial(mat);
pe->setLowLife(3);
pe->setHighLife(3);
pe->setSize(10 * Vector2::VEC_IJ);
pe->setSpeed(0);
Node *node = new Node(pos + Vector3(0, 2, 0));
node->attachParticleEmitter(pe);
node->lookAt(Vector3::VEC_J, Vector3::VEC_K);
root->getRootNode()->attachChild(node);
Fx fx(50, 2500, explosionSfx, node);
fx.activate();
addFx(fx);
}
}