From 902302b65e4d764ad8174dada1e23c95bf3260bc Mon Sep 17 00:00:00 2001 From: Chaosvolt Date: Tue, 25 Jun 2024 04:49:44 -0500 Subject: [PATCH] feat: allow stashing items in holsters/sheathes in `r`eload menu (#4874) * feat: allow stashing items in holsters/sheathes in `r`eload menu * Update character.cpp --- src/avatar_action.cpp | 16 +++++++++++++--- src/character.cpp | 5 +++++ src/character_functions.cpp | 13 +++++++++---- src/item.cpp | 2 +- 4 files changed, 28 insertions(+), 8 deletions(-) diff --git a/src/avatar_action.cpp b/src/avatar_action.cpp index a3b56c4283cc..773e9392575b 100644 --- a/src/avatar_action.cpp +++ b/src/avatar_action.cpp @@ -1232,9 +1232,19 @@ void avatar_action::reload( item &loc, bool prompt, bool empty ) use_loc = false; } - // for holsters and ammo pouches try to reload any contained item - if( it->type->can_use( "holster" ) && !it->contents.empty() ) { - it = &it->contents.front(); + if( it->is_holster() ) { + auto ptr = dynamic_cast + ( it->type->get_use( "holster" )->get_actor_ptr() ); + if( static_cast( it->contents.num_item_stacks() ) < ptr->multi ) { + item *loc = game_menus::inv::holster( u, *it ); + + if( !loc ) { + u.add_msg_if_player( _( "Never mind." ) ); + return; + } + ptr->store( u, *it, loc->detach() ); + return; + } } // for bandoliers we currently defer to iuse_actor methods diff --git a/src/character.cpp b/src/character.cpp index a430f8e2ae5e..eac415f50e19 100644 --- a/src/character.cpp +++ b/src/character.cpp @@ -11648,6 +11648,11 @@ int Character::hp_percentage() const bool Character::can_reload( const item &it, const itype_id &ammo ) const { + if( it.is_holster() ) { + const holster_actor *ptr = dynamic_cast + ( it.get_use( "holster" )->get_actor_ptr() ); + return static_cast( it.contents.num_item_stacks() ) < ptr->multi; + } if( !it.is_reloadable_with( ammo ) ) { return false; } diff --git a/src/character_functions.cpp b/src/character_functions.cpp index 2c157eb54504..f74e2feef76b 100644 --- a/src/character_functions.cpp +++ b/src/character_functions.cpp @@ -12,6 +12,7 @@ #include "game.h" #include "handle_liquid.h" #include "itype.h" +#include "iuse_actor.h" #include "make_static.h" #include "map_iterator.h" #include "map_selector.h" @@ -1027,7 +1028,7 @@ item_reload_option select_ammo( const Character &who, item &base, bool prompt, const bool ammo_match_found = list_ammo( who, base, ammo_list, include_empty_mags, include_potential ); - if( ammo_list.empty() ) { + if( ammo_list.empty() && !base.is_holster() ) { if( !who.is_npc() ) { if( !base.is_magazine() && !base.magazine_integral() && !base.magazine_current() ) { who.add_msg_if_player( m_info, _( "You need a compatible magazine to reload the %s!" ), @@ -1202,9 +1203,6 @@ std::vector find_reloadables( Character &who ) std::vector reloadables; who.visit_items( [&]( item * node ) { - if( node->is_holster() ) { - return VisitResponse::NEXT; - } bool reloadable = false; if( node->is_gun() && !node->magazine_compatible().empty() ) { reloadable = node->magazine_current() == nullptr || @@ -1214,6 +1212,13 @@ std::vector find_reloadables( Character &who ) ( node->is_gun() && node->magazine_integral() ) ) && node->ammo_remaining() < node->ammo_capacity(); } + if( node->is_holster() ) { + const holster_actor *ptr = dynamic_cast + ( node->get_use( "holster" )->get_actor_ptr() ); + if( static_cast( node->contents.num_item_stacks() ) < ptr->multi ) { + reloadable = true; + } + } if( reloadable ) { reloadables.push_back( node ); } diff --git a/src/item.cpp b/src/item.cpp index 54f91eebff5a..41fa2290aff6 100644 --- a/src/item.cpp +++ b/src/item.cpp @@ -10052,7 +10052,7 @@ bool item::is_reloadable() const if( has_flag( flag_NO_RELOAD ) && !has_flag( flag_VEHICLE ) ) { return false; // turrets ignore NO_RELOAD flag - } else if( is_bandolier() ) { + } else if( is_bandolier() || is_holster() ) { return true; } else if( is_container() ) {