4주차 Unreal/C++ 과제 5 (2)
4주차 Unreal/C++ 과제 5 (2)
언리얼 엔진 맛보기 과제
그냥 LOG로만 찍으면 아쉬우니
가벼운 Character 클래스를 만들어 처리해 보았다
구현 기능
랜덤한 위치로 ‘이동’
(이동 예상 지점에 ‘화살표’ 이펙트)
이벤트 발생시
캐릭터 머리 위에 ‘이펙트’ 발생
클래스 설명과 기타 파일
- 클래스
MyCharacter
- 과제에서 요구하는 지점 이동, 로깅, 이벤트 체크 등에 대한 구현
- 유틸 파일
LogTests
- 커스텀 Log 인 LogCoord 생성
MyUtils
- namespace와 ForceInline으로 묶은 기타 유틸리티 함수 묶음 파일
트러블 슈팅 - UAIBlueprintHelperLibrary::SimpleMoveToLocation 가 제대로 동작하지 않는다?
일단 내 방식은
Unreal 예제의 TopDownProject 방식의 일부 방식을 카피하여 구현하였다
대신,
직접 플레이어를 구현할 필요는 없고
(입력이 필요 없기에!)
그냥 캐릭터만 움직이고 싶었기에
그냥 PlayerController의 이러한 기능만 사용하였다
if (AController* controller = GetController())
{
UAIBlueprintHelperLibrary::SimpleMoveToLocation(controller, NextCoord);
UNiagaraFunctionLibrary::SpawnSystemAtLocation(controller, FXCursor, NextCoord, FRotator::ZeroRotator, FVector(1.f, 1.f, 1.f), true, true, ENCPoolMethod::None, true);
}
UAIBlueprintHelperLibrary::SimpleMoveToLocation
- 간단한 NavMesh 기반 이동 함수
(내부적으로 AIController -> MoveToLocation 사용한 래핑 함수) - 목적지까지 이동시키는 용도
(도착한 후의 Delegate 바인딩 등은 없다)
UNiagaraFunctionLibrary::SpawnSystemAtLocation
- 월드에 나이아가라 시스템을 스폰하는 함수
(BP의 SpawnSystem at location 노드와 동일)
문제 1 - ‘이동’ 과 ‘이펙트’가 안나온다?
거리 검사 코드를 이용하여
다음 목적지 도착을 ‘체크’하였는데
‘이동’과 ‘이펙트 출력’이 제대로 되지 않았다
처음에는 ‘NavMesh’관련 문제인줄 알고
NavMesh Volumn을 깔았으나
여전히 먹히지 않는다…
알고보니…
-
Character에 ‘컨트롤러’가 Possess해야 GetController가
‘해당’ 컨트롤러를 반환한다 -
Player Controller는 기본적으로 GameMode가 게임 시작시
CreatePlayerController 등으로 만들어 주며
Possess 설정에 따라서 Player 로 지정한 캐릭터에 빙의시켜 준다
별도의 컨트롤러 설정을 하지 않았기에 발생했던 문제였다
그런데 딱히, Input 설정을 할 필요는 없었기에
Player Controller를 설정하는 것은 다소 과하다고 생각하였다
해결법
그렇기에 AIController를 사용하였다
(기본 AIController 클래스를 AIControllerClass에 설정)
그리고 스폰되거나, 에디터에서 배치된 경우에 Possess되도록
AutoPossessAI 옵션을 설정하였다
AIControllerClass = AAIController::StaticClass();
AutoPossessAI = EAutoPossessAI::PlacedInWorldOrSpawned;
문제 2 - ‘거리 검사’가 제대로 안된다?
목적지 도착여부를 확인하는 거리 검사 코드는 이렇다
bool AMyCharacter::CheckArrive()
{
FVector nowLoc = GetActorLocation();
if (Task5::Utils::GetDistance(nowLoc, NextCoord) <= 10.0)
return true;
return false;
}
현재 위치와 다음 목적지의 거리를 2차원 거리를 구하여
(피타고라스)
일정 범위내로 들어오면 true를 반환한다
그런데
저 10.0 이 비교적 널널하다고 생각하였으나
자꾸 이동이 false가 되며,
목적지에 도달하지 않는다고 판정되었다
정확히는
목표 근처까지 가는데
근처에 와서 이동이 종료되며
목적지에 제대로 ‘도착’이 안된 상황이였다
알고보니…
-
- UAIBlueprintHelperLibrary::SimpleMoveToLocation는
- ‘캡슐 콜리전의 중심’이 일정거리 이상이면 종료 판정
- UAIBlueprintHelperLibrary::SimpleMoveToLocation는
나는 GetActorLocation을 기반으로 위치를 재고 있었고
해당 함수는 캡슐 콜리전이 ‘일정거리’까지 도달하면 종료하여
두 거리간의 미세한 차이가 존재하였다
해결법
따라서 캡슐 콜리전의 Radius를 거리 측정에 포함하였다
bool AMyCharacter::CheckArrive()
{
FVector nowLoc = GetActorLocation();
if (Task5::Utils::GetDistance(nowLoc, NextCoord) <= 10.0 + GetCapsuleComponent()->GetScaledCapsuleRadius())
return true;
return false;
}
이제 영상처럼 잘 작동한다!
아니면 위에 설명한 ‘일정거리’를 코드로 직접 지정해줄 수도 있다
if (AAIController* AI = Cast<AAIController>(GetController()))
{
FAIMoveRequest Req(NextCoord);
Req.SetAcceptanceRadius(50.f); // 원하는 거리
AI->MoveTo(Req);
}
댓글남기기