class_name Inventory extends RefCounted const MAX_STACK: int = 64 const TOTAL_SLOTS: int = 36 const HOTBAR_SIZE: int = 9 signal inventory_changed var slots: Array = [] var selected_hotbar: int = 0 func _init() -> void: slots.resize(TOTAL_SLOTS) for i: int in range(TOTAL_SLOTS): slots[i] = null func add_item(item_id: int, count: int = 1) -> int: var remaining: int = count # First pass: stack into existing slots for i: int in range(TOTAL_SLOTS): if remaining <= 0: break if slots[i] != null and slots[i]["item_id"] == item_id: var space: int = MAX_STACK - slots[i]["count"] if space > 0: var add_amount: int = mini(space, remaining) slots[i]["count"] += add_amount remaining -= add_amount # Second pass: fill empty slots for i: int in range(TOTAL_SLOTS): if remaining <= 0: break if slots[i] == null: var add_amount: int = mini(MAX_STACK, remaining) slots[i] = {"item_id": item_id, "count": add_amount} remaining -= add_amount inventory_changed.emit() return remaining func remove_item_from_slot(slot_index: int, count: int = 1) -> bool: if slot_index < 0 or slot_index >= TOTAL_SLOTS: return false if slots[slot_index] == null: return false if slots[slot_index]["count"] < count: return false slots[slot_index]["count"] -= count if slots[slot_index]["count"] <= 0: slots[slot_index] = null inventory_changed.emit() return true func get_selected_item() -> Variant: return slots[selected_hotbar] func scroll_hotbar(direction: int) -> void: selected_hotbar = (selected_hotbar + direction + HOTBAR_SIZE) % HOTBAR_SIZE inventory_changed.emit() func has_items(requirements: Array) -> bool: for req: Dictionary in requirements: var needed: int = req["count"] for i: int in range(TOTAL_SLOTS): if slots[i] != null and slots[i]["item_id"] == req["item_id"]: needed -= slots[i]["count"] if needed > 0: return false return true func get_all_slots() -> Array: return slots.duplicate(true) func load_slots(saved_slots: Array) -> void: for i: int in range(min(saved_slots.size(), TOTAL_SLOTS)): slots[i] = saved_slots[i] inventory_changed.emit() func consume_items(requirements: Array) -> bool: if not has_items(requirements): return false for req: Dictionary in requirements: var to_consume: int = req["count"] for i: int in range(TOTAL_SLOTS): if to_consume <= 0: break if slots[i] != null and slots[i]["item_id"] == req["item_id"]: var take: int = mini(slots[i]["count"], to_consume) slots[i]["count"] -= take to_consume -= take if slots[i]["count"] <= 0: slots[i] = null inventory_changed.emit() return true