Skip to content

Commit 0b044e9

Browse files
committed
Improve Lighthouse
- Add visibility radius in which enemies are revealed - Lighthouse takes damage with enemy contact - Stop game when Lighthouse HP reaches 0 - Add Health text
1 parent 0770ebb commit 0b044e9

File tree

7 files changed

+53
-8
lines changed

7 files changed

+53
-8
lines changed

src/enemy.cpp

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -19,7 +19,7 @@ Enemy::Enemy(gsl::not_null<le::ServiceLocator const*> services, EnemyParams cons
1919
}
2020

2121
void Enemy::render(le::Renderer& renderer) const {
22-
if (m_can_render) { m_sprite.draw(renderer); }
22+
if (can_render) { m_sprite.draw(renderer); }
2323
}
2424

2525
void Enemy::translate(kvf::Seconds const dt) {
@@ -30,7 +30,7 @@ void Enemy::translate(kvf::Seconds const dt) {
3030

3131
std::pair<glm::vec2, float> Enemy::get_pos_diameter() const { return {m_sprite.transform.position, m_diameter}; }
3232
void Enemy::take_damage(std::size_t dmg) {
33-
m_can_render = true;
33+
can_render = true;
3434
m_health = (dmg >= m_health) ? 0 : (m_health - dmg);
3535
}
3636

src/enemy.hpp

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -22,7 +22,7 @@ class Enemy {
2222
void take_damage(std::size_t dmg);
2323
[[nodiscard]] std::size_t get_health() const { return m_health; }
2424
[[nodiscard]] std::pair<glm::vec2, float> get_pos_diameter() const;
25-
bool m_can_render{false};
25+
bool can_render{false};
2626

2727
private:
2828
gsl::not_null<le::ServiceLocator const*> m_services;

src/game.cpp

Lines changed: 17 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -6,6 +6,7 @@
66
#include <vector>
77
#include "enemy.hpp"
88
#include "enemy_params.hpp"
9+
#include "glm/ext/vector_float2.hpp"
910
#include "kvf/time.hpp"
1011
#include "le2d/asset_loader.hpp"
1112
#include "le2d/data_loader.hpp"
@@ -22,8 +23,9 @@ Game::Game(gsl::not_null<le::ServiceLocator const*> services)
2223
auto const asset_loader = le::AssetLoader{&data_loader, &context};
2324
m_font = asset_loader.load_font("fonts/specialElite.ttf");
2425
auto const framebuffer_size = m_services->get<le::Context>().framebuffer_size();
25-
26-
m_score_text.transform.position.y = static_cast<float>(framebuffer_size.y) / 2.0f - 50.0f;
26+
auto const y = (static_cast<float>(framebuffer_size.y) / 2.0f) - 50.0f;
27+
m_score_text.transform.position.y = y;
28+
m_health_text.transform.position = glm::vec2{(static_cast<float>(framebuffer_size.y) / 2.0f) - 50.0f, y};
2729
}
2830

2931
void Game::on_cursor_pos(le::event::CursorPos const& cursor_pos) {
@@ -32,19 +34,24 @@ void Game::on_cursor_pos(le::event::CursorPos const& cursor_pos) {
3234
}
3335

3436
void Game::tick([[maybe_unused]] kvf::Seconds const dt) {
37+
m_running = m_lighthouse.get_health() > 0;
3538
if (!m_running) { return; }
39+
3640
m_time_since_last_wave_spawn += dt;
3741
if (m_time_since_last_wave_spawn >= m_wave_interval) {
3842
spawn_wave();
3943
m_time_since_last_wave_spawn = kvf::Seconds{};
4044
}
4145
for (auto& enemy : m_enemies) {
4246
m_light.check_enemy_collision(enemy);
47+
m_lighthouse.check_visibility_range(enemy);
48+
set_health_text();
4349
enemy.translate(dt);
4450
}
4551
// Keep track of how many enemies were defeated and calculate score
4652
auto res = std::erase_if(m_enemies, [](Enemy const& enemy) { return !enemy.get_health(); });
4753
increase_score(res * 10);
54+
4855
m_light.set_position(m_cursor_pos);
4956
m_lighthouse.rotate_towards_cursor(m_cursor_pos);
5057
}
@@ -54,6 +61,7 @@ void Game::render(le::Renderer& renderer) const {
5461
m_lighthouse.render(renderer);
5562
for (auto const& enemy : m_enemies) { enemy.render(renderer); }
5663
m_score_text.draw(renderer);
64+
m_health_text.draw(renderer);
5765
}
5866

5967
void Game::spawn_wave() {
@@ -72,4 +80,11 @@ void Game::increase_score(std::size_t points) {
7280
m_score += points;
7381
m_score_text.set_string(m_font, "Score: " + std::to_string(m_score));
7482
}
83+
84+
void Game::set_health_text() {
85+
float const health = m_lighthouse.get_health();
86+
std::string text = health > 0 ? "Health: " + std::format("{:.1f}", health) : "Game Over";
87+
m_health_text.set_string(m_font, text);
88+
}
89+
7590
} // namespace miracle

src/game.hpp

Lines changed: 3 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -21,7 +21,7 @@ class Game {
2121
void tick(kvf::Seconds dt);
2222
void render(le::Renderer& renderer) const;
2323
void increase_score(std::size_t points);
24-
[[nodiscard]] std::string get_score_string() const;
24+
void set_health_text();
2525
void spawn_wave();
2626

2727
private:
@@ -31,6 +31,8 @@ class Game {
3131

3232
le::Font m_font{};
3333
le::drawable::Text m_score_text{};
34+
le::drawable::Text m_health_text{};
35+
3436
glm::vec2 m_cursor_pos{};
3537
std::size_t m_wave_count{};
3638
bool m_running{true};

src/lighhouse.hpp

Lines changed: 9 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -6,7 +6,9 @@
66
#include <le2d/event.hpp>
77
#include <le2d/renderer.hpp>
88
#include <le2d/service_locator.hpp>
9+
#include <cstddef>
910
#include <optional>
11+
#include "enemy.hpp"
1012
#include "le2d/texture.hpp"
1113

1214
namespace miracle {
@@ -16,10 +18,17 @@ class Lighthouse {
1618

1719
void rotate_towards_cursor(glm::vec2 cursor_pos);
1820
void render(le::Renderer& renderer) const;
21+
void check_visibility_range(Enemy& enemy);
22+
void check_damage_taken(Enemy& enemy);
23+
void take_damage(float dmg);
24+
[[nodiscard]] float get_health() const;
1925

2026
private:
2127
gsl::not_null<le::ServiceLocator const*> m_services;
28+
float m_hitbog_diameter{150.0f};
29+
float m_visibility_diameter{250.0f};
2230
std::optional<le::Texture> m_texture;
2331
le::drawable::Circle m_sprite{};
32+
float m_health{100};
2433
};
2534
} // namespace miracle

src/light.cpp

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -9,7 +9,7 @@ void Light::check_enemy_collision(Enemy& enemy) {
99
if (glm::distance(pos, m_sprite.transform.position) < (diameter + m_diameter)) {
1010
enemy.take_damage(1);
1111
} else {
12-
enemy.m_can_render = false;
12+
enemy.can_render = false;
1313
}
1414
}
1515
void Light::render(le::Renderer& renderer) const { m_sprite.draw(renderer); }

src/lighthouse.cpp

Lines changed: 20 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1,10 +1,12 @@
11
#include <lighhouse.hpp>
2+
#include <cstddef>
3+
#include "glm/geometric.hpp"
24
#include "le2d/asset_loader.hpp"
35
#include "le2d/data_loader.hpp"
46

57
namespace miracle {
68
Lighthouse::Lighthouse(gsl::not_null<le::ServiceLocator const*> services) : m_services(services) {
7-
m_sprite.create(200.0f);
9+
m_sprite.create(m_hitbog_diameter);
810
auto const& data_loader = services->get<le::IDataLoader>();
911
auto const& context = services->get<le::Context>();
1012
auto const asset_loader = le::AssetLoader{&data_loader, &context};
@@ -23,6 +25,23 @@ void Lighthouse::rotate_towards_cursor(glm::vec2 cursor_pos) {
2325
m_sprite.transform.orientation = cursor_pos.x > 0.0f ? -angle : angle;
2426
}
2527
}
28+
void Lighthouse::check_visibility_range(Enemy& enemy) {
29+
auto [enemy_pos, enemy_diameter] = enemy.get_pos_diameter();
30+
if (glm::distance(m_sprite.transform.position, enemy_pos) < (m_visibility_diameter + enemy_diameter) / 2.0f) {
31+
enemy.can_render = true;
32+
// No need to check for damage taken if enemy isn't already in visibility radius
33+
check_damage_taken(enemy);
34+
}
35+
}
36+
void Lighthouse::check_damage_taken(Enemy& enemy) {
37+
auto [enemy_pos, enemy_diameter] = enemy.get_pos_diameter();
38+
if (glm::distance(m_sprite.transform.position, enemy_pos) < (m_hitbog_diameter + enemy_diameter) / 2.0f) {
39+
take_damage(enemy_diameter / 200);
40+
} // magic numbers
41+
}
42+
43+
void Lighthouse::take_damage(float dmg) { m_health -= dmg; }
2644

45+
float Lighthouse::get_health() const { return m_health; }
2746
void Lighthouse::render(le::Renderer& renderer) const { m_sprite.draw(renderer); }
2847
} // namespace miracle

0 commit comments

Comments
 (0)