From 33a2a1e5fcac60ddd0f2840449488e48069493ec Mon Sep 17 00:00:00 2001 From: zaaarf Date: Thu, 28 Sep 2023 11:29:57 +0200 Subject: fix: use timespan for unit build time --- src/openvic-simulation/units/Unit.cpp | 10 ++++++---- src/openvic-simulation/units/Unit.hpp | 7 ++++--- 2 files changed, 10 insertions(+), 7 deletions(-) diff --git a/src/openvic-simulation/units/Unit.cpp b/src/openvic-simulation/units/Unit.cpp index f57e0a7..b965f93 100644 --- a/src/openvic-simulation/units/Unit.cpp +++ b/src/openvic-simulation/units/Unit.cpp @@ -52,7 +52,7 @@ fixed_point_t Unit::get_maximum_speed() const { return maximum_speed; } -uint32_t Unit::get_build_time() const { +Timespan Unit::get_build_time() const { return build_time; } @@ -210,14 +210,14 @@ bool UnitManager::add_naval_unit(const std::string_view identifier, UNIT_PARAMS, return units.add_item(NavalUnit { identifier, UNIT_ARGS, NAVY_ARGS }); } -//TODO forgot fcking capital flag for naval units + bool UnitManager::load_unit_file(GoodManager const& good_manager, ast::NodeCPtr root) { return NodeTools::expect_dictionary([this, &good_manager](std::string_view key, ast::NodeCPtr value) -> bool { Unit::icon_t icon; std::string_view category, type; Unit::sprite_t sprite; bool active = true, floating_flag; - uint32_t priority, build_time; + uint32_t priority, build_time_days; fixed_point_t maximum_speed, max_strength, default_organisation, weighted_value, supply_consumption; std::map build_cost, supply_cost; @@ -234,12 +234,14 @@ bool UnitManager::load_unit_file(GoodManager const& good_manager, ast::NodeCPtr "default_organisation", ONE_EXACTLY, expect_fixed_point(assign_variable_callback(default_organisation)), "maximum_speed", ONE_EXACTLY, expect_fixed_point(assign_variable_callback(maximum_speed)), "weighted_value", ONE_EXACTLY, expect_fixed_point(assign_variable_callback(weighted_value)), - "build_time", ONE_EXACTLY, expect_uint(assign_variable_callback_uint("unit build time", build_time)), + "build_time", ONE_EXACTLY, expect_uint(assign_variable_callback_uint("unit build time", build_time_days)), "build_cost", ONE_EXACTLY, good_manager.expect_good_decimal_map(assign_variable_callback(build_cost)), "supply_consumption", ONE_EXACTLY, expect_fixed_point(move_variable_callback(supply_consumption)), "supply_cost", ONE_EXACTLY, good_manager.expect_good_decimal_map(move_variable_callback(supply_cost)) )(value); + Timespan build_time = { build_time_days }; + if (category == "land") { fixed_point_t reconnaissance, attack, defence, discipline, support, maneuver, siege; diff --git a/src/openvic-simulation/units/Unit.hpp b/src/openvic-simulation/units/Unit.hpp index 507adbd..dc7c00f 100644 --- a/src/openvic-simulation/units/Unit.hpp +++ b/src/openvic-simulation/units/Unit.hpp @@ -7,10 +7,11 @@ #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" #define UNIT_PARAMS Unit::icon_t icon, Unit::sprite_t sprite, bool active, std::string_view 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, uint32_t build_time, \ + fixed_point_t maximum_speed, fixed_point_t weighted_value, Timespan build_time, \ std::map build_cost, fixed_point_t supply_consumption, \ std::map supply_cost #define LAND_PARAMS fixed_point_t reconnaissance, fixed_point_t attack, fixed_point_t defence, fixed_point_t discipline, \ @@ -40,7 +41,7 @@ namespace OpenVic { const fixed_point_t maximum_speed; const fixed_point_t weighted_value; - const uint32_t build_time; + const Timespan build_time; const std::map build_cost; const fixed_point_t supply_consumption; const std::map supply_cost; @@ -64,7 +65,7 @@ namespace OpenVic { fixed_point_t get_maximum_speed() const; fixed_point_t get_weighted_value() const; - uint32_t get_build_time() const; + Timespan get_build_time() const; std::map const& get_build_cost() const; fixed_point_t get_supply_consumption() const; std::map const& get_supply_cost() const; -- cgit v1.2.3-56-ga3b1 From 7a8ac1cdb8e71a4166393ac06b1b60512db0ef8c Mon Sep 17 00:00:00 2001 From: zaaarf Date: Thu, 28 Sep 2023 13:16:17 +0200 Subject: feat: renamed Building to BuildingInstance, implemented Building and BuildingType defines --- src/openvic-simulation/GameManager.cpp | 16 +--- src/openvic-simulation/map/Building.cpp | 164 ++++++++++++++++++++++---------- src/openvic-simulation/map/Building.hpp | 137 ++++++++++++++++++++------ src/openvic-simulation/map/Province.cpp | 21 ++-- src/openvic-simulation/map/Province.hpp | 8 +- 5 files changed, 236 insertions(+), 110 deletions(-) diff --git a/src/openvic-simulation/GameManager.cpp b/src/openvic-simulation/GameManager.cpp index d9dc3d9..958049d 100644 --- a/src/openvic-simulation/GameManager.cpp +++ b/src/openvic-simulation/GameManager.cpp @@ -177,12 +177,12 @@ bool GameManager::load_hardcoded_defines() { } }, { "mapmode_infrastructure", [](Map const& map, Province const& province) -> colour_t { - Building const* railroad = province.get_building_by_identifier("building_railroad"); + BuildingInstance const* railroad = province.get_building_by_identifier("building_railroad"); if (railroad != nullptr) { - colour_t val = fraction_to_colour_byte(railroad->get_level(), railroad->get_type().get_max_level() + 1, 0.5f, 1.0f); + colour_t val = fraction_to_colour_byte(railroad->get_current_level(), railroad->get_building().get_max_level() + 1, 0.5f, 1.0f); switch (railroad->get_expansion_state()) { - case Building::ExpansionState::CannotExpand: val <<= 16; break; - case Building::ExpansionState::CanExpand: break; + case ExpansionState::CannotExpand: val <<= 16; break; + case ExpansionState::CanExpand: break; default: val <<= 8; break; } return HIGH_ALPHA_VALUE | val; @@ -208,13 +208,5 @@ bool GameManager::load_hardcoded_defines() { ret &= map.add_mapmode(mapmode.first, mapmode.second); map.lock_mapmodes(); - using building_type_t = std::tuple; - const std::vector building_types { - { "building_fort", 4, 8 }, { "building_naval_base", 6, 15 }, { "building_railroad", 5, 10 } // Move this to building.hpp - }; - for (building_type_t const& type : building_types) - ret &= building_manager.add_building_type(std::get<0>(type), std::get<1>(type), std::get<2>(type)); - building_manager.lock_building_types(); - return ret; } diff --git a/src/openvic-simulation/map/Building.cpp b/src/openvic-simulation/map/Building.cpp index eba2049..f4b5034 100644 --- a/src/openvic-simulation/map/Building.cpp +++ b/src/openvic-simulation/map/Building.cpp @@ -1,45 +1,133 @@ #include "Building.hpp" -#include - -#include "openvic-simulation/map/Province.hpp" -#include "openvic-simulation/utility/Logger.hpp" +#include "openvic-simulation/map/Province.hpp" //imported here so the hpp doesn't get circular imports using namespace OpenVic; +using namespace OpenVic::NodeTools; -Building::Building(BuildingType const& new_type) - : HasIdentifier { new_type.get_identifier() }, - type { new_type } {} - -bool Building::_can_expand() const { - return level < type.get_max_level(); -} +Building::Building(std::string_view identifier, ARGS) : HasIdentifier { identifier }, type { type }, on_completion { on_completion }, + completion_size { completion_size }, max_level { max_level }, build_cost { build_cost }, build_time { build_time }, visibility { visibility }, on_map { on_map }, + default_enabled { default_enabled }, production_type { production_type }, pop_build_factory { pop_build_factory }, strategic_factory { strategic_factory }, + fort_level { fort_level }, naval_capacity { naval_capacity }, colonial_points { colonial_points }, in_province { in_province }, one_per_state { one_per_state }, + colonial_range { colonial_range }, infrastructure { infrastructure }, movement_cost { movement_cost }, spawn_railway_track { spawn_railway_track } {} BuildingType const& Building::get_type() const { return type; } -Building::level_t Building::get_level() const { +Building::sound_t Building::get_on_completion() const { + return on_completion; +} + +fixed_point_t Building::get_completion_size() const { + return completion_size; +} + +Building::level_t Building::get_max_level() const { + return max_level; +} + +std::map const& Building::get_build_cost() const { + return build_cost; +} + +Timespan Building::get_build_time() const { + return build_time; +} + +bool Building::has_visibility() const { + return visibility; +} + +bool Building::is_on_map() const { + return on_map; +} + +bool Building::is_default_enabled() const { + return default_enabled; +} + +ProductionType const* Building::get_production_type() const { + return production_type; +} + +bool Building::is_pop_built_factory() const { + return pop_build_factory; +} + +bool Building::is_strategic_factory() const { + return strategic_factory; +} + +Building::level_t Building::get_fort_level() const { + return fort_level; +} + +uint64_t Building::get_naval_capacity() const { + return naval_capacity; +} + +std::vector const& Building::get_colonial_points() const { + return colonial_points; +} + +bool Building::is_in_province() const { + return in_province; +} + +bool Building::is_one_per_state() const { + return one_per_state; +} + +uint64_t Building::get_colonial_range() const { + return colonial_range; +} + +fixed_point_t Building::get_infrastructure() const { + return infrastructure; +} + +fixed_point_t Building::get_movement_cost() const { + return movement_cost; +} + +bool Building::spawned_railway_track() const { + return spawn_railway_track; +} + +BuildingType::BuildingType(const std::string_view new_identifier) : HasIdentifier { new_identifier } {} + +BuildingInstance::BuildingInstance(Building const& building) : HasIdentifier { building.get_identifier() }, building { building } {} + +Building const& BuildingInstance::get_building() const { + return building; +} + +bool BuildingInstance::_can_expand() const { + return level < building.get_max_level(); +} + +BuildingInstance::level_t BuildingInstance::get_current_level() const { return level; } -Building::ExpansionState Building::get_expansion_state() const { +ExpansionState BuildingInstance::get_expansion_state() const { return expansion_state; } -Date const& Building::get_start_date() const { +Date const& BuildingInstance::get_start_date() const { return start; } -Date const& Building::get_end_date() const { +Date const& BuildingInstance::get_end_date() const { return end; } -float Building::get_expansion_progress() const { +float BuildingInstance::get_expansion_progress() const { return expansion_progress; } -bool Building::expand() { +bool BuildingInstance::expand() { if (expansion_state == ExpansionState::CanExpand) { expansion_state = ExpansionState::Preparing; expansion_progress = 0.0f; @@ -51,11 +139,11 @@ bool Building::expand() { /* REQUIREMENTS: * MAP-71, MAP-74, MAP-77 */ -void Building::update_state(Date const& today) { +void BuildingInstance::update_state(Date const& today) { switch (expansion_state) { case ExpansionState::Preparing: start = today; - end = start + type.get_build_time(); + end = start + building.get_build_time(); break; case ExpansionState::Expanding: expansion_progress = static_cast(today - start) / static_cast(end - start); @@ -64,7 +152,7 @@ void Building::update_state(Date const& today) { } } -void Building::tick(Date const& today) { +void BuildingInstance::tick(Date const& today) { if (expansion_state == ExpansionState::Preparing) { expansion_state = ExpansionState::Expanding; } @@ -76,38 +164,14 @@ void Building::tick(Date const& today) { } } -BuildingType::BuildingType(const std::string_view new_identifier, Building::level_t new_max_level, Timespan new_build_time) - : HasIdentifier { new_identifier }, - max_level { new_max_level }, - build_time { new_build_time } { - assert(max_level >= 0); - assert(build_time >= 0); -} - -Building::level_t BuildingType::get_max_level() const { - return max_level; -} - -Timespan BuildingType::get_build_time() const { - return build_time; -} +BuildingManager::BuildingManager() : building_types { "building types" }, buildings { "buildings" } {} -BuildingManager::BuildingManager() : building_types { "building types" } {} - -bool BuildingManager::add_building_type(const std::string_view identifier, Building::level_t max_level, Timespan build_time) { +bool BuildingManager::add_building_type(const std::string_view identifier) { if (identifier.empty()) { Logger::error("Invalid building type identifier - empty!"); return false; } - if (max_level < 0) { - Logger::error("Invalid building type max level for ", identifier, ": ", max_level); - return false; - } - if (build_time < 0) { - Logger::error("Invalid building type build time for ", identifier, ": ", build_time); - return false; - } - return building_types.add_item({ identifier, max_level, build_time }); + return building_types.add_item({ identifier }); } bool BuildingManager::generate_province_buildings(Province& province) const { @@ -118,10 +182,10 @@ bool BuildingManager::generate_province_buildings(Province& province) const { } bool ret = true; if (!province.get_water()) { - for (BuildingType const& type : building_types.get_items()) { - ret &= province.add_building({ type }); + for (Building const& building : buildings.get_items()) { + ret &= province.add_building({ building }); } } province.lock_buildings(); return ret; -} +} \ No newline at end of file diff --git a/src/openvic-simulation/map/Building.hpp b/src/openvic-simulation/map/Building.hpp index d36dfd4..cd649ff 100644 --- a/src/openvic-simulation/map/Building.hpp +++ b/src/openvic-simulation/map/Building.hpp @@ -1,9 +1,19 @@ #pragma once +#include +#include #include #include "openvic-simulation/types/Date.hpp" +#include "openvic-simulation/types/fixed_point/FixedPoint.hpp" #include "openvic-simulation/types/IdentifierRegistry.hpp" +#include "openvic-simulation/economy/Good.hpp" +#include "openvic-simulation/economy/ProductionType.hpp" + +#define ARGS BuildingType const& type, sound_t on_completion, fixed_point_t completion_size, level_t max_level, std::map build_cost, \ + Timespan build_time, bool visibility, bool on_map, const bool default_enabled, ProductionType const* production_type, bool pop_build_factory, \ + bool strategic_factory, level_t fort_level, uint64_t naval_capacity, std::vector colonial_points, bool in_province, bool one_per_state, \ + uint64_t colonial_range, fixed_point_t infrastructure, fixed_point_t movement_cost, bool spawn_railway_track namespace OpenVic { @@ -18,31 +28,109 @@ namespace OpenVic { struct Building : HasIdentifier { friend struct BuildingManager; - using level_t = int8_t; - - enum class ExpansionState { - CannotExpand, - CanExpand, - Preparing, - Expanding - }; + using level_t = uint8_t; + using sound_t = std::string_view; private: BuildingType const& type; + const sound_t on_completion; //probably sound played on completion + const fixed_point_t completion_size; + const level_t max_level; + const std::map build_cost; + const Timespan build_time; //time + const bool visibility; + const bool on_map; //onmap + + const bool default_enabled; //some(false) + ProductionType const* production_type; + const bool pop_build_factory; + const bool strategic_factory; + + const level_t fort_level; //some(0), probably the step-per-level? + + const uint64_t naval_capacity; //some(0) + const std::vector colonial_points; + const bool in_province; //province some(false) + const bool one_per_state; + const uint64_t colonial_range; + + const fixed_point_t infrastructure; + const fixed_point_t movement_cost; + const bool spawn_railway_track; //some(false) + + //any modifiers really + + Building(std::string_view identifier, ARGS); + + public: + Building(Building&&) = default; + + BuildingType const& get_type() const; + sound_t get_on_completion() const; + fixed_point_t get_completion_size() const; + level_t get_max_level() const; + std::map const& get_build_cost() const; + Timespan get_build_time() const; + bool has_visibility() const; + bool is_on_map() const; + + bool is_default_enabled() const; + ProductionType const* get_production_type() const; + bool is_pop_built_factory() const; + bool is_strategic_factory() const; + + level_t get_fort_level() const; + + uint64_t get_naval_capacity() const; + std::vector const& get_colonial_points() const; + bool is_in_province() const; + bool is_one_per_state() const; + uint64_t get_colonial_range() const; + + fixed_point_t get_infrastructure() const; + fixed_point_t get_movement_cost() const; + bool spawned_railway_track() const; + }; + + struct BuildingType : HasIdentifier { + friend struct BuildingManager; + + private: + BuildingType(const std::string_view new_identifier); + + public: + BuildingType(BuildingType&&) = default; + }; + + enum class ExpansionState { + CannotExpand, + CanExpand, + Preparing, + Expanding + }; + + struct BuildingInstance : HasIdentifier { //used in the actual game + friend struct BuildingManager; + using level_t = Building::level_t; + + private: + Building const& building; + level_t level = 0; ExpansionState expansion_state = ExpansionState::CannotExpand; Date start, end; float expansion_progress; - Building(BuildingType const& new_type); - bool _can_expand() const; + BuildingInstance(Building const& building); + public: - Building(Building&&) = default; + BuildingInstance(BuildingInstance&&) = default; - BuildingType const& get_type() const; - level_t get_level() const; + Building const& get_building() const; + + level_t get_current_level() const; ExpansionState get_expansion_state() const; Date const& get_start_date() const; Date const& get_end_date() const; @@ -51,22 +139,7 @@ namespace OpenVic { bool expand(); void update_state(Date const& today); void tick(Date const& today); - }; - struct BuildingType : HasIdentifier { - friend struct BuildingManager; - - private: - const Building::level_t max_level; - const Timespan build_time; - - BuildingType(const std::string_view new_identifier, Building::level_t new_max_level, Timespan new_build_time); - - public: - BuildingType(BuildingType&&) = default; - - Building::level_t get_max_level() const; - Timespan get_build_time() const; }; struct Province; @@ -74,12 +147,18 @@ namespace OpenVic { struct BuildingManager { private: IdentifierRegistry building_types; + IdentifierRegistry buildings; public: BuildingManager(); - bool add_building_type(const std::string_view identifier, Building::level_t max_level, Timespan build_time); + bool add_building_type(const std::string_view identifier); IDENTIFIER_REGISTRY_ACCESSORS(BuildingType, building_type) bool generate_province_buildings(Province& province) const; + + bool add_building(std::string_view identifier); + IDENTIFIER_REGISTRY_ACCESSORS(Building, building) + + //bool load_buildings_file(ast::NodeCPtr root); }; } diff --git a/src/openvic-simulation/map/Province.cpp b/src/openvic-simulation/map/Province.cpp index ef574cf..21bdb85 100644 --- a/src/openvic-simulation/map/Province.cpp +++ b/src/openvic-simulation/map/Province.cpp @@ -1,20 +1,11 @@ #include "Province.hpp" -#include -#include -#include -#include -#include - -#include "openvic-simulation/map/TerrainType.hpp" - using namespace OpenVic; using namespace OpenVic::NodeTools; Province::Province(const std::string_view new_identifier, colour_t new_colour, index_t new_index) : HasIdentifierAndColour { new_identifier, new_colour, false, false }, - index { new_index }, - buildings { "buildings", false } { + index { new_index }, buildings { "buildings", false } { assert(index != NULL_INDEX); } @@ -48,8 +39,8 @@ bool Province::load_positions(BuildingManager const& building_manager, ast::Node return true; } -bool Province::add_building(Building&& building) { - return buildings.add_item(std::move(building)); +bool Province::add_building(BuildingInstance&& building_instance) { + return buildings.add_item(std::move(building_instance)); } void Province::reset_buildings() { @@ -57,7 +48,7 @@ void Province::reset_buildings() { } bool Province::expand_building(const std::string_view building_type_identifier) { - Building* building = buildings.get_item_by_identifier(building_type_identifier); + BuildingInstance* building = buildings.get_item_by_identifier(building_type_identifier); if (building == nullptr) return false; return building->expand(); } @@ -136,13 +127,13 @@ void Province::update_pops() { } void Province::update_state(Date const& today) { - for (Building& building : buildings.get_items()) + for (BuildingInstance& building : buildings.get_items()) building.update_state(today); update_pops(); } void Province::tick(Date const& today) { - for (Building& building : buildings.get_items()) + for (BuildingInstance& building : buildings.get_items()) building.tick(today); } diff --git a/src/openvic-simulation/map/Province.hpp b/src/openvic-simulation/map/Province.hpp index 6e4ac7e..349c16d 100644 --- a/src/openvic-simulation/map/Province.hpp +++ b/src/openvic-simulation/map/Province.hpp @@ -1,6 +1,6 @@ #pragma once -#include +#include #include "openvic-simulation/map/Building.hpp" #include "openvic-simulation/pop/Pop.hpp" @@ -46,7 +46,7 @@ namespace OpenVic { Region* region = nullptr; bool has_region = false, water = false; life_rating_t life_rating = 0; - IdentifierRegistry buildings; + IdentifierRegistry buildings; // TODO - change this into a factory-like structure Good const* rgo = nullptr; @@ -73,8 +73,8 @@ namespace OpenVic { life_rating_t get_life_rating() const; bool load_positions(BuildingManager const& building_manager, ast::NodeCPtr root); - bool add_building(Building&& building); - IDENTIFIER_REGISTRY_ACCESSORS(Building, building) + bool add_building(BuildingInstance&& building_instance); + IDENTIFIER_REGISTRY_ACCESSORS(BuildingInstance, building) void reset_buildings(); bool expand_building(const std::string_view building_type_identifier); Good const* get_rgo() const; -- cgit v1.2.3-56-ga3b1 From c541a249247b7fe3bdd4c62bce6638e875790f8a Mon Sep 17 00:00:00 2001 From: zaaarf Date: Thu, 28 Sep 2023 15:40:34 +0200 Subject: feat: implemented building loading and missing parameters --- src/openvic-simulation/dataloader/Dataloader.cpp | 23 +++-- src/openvic-simulation/dataloader/Dataloader.hpp | 5 + src/openvic-simulation/economy/ProductionType.hpp | 12 +-- src/openvic-simulation/map/Building.cpp | 112 ++++++++++++++++++++-- src/openvic-simulation/map/Building.hpp | 60 +++++++----- 5 files changed, 161 insertions(+), 51 deletions(-) diff --git a/src/openvic-simulation/dataloader/Dataloader.cpp b/src/openvic-simulation/dataloader/Dataloader.cpp index 530aa76..c21c6da 100644 --- a/src/openvic-simulation/dataloader/Dataloader.cpp +++ b/src/openvic-simulation/dataloader/Dataloader.cpp @@ -1,12 +1,5 @@ #include "Dataloader.hpp" -#include -#include -#include - -#include "openvic-simulation/GameManager.hpp" -#include "openvic-simulation/utility/Logger.hpp" - using namespace OpenVic; using namespace OpenVic::NodeTools; using namespace ovdl; @@ -282,6 +275,7 @@ bool Dataloader::load_defines(GameManager& game_manager) const { static const fs::path ideology_file = "common/ideologies.txt"; static const fs::path issues_file = "common/issues.txt"; static const fs::path production_types_file = "common/production_types.txt"; + static const fs::path buildings_file = "common/buildings.txt"; static const fs::path map_directory = "map"; static const fs::path units_directory = "units"; @@ -320,19 +314,28 @@ bool Dataloader::load_defines(GameManager& game_manager) const { ret = false; } if (!game_manager.get_production_type_manager().load_production_types_file( - game_manager.get_good_manager(), game_manager.get_pop_manager(), + game_manager.get_good_manager(), + game_manager.get_pop_manager(), _parse_defines(lookup_file(production_types_file)).get_file_node())) { Logger::error("Failed to load production types!"); ret = false; } - if (!_load_units(game_manager, units_directory)) { - Logger::error("Failed to load units!"); + if (!game_manager.get_building_manager().load_buildings_file( + game_manager.get_good_manager(), + game_manager.get_production_type_manager(), + game_manager.get_modifier_manager(), + _parse_defines(lookup_file(buildings_file)).get_file_node())) { + Logger::error("Failed to load buildings!"); ret = false; } if (!_load_map_dir(game_manager, map_directory)) { Logger::error("Failed to load map!"); ret = false; } + if (!_load_units(game_manager, units_directory)) { + Logger::error("Failed to load units!"); + ret = false; + } return ret; } diff --git a/src/openvic-simulation/dataloader/Dataloader.hpp b/src/openvic-simulation/dataloader/Dataloader.hpp index e935091..e1a2614 100644 --- a/src/openvic-simulation/dataloader/Dataloader.hpp +++ b/src/openvic-simulation/dataloader/Dataloader.hpp @@ -5,6 +5,11 @@ #include #include "openvic-simulation/dataloader/NodeTools.hpp" +#include +#include +#include +#include "openvic-simulation/GameManager.hpp" +#include "openvic-simulation/utility/Logger.hpp" namespace OpenVic { namespace fs = std::filesystem; diff --git a/src/openvic-simulation/economy/ProductionType.hpp b/src/openvic-simulation/economy/ProductionType.hpp index 50af41e..57d04ea 100644 --- a/src/openvic-simulation/economy/ProductionType.hpp +++ b/src/openvic-simulation/economy/ProductionType.hpp @@ -58,16 +58,16 @@ namespace OpenVic { } type; const Pop::pop_size_t workforce; - const std::map input_goods; // farms generally lack this + const std::map input_goods; Good const* output_goods; const fixed_point_t value; - const std::vector bonuses; // some + const std::vector bonuses; - const std::map efficiency; // some - const bool coastal; // is_coastal some(false) + const std::map efficiency; + const bool coastal; // is_coastal - const bool farm; // some (false) - const bool mine; // some (false) + const bool farm; + const bool mine; ProductionType(PRODUCTION_TYPE_ARGS(type_t, Good const*)); diff --git a/src/openvic-simulation/map/Building.cpp b/src/openvic-simulation/map/Building.cpp index f4b5034..29ee354 100644 --- a/src/openvic-simulation/map/Building.cpp +++ b/src/openvic-simulation/map/Building.cpp @@ -5,17 +5,19 @@ using namespace OpenVic; using namespace OpenVic::NodeTools; -Building::Building(std::string_view identifier, ARGS) : HasIdentifier { identifier }, type { type }, on_completion { on_completion }, - completion_size { completion_size }, max_level { max_level }, build_cost { build_cost }, build_time { build_time }, visibility { visibility }, on_map { on_map }, - default_enabled { default_enabled }, production_type { production_type }, pop_build_factory { pop_build_factory }, strategic_factory { strategic_factory }, - fort_level { fort_level }, naval_capacity { naval_capacity }, colonial_points { colonial_points }, in_province { in_province }, one_per_state { one_per_state }, - colonial_range { colonial_range }, infrastructure { infrastructure }, movement_cost { movement_cost }, spawn_railway_track { spawn_railway_track } {} +Building::Building(std::string_view identifier, ARGS) : HasIdentifier { identifier }, ModifierValue { std::move(modifiers) }, type { type }, + on_completion { on_completion }, completion_size { completion_size }, max_level { max_level }, goods_cost { goods_cost }, cost { cost }, build_time { build_time }, + visibility { visibility }, on_map { on_map }, default_enabled { default_enabled }, production_type { production_type }, pop_build_factory { pop_build_factory }, + strategic_factory { strategic_factory }, advanced_factory { advanced_factory }, fort_level { fort_level }, naval_capacity { naval_capacity }, + colonial_points { colonial_points }, in_province { in_province }, one_per_state { one_per_state }, colonial_range { colonial_range }, + infrastructure { infrastructure }, movement_cost { movement_cost }, local_ship_build { local_ship_build }, spawn_railway_track { spawn_railway_track }, + sail { sail }, steam { steam }, capital { capital }, port { port } {} BuildingType const& Building::get_type() const { return type; } -Building::sound_t Building::get_on_completion() const { +std::string_view Building::get_on_completion() const { return on_completion; } @@ -27,8 +29,12 @@ Building::level_t Building::get_max_level() const { return max_level; } -std::map const& Building::get_build_cost() const { - return build_cost; +std::map const& Building::get_goods_cost() const { + return goods_cost; +} + +fixed_point_t Building::get_cost() const { + return cost; } Timespan Building::get_build_time() const { @@ -59,6 +65,10 @@ bool Building::is_strategic_factory() const { return strategic_factory; } +bool Building::is_advanced_factory() const { + return advanced_factory; +} + Building::level_t Building::get_fort_level() const { return fort_level; } @@ -79,7 +89,7 @@ bool Building::is_one_per_state() const { return one_per_state; } -uint64_t Building::get_colonial_range() const { +fixed_point_t Building::get_colonial_range() const { return colonial_range; } @@ -174,6 +184,88 @@ bool BuildingManager::add_building_type(const std::string_view identifier) { return building_types.add_item({ identifier }); } +bool BuildingManager::add_building(std::string_view identifier, ARGS) { + if (identifier.empty()) { + Logger::error("Invalid building identifier - empty!"); + return false; + } + + return buildings.add_item({ + identifier, type, on_completion, completion_size, max_level, goods_cost, cost, build_time, visibility, on_map, default_enabled, + production_type, pop_build_factory, strategic_factory, advanced_factory, fort_level, naval_capacity, colonial_points, in_province, one_per_state, + colonial_range, infrastructure, movement_cost, local_ship_build, spawn_railway_track, sail, steam, capital, port, std::move(modifiers) + }); +} + +bool BuildingManager::load_buildings_file(GoodManager const& good_manager, ProductionTypeManager const& production_type_manager, ModifierManager const& modifier_manager, ast::NodeCPtr root) { + bool ret = expect_dictionary([this, &good_manager, &production_type_manager, &modifier_manager](std::string_view key, ast::NodeCPtr value) -> bool { + std::string_view type, on_completion = "", production_type; + fixed_point_t completion_size = 0, cost = 0, infrastructure = 0, movement_cost = 0, colonial_range = 0, local_ship_build = 0; + Building::level_t max_level, fort_level = 0; + std::map goods_cost; + uint32_t build_days; + bool visibility, on_map, default_enabled, pop_build_factory, strategic_factory, advanced_factory, in_province, one_per_state, spawn_railway_track, sail, steam, capital, port; + default_enabled = pop_build_factory = strategic_factory = advanced_factory = in_province = one_per_state = spawn_railway_track = sail = steam = capital = port = false; + uint64_t naval_capacity = 0; + std::vector colonial_points; + ModifierValue modifiers; + + bool ret = modifier_manager.expect_modifier_value_and_keys(move_variable_callback(modifiers), + "type", ONE_EXACTLY, expect_identifier(assign_variable_callback(type)), + "on_completion", ZERO_OR_ONE, expect_identifier(assign_variable_callback(on_completion)), + "completion_size", ZERO_OR_ONE, expect_fixed_point(assign_variable_callback(completion_size)), + "max_level", ONE_EXACTLY, expect_uint(assign_variable_callback(max_level)), + "goods_cost", ONE_EXACTLY, good_manager.expect_good_decimal_map(assign_variable_callback(goods_cost)), + "cost", ZERO_OR_MORE, expect_fixed_point(assign_variable_callback(cost)), + "time", ONE_EXACTLY, expect_uint(assign_variable_callback_uint("building build time", build_days)), + "visibility", ONE_EXACTLY, expect_bool(assign_variable_callback(visibility)), + "onmap", ONE_EXACTLY, expect_bool(assign_variable_callback(on_map)), + "default_enabled", ZERO_OR_ONE, expect_bool(assign_variable_callback(default_enabled)), + "production_type", ZERO_OR_ONE, expect_identifier(assign_variable_callback(production_type)), + "pop_build_factory", ZERO_OR_ONE, expect_bool(assign_variable_callback(pop_build_factory)), + "strategic_factory", ZERO_OR_ONE, expect_bool(assign_variable_callback(strategic_factory)), + "advanced_factory", ZERO_OR_ONE, expect_bool(assign_variable_callback(advanced_factory)), + "fort_level", ZERO_OR_ONE, expect_uint(assign_variable_callback_uint("building fort level", fort_level)), + "naval_capacity", ZERO_OR_ONE, expect_uint(assign_variable_callback_uint("building naval capacity", naval_capacity)), + "colonial_points", ZERO_OR_ONE, expect_list(expect_uint([&colonial_points](uint64_t points) -> bool { + return colonial_points.emplace_back(points); + })), "province", ZERO_OR_ONE, expect_bool(assign_variable_callback(in_province)), + "one_per_state", ZERO_OR_ONE, expect_bool(assign_variable_callback(one_per_state)), + "colonial_range", ZERO_OR_ONE, expect_fixed_point(assign_variable_callback(colonial_range)), + "infrastructure", ZERO_OR_ONE, expect_fixed_point(assign_variable_callback(infrastructure)), + "movement_cost", ZERO_OR_ONE, expect_fixed_point(assign_variable_callback(movement_cost)), + "local_ship_build", ZERO_OR_ONE, expect_fixed_point(assign_variable_callback(local_ship_build)), + "spawn_railway_track", ZERO_OR_ONE, expect_bool(assign_variable_callback(spawn_railway_track)), + "sail", ZERO_OR_ONE, expect_bool(assign_variable_callback(sail)), + "steam", ZERO_OR_ONE, expect_bool(assign_variable_callback(steam)), + "capital", ZERO_OR_ONE, expect_bool(assign_variable_callback(capital)), + "port", ZERO_OR_ONE, expect_bool(assign_variable_callback(port)) + )(value); + + BuildingType const* type_ref = building_types.get_item_by_identifier(type); + if (type_ref == nullptr) { + building_types.add_item({ type }); + type_ref = building_types.get_item_by_identifier(type); + } + + Timespan build_time = Timespan(build_days); + + ProductionType const* production_type_ref = production_type_manager.get_production_type_by_identifier(production_type); + + ret &= add_building( + key, *type_ref, on_completion, completion_size, max_level, goods_cost, cost, build_time, visibility, on_map, default_enabled, + production_type_ref, pop_build_factory, strategic_factory, advanced_factory, fort_level, naval_capacity, colonial_points, in_province, + one_per_state, colonial_range, infrastructure, movement_cost, local_ship_build, spawn_railway_track, sail, steam, capital, port, std::move(modifiers) + ); + + return ret; + })(root); + lock_building_types(); + lock_buildings(); + + return ret; +} + bool BuildingManager::generate_province_buildings(Province& province) const { province.reset_buildings(); if (!building_types.is_locked()) { @@ -188,4 +280,4 @@ bool BuildingManager::generate_province_buildings(Province& province) const { } province.lock_buildings(); return ret; -} \ No newline at end of file +} diff --git a/src/openvic-simulation/map/Building.hpp b/src/openvic-simulation/map/Building.hpp index cd649ff..9b11c1c 100644 --- a/src/openvic-simulation/map/Building.hpp +++ b/src/openvic-simulation/map/Building.hpp @@ -1,19 +1,18 @@ #pragma once -#include -#include -#include - #include "openvic-simulation/types/Date.hpp" #include "openvic-simulation/types/fixed_point/FixedPoint.hpp" #include "openvic-simulation/types/IdentifierRegistry.hpp" #include "openvic-simulation/economy/Good.hpp" #include "openvic-simulation/economy/ProductionType.hpp" +#include "openvic-simulation/Modifier.hpp" -#define ARGS BuildingType const& type, sound_t on_completion, fixed_point_t completion_size, level_t max_level, std::map build_cost, \ - Timespan build_time, bool visibility, bool on_map, const bool default_enabled, ProductionType const* production_type, bool pop_build_factory, \ - bool strategic_factory, level_t fort_level, uint64_t naval_capacity, std::vector colonial_points, bool in_province, bool one_per_state, \ - uint64_t colonial_range, fixed_point_t infrastructure, fixed_point_t movement_cost, bool spawn_railway_track +#define ARGS BuildingType const& type, std::string_view on_completion, fixed_point_t completion_size, level_t max_level, \ + std::map goods_cost, fixed_point_t cost, Timespan build_time, bool visibility, bool on_map, bool default_enabled, \ + ProductionType const* production_type, bool pop_build_factory, bool strategic_factory, bool advanced_factory, level_t fort_level, \ + uint64_t naval_capacity, std::vector colonial_points, bool in_province, bool one_per_state, fixed_point_t colonial_range, \ + fixed_point_t infrastructure, fixed_point_t movement_cost, fixed_point_t local_ship_build, bool spawn_railway_track, bool sail, bool steam, \ + bool capital, bool port, ModifierValue&& modifiers namespace OpenVic { @@ -25,40 +24,45 @@ namespace OpenVic { * MAP-12, MAP-75, MAP-76 * MAP-13, MAP-78, MAP-79 */ - struct Building : HasIdentifier { + struct Building : HasIdentifier, ModifierValue { friend struct BuildingManager; using level_t = uint8_t; - using sound_t = std::string_view; private: BuildingType const& type; - const sound_t on_completion; //probably sound played on completion + const std::string_view on_completion; //probably sound played on completion const fixed_point_t completion_size; const level_t max_level; - const std::map build_cost; + const std::map goods_cost; + const fixed_point_t cost; const Timespan build_time; //time const bool visibility; const bool on_map; //onmap - const bool default_enabled; //some(false) + const bool default_enabled; ProductionType const* production_type; const bool pop_build_factory; const bool strategic_factory; + const bool advanced_factory; - const level_t fort_level; //some(0), probably the step-per-level? + const level_t fort_level; //probably the step-per-level - const uint64_t naval_capacity; //some(0) + const uint64_t naval_capacity; const std::vector colonial_points; - const bool in_province; //province some(false) + const bool in_province; //province const bool one_per_state; - const uint64_t colonial_range; + const fixed_point_t colonial_range; const fixed_point_t infrastructure; const fixed_point_t movement_cost; - const bool spawn_railway_track; //some(false) + const fixed_point_t local_ship_build; + const bool spawn_railway_track; - //any modifiers really + const bool sail; //only in clipper shipyard + const bool steam; //only in steamer shipyard + const bool capital; //only in naval base + const bool port; //only in naval base Building(std::string_view identifier, ARGS); @@ -66,10 +70,11 @@ namespace OpenVic { Building(Building&&) = default; BuildingType const& get_type() const; - sound_t get_on_completion() const; + std::string_view get_on_completion() const; fixed_point_t get_completion_size() const; level_t get_max_level() const; - std::map const& get_build_cost() const; + std::map const& get_goods_cost() const; + fixed_point_t get_cost() const; Timespan get_build_time() const; bool has_visibility() const; bool is_on_map() const; @@ -78,6 +83,7 @@ namespace OpenVic { ProductionType const* get_production_type() const; bool is_pop_built_factory() const; bool is_strategic_factory() const; + bool is_advanced_factory() const; level_t get_fort_level() const; @@ -85,10 +91,11 @@ namespace OpenVic { std::vector const& get_colonial_points() const; bool is_in_province() const; bool is_one_per_state() const; - uint64_t get_colonial_range() const; + fixed_point_t get_colonial_range() const; fixed_point_t get_infrastructure() const; fixed_point_t get_movement_cost() const; + fixed_point_t get_local_ship_build() const; bool spawned_railway_track() const; }; @@ -145,6 +152,8 @@ namespace OpenVic { struct Province; struct BuildingManager { + using level_t = Building::level_t; //this is getting ridiculous + private: IdentifierRegistry building_types; IdentifierRegistry buildings; @@ -154,11 +163,12 @@ namespace OpenVic { bool add_building_type(const std::string_view identifier); IDENTIFIER_REGISTRY_ACCESSORS(BuildingType, building_type) - bool generate_province_buildings(Province& province) const; - bool add_building(std::string_view identifier); + bool add_building(std::string_view identifier, ARGS); IDENTIFIER_REGISTRY_ACCESSORS(Building, building) - //bool load_buildings_file(ast::NodeCPtr root); + bool load_buildings_file(GoodManager const& good_manager, ProductionTypeManager const& production_type_manager, ModifierManager const& modifier_manager, ast::NodeCPtr root); + + bool generate_province_buildings(Province& province) const; }; } -- cgit v1.2.3-56-ga3b1