121 lines
3.4 KiB
C++
121 lines
3.4 KiB
C++
#include "game.h"
|
|
|
|
void Game::awakeGod() {
|
|
god.counter = 0;
|
|
god.state = GodState::AWAKE;
|
|
}
|
|
|
|
void Game::manageGod() {
|
|
switch (god.state) {
|
|
case GodState::NONE: {
|
|
break;
|
|
}
|
|
case GodState::AWAKE: {
|
|
if (god.counter == GOD_BENCH_SIZE) {
|
|
god.counter = 0;
|
|
god.state = GodState::WAIT;
|
|
} else ++god.counter;
|
|
break;
|
|
}
|
|
case GodState::WAIT: {
|
|
if (god.counter < 100) {
|
|
++god.counter;
|
|
break;
|
|
}
|
|
// init throw
|
|
god.counter = 0;
|
|
god.state = GodState::RETRIEVE1;
|
|
god.thrownInvPosX = grid.randomValid();
|
|
god.thrownInvPosY = grid[god.thrownInvPosX].randomValid();
|
|
god.thrownInvType = InvaderType::NONE;
|
|
|
|
god.thrownTransition.setX(pm.getScreenWidth() - GOD_HAND_DISTANCE - GOD_HAND_SIZE);
|
|
god.thrownTransition.setY(basePos.getY() + INV_GET_POS(god.thrownInvPosY));
|
|
break;
|
|
}
|
|
case GodState::RETRIEVE1: {
|
|
if (god.counter < 100) {
|
|
god.counter += 2;
|
|
break;
|
|
}
|
|
if (grid.size() > god.thrownInvPosY && grid[god.thrownInvPosX][god.thrownInvPosY] != InvaderType::NONE) {
|
|
god.thrownInvType = grid[god.thrownInvPosX][god.thrownInvPosY];
|
|
grid[god.thrownInvPosX][god.thrownInvPosY] = InvaderType::NONE;
|
|
updateColumns();
|
|
}
|
|
god.state = GodState::RETRIEVE2;
|
|
break;
|
|
}
|
|
case GodState::RETRIEVE2: {
|
|
if (god.counter > 0) {
|
|
god.counter -= 2;
|
|
break;
|
|
}
|
|
if(god.thrownInvType==InvaderType::NONE){
|
|
god.state = GodState::WAIT;
|
|
break;
|
|
}
|
|
god.state = GodState::THROW;
|
|
|
|
// compute the launch vector
|
|
|
|
Position invaderMiddlePos(pm.getScreenWidth() - GOD_HAND_DISTANCE - GOD_HAND_SIZE / 2,
|
|
GOD_HAND_SIZE / 2);
|
|
|
|
|
|
playerID target;
|
|
if (players.size() == 1)target = 0; // don't want to use random if not needed
|
|
else target = rand() % players.size();
|
|
Position playerMiddlePos(players[target].x + confData.playersWidth / 2,
|
|
pm.getScreenHeight() - PLAYER_HEIGHT / 2);
|
|
|
|
god.thrownVector = playerMiddlePos - invaderMiddlePos;
|
|
god.thrownVector = god.thrownVector / (god.thrownVector.computeMagnitude() / 1000.0);
|
|
// let's normalize it, but keep it's length big so x and y and non-zero
|
|
// We will divide it in display
|
|
break;
|
|
}
|
|
case GodState::THROW: {
|
|
++god.counter;
|
|
|
|
|
|
Position invaderPos = god.getRightHandPos(pm.getScreenWidth());
|
|
applyTransformation(invaderPos, GOD_HAND_SIZE, confData.invadersSize);
|
|
Position a = god.thrownVector * (god.counter / 100.0);
|
|
invaderPos = invaderPos + a;
|
|
|
|
bool touched = false;
|
|
|
|
// check if OOB (Out Of Bounds)
|
|
if (invaderPos.getY()+confData.invadersSize >= pm.getScreenWidth() ||
|
|
(invaderPos.getX() < 0 || invaderPos.getX() + confData.invadersSize >= pm.getScreenWidth())) {
|
|
touched = true;
|
|
// check player collision
|
|
} else if (invaderPos.getY() + confData.invadersSize >= pm.getScreenHeight() - PLAYER_HEIGHT) {
|
|
for (Player &p: players) {
|
|
if (areLinesColliding(
|
|
p.x, p.x + confData.playersWidth,
|
|
invaderPos.getX(), invaderPos.getX() + confData.invadersSize
|
|
)) {
|
|
// TODO manage player death
|
|
touched = true;
|
|
// do not break, the other player also deserves to be hit
|
|
}
|
|
}
|
|
}
|
|
if (touched){
|
|
god.state = GodState::WAIT;
|
|
god.counter = 0;
|
|
}
|
|
/*
|
|
* we do not need to reset other members, they'll be treated as non-initialized
|
|
* When we cycle back between states
|
|
*/
|
|
}
|
|
break;
|
|
}
|
|
}
|
|
|
|
Position God::getRightHandPos(unsigned screenWidth) const {
|
|
return Position(screenWidth - GOD_HAND_DISTANCE - GOD_HAND_SIZE, 0);
|
|
} |