Notice
Recent Posts
Recent Comments
Link
«   2024/05   »
1 2 3 4
5 6 7 8 9 10 11
12 13 14 15 16 17 18
19 20 21 22 23 24 25
26 27 28 29 30 31
Archives
Today
Total
관리 메뉴

codingfarm

네비게이션 메쉬(Navigation Mesh) 본문

Unity3d

네비게이션 메쉬(Navigation Mesh)

scarecrow1992 2022. 2. 22. 00:35

https://docs.unity3d.com/ScriptReference/AI.NavMeshAgent.html

유니티에서 자체적으로 제공해주는 경로찾기기능이다.

발판 역할을 할 plane과 장애물이 될 cube들이 놓여 있다.

2개의 오브젝트 모두 Navigation Static을 활성화 하고

Navigation Area를 상자는 "Not Walkable"로, 판자는 Walkable로 설정한다.

 

Bake 탭에서 하단의 "Bake" 버튼을 누르면 navmesh가 설정된다. 

NavMeshAgent 컴포넌트를 가진 게임 오브젝트는 위의 navmesh 위에서 경로를 찾을 수 있게 된다.

 

기본적인 활용법은 아래와 같다.

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
using UnityEngine;
using System.Collections;
using UnityEngine.AI;
 
[RequireComponent (typeof (NavMeshAgent))]
public class Enemy : LivingEntity {
 
    NavMeshAgent pathfinder;
 
    void Awake() {
        pathfinder = GetComponent<NavMeshAgent> ();
        pathfinder.speed = 5;
        
        if (GameObject.FindGameObjectWithTag ("Player"!= null) {
            hasTarget = true;
            
            target = GameObject.FindGameObjectWithTag ("Player").transform;
            targetEntity = target.GetComponent<LivingEntity> ();
            
            myCollisionRadius = GetComponent<CapsuleCollider> ().radius;
            targetCollisionRadius = target.GetComponent<CapsuleCollider> ().radius;
        }
    }
 
    IEnumerator Attack() {
        currentState = State.Attacking;
        pathfinder.enabled = false;
 
        whiile(true){
            // attack code
            yield return null;
        }
        
        currentState = State.Chasing;
        pathfinder.enabled = true;
    }
 
    
    IEnumerator UpdatePath() {
        float refreshRate = .25f;
 
        while (hasTarget) {
            if (currentState == State.Chasing) {
                Vector3 dirToTarget = (target.position - transform.position).normalized;
                Vector3 targetPosition = target.position - dirToTarget * (myCollisionRadius + targetCollisionRadius + attackDistanceThreshold/2);
                if (!dead) {
                    pathfinder.SetDestination (targetPosition);
                }
            }
            yield return new WaitForSeconds(refreshRate);
        }
    }
}
cs

NavMeshAgent 의 속도를 설정한다. 그리고 UpdatePath가 호출 될때마다 SetDestination 함수를 통해 목표지까지 경로가 재설정된다. 이 함수는 적지않은 연산량이 필요하므로 위 처럼 coroutine을 통해 시간 제한을 두거나 아니면, 특수한 조건이 발생 될때만 호출되도록 한다.

공격등 특정한 행동을 하는 도중엔 추적이 필요 없으므로 일시적으로 NavMeshAgent의 enabled를 false 상태로 빠뜨려 움직임을 멈춘다.

 

 

 

위 Nav Mesh는 런타임 도중 베이킹이 불가능 하다는 단점이 있다.

그렇기 때문에 도중에 장애물이 추가되는 등의 상황에 대한 대응이 곤란하다.

유니티에서는 이를 해결하기 위한 오픈소스를 제공해주므로 참고해보자.

https://github.com/Unity-Technologies/NavMeshComponents

https://www.youtube.com/watch?v=mV-Uh_FEBn4

https://algorfati.tistory.com/25

 

 

 

 

 

 

 

'Unity3d' 카테고리의 다른 글

input event 인터페이스 관련  (0) 2022.09.17
애니메이션  (0) 2022.02.22
상속  (0) 2022.02.21
시간  (0) 2022.02.21
생성  (0) 2022.02.21
Comments