이 페이지에서는 Unity 사용자를 위한 언리얼 엔진(UE) 게임플레이 프로그래밍 콘셉트에 대해 설명합니다. 아래 설명에서는 사용자가 Unity C#에 익숙하고 UE C++와 블루프린트를 배우고자 한다고 가정합니다.
아래 예시에서는 Unity C#의 몇 가지 일반적인 게임플레이 프로그래밍 사용 사례와 UE에서 동일한 함수 기능을 구현하는 방법을 다룹니다.
GameObject 인스턴스화/ 액터 스폰
Unity에서는 Instantiate 함수를 사용하여 오브젝트의 새 인스턴스를 생성합니다. 이 함수는 GameObject, MonoBehaviour 등의 UnityEngine.Object 타입을 취하여 사본을 생성합니다.
public GameObject EnemyPrefab;
public Vector3 SpawnPosition;
public Quaternion SpawnRotation;
void Start()
{
GameObject NewGO = (GameObject)Instantiate(EnemyPrefab, SpawnPosition, SpawnRotation);
NewGO.name = "MyNewGameObject";
}UE에서는 다음 두 가지 함수를 사용하여 오브젝트를 인스턴스화합니다.
NewObject는 새UObject타입을 생성합니다.SpawnActor는AActor타입을 스폰합니다.
UObjects와 NewObject
UE에서 UObject 서브클래싱은 Unity에서 ScriptableObject 서브클래싱과 비슷합니다. 이것은 액터처럼 월드에 스폰하거나 어태치된 컴포넌트를 갖출 필요가 없는 게임플레이 클래스에 유용합니다.
Unity에서 ScriptableObject의 서브클래스를 생성하면 다음과 같이 인스턴스화할 수 있습니다.
MyScriptableObject NewSO = ScriptableObject.CreateInstance<MyScriptableObject>();UE에서 UObject 의 서브클래스를 생성하면 다음과 같이 인스턴스화할 수 있습니다.
UMyObject* NewObj = NewObject<UMyObject>();AActors와 SpawnActor
월드(C++에서의 UWorld) 오브젝트에서 SpawnActor 메서드를 사용하여 액터를 스폰할 수 있습니다. 일부 UObject와 모든 액터는 월드 오브젝트를 가져오는 GetWorld 메서드를 제공합니다.
아래 예시에서는 이러한 메서드와 기존 액터의 스폰 파라미터를 사용하여 Unity의 Instantiate 메서드의 함수 기능을 에뮬레이트합니다.
예시
아래는 예시 AActor 서브클래스인 AMyActor입니다. 디폴트 생성자는 int32 및 USphereComponent*를 초기화합니다.
CreateDefaultSubobject 함수의 사용에 주목하세요. 이 함수는 컴포넌트를 생성하고, 그 컴포넌트에 디폴트 프로퍼티를 할당합니다. 이 함수를 사용하여 생성된 서브 오브젝트는 디폴트 템플릿으로 작동하기 때문에 서브클래스 또는 블루프린트에서 수정할 수 있습니다.
UCLASS()
class AMyActor : public AActor
{
GENERATED_BODY()
UPROPERTY()
int32 MyIntProp;
UPROPERTY()
USphereComponent* MyCollisionComp;
이에 따라, 모든 멤버 변수와 UPROPERTY, 컴포넌트를 포함한 AMyActor의 복제가 생성됩니다.
AMyActor* CreateCloneOfMyActor(AMyActor* ExistingActor, FVector SpawnLocation, FRotator SpawnRotation)
{
UWorld* World = ExistingActor->GetWorld();
FActorSpawnParameters SpawnParams;
SpawnParams.Template = ExistingActor;
World->SpawnActor<AMyActor>(ExistingActor->GetClass(), SpawnLocation, SpawnRotation, SpawnParams);
}한 타입에서 다른 타입으로의 형변환
이 경우에는 이미 가지고 있는 컴포넌트를 구하여 특정 타입으로 형변환한 다음 조건부로 무언가를 수행합니다.
Unity
Collider collider = gameObject.GetComponent<Collider>;
SphereCollider sphereCollider = collider as SphereCollider;
if (sphereCollider != null)
{
// ...
}UE C++
UPrimitiveComponent* Primitive = MyActor->GetComponentByClass(UPrimitiveComponent::StaticClass());
USphereComponent* SphereCollider = Cast<USphereComponent>(Primitive);
if (SphereCollider != nullptr)
{
// ...
}블루프린트
블루프린트에서 Cast to 노드를 사용하여 형변환할 수 있습니다. 자세한 내용은 형변환 퀵스타트 가이드를 참조하세요.
GameObject/액터 소멸
GameObject/액터 소멸(1초 딜레이)
GameObject/액터 비활성화
Unity C# C# | UE C++ C++ | 블루프린트 |
컴포넌트에서 GameObject/액터를 액세스합니다.
Unity C# C++ | UE C++ C++ | 블루프린트 |
GameObject/액터에서 컴포넌트를 액세스합니다.
Unity
MyComponent MyComp = gameObject.GetComponent<MyComponent>();UE C++
UMyComponent* MyComp = MyActor->FindComponentByClass<UMyComponent>();블루프린트
GameObject/액터 찾기
Unity
// Find GameObject by name
GameObject MyGO = GameObject.Find("MyNamedGameObject");
// Find Objects by type
MyComponent[] Components = Object.FindObjectsOfType(typeof(MyComponent)) as MyComponent[];
foreach (MyComponent Component in Components)
{
// ...
}
UE C++
// Find UObjects by type
for (TObjectIterator<UMyObject> It; It; ++it)
{
UMyObject* MyObject = *It;
// ...
}
// Find Actor by name (also works on UObjects)
AActor* MyActor = FindObject<AActor>(nullptr, TEXT("MyNamedActor"));
블루프린트
GameObject/Actor에 태그 추가
Unity
MyGameObject.tag = "MyTag";UE C++
// Actors can have multiple tags
MyActor.Tags.AddUnique(TEXT("MyTag"));블루프린트
MonoBehaviour/ActorComponent에 태그 추가
Unity
// This changes the tag on the GameObject it is attached to
MyComponent.tag = "MyTag";UE C++
// Components have their own array of tags
MyComponent.ComponentTags.AddUnique(TEXT("MyTag"));GameObject/Actor와 MonoBehaviour/ActorComponent의 태그 비교
Unity
if (MyGameObject.CompareTag("MyTag"))
{
// ...
}
// Checks the tag on the GameObject it is attached to
if (MyComponent.CompareTag("MyTag"))
{
// ...
}UE C++
// Checks if an Actor has this tag
if (MyActor->ActorHasTag(FName(TEXT("MyTag"))))
{
// ...
}블루프린트
UE C++
// Checks if an ActorComponent has this tag
if (MyComponent->ComponentHasTag(FName(TEXT("MyTag"))))
{
// ...
}블루프린트
피직스: 리지드 바디 vs. Primitive Component
Unity에서는 GameObject에 피직스 특성을 제공하기 위해 리지드 바디(RigidBody) 컴포넌트를 어태치합니다.
언리얼 엔진에서는 어떤 프리미티브 컴포넌트(C++에서의 UPrimitiveComponent)든 피지컬 오브젝트를 나타낼 수 있습니다. 일반적인 프리미티브 컴포넌트에는 다음이 포함됩니다.
셰이프 컴포넌트(
USphereComponent,UCapsuleComponent등)'스태틱 메시(Static Mesh)' 컴포넌트
'스켈레탈 메시(Skeletal Mesh)' 컴포넌트
Unity에서는 콜리전과 시각화 역할을 별도의 컴포넌트로 분리하는 것과 달리, UE에서는 '잠재적 피지컬'과 '잠재적 표시' 콘셉트를 단일 프리미티브 컴포넌트에 결합합니다. 월드에 지오메트리가 있고 렌더링되거나 물리적으로 상호작용할 수 있는 컴포넌트는 모두 UPrimitiveComponent의 서브클래스입니다.
UE 콜리전 채널은 Unity의 레이어에 해당합니다. 자세한 내용은 콜리전 필터링을 참조하세요.
레이캐스트 vs. 레이트레이싱
Unity
GameObject FindGOCameraIsLookingAt()
{
Vector3 Start = Camera.main.transform.position;
Vector3 Direction = Camera.main.transform.forward;
float Distance = 100.0f;
int LayerBitMask = 1 << LayerMask.NameToLayer("Pawn");
RaycastHit Hit;
bool bHit = Physics.Raycast(Start, Direction, out Hit, Distance, LayerBitMask);
UE C++
APawn* AMyPlayerController::FindPawnCameraIsLookingAt()
{
// You can use this to customize various properties about the trace
FCollisionQueryParams Params;
// Ignore the player's pawn
Params.AddIgnoredActor(GetPawn());
// The hit result gets populated by the line trace
FHitResult Hit;
블루프린트
트리거 볼륨
Unity
public class MyComponent : MonoBehaviour
{
void Start()
{
collider.isTrigger = true;
}
void OnTriggerEnter(Collider Other)
{
// ...
}
UE C++
UCLASS()
class AMyActor : public AActor
{
GENERATED_BODY()
// My trigger component
UPROPERTY()
UPrimitiveComponent* Trigger;
AMyActor()
블루프린트
콜리전 응답 구성에 대한 자세한 내용은 콜리전을 참조하세요.
키네마틱 리지드바디
Unity
public class MyComponent : MonoBehaviour
{
void Start()
{
rigidbody.isKinematic = true;
rigidbody.velocity = transform.forward * 10.0f;
}
}UE C++
UCLASS()
class AMyActor : public AActor
{
GENERATED_BODY()
UPROPERTY()
UPrimitiveComponent* PhysicalComp;
AMyActor()
{
입력 이벤트
Unity
public class MyPlayerController : MonoBehaviour
{
void Update()
{
if (Input.GetButtonDown("Fire"))
{
// ...
}
float Horiz = Input.GetAxis("Horizontal");
float Vert = Input.GetAxis("Vertical");
UE C++
UCLASS()
class AMyPlayerController : public APlayerController
{
GENERATED_BODY()
void SetupInputComponent()
{
Super::SetupInputComponent();
InputComponent->BindAction("Fire", IE_Pressed, this, &AMyPlayerController::HandleFireInputEvent);
블루프린트
'프로젝트 세팅(Project Settings)'의 입력 프로퍼티는 다음과 같습니다.
UE 프로젝트에서 입력을 구성하는 방법에 대한 자세한 내용은 입력을 참조하세요.
추가 참고 자료
위의 콘셉트와 관련된 자세한 내용을 알아보려면 다음 섹션을 검토하는 것이 좋습니다.
게임플레이 프레임워크 - 게임 모드, 플레이어 상태, 컨트롤러, 폰, 카메라 등과 같은 핵심 게임 시스템을 다룹니다.
게임플레이 아키텍처 - 게임플레이 클래스 생성 및 구현에 대한 레퍼런스입니다.
게임플레이 튜토리얼 - 일반적인 게임플레이 엘리먼트를 재현하기 위한 튜토리얼입니다.