From 0780c816b15646a83a5f6f6cf72571301d2cb08a Mon Sep 17 00:00:00 2001 From: Peisong Xiao Date: Mon, 22 Jul 2024 12:19:42 -0400 Subject: [PATCH] added locking to dragon hoards --- src/enemies.cc | 14 ++++++-------- src/enemies.h | 5 +++-- src/enemies/dragon.cc | 10 ++++++++-- src/enemies/dragon.h | 3 ++- src/gold.cc | 14 ++++++++++++-- src/gold.h | 3 +++ src/level.cc | 35 +++++++++++++++++++++++++---------- src/player.cc | 9 +++++++++ 8 files changed, 68 insertions(+), 25 deletions(-) diff --git a/src/enemies.cc b/src/enemies.cc index aa320ff..3f6161a 100644 --- a/src/enemies.cc +++ b/src/enemies.cc @@ -18,15 +18,13 @@ std::unique_ptr new_dragon(RNG *rng, const position &pos, const position &fallback, const feature enabled_features, - int which_room) { - const position nil{0, 0}; - - if (pos != nil) + int which_room, const position &guards) { + if (pos != POS_NIL) return std::make_unique(rng, enabled_features, - pos, which_room); + pos, which_room, guards); else return std::make_unique(rng, enabled_features, - fallback, which_room); + fallback, which_room, guards); } const int EXCNT = 12; @@ -67,7 +65,7 @@ std::unique_ptr new_enemy(RNG *rng, const position &pos, std::unique_ptr new_enemy(const race &race, const position &pos, const feature enabled_features, - int which_room, RNG *rng) { + int which_room, RNG *rng, const position &guards) { using std::make_unique; switch (race) { @@ -121,7 +119,7 @@ std::unique_ptr new_enemy(const race &race, const position &pos, case DRAGON: return make_unique(rng, enabled_features, - pos, which_room); + pos, which_room, guards); default: break; diff --git a/src/enemies.h b/src/enemies.h index 3604019..df264a8 100644 --- a/src/enemies.h +++ b/src/enemies.h @@ -9,7 +9,7 @@ enum race : int; std::unique_ptr new_dragon(RNG *rng, const position &pos, const position &fallback, const feature enabled_features, - int which_room); + int which_room, const position &guards); std::unique_ptr new_enemy(RNG *rng, const position &pos, const feature enabled_features, @@ -17,6 +17,7 @@ std::unique_ptr new_enemy(RNG *rng, const position &pos, std::unique_ptr new_enemy(const race &race, const position &pos, const feature enabled_features, - int which_room, RNG *rng); + int which_room, RNG *rng, + const position &guards = {0, 0}); #endif diff --git a/src/enemies/dragon.cc b/src/enemies/dragon.cc index 64a70d0..3a5d803 100644 --- a/src/enemies/dragon.cc +++ b/src/enemies/dragon.cc @@ -1,10 +1,12 @@ #include "dragon.h" #include "../constants.h" +#include "../level.h" dragon::dragon(RNG *rng, const feature enabled_features, const position &pos, - const int gen_room_num): - enemy_base{rng, enabled_features, DRAGON, pos, gen_room_num, "D"} {} + const int gen_room_num, const position &guards): + enemy_base{rng, enabled_features, DRAGON, pos, gen_room_num, "D"}, + guards{guards} {} const char *dragon::get_race_name() const { return "Dragon"; @@ -18,5 +20,9 @@ long_result dragon::act(level *lvl, character *pc, bool hostile) { } int dragon::dies(level *lvl) { + for (auto &g : lvl->get_glist()) + if (g.get_pos() == guards) + g.unlock(); + return 0; } diff --git a/src/enemies/dragon.h b/src/enemies/dragon.h index 0316265..f7955d6 100644 --- a/src/enemies/dragon.h +++ b/src/enemies/dragon.h @@ -4,9 +4,10 @@ #include "../enemy.h" class dragon final: public enemy_base { + const position guards; public: dragon(RNG *rng, const feature enabled_features, const position &pos, - const int gen_room_num); + const int gen_room_num, const position &guards); const char *get_race_name() const override; long_result act(level *lvl, character *pc, bool hostile) override; int dies(level *lvl) override; diff --git a/src/gold.cc b/src/gold.cc index b9c3c7f..8ce735c 100644 --- a/src/gold.cc +++ b/src/gold.cc @@ -23,9 +23,10 @@ gold get_gold_at(const position &pos, gold_list &glist) { gold ret({0, 0}, 0); for (size_t i = 0; i < glist.size(); ++i) - if (glist[i].get_pos() == pos) { + if (!glist[i].is_locked() && glist[i].get_pos() == pos) { ret = glist[i]; glist.erase(i + glist.begin()); + return ret; } @@ -39,7 +40,8 @@ int rand_gold_drop(RNG *rng) { return GOLD_SMALL; } -gold::gold(const position &pos, const int amount): item{pos}, amount{amount} {} +gold::gold(const position &pos, const int amount): item{pos}, amount{amount}, + locked{amount == GOLD_DRAGON ? true : false} {} void gold::print(output *out) const { out->print_char(pos, 'G', COLOR_PAIR(COLOR_YELLOW)); @@ -52,3 +54,11 @@ int gold::get_amount() const { void gold::set_amount(const int new_amount) { amount = new_amount; } + +bool gold::is_locked() const { + return locked; +} + +void gold::unlock() { + locked = false; +} diff --git a/src/gold.h b/src/gold.h index a3e6564..34a9803 100644 --- a/src/gold.h +++ b/src/gold.h @@ -9,12 +9,15 @@ class gold : public item { private: int amount; + bool locked; public: gold(const position &pos, const int amount); void print(output *out) const override; int get_amount() const; void set_amount(const int new_amount); + bool is_locked() const; + void unlock(); }; typedef std::vector gold_list; diff --git a/src/level.cc b/src/level.cc index 9d14fa4..dd1d8ec 100644 --- a/src/level.cc +++ b/src/level.cc @@ -48,15 +48,6 @@ level::level(const level_data &lvl, character *player, RNG *rng, void level::fill(const level_data &lvl, std::vector &tiles, RNG *rng) { - for (auto [type, pos] : lvl.enemies) { - for (size_t i = 0; i < tiles.size(); ++i) - remove_from_list(tiles[i], pos); - - pelist.push_back(new_enemy(type, pos, enabled_features, - map.which_room(pos), rng)); - elist.push_back(pelist[pelist.size() - 1].get()); - } - for (auto [type, pos] : lvl.potions) { for (size_t i = 0; i < tiles.size(); ++i) remove_from_list(tiles[i], pos); @@ -71,6 +62,29 @@ void level::fill(const level_data &lvl, std::vector &tiles, glist.push_back(g); } + + for (auto [type, pos] : lvl.enemies) { + for (size_t i = 0; i < tiles.size(); ++i) + remove_from_list(tiles[i], pos); + + if (type != DRAGON) + pelist.push_back(new_enemy(type, pos, enabled_features, + map.which_room(pos), rng)); + else { + gold guards{POS_NIL, 0}; + + for (size_t i = 0; i < glist.size(); ++i) + if (glist[i].get_amount() == GOLD_DRAGON && + is_adjacent(glist[i].get_pos(), pos)) + guards = glist[i]; + + pelist.push_back(new_enemy(type, pos, enabled_features, + map.which_room(pos), rng, + guards.get_pos())); + } + + elist.push_back(pelist[pelist.size() - 1].get()); + } } gold_list level::dragon_hoard(const level_data &lvl) { @@ -116,7 +130,8 @@ void level::gen_enemies(const level_data &lvl, RNG *rng, dhoard[i].get_pos(); pelist.push_back(new_dragon(rng, pos, dhoard[i].get_pos(), enabled_features, - map.which_room(dhoard[i].get_pos()))); + map.which_room(dhoard[i].get_pos()), + dhoard[i].get_pos())); int room = map.which_room(pos); remove_from_list(tiles[room], pos); diff --git a/src/player.cc b/src/player.cc index cc97c1e..3516e7b 100644 --- a/src/player.cc +++ b/src/player.cc @@ -200,6 +200,15 @@ long_result player_base::interpret_command(level *lvl, game_command cmd) { res.msg += "PC picked up " + std::to_string(gold_tmp) + " pieces of gold. "; + bool locked = false; + + for (auto g : lvl->get_glist()) + if (g.is_locked() && g.get_pos() == pos) + locked = true; + + if (locked) + res.msg += "There's a pile of gold here that PC cannot pick up. "; + gold_cnt += gold_tmp;