The game engine now has two bonuses for long build streaks. +10% max hp or 1 free death. I'll be adding more but that's enough to work on the real UI.
This commit is contained in:
parent
07553400f5
commit
0a9fa59365
3 changed files with 81 additions and 9 deletions
|
@ -12,7 +12,7 @@ using namespace fmt;
|
||||||
using namespace std;
|
using namespace std;
|
||||||
|
|
||||||
GameEngine::GameEngine(int hp) : starting_hp(hp) {
|
GameEngine::GameEngine(int hp) : starting_hp(hp) {
|
||||||
hit_points = starting_hp;
|
hit_points = max_hp();
|
||||||
};
|
};
|
||||||
|
|
||||||
int GameEngine::determine_damage(string &type) {
|
int GameEngine::determine_damage(string &type) {
|
||||||
|
@ -25,8 +25,17 @@ int GameEngine::determine_damage(string &type) {
|
||||||
}
|
}
|
||||||
|
|
||||||
void GameEngine::reset() {
|
void GameEngine::reset() {
|
||||||
streak = 0;
|
println("!!!!!!! RESET hit_points={}, max={}", hit_points, max_hp());
|
||||||
hit_points = starting_hp;
|
if(free_death) {
|
||||||
|
hit_points = max_hp() * 0.5f;
|
||||||
|
} else {
|
||||||
|
streak = 0;
|
||||||
|
hit_points = max_hp();
|
||||||
|
}
|
||||||
|
|
||||||
|
println("!!!!!!!! AFTER RESET hit_points={}, max={}", hit_points, max_hp());
|
||||||
|
|
||||||
|
free_death = false;
|
||||||
}
|
}
|
||||||
|
|
||||||
bool GameEngine::hit(string &type) {
|
bool GameEngine::hit(string &type) {
|
||||||
|
@ -37,12 +46,12 @@ bool GameEngine::hit(string &type) {
|
||||||
}
|
}
|
||||||
|
|
||||||
void GameEngine::heal() {
|
void GameEngine::heal() {
|
||||||
hit_points = hit_points * 1.10;
|
hit_points = hit_points * 1.10f;
|
||||||
if(hit_points > 100) hit_points = 100;
|
if(hit_points > max_hp()) hit_points = max_hp();
|
||||||
}
|
}
|
||||||
|
|
||||||
bool GameEngine::is_dead() {
|
bool GameEngine::is_dead() {
|
||||||
return hit_points <= 0;
|
return free_death ? false : hit_points <= 0;
|
||||||
}
|
}
|
||||||
|
|
||||||
void GameEngine::start(GameEvent ev) {
|
void GameEngine::start(GameEvent ev) {
|
||||||
|
@ -63,7 +72,9 @@ void GameEngine::in_round(GameEvent ev, string &hit_type) {
|
||||||
switch(ev) {
|
switch(ev) {
|
||||||
case GameEvent::HIT:
|
case GameEvent::HIT:
|
||||||
hit(hit_type);
|
hit(hit_type);
|
||||||
if(is_dead()) {
|
|
||||||
|
// NOTE: don't use is_dead to avoid free_death
|
||||||
|
if(hit_points <= 0) {
|
||||||
state(GameState::DEAD);
|
state(GameState::DEAD);
|
||||||
} else {
|
} else {
|
||||||
state(GameState::IN_ROUND);
|
state(GameState::IN_ROUND);
|
||||||
|
@ -103,6 +114,22 @@ void GameEngine::success(GameEvent ev) {
|
||||||
void GameEngine::failure(GameEvent ev) {
|
void GameEngine::failure(GameEvent ev) {
|
||||||
assert(ev == GameEvent::BUILD_DONE && "failure state expected BUILD_DONE");
|
assert(ev == GameEvent::BUILD_DONE && "failure state expected BUILD_DONE");
|
||||||
++rounds;
|
++rounds;
|
||||||
streak = 0;
|
// streak is handled by reset()
|
||||||
state(GameState::IDLE);
|
state(GameState::IDLE);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
int GameEngine::max_hp() {
|
||||||
|
return starting_hp * hp_bonus;
|
||||||
|
}
|
||||||
|
|
||||||
|
void GameEngine::add_bonus(GameBonus bonus) {
|
||||||
|
switch(bonus) {
|
||||||
|
case GameBonus::MORE_HP:
|
||||||
|
hp_bonus += 0.10f;
|
||||||
|
hit_points = max_hp();
|
||||||
|
break;
|
||||||
|
case GameBonus::FREE_DEATH:
|
||||||
|
free_death = true;
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
|
@ -19,6 +19,10 @@ enum class GameEvent {
|
||||||
BUILD_DONE, BUILD_FAILED, HIT
|
BUILD_DONE, BUILD_FAILED, HIT
|
||||||
};
|
};
|
||||||
|
|
||||||
|
enum class GameBonus {
|
||||||
|
MORE_HP, FREE_DEATH
|
||||||
|
};
|
||||||
|
|
||||||
class GameEngine : DeadSimpleFSM<GameState, GameEvent> {
|
class GameEngine : DeadSimpleFSM<GameState, GameEvent> {
|
||||||
|
|
||||||
std::map<string, int> damage_types{
|
std::map<string, int> damage_types{
|
||||||
|
@ -33,6 +37,8 @@ class GameEngine : DeadSimpleFSM<GameState, GameEvent> {
|
||||||
int hits_taken = 0;
|
int hits_taken = 0;
|
||||||
int rounds = 0;
|
int rounds = 0;
|
||||||
int streak = 0;
|
int streak = 0;
|
||||||
|
float hp_bonus = 1.0f;
|
||||||
|
bool free_death = false;
|
||||||
|
|
||||||
GameEngine(int hp);
|
GameEngine(int hp);
|
||||||
|
|
||||||
|
@ -82,4 +88,6 @@ class GameEngine : DeadSimpleFSM<GameState, GameEvent> {
|
||||||
void heal();
|
void heal();
|
||||||
bool hit(string &type);
|
bool hit(string &type);
|
||||||
void reset();
|
void reset();
|
||||||
|
void add_bonus(GameBonus bonus);
|
||||||
|
int max_hp();
|
||||||
};
|
};
|
||||||
|
|
|
@ -36,7 +36,44 @@ TEST_CASE("game engine death cycle", "[game_engine]") {
|
||||||
}
|
}
|
||||||
|
|
||||||
TEST_CASE("game can do success build", "[game_engine]") {
|
TEST_CASE("game can do success build", "[game_engine]") {
|
||||||
|
GameEngine game{10};
|
||||||
|
|
||||||
// test fails on purpose right now
|
// test fails on purpose right now
|
||||||
GameEngine game{100};
|
for(int i = 0; i < 10; i++) {
|
||||||
|
game.event(GameEvent::BUILD_START);
|
||||||
|
game.event(GameEvent::BUILD_SUCCESS);
|
||||||
|
REQUIRE(game.hits_taken == 0);
|
||||||
|
REQUIRE(game.hit_points == game.starting_hp);
|
||||||
|
// confirm streaks, hit_taken, rounds are maintained
|
||||||
|
REQUIRE(game.streak == i);
|
||||||
|
REQUIRE(game.rounds == i);
|
||||||
|
REQUIRE(game.is_dead() == false);
|
||||||
|
game.event(GameEvent::BUILD_DONE);
|
||||||
|
}
|
||||||
|
|
||||||
|
// if you hit a streak of 10 then you get one of two bonuses
|
||||||
|
// 1. 10% more hp
|
||||||
|
// 2. 1 free death
|
||||||
|
|
||||||
|
game.add_bonus(GameBonus::MORE_HP);
|
||||||
|
REQUIRE(game.max_hp() > game.starting_hp);
|
||||||
|
REQUIRE(game.hit_points == game.starting_hp * game.hp_bonus);
|
||||||
|
REQUIRE(game.hit_points == game.max_hp());
|
||||||
|
|
||||||
|
game.add_bonus(GameBonus::FREE_DEATH);
|
||||||
|
REQUIRE(game.free_death == true);
|
||||||
|
|
||||||
|
game.event(GameEvent::BUILD_START);
|
||||||
|
game.event(GameEvent::HIT, "error");
|
||||||
|
game.event(GameEvent::HIT, "error");
|
||||||
|
game.event(GameEvent::HIT, "error");
|
||||||
|
|
||||||
REQUIRE(game.is_dead() == false);
|
REQUIRE(game.is_dead() == false);
|
||||||
|
REQUIRE(game.streak == 10);
|
||||||
|
game.event(GameEvent::BUILD_FAILED);
|
||||||
|
game.event(GameEvent::BUILD_DONE);
|
||||||
|
|
||||||
|
REQUIRE(game.streak == 10);
|
||||||
|
REQUIRE(game.free_death == false);
|
||||||
|
REQUIRE(game.hit_points == int(game.max_hp() * 0.5f));
|
||||||
}
|
}
|
||||||
|
|
Loading…
Add table
Add a link
Reference in a new issue