본문 바로가기
🌐 유니티 (Unity)

Day 36 - AI 네비게이션

by shin0707 2024. 6. 3.
728x90
반응형

  • 주제

>> NavMesh

>> NavMesh Agent

>> NavMesh Obstacle

(캐릭터를 목표 지점까지 이동)

(적 몬스터가 일정 지역에만 머무름)


  • 공부내용

1. NavMesh

: 게임 세계에서 이동 가능한 영역(캐릭터가 움직일 수 있는 바닥과 장애물을 포함한 3D 공간)

 

- NavMesh Baking : NavMesh 공간을 생성하는 과정

 

- NavMesh Agent : NavMesh 공간에서 경로를 탐색하고 이동할 수 있는 AI 캐릭터

 

- NavMesh Obstacle: NavMesh 공간에서 이동할 수 없는 장애물


예제 1: 캐릭터를 목표 지점까지 이동

- 바닥 생성: 바닥 역할을 할 Plane을 생성 ('GameObject > 3D Object > Plane')

 

- NavMesh 생성: Plane 선택 -> 'Inspector' 창에서 'Navigation Static' 체크 ->

메뉴 -> Window -> AI -> Navigation -> Bake 탭 -> Bake 버튼 클릭

 

- NavMesh Agent 설정: 이동할 캐릭터 추가 ('GameObject > 3D Object > Capsule')

Capsule 선택 -> 'Inspector' 창에서 'Add Component' 클릭 -> 'NavMesh Agent' 추가

 

- 목표 지점 설정: 이동 목표 지점을 표시할 오브젝트 추가 ('GameObject > 3D Object > Sphere')

 

- 스크립트 작성: Capsule에 추가 -> 'Inspector' 창에서 'Target' 필드에 Sphere 설정

using UnityEngine;
using UnityEngine.AI;

public class MoveToTarget : MonoBehaviour
{
    public Transform target; // 목표 지점

    private NavMeshAgent agent; // 네브메쉬 에이전트

    void Start()
    {
        agent = GetComponent<NavMeshAgent>(); // 네브메쉬 에이전트 초기화
    }

    void Update()
    {
        if (target != null) // 목표 지점 확인
        {
            agent.SetDestination(target.position); // 목표 지점 설정
        }
    }
}

예제 2: 적 몬스터가 일정 지역에만 머무름

- 바닥 생성: 바닥 역할을 할 Plane을 생성 ('GameObject > 3D Object > Plane')

 

- NavMesh 생성: Plane 선택 -> 'Inspector' 창에서 'Navigation Static' 체크 ->

메뉴 -> Window -> AI -> Navigation -> Bake 탭 -> Bake 버튼 클릭

 

- NavMesh Agent, Obstacle 설정: 적 몬스터 추가 ('GameObject > 3D Object > Capsule') ->

Capsule 선택 -> 'Inspector' 창에서 'Add Component' 클릭 -> 'NavMesh Agent' 추가 ->

몬스터가 가지 못할 지역을 표시할 Obstacle 추가 ( 'GameObject > 3D Object > Cube' ) ->

Cube를 적절한 위치에 배치하여 장애물 역할을 하게 함 -> 

Cube  선택 -> 'Inspector' 창에서 'Add Component' 클릭 -> 'NavMesh Obstacle' 추가 ->

'Carve' 옵션 체크

 

- 경계 설정: Plane 위에 빈 GameObject를 추가 (GameObject > Create Empty -> WanderArea로 이름 설정) ->

WanderArea  선택 -> 'Inspector' 창에서 'Box Collider' 추가하여 적절한 크기로 조정

 

- 스크립트 작성: Capsule(적 몬스터)에 추가 -> 'Inspector' 창에서 'wanderArea' 필드에 WanderArea 드래그하여 설정

using UnityEngine;
using UnityEngine.AI;

public class MonsterWander : MonoBehaviour
{
    public Transform wanderArea; // 배회 영역
    private NavMeshAgent agent; // 네브메쉬 에이전트
    private Vector3 wanderTarget; // 배회 목표 지점

    void Start()
    {
        agent = GetComponent<NavMeshAgent>(); // 네브메쉬 에이전트 초기화
        SetNewWanderTarget(); // 새로운 배회 목표 지점 설정
    }

    void Update()
    {
        if (!agent.pathPending && agent.remainingDistance < 0.5f) // 경로 계산 대기 상태 확인 및 남은 거리 확인
        {
            SetNewWanderTarget(); // 새로운 배회 목표 지점 설정
        }
    }

    void SetNewWanderTarget()
    {
        Vector3 randomPoint = wanderArea.position + new Vector3(
            Random.Range(-wanderArea.localScale.x / 2, wanderArea.localScale.x / 2), // 무작위 x 좌표
            0, // y 좌표
            Random.Range(-wanderArea.localScale.z / 2, wanderArea.localScale.z / 2)  // 무작위 z 좌표
        );

        NavMeshHit hit; // 네브메쉬 히트
        if (NavMesh.SamplePosition(randomPoint, out hit, 1.0f, NavMesh.AllAreas)) // 네브메쉬 샘플 위치 확인
        {
            wanderTarget = hit.position; // 배회 목표 지점 설정
            agent.SetDestination(wanderTarget); // 목표 지점으로 이동 설정
        }
    }
}

 

728x90
반응형

loading