본문 바로가기
게임프로그래밍/TheZombie

게임 개발 - 인벤토리와 장비창(3)

by 설련 2022. 2. 10.

오랜만에 온갖 잘못된 짓은 다하고 다닌 것 같다.

우선적으로 위젯 클래스를 블루프린트로 받아야 되는데 StaticClass로 받아서 되지도 않는 걸

일일이 왜 안 되지? 하면서 변경하고 있던 내 모습을 발견할 수 있었다.

 

이쯤되면 정신머리가 없는 수준.

 

그것을 파악하고 나서 정리하니까 바로 되었다.

(현타오지게 옴)

UCLASS()
class THEZOMBIES_API UGameIns : public UGameInstance
{
    //...
 
    UPROPERTY(VisibleAnywhere, BlueprintReadOnly, Category = Data, meta = (AllowPrivateAccess = "true"))
        TArray<FItemData> InventoryData;
 
protected:
    virtual void Init() override;
 
    //...
};
 
void UGameIns::Init() {
    Super::Init();
 
    InventoryData.SetNum(60);
}

인벤토리는 게임 인스턴스를 통해서 정의하고

Data는 TArray로서 아이템 데이터를 받는다.

아이템 데이터는 트리 형식으로 모든 아이템을 업캐스팅으로 정의받으므로 모든 데이터를 정리할 수 있다.

인벤토리는 60개의 칸을 정의하고, 사용자가 인벤토리를 원하는 만큼 정리할 수 있도록 구현할 예정이다.

60개의 칸을 따라서 빈곳과 아이템 공간으로 나뉘어야 하는데 지금으로서는 Name으로 그것을 판별하기로 한다.

UCLASS()
class THEZOMBIES_API UItemSlot : public UUserWidget
{
    GENERATED_BODY()
 
    UPROPERTY(meta = (BindWidget))
        class UImage* ItemIcon;
 
    UPROPERTY(meta = (BindWidget))
        class UButton* ItemBtn;
 
    UPROPERTY(meta = (BindWidget))
        class UTextBlock* CurrentCount;
 
public:
    void SetItemIcon(class UTexture* Icon);
    void SetCurrentCount(int32 Count);
};
 
void UItemSlot::SetItemIcon(class UTexture* Icon) {
    ItemIcon->SetBrushResourceObject(Icon);
    ItemIcon->SetVisibility(ESlateVisibility::Visible);
}
 
void UItemSlot::SetCurrentCount(int32 Count) {
    CurrentCount->SetText(FText::FromString(FString::Printf(TEXT("x %d"), Count)));
    CurrentCount->SetVisibility(ESlateVisibility::Visible);
}
 
 
UEquipmentAndInventoryUIWidget::UEquipmentAndInventoryUIWidget(const FObjectInitializer& ObjectInitializer)
    : Super(ObjectInitializer) {
    
    static ConstructorHelpers::FClassFinder<UUserWidget> AItemSlotClass(TEXT("/Game/Resource/Character/UI/ItemSlot"));
    if (AItemSlotClass.Succeeded()) {
        ItemSlotClass = AItemSlotClass.Class;
    }
}
 
void UEquipmentAndInventoryUIWidget::NativeConstruct() {
    Super::NativeConstruct();
 
    auto instance = Cast<UGameIns>(GetGameInstance());
    auto ItemData = instance->GetInventoryData();
    
    for (int32 i = 0; i < ItemData.Num(); i++) {
        FItemData Data = ItemData[i];
        UItemSlot* Item = Cast<UItemSlot>(CreateWidget(this, ItemSlotClass));
        if (Data.Name.ToString().Compare(TEXT(""))) {
            Item->SetItemIcon(Data.Icon);
            Item->SetCurrentCount(Data.CurrentCount);
        }
        InventoryList->AddChildToUniformGrid(Item, i / 5, i % 5);
    }
}

 

댓글