// Copyright ExByte Studios. Item Interaction Ecosystem. #pragma once #include "CoreMinimal.h" #include "GameplayTagContainer.h" #include "ItemEnums.h" #include "InventoryContainer.generated.h" /** * Metadata describing one container owned by an inventory (section 7.2). * * NOTE (design deviation from the TЗ sketch): the actual item entries do NOT live * inside the container struct. They live in the component's single * FReplicatedInventoryList, tagged with this ContainerId. A FastArraySerializer * only delta-replicates correctly as a direct UPROPERTY, so nesting one inside a * replicated TArray would silently fall back to full-array * replication. Keeping containers as lightweight metadata fixes that (section 32). */ USTRUCT(BlueprintType) struct ITEMINVENTORY_API FInventoryContainer { GENERATED_BODY() UPROPERTY(EditAnywhere, BlueprintReadOnly, Category = "Container") FGuid ContainerId; /** Logical identity, e.g. Container.Backpack / Container.Hotbar / Container.Vehicle.Cargo. */ UPROPERTY(EditAnywhere, BlueprintReadOnly, Category = "Container") FGameplayTag ContainerTag; UPROPERTY(EditAnywhere, BlueprintReadOnly, Category = "Container") EInventoryContainerType Type = EInventoryContainerType::SlotList; UPROPERTY(EditAnywhere, BlueprintReadOnly, Category = "Container") int32 Width = 0; UPROPERTY(EditAnywhere, BlueprintReadOnly, Category = "Container") int32 Height = 0; /** Used by SlotList/Equipment/Hotbar; for Grid types capacity is Width*Height. */ UPROPERTY(EditAnywhere, BlueprintReadOnly, Category = "Container") int32 MaxSlots = 0; UPROPERTY(EditAnywhere, BlueprintReadOnly, Category = "Container") float MaxWeight = 0.f; UPROPERTY(EditAnywhere, BlueprintReadOnly, Category = "Container") FGameplayTagContainer AcceptedItemTags; UPROPERTY(EditAnywhere, BlueprintReadOnly, Category = "Container") FGameplayTagContainer BlockedItemTags; /** Set when this container lives inside another item (a backpack/pouch item) - section 7. */ UPROPERTY(BlueprintReadOnly, Category = "Container") FGuid OwnerItemInstanceId; FInventoryContainer() = default; bool IsNested() const { return OwnerItemInstanceId.IsValid(); } /** Number of addressable slots in this container (0 = unlimited weight-gated list). */ int32 GetSlotCount() const { if (Type == EInventoryContainerType::Grid) { return FMath::Max(0, Width) * FMath::Max(0, Height); } return FMath::Max(0, MaxSlots); } bool HasSlotLimit() const { return GetSlotCount() > 0; } bool HasWeightLimit() const { return MaxWeight > 0.f; } };