diff --git a/src/ship/items/inventory.rs b/src/ship/items/inventory.rs index c949d74..a44c97d 100644 --- a/src/ship/items/inventory.rs +++ b/src/ship/items/inventory.rs @@ -240,6 +240,13 @@ impl InventoryItem { } } + pub fn stacked_mut(&mut self) -> Option<&mut StackedInventoryItem> { + match self { + InventoryItem::Stacked(ref mut stacked_inventory_item) => Some(stacked_inventory_item), + _ => None + } + } + pub fn mag(&self) -> Option<&Mag> { match self { InventoryItem::Individual(individual_inventory_item) => individual_inventory_item.mag(), @@ -477,6 +484,23 @@ impl CharacterInventory { } } + pub fn stack_item_id(&self, tool: &Tool) -> Option { + self.items.iter() + .filter_map(|item| { + match item { + InventoryItem::Stacked(s_item) => { + Some(s_item) + }, + _ => None + } + }) + .find(|s_item| { + s_item.tool == *tool + }) + .map(|item| { + item.item_id + }) + } pub fn get_item_handle_by_id(&mut self, item_id: ClientItemId) -> Option { let (slot, _) = self.items.iter() @@ -571,10 +595,57 @@ impl CharacterInventory { .next() } - pub fn add_item(&mut self, item: InventoryItem) -> Result<(), InventoryAddError> { // TODO: errors - // TODO: check slot conflict? + pub fn take_stacked_item_by_id(&mut self, item_id: ClientItemId, amount: usize) -> Option { + let idx = self.items + .iter_mut() + .position(|i| i.item_id() == item_id)?; + let item: &mut StackedInventoryItem = self.items.get_mut(idx)?.stacked_mut()?; + match item.entity_ids.len().cmp(&amount) { + Ordering::Equal => { + let item = self.items.remove(idx); + item.stacked().cloned() + }, + Ordering::Greater => { + let entity_ids = item.entity_ids.drain(..amount).collect(); + Some(StackedInventoryItem { + entity_ids, + tool: item.tool, + item_id: item.item_id, + }) + }, + Ordering::Less => { + None + } + } + } + + pub fn add_item(&mut self, item: InventoryItem) { self.items.push(item); - Ok(()) + } + + pub fn add_stacked_item(&mut self, mut item: StackedInventoryItem) { + let existing_item = self.items + .iter_mut() + .filter_map(|i| { + match i { + InventoryItem::Stacked(stacked) => { + Some(stacked) + }, + _ => None + } + }) + .find(|i| { + i.tool == item.tool + }); + + match existing_item { + Some(existing_item) => { + existing_item.entity_ids.append(&mut item.entity_ids) + }, + None => { + self.items.push(InventoryItem::Stacked(item)) + } + } } pub fn add_individual_floor_item(&mut self, floor_item: &IndividualFloorItem) -> &InventoryItem {