From 84b1d718540ba77e7e28e4c4ba1b4fa892b8d05c Mon Sep 17 00:00:00 2001 From: KorGgenT Date: Wed, 16 Oct 2019 20:01:30 -0400 Subject: [PATCH 1/3] change scope of rooted() --- src/character.h | 34 ++++++++++++++++++++++++++++++++++ src/consumption.cpp | 4 ++-- src/player.cpp | 12 ++++++------ src/player.h | 35 ----------------------------------- 4 files changed, 42 insertions(+), 43 deletions(-) diff --git a/src/character.h b/src/character.h index 47c70d98b46c2..e0bd0ff3f6004 100644 --- a/src/character.h +++ b/src/character.h @@ -1137,6 +1137,38 @@ class Character : public Creature, public visitable void spores(); void blossoms(); + + /** Handles rooting effects */ + void rooted_message() const; + void rooted(); + + /** Set vitamin deficiency/excess disease states dependent upon current vitamin levels */ + void update_vitamins( const vitamin_id &vit ); + /** + * Check current level of a vitamin + * + * Accesses level of a given vitamin. If the vitamin_id specified does not + * exist then this function simply returns 0. + * + * @param vit ID of vitamin to check level for. + * @returns current level for specified vitamin + */ + int vitamin_get( const vitamin_id &vit ) const; + /** + * Add or subtract vitamins from player storage pools + * @param vit ID of vitamin to modify + * @param qty amount by which to adjust vitamin (negative values are permitted) + * @param capped if true prevent vitamins which can accumulate in excess from doing so + * @return adjusted level for the vitamin or zero if vitamin does not exist + */ + int vitamin_mod( const vitamin_id &vit, int qty, bool capped = true ); + + /** Returns true if the player is wearing something on the entered body_part */ + bool wearing_something_on( body_part bp ) const; + /** Returns 1 if the player is wearing something on both feet, .5 if on one, and 0 if on neither */ + double footwear_factor() const; + /** Returns true if the player is wearing something on their feet that is not SKINTIGHT */ + bool is_wearing_shoes( const side &which_side = side::BOTH ) const; protected: Character(); Character( Character && ); @@ -1222,6 +1254,8 @@ class Character : public Creature, public visitable faction *my_fac = nullptr; character_movemode move_mode; + /** Current deficiency/excess quantity for each vitamin */ + std::map vitamin_levels; private: // a cache of all active enchantment values. diff --git a/src/consumption.cpp b/src/consumption.cpp index 02ed438124870..d90d17aef5869 100644 --- a/src/consumption.cpp +++ b/src/consumption.cpp @@ -345,7 +345,7 @@ time_duration player::vitamin_rate( const vitamin_id &vit ) const return res; } -int player::vitamin_mod( const vitamin_id &vit, int qty, bool capped ) +int Character::vitamin_mod( const vitamin_id &vit, int qty, bool capped ) { auto it = vitamin_levels.find( vit ); if( it == vitamin_levels.end() ) { @@ -373,7 +373,7 @@ void player::vitamins_mod( const std::map &vitamins, bool cappe } } -int player::vitamin_get( const vitamin_id &vit ) const +int Character::vitamin_get( const vitamin_id &vit ) const { if( get_option( "NO_VITAMINS" ) ) { return 0; diff --git a/src/player.cpp b/src/player.cpp index 3860cbee6598d..470a4561f3038 100644 --- a/src/player.cpp +++ b/src/player.cpp @@ -3446,7 +3446,7 @@ void player::update_stomach( const time_point &from, const time_point &to ) } } -void player::update_vitamins( const vitamin_id &vit ) +void Character::update_vitamins( const vitamin_id &vit ) { if( is_npc() ) { return; // NPCs cannot develop vitamin diseases @@ -6864,7 +6864,7 @@ bool player::consume( int target_position ) return true; } -void player::rooted_message() const +void Character::rooted_message() const { bool wearing_shoes = is_wearing_shoes( side::LEFT ) || is_wearing_shoes( side::RIGHT ); if( ( has_trait( trait_ROOTS2 ) || has_trait( trait_ROOTS3 ) ) && @@ -6875,7 +6875,7 @@ void player::rooted_message() const } // TODO: Move this into player::suffer() -void player::rooted() +void Character::rooted() // Should average a point every two minutes or so; ground isn't uniformly fertile { double shoe_factor = footwear_factor(); @@ -9652,7 +9652,7 @@ int player::get_env_resist( body_part bp ) const return ret; } -bool player::wearing_something_on( body_part bp ) const +bool Character::wearing_something_on( body_part bp ) const { for( auto &i : worn ) { if( i.covers( bp ) ) { @@ -9673,7 +9673,7 @@ bool player::natural_attack_restricted_on( body_part bp ) const return false; } -bool player::is_wearing_shoes( const side &which_side ) const +bool Character::is_wearing_shoes( const side &which_side ) const { bool left = true; bool right = true; @@ -9727,7 +9727,7 @@ int player::head_cloth_encumbrance() const return ret; } -double player::footwear_factor() const +double Character::footwear_factor() const { double ret = 0; if( wearing_something_on( bp_foot_l ) ) { diff --git a/src/player.h b/src/player.h index 073df11035850..a82860301f65a 100644 --- a/src/player.h +++ b/src/player.h @@ -251,9 +251,6 @@ class player : public Character void update_needs( int rate_multiplier ); needs_rates calc_needs_rates(); - /** Set vitamin deficiency/excess disease states dependent upon current vitamin levels */ - void update_vitamins( const vitamin_id &vit ); - /** * Handles passive regeneration of pain and maybe hp. */ @@ -829,28 +826,8 @@ class player : public Character /** Get vitamin usage rate (minutes per unit) accounting for bionics, mutations and effects */ time_duration vitamin_rate( const vitamin_id &vit ) const; - /** - * Add or subtract vitamins from player storage pools - * @param vit ID of vitamin to modify - * @param qty amount by which to adjust vitamin (negative values are permitted) - * @param capped if true prevent vitamins which can accumulate in excess from doing so - * @return adjusted level for the vitamin or zero if vitamin does not exist - */ - int vitamin_mod( const vitamin_id &vit, int qty, bool capped = true ); - void vitamins_mod( const std::map &, bool capped = true ); - /** - * Check current level of a vitamin - * - * Accesses level of a given vitamin. If the vitamin_id specified does not - * exist then this function simply returns 0. - * - * @param vit ID of vitamin to check level for. - * @returns current level for specified vitamin - */ - int vitamin_get( const vitamin_id &vit ) const; - /** * Sets level of a vitamin or returns false if id given in vit does not exist * @@ -866,9 +843,6 @@ class player : public Character float metabolic_rate() const; /** Handles the effects of consuming an item */ bool consume_effects( item &food ); - /** Handles rooting effects */ - void rooted_message() const; - void rooted(); int get_lift_assist() const; bool list_ammo( const item &base, std::vector &ammo_list, @@ -1124,18 +1098,12 @@ class player : public Character int get_armor_fire( body_part bp ) const; /** Returns overall resistance to given type on the bod part */ int get_armor_type( damage_type dt, body_part bp ) const override; - /** Returns true if the player is wearing something on the entered body_part */ - bool wearing_something_on( body_part bp ) const; /** Returns true if the player is wearing something on the entered body_part, ignoring items with the ALLOWS_NATURAL_ATTACKS flag */ bool natural_attack_restricted_on( body_part bp ) const; - /** Returns true if the player is wearing something on their feet that is not SKINTIGHT */ - bool is_wearing_shoes( const side &which_side = side::BOTH ) const; /** Returns true if the player is wearing something occupying the helmet slot */ bool is_wearing_helmet() const; /** Returns the total encumbrance of all SKINTIGHT and HELMET_COMPAT items covering the head */ int head_cloth_encumbrance() const; - /** Returns 1 if the player is wearing something on both feet, .5 if on one, and 0 if on neither */ - double footwear_factor() const; /** Same as footwear factor, but for arms */ double armwear_factor() const; /** Returns 1 if the player is wearing an item of that count on one foot, 2 if on both, and zero if on neither */ @@ -1734,9 +1702,6 @@ class player : public Character std::shared_ptr tdata; protected: - // TODO: move these to avatar - /** Current deficiency/excess quantity for each vitamin */ - std::map vitamin_levels; /** Subset of learned recipes. Needs to be mutable for lazy initialization. */ mutable pimpl learned_recipes; From 8c2186d82ecfafaa714ca044efddc2893330cced Mon Sep 17 00:00:00 2001 From: KorGgenT Date: Wed, 16 Oct 2019 20:06:33 -0400 Subject: [PATCH 2/3] move roots() to player.cpp --- src/character.cpp | 113 ++++++++++++++++++++++++++++++++++++++++++++++ src/player.cpp | 111 --------------------------------------------- 2 files changed, 113 insertions(+), 111 deletions(-) diff --git a/src/character.cpp b/src/character.cpp index 8e82e7c3faeb6..8768fbc592152 100644 --- a/src/character.cpp +++ b/src/character.cpp @@ -55,6 +55,7 @@ #include "rng.h" #include "stomach.h" #include "ui.h" +#include "vitamin.h" static const bionic_id bio_ads( "bio_ads" ); static const bionic_id bio_armor_arms( "bio_armor_arms" ); @@ -131,6 +132,8 @@ static const trait_id trait_NIGHTVISION( "NIGHTVISION" ); static const trait_id trait_PACKMULE( "PACKMULE" ); static const trait_id trait_PER_SLIME_OK( "PER_SLIME_OK" ); static const trait_id trait_PER_SLIME( "PER_SLIME" ); +static const trait_id trait_ROOTS2( "ROOTS2" ); +static const trait_id trait_ROOTS3( "ROOTS3" ); static const trait_id trait_SEESLEEP( "SEESLEEP" ); static const trait_id trait_SHELL2( "SHELL2" ); static const trait_id trait_SHELL( "SHELL" ); @@ -4989,3 +4992,113 @@ void Character::blossoms() g->m.add_field( tmp, fd_fungal_haze, rng( 1, 2 ) ); } } + +void Character::update_vitamins( const vitamin_id &vit ) +{ + if( is_npc() ) { + return; // NPCs cannot develop vitamin diseases + } + + efftype_id def = vit.obj().deficiency(); + efftype_id exc = vit.obj().excess(); + + int lvl = vit.obj().severity( vitamin_get( vit ) ); + if( lvl <= 0 ) { + remove_effect( def ); + } + if( lvl >= 0 ) { + remove_effect( exc ); + } + if( lvl > 0 ) { + if( has_effect( def, num_bp ) ) { + get_effect( def, num_bp ).set_intensity( lvl, true ); + } else { + add_effect( def, 1_turns, num_bp, true, lvl ); + } + } + if( lvl < 0 ) { + if( has_effect( exc, num_bp ) ) { + get_effect( exc, num_bp ).set_intensity( lvl, true ); + } else { + add_effect( exc, 1_turns, num_bp, true, lvl ); + } + } +} + +void Character::rooted_message() const +{ + bool wearing_shoes = is_wearing_shoes( side::LEFT ) || is_wearing_shoes( side::RIGHT ); + if( ( has_trait( trait_ROOTS2 ) || has_trait( trait_ROOTS3 ) ) && + g->m.has_flag( "PLOWABLE", pos() ) && + !wearing_shoes ) { + add_msg( m_info, _( "You sink your roots into the soil." ) ); + } +} + +void Character::rooted() +// Should average a point every two minutes or so; ground isn't uniformly fertile +{ + double shoe_factor = footwear_factor(); + if( ( has_trait( trait_ROOTS2 ) || has_trait( trait_ROOTS3 ) ) && + g->m.has_flag( "PLOWABLE", pos() ) && shoe_factor != 1.0 ) { + if( one_in( 96 ) ) { + vitamin_mod( vitamin_id( "iron" ), 1, true ); + vitamin_mod( vitamin_id( "calcium" ), 1, true ); + } + if( get_thirst() <= -2000 && x_in_y( 75, 425 ) ) { + mod_thirst( -1 ); + } + mod_healthy_mod( 5, 50 ); + } +} + +bool Character::wearing_something_on( body_part bp ) const +{ + for( auto &i : worn ) { + if( i.covers( bp ) ) { + return true; + } + } + return false; +} + +bool Character::is_wearing_shoes( const side &which_side ) const +{ + bool left = true; + bool right = true; + if( which_side == side::LEFT || which_side == side::BOTH ) { + left = false; + for( const item &worn_item : worn ) { + if( worn_item.covers( bp_foot_l ) && !worn_item.has_flag( "BELTED" ) && + !worn_item.has_flag( "PERSONAL" ) && !worn_item.has_flag( "AURA" ) && + !worn_item.has_flag( "SEMITANGIBLE" ) && !worn_item.has_flag( "SKINTIGHT" ) ) { + left = true; + break; + } + } + } + if( which_side == side::RIGHT || which_side == side::BOTH ) { + right = false; + for( const item &worn_item : worn ) { + if( worn_item.covers( bp_foot_r ) && !worn_item.has_flag( "BELTED" ) && + !worn_item.has_flag( "PERSONAL" ) && !worn_item.has_flag( "AURA" ) && + !worn_item.has_flag( "SEMITANGIBLE" ) && !worn_item.has_flag( "SKINTIGHT" ) ) { + right = true; + break; + } + } + } + return ( left && right ); +} + +double Character::footwear_factor() const +{ + double ret = 0; + if( wearing_something_on( bp_foot_l ) ) { + ret += .5; + } + if( wearing_something_on( bp_foot_r ) ) { + ret += .5; + } + return ret; +} diff --git a/src/player.cpp b/src/player.cpp index 470a4561f3038..55dc8a93f1b93 100644 --- a/src/player.cpp +++ b/src/player.cpp @@ -3446,38 +3446,6 @@ void player::update_stomach( const time_point &from, const time_point &to ) } } -void Character::update_vitamins( const vitamin_id &vit ) -{ - if( is_npc() ) { - return; // NPCs cannot develop vitamin diseases - } - - efftype_id def = vit.obj().deficiency(); - efftype_id exc = vit.obj().excess(); - - int lvl = vit.obj().severity( vitamin_get( vit ) ); - if( lvl <= 0 ) { - remove_effect( def ); - } - if( lvl >= 0 ) { - remove_effect( exc ); - } - if( lvl > 0 ) { - if( has_effect( def, num_bp ) ) { - get_effect( def, num_bp ).set_intensity( lvl, true ); - } else { - add_effect( def, 1_turns, num_bp, true, lvl ); - } - } - if( lvl < 0 ) { - if( has_effect( exc, num_bp ) ) { - get_effect( exc, num_bp ).set_intensity( lvl, true ); - } else { - add_effect( exc, 1_turns, num_bp, true, lvl ); - } - } -} - void player::get_sick() { // NPCs are too dumb to handle infections now @@ -6864,34 +6832,6 @@ bool player::consume( int target_position ) return true; } -void Character::rooted_message() const -{ - bool wearing_shoes = is_wearing_shoes( side::LEFT ) || is_wearing_shoes( side::RIGHT ); - if( ( has_trait( trait_ROOTS2 ) || has_trait( trait_ROOTS3 ) ) && - g->m.has_flag( "PLOWABLE", pos() ) && - !wearing_shoes ) { - add_msg( m_info, _( "You sink your roots into the soil." ) ); - } -} - -// TODO: Move this into player::suffer() -void Character::rooted() -// Should average a point every two minutes or so; ground isn't uniformly fertile -{ - double shoe_factor = footwear_factor(); - if( ( has_trait( trait_ROOTS2 ) || has_trait( trait_ROOTS3 ) ) && - g->m.has_flag( "PLOWABLE", pos() ) && shoe_factor != 1.0 ) { - if( one_in( 96 ) ) { - vitamin_mod( vitamin_id( "iron" ), 1, true ); - vitamin_mod( vitamin_id( "calcium" ), 1, true ); - } - if( get_thirst() <= -2000 && x_in_y( 75, 425 ) ) { - mod_thirst( -1 ); - } - mod_healthy_mod( 5, 50 ); - } -} - bool player::add_faction_warning( const faction_id &id ) { const auto it = warning_record.find( id ); @@ -9652,16 +9592,6 @@ int player::get_env_resist( body_part bp ) const return ret; } -bool Character::wearing_something_on( body_part bp ) const -{ - for( auto &i : worn ) { - if( i.covers( bp ) ) { - return true; - } - } - return false; -} - bool player::natural_attack_restricted_on( body_part bp ) const { for( auto &i : worn ) { @@ -9673,35 +9603,6 @@ bool player::natural_attack_restricted_on( body_part bp ) const return false; } -bool Character::is_wearing_shoes( const side &which_side ) const -{ - bool left = true; - bool right = true; - if( which_side == side::LEFT || which_side == side::BOTH ) { - left = false; - for( const item &worn_item : worn ) { - if( worn_item.covers( bp_foot_l ) && !worn_item.has_flag( "BELTED" ) && - !worn_item.has_flag( "PERSONAL" ) && !worn_item.has_flag( "AURA" ) && - !worn_item.has_flag( "SEMITANGIBLE" ) && !worn_item.has_flag( "SKINTIGHT" ) ) { - left = true; - break; - } - } - } - if( which_side == side::RIGHT || which_side == side::BOTH ) { - right = false; - for( const item &worn_item : worn ) { - if( worn_item.covers( bp_foot_r ) && !worn_item.has_flag( "BELTED" ) && - !worn_item.has_flag( "PERSONAL" ) && !worn_item.has_flag( "AURA" ) && - !worn_item.has_flag( "SEMITANGIBLE" ) && !worn_item.has_flag( "SKINTIGHT" ) ) { - right = true; - break; - } - } - } - return ( left && right ); -} - bool player::is_wearing_helmet() const { for( const item &i : worn ) { @@ -9727,18 +9628,6 @@ int player::head_cloth_encumbrance() const return ret; } -double Character::footwear_factor() const -{ - double ret = 0; - if( wearing_something_on( bp_foot_l ) ) { - ret += .5; - } - if( wearing_something_on( bp_foot_r ) ) { - ret += .5; - } - return ret; -} - double player::armwear_factor() const { double ret = 0; From 5b88f69d9b6c91b640a18700e1cd9f842b4cface Mon Sep 17 00:00:00 2001 From: KorGgenT Date: Wed, 16 Oct 2019 20:12:35 -0400 Subject: [PATCH 3/3] move vitamin save/load to Character --- src/savegame_json.cpp | 18 +++++++++--------- 1 file changed, 9 insertions(+), 9 deletions(-) diff --git a/src/savegame_json.cpp b/src/savegame_json.cpp index e5b9d0687a866..df9e9b451d313 100644 --- a/src/savegame_json.cpp +++ b/src/savegame_json.cpp @@ -395,6 +395,14 @@ void Character::load( JsonObject &data ) data.read( "stored_calories", stored_calories ); data.read( "radiation", radiation ); data.read( "oxygen", oxygen ); + + JsonObject vits = data.get_object( "vitamin_levels" ); + for( const std::pair &v : vitamin::all() ) { + int lvl = vits.get_int( v.first.str(), 0 ); + lvl = std::max( std::min( lvl, v.first.obj().max() ), v.first.obj().min() ); + vitamin_levels[v.first] = lvl; + } + // npc activity on vehicles. data.read( "activity_vehicle_part_index", activity_vehicle_part_index ); // health @@ -575,6 +583,7 @@ void Character::store( JsonOut &json ) const json.member( "stored_calories", stored_calories ); json.member( "radiation", radiation ); json.member( "stamina", stamina ); + json.member( "vitamin_levels", vitamin_levels ); // breathing json.member( "underwater", underwater ); @@ -896,8 +905,6 @@ void avatar::store( JsonOut &json ) const // Player only, books they have read at least once. json.member( "items_identified", items_identified ); - json.member( "vitamin_levels", vitamin_levels ); - json.member( "stomach", stomach ); json.member( "guts", guts ); @@ -1022,13 +1029,6 @@ void avatar::load( JsonObject &data ) items_identified.clear(); data.read( "items_identified", items_identified ); - auto vits = data.get_object( "vitamin_levels" ); - for( const auto &v : vitamin::all() ) { - int lvl = vits.get_int( v.first.str(), 0 ); - lvl = std::max( std::min( lvl, v.first.obj().max() ), v.first.obj().min() ); - vitamin_levels[ v.first ] = lvl; - } - data.read( "stomach", stomach ); data.read( "guts", guts );