[UE5] Boss - Melee Attack Skill

윤정민·2023년 4월 28일
0

1. 개요

Melee Attack을 구현하는 방법은 다양하다. 이번 포스트에서는 fist에 collision component를 붙여 공격하는 법과 Trace를 사용하는 방법을 알아보자.

2. Collision Component

2.1. 초기 설정

  • 양쪽 주먹에 Box Collision을 붙여주자
    • Skeletal에 들어가 Hand 왼쪽 오른쪽 모두 소켓을 생성한 뒤 해당 소켓에 붙이면 됨
  LeftBox->AttachToComponent(GetMesh(), AttachmentRules, "LeftFist");
  RightBox->AttachToComponent(GetMesh(), AttachmentRules, "RightFist");

  • 해당 콜리전을 OverlapAll로 설정
LeftBox->SetCollisionProfileName(TEXT("OverlapAll"));
RightBox->SetCollisionProfileName(TEXT("OverlapAll"));
  • 콜리전이 overlap될 때 공격을 실행할 수 있도록 공격함수를 bind 하자
LeftBox->OnComponentBeginOverlap.AddDynamic(this, &AMonsterBase::OnOverlapBegin);
RightBox->OnComponentBeginOverlap.AddDynamic(this, &AMonsterBase::OnOverlapBegin);

2.2 콜리전 활성화

항상 주먹에 닿일 때 공격이 된다면 이상할 것이다. 그러니 공격시에만 콜리전을 활성화 시켜주자

  • 콜리전 활성화
LeftBox->SetGenerateOverlapEvents(true);
RightBox->SetGenerateOverlapEvents(true);
  • 콜리전 비활성화
LeftBox->SetGenerateOverlapEvents(false);
RightBox->SetGenerateOverlapEvents(false);
  • Animation notify
    • Attack Notify: Enable Collision
    • AttackEnd Notify: Disable Collision

3.Trace 생성

3.1. Trace 생성 타이밍

  • ChargedAtk Notify가 실행될 때 Collsion을 생성

3.2. Trace 생성 위치

나는 콤보 공격으로 구성했기 때문에 왼손으로 공격시엔 왼손 위치에 Trace를 생성하고 오른손으로 공격시엔 오른손 위치에 Trace를 생성해야 한다.

  • 구현방법: Montage slot Name으로 해당 공격이 어느손으로 진행되고 있는지 판별
switch (FistIndex)
{
case 1:
	FistLoc = GetMesh()->GetSocketLocation(FName("LeftFist"));
	break;
case 0:
	FistLoc = GetMesh()->GetSocketLocation(FName("RightFist"));
	break;
}

3.3. Trace 생성

  • SweepSingleByChannel: Trace를 생성하는 함수
  • 구한 위치에 trace를 생성
FHitResult HitResult;
FCollisionQueryParams Params(NAME_None, false, this);
bool bResult = GetWorld()->SweepSingleByChannel(
	HitResult,
	FistLoc,
	FistLoc+ 50.f,
	FQuat::Identity,
	ECollisionChannel::ECC_GameTraceChannel1,
	FCollisionShape::MakeSphere(50.f),
	Params
);

3.4. 공격

  • 해당 Trace가 인식한 객체에 Damage를 입힘
if (bResult)
{
	if (HitResult.GetActor()->IsValidLowLevel())
	{
		FDamageEvent DamageEvent;
		HitResult.GetActor()->TakeDamage(ChargedAttackDamage, DamageEvent, GetController(), this);
	}
}

3.5. 참고

Trace가 생성되는 모양을 보고싶다면 DrawDebug로 똑같이 그려줘야된다. 좀 귀찮다.. 하는김에 결과에 따라 색도 변경해보자

	FColor DrawColor = bResult ? FColor::Green : FColor::Red;
	DrawDebugCapsule(
		GetWorld(),
		TargetLoc,
		100.f,
		100.f,
		FRotationMatrix::MakeFromZ(GetActorForwardVector()).ToQuat(),
		DrawColor,
		false,
		3.f);

4. 스킬 구현

멀리있는 플레이어에게 점프하여 공격하는 스킬을 구현하기 위해 필요한 기능을 생각해보자. 해당 위치로 이동하여 똑같이 Trace를 생성하면 된다.

4.1. 해당 위치로 이동

  • MoveComponentTo: Component를 원하는 위치로 이동해주는 함수
  • TargetLoc: player의 위치
  • Rotation: 몬스터가 Player를 바라보는 Rot로 설정(PlayerLoc-MonsterLoc)
    FLatentActionInfo Info;
	Info.CallbackTarget = this;
	UKismetSystemLibrary::MoveComponentTo(
		GetCapsuleComponent(),
		TargetLoc,
		(Target->GetActorLocation() - GetActorLocation()).Rotation(),
		true,
		true,
		0.35f,
		false,
		EMoveComponentAction::Type::Move,
		Info);
profile
그냥 하자

0개의 댓글