언리얼 엔진(UE5)에서 대규모 월드를 관리하기 위해 사용하는 두 가지 대표적인 방식인 서브레벨(Sub-Level)과 월드 파티션(World Partition)에 대해 알아보겠습니다. 이 글에서는 두 시스템의 차이점을 설명하고, 어떤 경우에 각각의 방식을 사용하는 것이 적합한지 살펴보겠습니다.
서브레벨은 언리얼 엔진의 전통적인 레벨 관리 방식으로, 퍼시스턴트 레벨(Persistent Level)에 여러 서브레벨을 추가하여 필요에 따라 로드하거나 언로드하는 방식입니다. 이 방식을 사용하면 큰 월드를 작은 단위로 나누어 메모리 사용을 최소화하고, 성능을 향상시킬 수 있습니다. 주로 던전이나 각기 다른 지역으로 나뉜 게임에서 자주 사용됩니다.
서브레벨을 로드하는 가장 일반적인 방법은 UGameplayStatics::LoadStreamLevel
함수를 사용하는 것입니다. 아래는 기본적인 서브레벨 로드 예시입니다.
void ALevelManager::LoadSubLevel(FName LevelName)
{
if (LevelName.IsNone()) return;
FLatentActionInfo LateInfo;
LateInfo.Linkage = Character->CurrentSubLevel;
LateInfo.UUID = Character->CurrentSubLevel;
LateInfo.ExecutionFunction = TEXT("OnLevelLoaded");
LateInfo.CallbackTarget = this;
UGameplayStatics::LoadStreamLevel(this, LevelName, true, false, LateInfo);
}
이 코드는 주어진 레벨 이름에 따라 서브레벨을 로드하며, 이후 레벨이 로드되면 OnLevelLoaded
함수가 실행됩니다. OnLevelLoaded
라는 이름의 함수에는 UFUNCTION 매크로를 붙이는 걸 잊으면 안됩니다.
서브레벨에 대한 정보를 데이터 테이블로 관리할 수 있습니다. 각 스테이지별 서브레벨 정보는 데이터 테이블에 저장되고, 이를 통해 레벨을 동적으로 로드할 수 있습니다.
USTRUCT(BlueprintType)
struct FLevelInfoData : public FTableRowBase
{
GENERATED_BODY()
UPROPERTY(EditAnywhere, BlueprintReadWrite)
int32 SubLevelNumber;
UPROPERTY(EditAnywhere, BlueprintReadWrite)
FName SubLevelName;
};
이러한 방식으로 각 서브레벨의 정보를 저장하고, 필요에 따라 로드되도록 만들 수 있습니다. 이를 사용하는 방법은 여러가지가 있지만, 몇 개로 정리해보자면.
트리거 박스를 만들어서 해당 트리거 박스에 도달하면 다음 서브레벨을 로드하는 방식.
레벨 스트리밍 볼륨을 만들어서 해당 볼륨안에 있을때만 서브레벨을 로드하는 방식.
사용자가 특정 키를 입력하면 서브레벨이 보이게 하는 방식.
등이 있습니다.
더 자세한 정보는 언리얼 엔진 서브레벨 관리 공식 문서에서 확인할 수 있습니다.
월드 파티션은 UE5에서 새롭게 도입된 시스템으로, 대규모 오픈 월드를 자동으로 관리할 수 있도록 설계되었습니다. 서브레벨과 달리 개발자가 수동으로 레벨을 관리할 필요 없이, 월드를 여러 그리드로 나누고 필요한 부분만 자동으로 스트리밍합니다. 이는 오픈 월드 게임에서 성능 최적화에 매우 유리합니다.
월드 파티션에 대한 더 자세한 정보는 언리얼 엔진 월드 파티션 공식 문서에서 확인할 수 있습니다.
항목 | 서브레벨 | 월드 파티션 |
---|---|---|
레벨 로드 | 수동 관리 (개발자가 직접 로드/언로드) | 자동 스트리밍 |
용도 | 특정 지역으로 나뉜 게임(던전 등) | 대규모 오픈 월드 |
메모리 관리 | 개발자가 직접 관리 | 자동으로 필요한 부분만 메모리 로드 |
도입 시기 | UE4부터 존재 | UE5에서 새롭게 도입 |
서브레벨과 월드 파티션은 각각의 게임 디자인 및 규모에 따라 선택해야 합니다. 서브레벨은 주로 작은 지역으로 구분된 게임에서 세밀한 제어가 필요할 때 유리하고, 월드 파티션은 대규모 오픈 월드를 처리할 때 훨씬 효율적인 솔루션입니다. 여러분의 게임이 어떤 규모의 월드를 필요로 하는지에 따라 적절한 방식을 선택하면 됩니다.
그러나 각각의 전환을 어떤 기준에 의해서 정하는지는 언리얼 엔진의 로깅 프레임워크를 사용하여 자원이 얼마만큼 사용되는지를 보아야합니다. 이는 다음 글에서 다룰 예정입니다.