카테고리 없음

{TIL_250205} 폰 클래스로 드론 구현하기 (Drone Player)

raindrovvv 2025. 2. 5. 23:29

💭회고

나는 블로그에 학습 내용을 정리할 때, 핵심 개념을 먼저 이해하고, 코드와 함께 기능을 단계적으로 정리한다. 그래야 뭔가 더 머리에 잘 들어오는 것 같다. 오늘은 Pawn 클래스를 활용한 드론 구현을 정리한다.

드론은 기본적인 이동뿐만 아니라, 상하 이동, 회전(Roll), 비행 유지 기능을 포함해야 한다.이를 위해 PlayerController, Pawn, Input System을 연계해서 작업했다.

🗺️마인드맵

📒학습 내용 : Pawn 클래스로 드론 구현하기

1️⃣ 게임모드 설정

드론을 사용할 게임 모드를 설정해야 한다.

#include "SP_GameMode.h"
#include "SP_Pawn.h"
#include "SP_PlayerController.h"

ASP_GameMode::ASP_GameMode()
{
    DefaultPawnClass = ASP_Pawn::StaticClass();
    PlayerControllerClass = ASP_PlayerController::StaticClass();
}
  • DefaultPawnClass = ASP_Pawn::StaticClass(); → 기본 Pawn을 드론(여기서는 SP_Pawn)으로 설정한다.
  • PlayerControllerClass = ASP_PlayerController::StaticClass(); → 사용할 PlayerController를 지정하여, 입력을 처리할 수 있도록 설정한다.

이제 ASP_PlayerController에서 입력 처리 시스템을 설정해 보자.


2️⃣ PlayerController에서 입력 설정

드론을 조종하려면 PlayerController에서 키 입력을 처리해야 한다.

//플레이어 컨트롤러 헤더 中...

UPROPERTY(EditAnywhere, BlueprintReadWrite, Category = Input)  
UInputMappingContext* InputMappingContext;  

UPROPERTY(EditAnywhere, BlueprintReadWrite, Category = Input)  
UInputAction* MoveForwardAction;  
UPROPERTY(EditAnywhere, BlueprintReadWrite, Category = Input)  
UInputAction* MoveRightAction;  
UPROPERTY(EditAnywhere, BlueprintReadWrite, Category = Input)  
UInputAction* LookAction;  

// 드론 조작 추가 입력
UPROPERTY(EditAnywhere, BlueprintReadWrite, Category = Input)  
UInputAction* MoveUpAction;  // Space/Shift 상하 이동  
UPROPERTY(EditAnywhere, BlueprintReadWrite, Category = Input)  
UInputAction* RotateRollAction;  // Roll 회전  
UPROPERTY(EditAnywhere, BlueprintReadWrite, Category = Input)  
UInputAction* FlightHoldAction;  // 비행 유지

✔ 기본 이동(MoveForward, MoveRight, Look) + 드론 특화 기능 추가:

  • 기본적인 이동 및 카메라 조작 입력을 정의한다.
    • MoveForwardAction, MoveRightAction → 기본 WASD 이동.
    • LookAction → 마우스로 시점 이동.
  • 드론 조작을 위한 추가 입력을 정의한다.
    • MoveUpAction → Space를 사용해 상승 이동.
    • RotateRollAction → 마우스 휠 또는 키 입력을 통해 Roll 회전(기울기) 조작.
    • FlightHoldAction → Ctrl 키를 눌러 비행 유지(호버링) 기능 활성화.

🔗참고링크 : https://rhksgml78.tistory.com/543


✅ 입력 매핑 컨텍스트 활성화

void ASP_PlayerController::BeginPlay()
{
    Super::BeginPlay();

    if (ULocalPlayer* LocalPlayer = GetLocalPlayer())
    {
        if (UEnhancedInputLocalPlayerSubsystem* Subsystem =
            LocalPlayer->GetSubsystem<UEnhancedInputLocalPlayerSubsystem>())
        {
            if (InputMappingContext)
                Subsystem->AddMappingContext(InputMappingContext, 0);
        }
    }
}
  • BeginPlay()에서 입력 매핑 컨텍스트(IMC) 추가
  • Enhanced Input System을 사용하여 키 입력을 효율적으로 관리
✨입력 시스템을 활성화하기 위한 과정
1. GetLocalPlayer() → 현재 로컬 플레이어를 가져온다.
2. GetSubsystem<UEnhancedInputLocalPlayerSubsystem>() → Enhanced Input System을 가져온다.
3. Subsystem->AddMappingContext(InputMappingContext, 0);
   ➡️설정한 입력 매핑 컨텍스트를 추가하여 입력을 활성화한다.

✅ Input Mapping Context, Input Action 생성

✅ IA,IMC 설정

  • IA_Look (마우스 회전)
    • IA: Value Type 설정 → Axis2D
    • IMC 설정:

  • IA_MoveForward (W/S)
    • IA: Value Type 설정 → Axis2D
    • IMC 설정:

  • IA_MoveRight (D/A)
    • IA: Value Type 설정 → Axis2D
    • IMC 설정:

  • IA_MoveUp (Space, 상향 비행)
    • IA: Value Type 설정 → Axis1D (float)
  • IA_RotateRoll (마우스 회전, Roll 회전)
    • IA: Value Type 설정 → Axis2D (float)
    • 마우스 회전에 따라 Roll 회전이 기울어지도록 설정한다.
  • IA_FlightHold (왼쪽 Ctrl, 호버링)
    • IA: Value Type 설정 → bool
    • IMC 설정 :

🚨IMC 설정 시 주의점!
- 각 액션의 Input Mapping Context(IMC)를 설정할 때 올바른 키와 축을 매핑한다.
- 각 액션에 대응하는 함수를 정확히 구현하고, 적절한 매핑이 되도록 한다.
- 위 설정에 따라 정확한 매핑을 통해 원활한 동작이 이루어지도록 한다.

이제 Pawn 클래스를 구현하여 드론이 실제로 움직이도록 만들어 보자.


3️⃣ Pawn 클래스로 드론 구현

이제 본격적으로 드론의 움직임을 구현한다.
ASP_Pawn을 만들어 기본 이동 + 드론 특화 기능을 추가한다.

✅ Pawn의 기본 구성

class START_API ASP_Pawn : public APawn
{
    GENERATED_BODY()

public:
    ASP_Pawn();
    virtual void Tick(float DeltaTime) override;
    virtual void SetupPlayerInputComponent(class UInputComponent* PlayerInputComponent) override;
    
    void Move(const FVector& Direction, float AxisValue);
    
private:
    void MoveForward(const FInputActionValue& Value);
    void MoveRight(const FInputActionValue& Value);
    void MoveUp(const FInputActionValue& Value);
    void RotateRoll(const FInputActionValue& Value);
    void ToggleFlightHold(const FInputActionValue& Value);
};
  • Tick() 사용 → 매 프레임 중력, 기울기, 이동 적용
  • 이동 관련 함수들
    • MoveForward(), MoveRight(), MoveUp() : 기본 구성
    • RotateRoll(), ToggleFlightHold() (비행 유지) : 드론 특화

✅ 기본 이동

void ASP_Pawn::Move(const FVector& Direction, float AxisValue)
{
    if (FMath::IsNearlyZero(AxisValue))
    {
        Velocity = FMath::VInterpTo(Velocity, FVector::ZeroVector, GetWorld()->GetDeltaSeconds(), 2.0f);
        return;
    }
    float SpeedMultiplier = bIsGrounded ? 1.0f : 0.8f;
    FVector TargetVelocity = Direction * (AxisValue * MoveSpeed * SpeedMultiplier);
    Velocity = FMath::VInterpTo(Velocity, TargetVelocity, GetWorld()->GetDeltaSeconds(), 6.0f);
}
  • Velocity는 현재 속도이며, 부드럽게 가속/감속 되도록 보간(InterpTo) 사용.
  • bIsGrounded 여부에 따라 지상/공중 속도를 다르게 적용.

✅ 상승 이동 (Space)

void ASP_Pawn::MoveUp(const FInputActionValue& Value)
{
    if (bIsFlightHold) return;
    Move(FVector::UpVector, Value.Get<float>());
}
  • Space → 드론 상승
  • bIsFlightHold 상태면 상승 금지

✅ Roll 회전

void ASP_Pawn::RotateRoll(const FInputActionValue& Value)
{
    float AxisValue = Value.Get<float>();
    if (FMath::IsNearlyZero(AxisValue)) return;
    
    FRotator CurrentRotation  = GetActorRotation();
    CurrentRotation.Roll += AxisValue * RotationSpeed * GetWorld()->GetDeltaSeconds();
    SetActorRotation(CurrentRotation);
}
  • 마우스 휠 축 입력으로 기울기(Roll) 회전
  • 부드러운 회전 보간 적용

✅ 비행 유지(호버링) 기능

void ASP_Pawn::ToggleFlightHold(const FInputActionValue& Value)
{
    bIsFlightHold = !bIsFlightHold;
    if (bIsFlightHold)
    {
        HoverAltitude = GetActorLocation().Z;
        Velocity.Z = 0.0f;
    }
}
  • Ctrl 키로 호버링 토글
  • 현재 높이를 고정하여 유지

4️⃣ 중력 및 틸트 효과

✅ 중력 적용

void ASP_Pawn::ApplyGravity(float DeltaTime)
{
    if (bIsFlightHold) return;

    Velocity.Z += Gravity * DeltaTime;
    FVector NewLocation = GetActorLocation() + Velocity * DeltaTime;
    SetActorLocation(NewLocation);
}
  • 비행 유지 상태(bIsFlightHold)면 중력 제거
  • 중력 가속도 적용하여 자연스러운 하강

✅ 기울기(틸트) 효과

void ASP_Pawn::ApplyTiltEffect(float DeltaTime)
{
    FRotator TargetRotation = GetActorRotation();
    TargetRotation.Pitch = -Velocity.X * MaxTiltAngle;
    TargetRotation.Roll = Velocity.Y * MaxTiltAngle;

    SetActorRotation(FMath::Lerp(GetActorRotation(), TargetRotation, TiltSpeed * DeltaTime));
}
  • 이동 방향에 따라 자동으로 드론이 기울어짐
  • 부드러운 보간을 사용해 자연스럽게 회전

 

🟣오늘의 옵시디언 현황