Unreal Works/Odyssey

[Unreal Odyssey Project] 이동 애니메이션

likepint 2025. 3. 4. 23:45


ESpeedType

UENUM(BlueprintType)
enum class ESpeedType : uint8
{
	Walk = 0, Sprint, Jog, CrouchWalk, MAX
};

UCLASS()
class ODYSSEY_API UCMovementComponent : public UCBaseComponent
{
	GENERATED_BODY()

private:
	UPROPERTY()
	float Speed[(int32)ESpeedType::MAX] = { 200, 450, 500, 250 };
	
public:
	UCMovementComponent();

protected:
	virtual void BeginPlay() override;

public:
	virtual void TickComponent(float DeltaTime, ELevelTick TickType, FActorComponentTickFunction* ThisTickFunction) override;
    
}
SpeedType의 경우 Enum class를 사용하여 Walk, Sprint, Jog, CrouchWalk로 나누어 정의
Enum class를 사용하게 되면 Enum의 크기로 배열을 생성하여 이름으로 배열 접근이 가능하게 됨

Enhanced Input Bind

void UCMovementComponent::OnBindEnhancedInputSystem(UEnhancedInputComponent* InEnhancedInput)
{
	InEnhancedInput->BindAction(IA_Movement, ETriggerEvent::Triggered, this, &UCMovementComponent::OnMovement);
	InEnhancedInput->BindAction(IA_Movement, ETriggerEvent::Completed, this, &UCMovementComponent::OffMovement);
}
MovementComponent에서 이동 입력을 받을 수 있도록 캐릭터에서 OnBindEnhancedInputSystem()을 호출하도록 설정

On, OffMovement

void UCMovementComponent::OnMovement(const FInputActionValue& InVal)
{
	if (!bMovable) return;

	auto lambda = [&]()
		{
			if (false == OwnerCharacter->GetCharacterMovement()->IsCrouching())
				OnJog();
		};

	if (!GetWorld()->GetTimerManager().IsTimerActive(HSpeed))
		GetWorld()->GetTimerManager().SetTimer(HSpeed, lambda, 2, false);

	// 캐릭터의 정면 방향을 가져오기 위해 컨트롤러의 회전 값을 구해서 Z축만을 사용
	FRotator rot = FRotator(0, OwnerCharacter->GetControlRotation().Yaw, 0);

	// Forward
	OwnerCharacter->AddMovementInput(FQuat(rot).GetForwardVector(), InVal.Get<FVector2D>().X);

	// Right
	OwnerCharacter->AddMovementInput(FQuat(rot).GetRightVector(), InVal.Get<FVector2D>().Y);

}

void UCMovementComponent::OffMovement(const FInputActionValue& InVal)
{
	if (GetWorld()->GetTimerManager().IsTimerActive(HSpeed))
		GetWorld()->GetTimerManager().ClearTimer(HSpeed);

	OnSprint();

}
Enhanced Input으로 이동의 입력 값을 받는 On, OffMovement 함수로,
기존의 레퍼런스와 동일하게 일정 시간(2초)동안 전력질주를 수행하게 되면, Jog 애니메이션 실행하도록 설정
Timer 함수를 이용하여 람다식을 받는 방식으로 구현
OffMovement 호출 시 타이머가 활성화 되어 있다면, 초기화 시켜주는 방식으로 구현

Lambda 식

auto lambda = [&]()
	{
		if (false == OwnerCharacter->GetCharacterMovement()->IsCrouching())
			OnJog();
	};
앉은 상태가 아니라면 Jog 애니메이션을 출력할 수 있도록 설정하는 람다 함수

Movement_Stand Animation


Movement_Walk Animation


Movement_Crouch Animation

⭕ Walk, Sprint, Run, Crouch 애니메이션 작업
❌ Turn 애니메이션 추가하고 싶었지만, 실패 ( 이유 : 루트모션이 있는 Turn 애니메이션을 찾을 수 없었음 )
      -> 잠깐 보류