[UE5] 오토타겟팅 구현 | AutoTargeting

seunghyun·2024년 5월 9일
0

ProjectGO

목록 보기
4/7

📌 1차 요구사항

  • 스킬마다 오토타겟팅 여부를 지정하고,
  • 스킬마다 각각 다른 특정 반경/범위 내에 누군가 있는지,
  • 있다면 누구인지 알아내기

ProjectGO에는 4개의 직업 캐릭터가 각각 고유한 스킬 5개를 가지고 있다. 각 스킬은 UGOSkillBase라는 이름의 UObject 를 상속받는 UObject 인스턴스이다.

이 UGOSkillBase 라는 UObject는 SkillStat이라는 구조체 정보를 가지고 있고
이 SkillStat 에는 아래 3가지의 정보가 있다.

...
UENUM(BlueprintType)
enum class EAutoDetectionType : uint8
{
	None = 0, // 없음
	Radius = 1, // 반경
	RadiusDegree = 2, // 반경 + 각도
};
...

에디터에서 데이터 테이블을 통해 각 스킬마다 이 3가지의 정보를 커스터마이징 할 수 있다.

...
AutoDetectionType(EAutoDetectionType::None),
DetectionRadius(200.0f),
DetectionDegree(45.0f)
...

UGOSkillBase를 상속받는 각 스킬 인스턴스마다 Target 정보를 가지고 있으면 좋겠다. GOSkillCastComponent에서 EAutoDetectionType 에 따라서 오토타겟팅이 가능하도록 설정해주고 스킬의 타겟을 설정하는 로직을 작성해보았다.


고려한 점

  • DetectClosestTarget (float Radius)

    • 단순히 지정된 반경 내의 적을 탐지 (반경: SkillStat에 지정한 DetectionRadius)

    • 플레이어 위치를 중심으로 지정된 반경 내에 있는 적 중에서 가장 가까운 적을 return 하며

    • OverlapMultiByChannel 을 사용하여 주변의 적들을 감지하고, 가장 가까운 적을 찾는다.

  • DetectClosestTargetRadiusDegreeBase (const FVector2D& Dir, float Radius, float Degree)

    • 플레이어의 시선 방향과 일치하는 각도 내의 액터를 적으로 한다.

    • 플레이어가 정면을 바라보는 방향의 적만을 공격 대상으로 설정한다.


코드

// GOSkillCastComponent.cpp

...
	if (CurrentSkill)
	{
		AGOCharacterBase* Target = nullptr;
		FVector ForwardVector = GetOwner()->GetActorForwardVector();
		FVector2D AttackDirection(ForwardVector.X, ForwardVector.Y); // Z 무시

		switch (CurrentSkill->GetAutoDetectionType())
		{
		case EAutoDetectionType::Radius:
			Target = DetectClosestTarget(CurrentSkill->GetAutoDetectionRadius());
			break;
		case EAutoDetectionType::RadiusDegree:
			Target = DetectClosestTargetRadiusDegreeBase(AttackDirection, CurrentSkill->GetAutoDetectionRadius(), CurrentSkill->GetAutoDetectionDegree());
			break;
		case EAutoDetectionType::None:
		default:
			Target = nullptr;
			break;
		}

		CurrentSkill->SetTarget(Target);  // UGOSkillBase에 추가한 SetTarget 메소드를 가정
		CurrentSkill->StartCast();  // 타겟이 설정된 후 캐스팅 프로세스 시작
	}
...
// GOSkillBase.h
 ...
void UGOSkillBase::SetTarget(AGOCharacterBase* NewTarget)
{
	TargetCharacter = NewTarget;  // 대상 캐릭터 설정
	UE_LOG(LogTemp, Warning, TEXT("[UGOSkillBase::SetTarget] TargetCharacter : %s "), *TargetCharacter.GetName());

}

결과

DetectClosestTargetRadiusDegreeBase을 발동시키는 타입의 스킬을 사용했을 때 위와 같은 부채꼴 Log를 확인할 수 있는데, 위 사진에서는 부채꼴 내에 액터가 없어어 타겟 액터가 None이라는 로그가 출력되었다.
이번에는 오토 타겟팅 감지 각도 내 (=부채꼴 내) 에 액터가 있어서 타겟 액터의 이름이 출력되는 것을 확인할 수 있다.

+) 수정 필요: 아래 2차 요구사항에 기재


📌 2차 요구사항

DamageRange 내 타겟 액터가 있다면 타겟 액터가 있는 쪽으로 방향을 변경하고 그 액터를 향해서 공격하기

Radius, RadiusDegree 타입의 스킬이라면 해당 스킬 인스턴스에 캐싱된 타겟 액터를 향해서 바라보고 스킬을 사용할 수 있도록 설정했다.

결과 화면 (GIF)

  1. Radius 타입인 탱커의 LMB 스킬
  2. Radius 타입인 힐러의 LMB 스킬
  3. RadiusDegree 타입인 원딜의 LMB 스킬

0개의 댓글

관련 채용 정보