Skip to content

Commit

Permalink
Bionics can require another bionic (#66996)
Browse files Browse the repository at this point in the history
* required_bionic

* required_bionic

* Update bionics.h

* Apply suggestions from code review

Co-authored-by: github-actions[bot] <41898282+github-actions[bot]@users.noreply.github.com>

* Update bionics.cpp

* Update src/bionics.cpp

Co-authored-by: github-actions[bot] <41898282+github-actions[bot]@users.noreply.github.com>

* hydraulics requires bio_weight

* put it in the itemdescription

* Update item.cpp

* Update src/item.cpp

Co-authored-by: github-actions[bot] <41898282+github-actions[bot]@users.noreply.github.com>

* Update item.cpp

* Update src/item.cpp

Co-authored-by: github-actions[bot] <41898282+github-actions[bot]@users.noreply.github.com>

* return false;

* astyle

Co-authored-by: github-actions[bot] <41898282+github-actions[bot]@users.noreply.github.com>

* if rubik sells hydraulics, they also always sell titanium skel

* document required_bionic

* add a prob

* Update data/json/npcs/exodii/exodii_merchant_itemlist.json

Co-authored-by: github-actions[bot] <41898282+github-actions[bot]@users.noreply.github.com>

* Update bionics.json

* Update exodii_merchant_itemlist.json

---------

Co-authored-by: github-actions[bot] <41898282+github-actions[bot]@users.noreply.github.com>
  • Loading branch information
anoobindisguise and github-actions[bot] authored Jul 22, 2023
1 parent 70b5d90 commit bc2cb58
Show file tree
Hide file tree
Showing 4 changed files with 48 additions and 2 deletions.
15 changes: 14 additions & 1 deletion doc/JSON_INFO.md
Original file line number Diff line number Diff line change
Expand Up @@ -1090,6 +1090,7 @@ mod = min( max, ( limb_score / denominator ) - subtract );
| `social_modifiers` | (_optional_) Json object with optional members: persuade, lie, and intimidate which add or subtract that amount from those types of social checks
| `dispersion_mod` | (_optional_) Modifier to change firearm dispersion.
| `activated_on_install` | (_optional_) Auto-activates this bionic when installed.
| `required_bionic` | (_optional_) Bionic which is required to install this bionic, and which cannot be uninstalled if this bionic is installed

```JSON
{
Expand Down Expand Up @@ -1123,7 +1124,19 @@ mod = min( max, ( limb_score / denominator ) - subtract );
[ "hand_r", { "bash": 3, "cut": 3, "bullet": 3 } ]
],
"flags": [ "BIONIC_NPC_USABLE" ]
}
},
{
"id": "bio_hydraulics",
"type": "bionic",
"name": { "str": "Hydraulic Muscles" },
"description": "While activated, your muscles will be greatly enhanced, increasing your strength by 20.",
"occupied_bodyparts": [ [ "torso", 10 ], [ "arm_l", 8 ], [ "arm_r", 8 ], [ "leg_l", 10 ], [ "leg_r", 10 ] ],
"flags": [ "BIONIC_TOGGLED", "BIONIC_NPC_USABLE" ],
"act_cost": "10 kJ",
"react_cost": "10 kJ",
"time": "1 s",
"required_bionic": "bio_weight"
}
```

Bionics effects are defined in the code and new effects cannot be created through JSON alone.
Expand Down
21 changes: 21 additions & 0 deletions src/bionics.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -364,6 +364,7 @@ void bionic_data::load( const JsonObject &jsobj, const std::string &src )
optional( jsobj, was_loaded, "included_bionics", included_bionics );
optional( jsobj, was_loaded, "included", included );
optional( jsobj, was_loaded, "upgraded_bionic", upgraded_bionic );
optional( jsobj, was_loaded, "required_bionic", required_bionic );
optional( jsobj, was_loaded, "fuel_options", fuel_opts );
optional( jsobj, was_loaded, "activated_on_install", activated_on_install, false );

Expand Down Expand Up @@ -568,6 +569,14 @@ void bionic_data::check_bionic_consistency()
bio.id.c_str(), bio.upgraded_bionic.c_str() );
}
}
if( bio.required_bionic ) {
if( bio.required_bionic == bio.id ) {
debugmsg( "Bionic %s requires itself as a prerequisite for installation", bio.id.c_str() );
} else if( !bio.required_bionic.is_valid() ) {
debugmsg( "Bionic %s requires undefined bionic %s",
bio.id.c_str(), bio.required_bionic.c_str() );
}
}
if( !item::type_is_defined( bio.itype() ) && !bio.included ) {
debugmsg( "Bionic %s has no defined item version", bio.id.c_str() );
}
Expand Down Expand Up @@ -2113,6 +2122,14 @@ bool Character::can_uninstall_bionic( const bionic &bio, Character &installer, b
return false;
}

for( const bionic_id &bid : get_bionics() ) {
if( bid->required_bionic && bid->required_bionic == bio.id ) {
popup( _( "%s cannot be removed because installed bionic %s requires it." ), bio.id->name,
bid->name );
return false;
}
}

if( bio.id->cant_remove_reason.has_value() ) {
popup( string_format( bio.id->cant_remove_reason.value(), disp_name( true ), disp_name() ) );
return false;
Expand Down Expand Up @@ -2331,6 +2348,10 @@ ret_val<void> Character::is_installable( const item *it, const bool by_autodoc )
!has_bionic( bid->upgraded_bionic ) &&
it->is_upgrade() ) {
return ret_val<void>::make_failure( _( "No base version installed." ) );
} else if( bid->required_bionic &&
!has_bionic( bid->required_bionic ) ) {
return ret_val<void>::make_failure( _( "CBM requires prior installation of %s." ),
bid->required_bionic.obj().name );
} else if( std::any_of( bid->available_upgrades.begin(),
bid->available_upgrades.end(),
[this]( const bionic_id & b ) {
Expand Down
8 changes: 7 additions & 1 deletion src/bionics.h
Original file line number Diff line number Diff line change
Expand Up @@ -167,7 +167,13 @@ struct bionic_data {
*/
std::set<bionic_id> available_upgrades;

/**Requirement to bionic installation*/
/**
* Id of another bionic which this bionic needs to have installed to be installed.
* Also prevents that bionic from being removed while this bionic is installed.
*/
bionic_id required_bionic;

/**Requirement to bionic installation - this is a crafting requirement such as soldering_standard or surface_heat*/
requirement_id installation_requirement;

cata::flat_set<json_character_flag> flags;
Expand Down
6 changes: 6 additions & 0 deletions src/item.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -5112,6 +5112,12 @@ void item::bionic_info( std::vector<iteminfo> &info, const iteminfo_query *parts

insert_separation_line( info );

if( bid->required_bionic ) {
info.emplace_back( "CBM", string_format( "* This CBM requires another CBM to also be installed: %s",
bid->required_bionic->name ) );
}
insert_separation_line( info );

// TODO refactor these almost identical blocks
if( !bid->encumbrance.empty() ) {
info.emplace_back( "DESCRIPTION", _( "<bold>Encumbrance</bold>:" ),
Expand Down

0 comments on commit bc2cb58

Please sign in to comment.