aboutsummaryrefslogtreecommitdiff
path: root/src/openvic-simulation/military
diff options
context:
space:
mode:
Diffstat (limited to 'src/openvic-simulation/military')
-rw-r--r--src/openvic-simulation/military/Deployment.cpp130
-rw-r--r--src/openvic-simulation/military/Deployment.hpp79
-rw-r--r--src/openvic-simulation/military/LeaderTrait.cpp2
-rw-r--r--src/openvic-simulation/military/LeaderTrait.hpp5
-rw-r--r--src/openvic-simulation/military/MilitaryManager.hpp6
-rw-r--r--src/openvic-simulation/military/Unit.hpp25
6 files changed, 231 insertions, 16 deletions
diff --git a/src/openvic-simulation/military/Deployment.cpp b/src/openvic-simulation/military/Deployment.cpp
new file mode 100644
index 0000000..d2637b1
--- /dev/null
+++ b/src/openvic-simulation/military/Deployment.cpp
@@ -0,0 +1,130 @@
+#include "Deployment.hpp"
+
+#include "openvic-simulation/GameManager.hpp" /* gosh don't we all just love circular inclusion :DDD */
+
+using namespace OpenVic;
+using namespace OpenVic::NodeTools;
+
+Deployment::Deployment(std::string_view new_path, std::vector<Army>&& new_armies, std::vector<Navy>&& new_navies, std::vector<Leader>&& new_leaders)
+ : HasIdentifier { new_path }, armies { std::move(new_armies) }, navies { std::move(new_navies) }, leaders { std::move(new_leaders) } {}
+
+const std::vector<Army>& Deployment::get_armies() const {
+ return armies;
+}
+
+const std::vector<Navy>& Deployment::get_navies() const {
+ return navies;
+}
+
+const std::vector<Leader>& Deployment::get_leaders() const {
+ return leaders;
+}
+
+DeploymentManager::DeploymentManager() : deployments { "deployments" } {}
+
+bool DeploymentManager::add_deployment(std::string_view path, std::vector<Army>&& armies, std::vector<Navy>&& navies, std::vector<Leader>&& leaders) {
+ if (path.empty()) {
+ Logger::error("Attemped to load order of battle with no path! Something is very wrong!");
+ return false;
+ }
+ if (armies.empty() && navies.empty() && leaders.empty() && path != "NULL") {
+ Logger::warning("Loading redundant empty order of battle at ", path);
+ }
+
+ return deployments.add_item({ path, std::move(armies), std::move(navies), std::move(leaders) });
+}
+
+bool DeploymentManager::load_oob_file(GameManager& game_manager, std::string_view path, ast::NodeCPtr root) {
+ std::vector<Army> armies;
+ std::vector<Navy> navies;
+ std::vector<Leader> leaders;
+
+ bool ret = expect_dictionary_keys_and_default(
+ key_value_success_callback, // TODO: load SOI information
+ "leader", ZERO_OR_MORE, [&leaders, &game_manager](ast::NodeCPtr node) -> bool {
+ std::string_view name;
+ Unit::type_t type;
+ Date date;
+ LeaderTrait const* personality;
+ LeaderTrait const* background;
+ fixed_point_t prestige = 0;
+
+ bool ret = expect_dictionary_keys(
+ "name", ONE_EXACTLY, expect_string(assign_variable_callback(name), false),
+ "date", ONE_EXACTLY, expect_identifier_or_string(expect_date_str(assign_variable_callback(date))),
+ "type", ONE_EXACTLY, expect_identifier([&type](std::string_view leader_type) -> bool {
+ if (leader_type == "land") {
+ type = Unit::type_t::LAND;
+ } else {
+ type = Unit::type_t::NAVAL;
+ }
+ return true;
+ }),
+ "personality", ONE_EXACTLY, game_manager.get_military_manager().get_leader_trait_manager().expect_leader_trait_identifier(assign_variable_callback_pointer(personality)),
+ "background", ONE_EXACTLY, game_manager.get_military_manager().get_leader_trait_manager().expect_leader_trait_identifier(assign_variable_callback_pointer(background)),
+ "prestige", ZERO_OR_ONE, expect_fixed_point(assign_variable_callback(prestige)),
+ "picture", ZERO_OR_ONE, success_callback
+ )(node);
+
+ if (!personality->is_personality_trait()) {
+ Logger::error("Leader ", name, " has personality ", personality->get_identifier(), " which is not a personality trait!");
+ return false;
+ }
+ if (!background->is_background_trait()) {
+ Logger::error("Leader ", name, " has background ", background->get_identifier(), " which is not a background trait!");
+ return false;
+ }
+
+ leaders.push_back(Leader{ std::string(name), type, date, personality, background, prestige });
+ return ret; },
+ "army", ZERO_OR_MORE, [&armies, &game_manager](ast::NodeCPtr node) -> bool {
+ std::string_view name;
+ Province const* location;
+ std::vector<Regiment> regiments;
+
+ bool ret = expect_dictionary_keys(
+ "leader", ZERO_OR_MORE, success_callback, /* another paradox gem, tested in game and they don't lead the army or even show up */
+ "name", ONE_EXACTLY, expect_string(assign_variable_callback(name), false),
+ "location", ONE_EXACTLY, game_manager.get_map().expect_province_identifier(assign_variable_callback_pointer(location)),
+ "regiment", ONE_OR_MORE, [&game_manager, &regiments](ast::NodeCPtr node) -> bool {
+ Regiment regiment;
+ bool ret = expect_dictionary_keys(
+ "name", ONE_EXACTLY, expect_string(assign_variable_callback_string(regiment.name), false),
+ "type", ONE_EXACTLY, game_manager.get_military_manager().get_unit_manager().expect_unit_identifier(assign_variable_callback_pointer(regiment.type)),
+ "home", ONE_EXACTLY, game_manager.get_map().expect_province_identifier(assign_variable_callback_pointer(regiment.home))
+ )(node);
+ regiments.push_back(regiment);
+ return ret;
+ }
+ )(node);
+ armies.push_back(Army{ std::string(name), location, std::move(regiments) });
+ return ret; },
+ "navy", ZERO_OR_MORE, [&navies, &game_manager](ast::NodeCPtr node) -> bool {
+ std::string_view name;
+ Province const* location;
+ std::vector<Ship> ships;
+
+ bool ret = expect_dictionary_keys(
+ "name", ONE_EXACTLY, expect_string(assign_variable_callback(name), false),
+ "location", ONE_EXACTLY, game_manager.get_map().expect_province_identifier(assign_variable_callback_pointer(location)),
+ "ship", ONE_OR_MORE, [&game_manager, &ships](ast::NodeCPtr node) -> bool {
+ Ship ship;
+ bool ret = expect_dictionary_keys(
+ "name", ONE_EXACTLY, expect_string(assign_variable_callback_string(ship.name), false),
+ "type", ONE_EXACTLY, game_manager.get_military_manager().get_unit_manager().expect_unit_identifier(assign_variable_callback_pointer(ship.type))
+ )(node);
+ ships.push_back(ship);
+ return ret;
+ },
+ "leader", ZERO_OR_MORE, success_callback
+ )(node);
+ navies.push_back(Navy{ std::string(name), location, std::move(ships) });
+ return ret; }
+ )(root);
+ /* need to do this for platform compatibility of identifiers */
+ std::string identifier = std::string { path };
+ std::replace(identifier.begin(), identifier.end(), '\\', '/');
+ ret &= add_deployment(identifier, std::move(armies), std::move(navies), std::move(leaders));
+
+ return ret;
+}
diff --git a/src/openvic-simulation/military/Deployment.hpp b/src/openvic-simulation/military/Deployment.hpp
new file mode 100644
index 0000000..8ec0e49
--- /dev/null
+++ b/src/openvic-simulation/military/Deployment.hpp
@@ -0,0 +1,79 @@
+#pragma once
+
+#include <filesystem>
+#include <string>
+#include <string_view>
+#include <vector>
+
+#include "openvic-simulation/dataloader/Dataloader.hpp"
+#include "openvic-simulation/dataloader/NodeTools.hpp"
+#include "openvic-simulation/map/Province.hpp"
+#include "openvic-simulation/military/LeaderTrait.hpp"
+#include "openvic-simulation/military/Unit.hpp"
+#include "openvic-simulation/types/Date.hpp"
+#include "openvic-simulation/types/fixed_point/FixedPoint.hpp"
+
+namespace OpenVic {
+ struct Leader {
+ std::string name;
+ const Unit::type_t type;
+ const Date date;
+ LeaderTrait const* personality;
+ LeaderTrait const* background;
+ fixed_point_t prestige;
+ };
+
+ struct Regiment {
+ std::string name;
+ Unit const* type;
+ Province const* home;
+ };
+
+ struct Ship {
+ std::string name;
+ Unit const* type;
+ };
+
+ struct Army {
+ std::string name;
+ Province const* location;
+ std::vector<Regiment> regiments;
+ };
+
+ struct Navy {
+ std::string name;
+ Province const* location;
+ std::vector<Ship> ships;
+ };
+
+ struct DeploymentManager;
+
+ struct Deployment : HasIdentifier {
+ friend struct DeploymentManager;
+
+ private:
+ const std::vector<Army> armies;
+ const std::vector<Navy> navies;
+ const std::vector<Leader> leaders;
+
+ Deployment(std::string_view new_path, std::vector<Army>&& new_armies, std::vector<Navy>&& new_navies, std::vector<Leader>&& new_leaders);
+
+ public:
+ const std::vector<Army>& get_armies() const;
+ const std::vector<Navy>& get_navies() const;
+ const std::vector<Leader>& get_leaders() const;
+ };
+
+ struct DeploymentManager {
+ private:
+ IdentifierRegistry<Deployment> deployments;
+
+ public:
+ DeploymentManager();
+
+ bool add_deployment(std::string_view path, std::vector<Army>&& armies, std::vector<Navy>&& navies, std::vector<Leader>&& leaders);
+ IDENTIFIER_REGISTRY_ACCESSORS(deployment);
+
+ bool load_oob_file(GameManager& game_manager, std::string_view path, ast::NodeCPtr root);
+ };
+} // namespace OpenVic
diff --git a/src/openvic-simulation/military/LeaderTrait.cpp b/src/openvic-simulation/military/LeaderTrait.cpp
index b90a399..ed21c1f 100644
--- a/src/openvic-simulation/military/LeaderTrait.cpp
+++ b/src/openvic-simulation/military/LeaderTrait.cpp
@@ -22,7 +22,7 @@ ModifierValue const& LeaderTrait::get_modifiers() const {
return modifiers;
}
-LeaderTraitManager::LeaderTraitManager() : leader_traits { "leader_traits" } {}
+LeaderTraitManager::LeaderTraitManager() : leader_traits { "leader trait" } {}
bool LeaderTraitManager::add_leader_trait(std::string_view identifier, LeaderTrait::trait_type_t type, ModifierValue&& modifiers) {
if (identifier.empty()) {
diff --git a/src/openvic-simulation/military/LeaderTrait.hpp b/src/openvic-simulation/military/LeaderTrait.hpp
index e525e23..d885057 100644
--- a/src/openvic-simulation/military/LeaderTrait.hpp
+++ b/src/openvic-simulation/military/LeaderTrait.hpp
@@ -2,10 +2,11 @@
#include <cstdint>
#include <string_view>
+
+#include "openvic-simulation/Modifier.hpp"
+#include "openvic-simulation/dataloader/NodeTools.hpp"
#include "openvic-simulation/types/IdentifierRegistry.hpp"
#include "openvic-simulation/types/fixed_point/FixedPoint.hpp"
-#include "openvic-simulation/dataloader/NodeTools.hpp"
-#include "openvic-simulation/Modifier.hpp"
namespace OpenVic {
struct LeaderTraitManager;
diff --git a/src/openvic-simulation/military/MilitaryManager.hpp b/src/openvic-simulation/military/MilitaryManager.hpp
index fd8135d..57ba8d1 100644
--- a/src/openvic-simulation/military/MilitaryManager.hpp
+++ b/src/openvic-simulation/military/MilitaryManager.hpp
@@ -1,15 +1,19 @@
#pragma once
-#include "openvic-simulation/military/Unit.hpp"
#include "openvic-simulation/military/LeaderTrait.hpp"
+#include "openvic-simulation/military/Deployment.hpp"
+#include "openvic-simulation/military/Unit.hpp"
namespace OpenVic {
struct MilitaryManager {
private:
UnitManager unit_manager;
LeaderTraitManager leader_trait_manager;
+ DeploymentManager deployment_manager;
+
public:
REF_GETTERS(unit_manager)
REF_GETTERS(leader_trait_manager)
+ REF_GETTERS(deployment_manager)
};
}
diff --git a/src/openvic-simulation/military/Unit.hpp b/src/openvic-simulation/military/Unit.hpp
index 17408cf..ea28511 100644
--- a/src/openvic-simulation/military/Unit.hpp
+++ b/src/openvic-simulation/military/Unit.hpp
@@ -2,36 +2,37 @@
#include <cstdint>
#include <string_view>
-#include "openvic-simulation/economy/Good.hpp"
-#include "openvic-simulation/types/IdentifierRegistry.hpp"
-#include "openvic-simulation/types/fixed_point/FixedPoint.hpp"
+
#include "openvic-simulation/dataloader/NodeTools.hpp"
#include "openvic-simulation/economy/Good.hpp"
#include "openvic-simulation/types/Date.hpp"
+#include "openvic-simulation/types/IdentifierRegistry.hpp"
+#include "openvic-simulation/types/fixed_point/FixedPoint.hpp"
#define UNIT_PARAMS \
Unit::icon_t icon, std::string_view sprite, bool active, std::string_view unit_type, \
- bool floating_flag, uint32_t priority, fixed_point_t max_strength, fixed_point_t default_organisation, \
- fixed_point_t maximum_speed, fixed_point_t weighted_value, std::string_view move_sound, \
- std::string_view select_sound, Timespan build_time, Good::good_map_t&& build_cost, \
- fixed_point_t supply_consumption, Good::good_map_t&& supply_cost
+ bool floating_flag, uint32_t priority, fixed_point_t max_strength, fixed_point_t default_organisation, \
+ fixed_point_t maximum_speed, fixed_point_t weighted_value, std::string_view move_sound, \
+ std::string_view select_sound, Timespan build_time, Good::good_map_t &&build_cost, \
+ fixed_point_t supply_consumption, Good::good_map_t &&supply_cost
#define LAND_PARAMS \
bool primary_culture, std::string_view sprite_override, std::string_view sprite_mount, \
- std::string_view sprite_mount_attach_node, fixed_point_t reconnaissance, fixed_point_t attack, fixed_point_t defence, \
- fixed_point_t discipline, fixed_point_t support, fixed_point_t maneuver, fixed_point_t siege
+ std::string_view sprite_mount_attach_node, fixed_point_t reconnaissance, fixed_point_t attack, fixed_point_t defence, \
+ fixed_point_t discipline, fixed_point_t support, fixed_point_t maneuver, fixed_point_t siege
#define NAVY_PARAMS \
Unit::icon_t naval_icon, bool sail, bool transport, bool capital, fixed_point_t colonial_points, bool build_overseas, \
- uint32_t min_port_level, int32_t limit_per_port, fixed_point_t supply_consumption_score, fixed_point_t hull, \
- fixed_point_t gun_power, fixed_point_t fire_range, fixed_point_t evasion, fixed_point_t torpedo_attack
+ uint32_t min_port_level, int32_t limit_per_port, fixed_point_t supply_consumption_score, fixed_point_t hull, \
+ fixed_point_t gun_power, fixed_point_t fire_range, fixed_point_t evasion, fixed_point_t torpedo_attack
namespace OpenVic {
struct Unit : HasIdentifier {
using icon_t = uint32_t;
enum struct type_t {
- LAND, NAVAL
+ LAND,
+ NAVAL
};
private: