본문으로 바로가기
반응형
동영상1

 

1. 블랙보드 세팅에 대하여... 

블랙보드(Blackboard) 에셋은 AI의 두뇌로 생각할 수 있으며, 비헤이비어 트리가 결정 내리는 데 사용하는 키(Key) 값을 저장한다. 

블랙보드는 필요에 따라 c++ 또는 블루프린트 안에서 Set, Get 할 수 있다. 

여기서 최상단에 SelfActor값과 TargetActor값의 거리를 service 하는데 이 두 값을 어디서 세팅하는지 알아보자. 

 

1.1. SelfActor

블랙보드 처음 생성하면 SelfActor가 나온다. 이 SelfActor는 그냥 현재 이 블랙보드를 사용하는 주체라고 생각하면 된다. 

C++ AAIController 클래스 내부에서 GetPawn()을 SelfActor에 세팅해주고 있다.

BlackboardKey.h
사진4.2 C++: KeySelf = SelfActor

1.2. TargetActor

TargetActor를 세팅하는 방법은 다양하게 있겠지만, 여기서는 UAIPerceptionComponent를 상속 받은 AI컨트롤러 속 내장함수 안에서 TargetActor를 지정해주고 있다. 

UAIPerceptionComponent를 상속 받은 AI컨트롤러 속에 OnTargetPerceptionUpdated가 있다. 

이 함수는 플레이어(적)를(을) 봤을 때, 소리를 들었을 때, 시야를 놓쳤을 때 등등 상황에 따라 이벤트가 호출되고, 여기서는 OnEnemyPerceptionUpdated를 바인딩해뒀다. 이때 Actor가 존재할 때, 블랙보드에 Set 해준다. 

사진4.1 c++ : SetTargetActor

 

 

 

 

사진1

[ 사진1 ] BT 시작 Root. 모든 트리에서 쓰는 값을 세팅해 주자. 

 

1.1. 왜 Selector일까? (Composite 중 Sequence가 아니라 Selector로 쓴 이유)

- 여러 행동 후보중 상황에 맞는 하나를 고르는 것.

 

1.2. BTService_GetDistToTarget이 Selector안에 있는 이유

- 트리 전체가 타겟 거리 정보를 공유해야 하고, 밑에 있는 조건들이 모두 이 값을 봐야 한다. 

- 나중에 거리 계산 방식을 바꾸고 싶어도 서비스 한 군데만 고치면 전체 로직이 따라가게 된다. 

 

1.3 위에 블랙보드에서 세팅한 값 ( SelfActor, TargetActor )의 거리를 계속해서 구해서 블랙보드 값에 셋 해준다. 

여기서 Conrtrolled Pawn이 아니라 블랙보드의 SelfActor를 하더라도 같은 결과가 나온다. 

사진1.1

(최적화가 중요한 실무에서는 네이티브 비헤이비어트리 서비스로 변경하는것이 더 좋다. C++로 만들어라.) 

 

 

 

사진2

[ 사진 2 ] 타깃이 죽었는지 확인해 보자. 

2.1. BTDecorator_ShouldAbortAllLogic

In Target Actor Key를 TargetActor로 지정해 두고, 데코레이션 안에서 조건을 확인한다. 내가 공격하려는 대상이 죽었을 때, 이 모든 비헤이비어트리를 멈추기 위한 동작이다.  

 

 

 

사진3

[ 사진3 ] 

3.1. 왜 Sequence일까? (Composite 중 Sequence가 아니라 Selector로 쓴 이유)

- 중간에 하나라도 실패하면 전체 패턴을 실패로 보고, 상위 Selector가 다음 브렌치로 넘어갈 수 있게 하기 위해서이다. 

3.2. Decorator : Am i under attack? BTDecorator::DoesActorHaveTag 

- 해당 엑터 In Actor Key To Check가 Tag To Check에 저장한 태그를 가지고 있는지 반환값을 던져준다.

사진3.1 : BTDecorator::DoesActorHaveTag 

3.3 Decorator: Is the target still in range? 

- DistToTarget이 Is Less Than or Equal To: 350 보다 작거나, 같으면 True!

3.4 Task : 실제로 작업을 하는 일을 하는 Task:: BTTask_ActivateAbilityByTag

적 캐릭터에게 melee 능력을 실행시킨다. 

 

 

 

 

사진4

[ 사진 4 ]

4.1. Am i in melee attack range?

Decorator :: Blackboard : Target과 200 거리에 있다면

4.2. Decorator :: Cooldown

1.50초간 한 번 실행하면 조건이 되더라도 실행 x  

4.3. Decorator :: Coditional Loop

IsHit 블랙보드 변수가 false 일 때만, 아래 Task가 실행된다. 

(IsHit는 EnemyHitReact Ability에서 True로 켜지고, BTTask_ToggleStrafingState에서 꺼준다. 협업에서 어떻게 블랙보드의 값을 Set 하는지 모르겠다. 블랙보드는 참조하는 곳을 찾기가 너무 어렵다..)

 

 

 

 

사진5

[ 사진 5 ] 

5.1.  Run EQS Query (EQS Query / Unreal 4) 

- 플러그인(Plugins)에서 Environment Query Editor옵션을 활성화해야 한다. 

EQS쿼리는 AI캐릭터가 플레이어를 공격할 시야가 확보되는 최적의 위치, 가장 가까운 체력 또는 탄약 아이템 등등 조건에 맞는 공간을 뽑아서 찾도록 지시하는 시스템이다. 

- Environment Query

- EnvQueryContext_BlueprintBase

EQS 시스템에서 다양한 테스트를 적용할 때 레퍼런스로 사용한다. (블루프린트보다 C++콘텍스트를 생성하는 것이 더 최적화이다)  여기서는 설정한 TargetActor를 중심을 두고 조건에 맞는 영역을 만든다 

사진5.1 Enviorment Query
사진 5.2 EnvQueryContext_BlueprintBase

 

 

 

사진6

[ 사진 6 ] 거리가 600보다 멀어져 있을 때

BTTask_ToggleStrafingState Task를 이용하여 Strafe를 멈추고, 타깃에게 이동한다. 

 

 

이렇게 몬스터의 기본적인 AI를 만들었다. 

끝.

반응형