File AgentBase.hpp
File List > core > AgentBase.hpp
Go to the documentation of this file
#pragma once
#include <cassert>
#include <string>
#include <unordered_map>
#include <utility>
#include "../DataCollection/AgentData.hpp"
#include "Data.hpp"
#include "Entity.hpp"
#include "GridPosition.hpp"
#include "WorldGrid.hpp"
namespace cse491 {
enum State
{
Healthy,
Taking_Damage,
Dying,
Deceased
};
class AgentBase : public Entity {
protected:
std::unordered_map<std::string, size_t> action_map;
int action;
int action_result = 0;
State agent_state = Healthy;
public:
AgentBase(size_t id, const std::string &name) : Entity(id, name) {}
~AgentBase() = default; // Already virtual from Entity
// -- World Interactions --
virtual bool Initialize() { return true; }
// -- Entity Overrides --
bool IsAgent() const override { return true; }
// -- Agent Interaction --
State GetAgentState() { return agent_state; }
void UpdateAgentState(cse491::AgentBase &agent) {
if (agent.HasProperty("Health")) {
if (agent.GetProperty<int>("Health") <= agent.GetProperty<int>("Max_Health") &&
agent.GetProperty<int>("Health") > 3) {
agent.agent_state = Healthy;
} else if (agent.GetProperty<int>("Health") <= 3 && agent.GetProperty<int>("Health") > 0) {
agent.agent_state = Dying;
} else if (agent.GetProperty<int>("Health") <= 0) {
agent.agent_state = Deceased;
}
}
if (agent.HasProperty("Taking_Damage")) {
if (agent.GetProperty<bool>("Taking_Damage") == true) {
agent.agent_state = Taking_Damage;
}
}
}
void TakeDamage(cse491::AgentBase &agent) {
agent.SetProperty<int>(
"Health", agent.GetProperty<int>("Health") - agent.GetProperty<int>("Taking_Damage"));
UpdateAgentState(agent);
}
// -- Action management --
[[nodiscard]] bool HasAction(const std::string &action_name) const {
return action_map.count(action_name);
}
[[nodiscard]] size_t GetActionID(const std::string &action_name) const {
auto it = action_map.find(action_name);
if (it == action_map.end()) return 0;
return it->second;
}
void storeActionMap(std::string name) {
DataCollection::AgentData data(name);
data.StoreAction(action_map);
}
[[nodiscard]] virtual GridPosition GetNextPosition() { return Entity::GetPosition(); }
virtual AgentBase &AddAction(const std::string &action_name, size_t action_id) {
assert(!HasAction(action_name)); // Cannot add existing action name.
action_map[action_name] = action_id;
return *this;
}
[[nodiscard]] virtual size_t SelectAction([[maybe_unused]] const WorldGrid &grid,
[[maybe_unused]] const type_options_t &type_options,
[[maybe_unused]] const item_map_t &item_map,
[[maybe_unused]] const agent_map_t &agent_map) {
return 0;
}
[[nodiscard]] int GetActionResult() const { return action_result; }
void SetActionResult(int result) { action_result = result; }
virtual void Notify(const std::string & /*message*/, const std::string & /*msg_type*/ = "none") {}
std::string GetTypeName_impl() const override { return "cse491::AgentBase"; }
void Serialize_impl(std::ostream &os) const override {
Entity::Serialize_impl(os);
SerializeValue(os, action_map);
SerializeValue(os, action);
SerializeValue(os, action_result);
SerializeValue(os, agent_state);
}
void Deserialize_impl(std::istream &is) override {
Entity::Deserialize_impl(is);
DeserializeValue(is, action_map);
DeserializeValue(is, action);
DeserializeValue(is, action_result);
DeserializeValue(is, agent_state);
}
};
} // End of namespace cse491