Skip to content

Commit

Permalink
item_location: add a parent_pocket() helper
Browse files Browse the repository at this point in the history
that caches the parent pocket so you don't have to run
contained_where() everytime
  • Loading branch information
andrei8l committed Mar 12, 2023
1 parent ce1081a commit 5d51407
Show file tree
Hide file tree
Showing 10 changed files with 41 additions and 16 deletions.
2 changes: 1 addition & 1 deletion src/avatar_action.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -1150,7 +1150,7 @@ void avatar_action::use_item( avatar &you, item_location &loc, std::string const

// Get the parent pocket before the item is obtained.
if( loc.has_parent() ) {
parent_pocket = loc.parent_item().get_item()->contained_where( *loc );
parent_pocket = loc.parent_pocket();
}

loc = loc.obtain( you, 1 );
Expand Down
2 changes: 1 addition & 1 deletion src/character.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -9102,7 +9102,7 @@ ret_val<crush_tool_type> Character::can_crush_frozen_liquid( item_location loc )
{
crush_tool_type tool_type = CRUSH_NO_TOOL;
bool success = false;
if( !loc.has_parent() || !loc.parent_item()->contained_where( *loc )->get_pocket_data()->rigid ) {
if( !loc.has_parent() || !loc.parent_pocket()->get_pocket_data()->rigid ) {
tool_type = CRUSH_HAMMER;
success = has_quality( qual_HAMMER );
} else {
Expand Down
2 changes: 1 addition & 1 deletion src/character_inventory.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -89,7 +89,7 @@ void Character::handle_contents_changed( const std::vector<item_location> &conta
if( loc.has_parent() ) {
item_location parent_loc = loc.parent_item();
item_loc_with_depth parent( parent_loc );
item_pocket *const pocket = parent_loc->contained_where( *loc );
item_pocket *const pocket = loc.parent_pocket();
pocket->unseal();
bool exists = false;
auto it = sorted_containers.lower_bound( parent );
Expand Down
2 changes: 1 addition & 1 deletion src/contents_change_handler.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -12,7 +12,7 @@ void contents_change_handler::unseal_pocket_containing( const item_location &loc
{
if( loc.has_parent() ) {
item_location parent = loc.parent_item();
item_pocket *const pocket = parent->contained_where( *loc );
item_pocket *const pocket = loc.parent_pocket();
if( pocket ) {
// on_contents_changed restacks the pocket and should be called later
// in Character::handle_contents_changed
Expand Down
2 changes: 1 addition & 1 deletion src/game.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -2135,7 +2135,7 @@ int game::inventory_item_menu( item_location locThisItem,
oThisItem.is_favorite = !oThisItem.is_favorite;
if( locThisItem.has_parent() ) {
item_location parent = locThisItem.parent_item();
item_pocket *const pocket = parent->contained_where( oThisItem );
item_pocket *const pocket = locThisItem.parent_pocket();
if( pocket ) {
pocket->restack();
} else {
Expand Down
4 changes: 2 additions & 2 deletions src/game_inventory.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -707,7 +707,7 @@ class comestible_inventory_preset : public inventory_selector_preset
item_location temp = loc;
// check if at least one parent container is sealed
while( temp.has_parent() ) {
item_pocket *pocket = temp.parent_item()->contained_where( *temp.get_item() );
item_pocket *pocket = temp.parent_pocket();
if( pocket->sealed() ) {
sealed = _( "sealed" );
break;
Expand Down Expand Up @@ -795,7 +795,7 @@ class comestible_inventory_preset : public inventory_selector_preset
} else if( time == 0_turns ) {
return 4;
} else if( loc.has_parent() &&
loc.parent_item()->contained_where( *loc )->spoil_multiplier() == 0.0f ) {
loc.parent_pocket()->spoil_multiplier() == 0.0f ) {
return 3;
} else {
return 2;
Expand Down
7 changes: 3 additions & 4 deletions src/inventory_ui.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -177,7 +177,7 @@ bool is_worn_ablative( item_location const &container, item_location const &chil
// if the item is in an ablative pocket then put it with the item it is in
// first do a short circuit test if the parent has ablative pockets at all
return container->is_ablative() && container->is_worn_by_player() &&
container->contained_where( *child )->get_pocket_data()->ablative;
child.parent_pocket()->get_pocket_data()->ablative;
}

/** The maximum distance from the screen edge, to snap a window to it */
Expand Down Expand Up @@ -508,11 +508,10 @@ bool inventory_entry::is_hidden( cata::optional<bool> const &hide_entries_overri
return *hide_entries_override;
}
while( item.has_parent() && item != topmost_parent ) {
item_location parent = item.parent_item();
if( parent.get_item()->contained_where( *item )->settings.is_collapsed() ) {
if( item.parent_pocket()->settings.is_collapsed() ) {
return true;
}
item = parent;
item = item.parent_item();
}
return false;
}
Expand Down
32 changes: 28 additions & 4 deletions src/item_location.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -85,6 +85,9 @@ class item_location::impl
virtual item_location parent_item() const {
return item_location();
}
virtual item_pocket *parent_pocket() const {
return nullptr;
}
virtual tripoint position() const = 0;
virtual std::string describe( const Character * ) const = 0;
virtual item_location obtain( Character &, int ) = 0;
Expand Down Expand Up @@ -564,6 +567,7 @@ class item_location::impl::item_in_container : public item_location::impl
{
private:
item_location container;
mutable item_pocket *container_pkt = nullptr;

// figures out the index for the item, which is where it is in the total list of contents
// note: could be a better way of handling this?
Expand All @@ -588,6 +592,18 @@ class item_location::impl::item_in_container : public item_location::impl
return container;
}

item_pocket *parent_pocket() const override {
if( container_pkt == nullptr ) {
std::vector<item_pocket *> const pkts = parent_item()->get_all_standard_pockets();
if( pkts.size() == 1 ) {
container_pkt = pkts.front();
} else {
container_pkt = parent_item()->contained_where( *target() );
}
}
return container_pkt;
}

item_in_container( const item_location &container, item *which ) :
impl( which ), container( container ) {}

Expand Down Expand Up @@ -718,11 +734,11 @@ class item_location::impl::item_in_container : public item_location::impl
}

units::volume volume_capacity() const override {
return container->contained_where( *target() )->remaining_volume();
return parent_pocket()->remaining_volume();
}

units::mass weight_capacity() const override {
return container->contained_where( *target() )->remaining_weight();
return parent_pocket()->remaining_weight();
}

bool check_parent_capacity_recursive() const override {
Expand Down Expand Up @@ -846,6 +862,14 @@ item_location item_location::parent_item() const
return item_location::nowhere;
}

item_pocket *item_location::parent_pocket() const
{
if( where() == type::container ) {
return ptr->parent_pocket();
}
return nullptr;
}

bool item_location::has_parent() const
{
if( where() == type::container ) {
Expand All @@ -861,7 +885,7 @@ bool item_location::parents_can_contain_recursive( item *it ) const
}

item_location parent = parent_item();
item_pocket *pocket = parent->contained_where( *get_item() );
item_pocket *pocket = parent_pocket();

if( pocket->can_contain( *it ).success() ) {
return parent.parents_can_contain_recursive( it );
Expand All @@ -877,7 +901,7 @@ int item_location::max_charges_by_parent_recursive( const item &it ) const
}

item_location parent = parent_item();
item_pocket *pocket = parent->contained_where( *get_item() );
item_pocket *pocket = parent_pocket();

return std::min( { it.charges_per_volume( pocket->remaining_volume() ),
it.charges_per_weight( pocket->remaining_weight() ),
Expand Down
2 changes: 2 additions & 0 deletions src/item_location.h
Original file line number Diff line number Diff line change
Expand Up @@ -14,6 +14,7 @@ class character_id;
class JsonObject;
class JsonOut;
class item;
class item_pocket;
class map_cursor;
class vehicle_cursor;
class talker;
Expand Down Expand Up @@ -106,6 +107,7 @@ class item_location

/** returns the parent item, or an invalid location if it has no parent */
item_location parent_item() const;
item_pocket *parent_pocket() const;

/** returns true if the item is in the inventory of the given character **/
bool held_by( Character const &who ) const;
Expand Down
2 changes: 1 addition & 1 deletion tests/unseal_and_spill_test.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -256,7 +256,7 @@ void match( Parent &&parent, Container &&contents,
match( content_loc, content_result );
item_location container = container_from_parent( parent );
if( container ) {
item_pocket *pocket = container->contained_where( *content );
item_pocket *pocket = content_loc.parent_pocket();
REQUIRE( pocket );
CHECK( content_result.parent_pocket_sealed == pocket->sealed() );
}
Expand Down

0 comments on commit 5d51407

Please sign in to comment.