2024/02/04 TIL

양우창·2025년 2월 4일

내일배움캠프 TIL

목록 보기
19/22

오늘 배운 내용

1. 인터페이스 이해하기

1. 인터페이스란?

  • 인터페이스 (Interface)란 클래스(또는 오브젝트)가 반드시 구현해야 할 함수 목록만을 미리 정의해 두고, 실제 함수의 동작(구현 내용)은 해당 클래스를 상속받거나 구현하는 쪽에서 자유롭게 작성할 수 있도록 하는 계약서 역할을 한다.
  • C++에서는 UInterface를 상속받아 IItemInterface 같은 인터페이스를 만들 수 있으며, 언리얼 블루프린트에서도 “블루프린트 인터페이스”를 통해 비슷한 개념을 구현할 수 있다.

2. 상속 (Inheritance)과의 차이점

구분상속 (Inheritance)인터페이스 (Interface)
목적부모 클래스의 속성과 기능을 상속반드시 구현해야 할 함수 목록 제공
구현 방식부모의 로직을 그대로 사용하거나 오버라이딩함수의 틀만 정의, 구현은 직접 작성
유연성단일 상속 (C++에서는 다중 상속 가능하나 복잡)다중 인터페이스 구현 가능

3. 인터페이스의 장점

  • 결합도 감소: 클래스 간 의존도를 낮춰 코드 변경이 용이함
  • 확장성 향상: 기존 시스템에 새로운 기능을 추가할 때 용이함
  • 다형성 극대화: TArray<IItemInterface*> Items; 같은 방식으로 다양한 아이템을 관리 가능

2. 인터페이스 정의 및 아이템 부모 클래스 구현

1. IItemInterface 인터페이스 정의

#pragma once

#include "CoreMinimal.h"
#include "UObject/Interface.h"
#include "IItemInterface.generated.h"

UINTERFACE(MinimalAPI)
class UItemInterface : public UInterface
{
    GENERATED_BODY()
};

class SPARTAPROJECT_API IItemInterface
{
    GENERATED_BODY()
public:
    virtual void OnItemOverlap(AActor* OverlapActor) = 0;
    virtual void OnItemEndOverlap(AActor* OverlapActor) = 0;
    virtual void ActivateItem(AActor* Activator) = 0;
    virtual FName GetItemType() const = 0;
};

2. 아이템 부모 클래스 ABaseItem 구현

#pragma once

#include "CoreMinimal.h"
#include "GameFramework/Actor.h"
#include "ItemInterface.h"
#include "BaseItem.generated.h"

UCLASS()
class SPARTAPROJECT_API ABaseItem : public AActor, public IItemInterface
{
    GENERATED_BODY()

public:
    ABaseItem();

protected:
    UPROPERTY(EditAnywhere, BlueprintReadWrite, Category = "Item")
    FName ItemType;

    virtual void OnItemOverlap(AActor* OverlapActor) override;
    virtual void OnItemEndOverlap(AActor* OverlapActor) override;
    virtual void ActivateItem(AActor* Activator) override;
    virtual FName GetItemType() const override;
    virtual void DestroyItem();
};
#include "BaseItem.h"

ABaseItem::ABaseItem()
{
    PrimaryActorTick.bCanEverTick = false;
}

void ABaseItem::OnItemOverlap(AActor* OverlapActor) {}
void ABaseItem::OnItemEndOverlap(AActor* OverlapActor) {}
void ABaseItem::ActivateItem(AActor* Activator) {}
FName ABaseItem::GetItemType() const { return ItemType; }
void ABaseItem::DestroyItem() { Destroy(); }

3. 코인 아이템 클래스 구현

  1. CoinItem 공통 부모 클래스
#pragma once

#include "CoreMinimal.h"
#include "BaseItem.h"
#include "CoinItem.generated.h"

UCLASS()
class SPARTAPROJECT_API ACoinItem : public ABaseItem
{
    GENERATED_BODY()

public:
    ACoinItem();

protected:
    UPROPERTY(EditAnywhere, BlueprintReadWrite, Category = "Item")
    int32 PointValue;
};
  1. BigCoinItem 구현
#pragma once

#include "CoreMinimal.h"
#include "CoinItem.h"
#include "BigCoinItem.generated.h"

UCLASS()
class SPARTAPROJECT_API ABigCoinItem : public ACoinItem
{
    GENERATED_BODY()

public:
    ABigCoinItem();
    virtual void ActivateItem(AActor* Activator) override;
};
#include "BigCoinItem.h"

ABigCoinItem::ABigCoinItem()
{
    PointValue = 50;
    ItemType = "BigCoin";
}

void ABigCoinItem::ActivateItem(AActor* Activator)
{
    DestroyItem();
}
  1. SmallCoinItem 구현
#pragma once

#include "CoreMinimal.h"
#include "CoinItem.h"
#include "SmallCoinItem.generated.h"

UCLASS()
class SPARTAPROJECT_API ASmallCoinItem : public ACoinItem
{
    GENERATED_BODY()

public:
    ASmallCoinItem();
    virtual void ActivateItem(AActor* Activator) override;
};
#include "SmallCoinItem.h"

ASmallCoinItem::ASmallCoinItem()
{
    PointValue = 10;
    ItemType = "SmallCoin";
}

void ASmallCoinItem::ActivateItem(AActor* Activator)
{
    DestroyItem();
}

4. 지뢰 및 힐링 아이템 구현

  1. MineItem 구현
#pragma once

#include "CoreMinimal.h"
#include "BaseItem.h"
#include "MineItem.generated.h"

UCLASS()
class SPARTAPROJECT_API AMineItem : public ABaseItem
{
    GENERATED_BODY()

public:
    AMineItem();

    UPROPERTY(EditAnywhere, BlueprintReadWrite, Category="Mine")
    float ExplosionDelay;
    UPROPERTY(EditAnywhere, BlueprintReadWrite, Category="Mine")
    float ExplosionRadius;
    UPROPERTY(EditAnywhere, BlueprintReadWrite, Category="Mine")
    float ExplosionDamage;

    virtual void ActivateItem(AActor* Activator) override;
};
#include "MineItem.h"

AMineItem::AMineItem()
{
    ExplosionDelay = 5.0f;
    ExplosionRadius = 300.0f;
    ExplosionDamage = 30.0f;
    ItemType = "Mine";
}

void AMineItem::ActivateItem(AActor* Activator)
{
    DestroyItem();
}
  1. HealingItem 구현
#pragma once

#include "CoreMinimal.h"
#include "BaseItem.h"
#include "HealingItem.generated.h"

UCLASS()
class SPARTAPROJECT_API AHealingItem : public ABaseItem
{
    GENERATED_BODY()

public:
    AHealingItem();
    UPROPERTY(EditAnywhere, BlueprintReadWrite, Category = "Item")
    float HealAmount;
    virtual void ActivateItem(AActor* Activator) override;
};
#include "HealingItem.h"

AHealingItem::AHealingItem()
{
    HealAmount = 20.0f;
    ItemType = "Healing";
}

void AHealingItem::ActivateItem(AActor* Activator)
{
    DestroyItem();
}

결론

인터페이스를 활용하면 다양한 아이템을 일관된 방식으로 다룰 수 있으며, 코드의 재사용성과 유지보수성을 높일 수 있다. IItemInterface를 통해 필요한 기능을 명확히 정의하고, BaseItem 클래스를 부모로 두어 아이템별 공통 기능을 제공하면 개발이 한층 더 유연해진다. 이를 통해 새로운 아이템 추가가 간편해지고, 코드가 더욱 깔끔해진다.

이제 이 구조를 활용해 다양한 게임 아이템을 효과적으로 설계하고 구현할 수 있다.

profile
내배캠 언리얼 엔진 1기

0개의 댓글