Skip to content

Commit

Permalink
Fix bionic removal (#44985)
Browse files Browse the repository at this point in the history
* Revert uninstal menu to uilist

* remove unused menu

* remove unused var
  • Loading branch information
Fris0uman authored Oct 20, 2020
1 parent ea096c2 commit 66360e0
Show file tree
Hide file tree
Showing 3 changed files with 11 additions and 121 deletions.
96 changes: 3 additions & 93 deletions src/game_inventory.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -1662,8 +1662,7 @@ void game_menus::inv::swap_letters( player &p )
}

static item_location autodoc_internal( player &u, player &patient,
const inventory_selector_preset &preset,
int radius, bool uninstall = false, bool surgeon = false )
const inventory_selector_preset &preset, int radius, bool surgeon = false )
{
inventory_pick_selector inv_s( u, preset );
std::string hint;
Expand All @@ -1688,11 +1687,7 @@ static item_location autodoc_internal( player &u, player &patient,
}
}

if( uninstall ) {
inv_s.set_title( string_format( _( "Bionic removal patient: %s" ), patient.get_name() ) );
} else {
inv_s.set_title( string_format( _( "Bionic installation patient: %s" ), patient.get_name() ) );
}
inv_s.set_title( string_format( _( "Bionic installation patient: %s" ), patient.get_name() ) );

inv_s.set_hint( hint );
inv_s.set_display_stats( false );
Expand Down Expand Up @@ -1910,97 +1905,12 @@ class bionic_install_surgeon_preset : public inventory_selector_preset
item_location game_menus::inv::install_bionic( player &p, player &patient, bool surgeon )
{
if( surgeon ) {
return autodoc_internal( p, patient, bionic_install_surgeon_preset( p, patient ), 5, false,
surgeon );
return autodoc_internal( p, patient, bionic_install_surgeon_preset( p, patient ), 5, surgeon );
} else {
return autodoc_internal( p, patient, bionic_install_preset( p, patient ), 5 );
}

}
// Menu used by autodoc when uninstalling a bionic
class bionic_uninstall_preset : public inventory_selector_preset
{
public:
bionic_uninstall_preset( player &pl, player &patient ) :
p( pl ), pa( patient ) {
append_cell( [this]( const item_location & loc ) {
return get_failure_chance( loc );
}, _( "FAILURE CHANCE" ) );

append_cell( [this]( const item_location & loc ) {
return get_operation_duration( loc );
}, _( "OPERATION DURATION" ) );

append_cell( [this]( const item_location & loc ) {
return get_anesth_amount( loc );
}, _( "ANESTHETIC REQUIRED" ) );
}

bool is_shown( const item_location &loc ) const override {
return loc->has_flag( flag_IN_CBM );
}

std::string get_denial( const item_location &loc ) const override {
const itype *itemtype = loc.get_item()->type;

if( !p.has_enough_anesth( *itemtype, pa ) ) {
const int weight = units::to_kilogram( pa.bodyweight() ) / 10;
const int duration = loc.get_item()->type->bionic->difficulty * 2;
const requirement_data req_anesth = *requirement_id( "anesthetic" ) *
duration * weight;
return string_format( _( "%i mL" ), req_anesth.get_tools().front().front().count );
}

return std::string();
}

protected:
player &p;
player &pa;

private:
// Returns a formatted string of how long the operation will take.
std::string get_operation_duration( const item_location &loc ) {
const int difficulty = loc.get_item()->type->bionic->difficulty;
// 20 minutes per bionic difficulty.
return to_string( time_duration::from_minutes( difficulty * 20 ) );
}

// Failure chance for bionic uninstall. Combines multiple other functions together.
std::string get_failure_chance( const item_location &loc ) {

// Uninstall difficulty gets a +2
const int difficulty = loc.get_item()->type->bionic->difficulty + 2;
int chance_of_failure = 100;
player &installer = p;

if( get_player_character().has_trait( trait_DEBUG_BIONICS ) ) {
chance_of_failure = 0;
} else {
chance_of_failure = 100 - bionic_success_chance( true, -1, difficulty, installer );
}

return string_format( _( "%i%%" ), chance_of_failure );
}

std::string get_anesth_amount( const item_location &loc ) {

const int weight = units::to_kilogram( pa.bodyweight() ) / 10;
const int duration = loc.get_item()->type->bionic->difficulty * 2;
const requirement_data req_anesth = *requirement_id( "anesthetic" ) *
duration * weight;
int count = 0;
if( !req_anesth.get_tools().empty() && !req_anesth.get_tools().front().empty() ) {
count = req_anesth.get_tools().front().front().count;
}
return string_format( _( "%i mL" ), count );
}
};

item_location game_menus::inv::uninstall_bionic( player &p, player &patient )
{
return autodoc_internal( p, patient, bionic_uninstall_preset( p, patient ), 0, true );
}

// Menu used by autoclave when sterilizing a bionic
class bionic_sterilize_preset : public inventory_selector_preset
Expand Down
2 changes: 0 additions & 2 deletions src/game_inventory.h
Original file line number Diff line number Diff line change
Expand Up @@ -123,8 +123,6 @@ item_location salvage( player &p, const salvage_actor *actor );
item_location repair( player &p, const repair_item_actor *actor, const item *main_tool );
/** Bionic install menu. */
item_location install_bionic( player &p, player &patient, bool surgeon = false );
/** Bionic uninstall menu. */
item_location uninstall_bionic( player &p, player &patient );
/**Autoclave sterilize menu*/
item_location sterilize_cbm( player &p );
/*@}*/
Expand Down
34 changes: 8 additions & 26 deletions src/iexamine.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -4880,40 +4880,22 @@ void iexamine::autodoc( player &p, const tripoint &examp )
return;
}

Character &player_character = get_player_character();
std::vector<bionic_id> bio_list;
std::vector<std::string> bionic_names;
for( const bionic &bio : installed_bionics ) {
if( bio.id != bio_power_storage ||
bio.id != bio_power_storage_mkII ) {
if( item::type_is_defined( bio.info().itype() ) ) {// put cbm items in your inventory
item bionic_to_uninstall( bio.id.str(), calendar::turn );
bionic_to_uninstall.set_flag( flag_IN_CBM );
bionic_to_uninstall.set_flag( flag_NO_STERILE );
bionic_to_uninstall.set_flag( flag_NO_PACKED );
// TODO: refactor this whole bit. adding items to the inventory will
// cause major issues when inv gets removed. this is a shim for now
// in order to reduce lines of change for nested containers.
player_character.inv->push_back( bionic_to_uninstall );
}
bio_list.emplace_back( bio.id );
bionic_names.emplace_back( bio.info().name.translated() );
}
}

const item_location bionic = game_menus::inv::uninstall_bionic( p, patient );
if( !bionic ) {
player_character.remove_items_with( []( const item & it ) {// remove cbm items from inventory
return it.has_flag( flag_IN_CBM );
} );
int bionic_index = uilist( _( "Choose bionic to uninstall" ), bionic_names );
if( bionic_index < 0 ) {
return;
}
const item *it = bionic.get_item();
const itype *itemtype = it->type;
const bionic_id &bid = itemtype->bionic->id;

player_character.remove_items_with( []( const item & it ) {// remove cbm items from inventory
return it.has_flag( flag_IN_CBM );
} );

// Malfunctioning bionics that don't have associated items and get a difficulty of 12
const int difficulty = itemtype->bionic ? itemtype->bionic->difficulty : 12;
const bionic_id &bid = bio_list[bionic_index];
const int difficulty = bid->itype()->bionic->difficulty;
const float volume_anesth = difficulty * 20 * 2; // 2ml/min

player &installer = best_installer( p, null_player, difficulty );
Expand Down

0 comments on commit 66360e0

Please sign in to comment.