我正在创建一个巡逻的AI,该AI可聚集到玩家并在Unity 3D中跟随它们

时间:2019-05-02 01:15:51

标签: c# unity3d artificial-intelligence

我无法保持此方法运行。它运行1帧,然后它们会自行关闭。我在确定使它保持运行的逻辑上遇到麻烦。是的,敌人确实会检测玩家是否在视野内,并且在与墙壁碰撞时会停止,并且在玩家离开视场时也不会检测到玩家。

我已经尝试过更改if语句,但是总的来说,使代码基于FOV对撞机中现有的播放器运行非常重要。这个问题非常具体,所以我不知道该做些什么。

using System.Collections;
using System.Collections.Generic;
using UnityEngine;
using UnityEngine.AI;

[RequireComponent(typeof(Animator))]
[RequireComponent(typeof(NavMeshAgent))]
[RequireComponent(typeof(AudioSource))]
public class EnemyAI : MonoBehaviour
{
    public float patrolSpeed, chaseSpeed, chaseWaitTime, patrolWaitTime, castRadius;
    public Transform[] wayPoints, wayPOI;
    public Transform player;
    public Animation flinch, die;
    public AudioClip grunt, callOut, death;
    public LayerMask mask;
    public PlayerCheck check;
    private float chaseTimer, patrolTimer, wanderTimer;
    private int destIndex, destInit, destStart, health;
    private bool playerIn;
    protected string aggro, resting, warned, sawPlayer;
    protected bool patroling;
    public bool aggress;
    private NavMeshAgent agent;
    private Transform playerLP;
    private Vector3 startPos;
    private Animator anim;
    private AudioSource aud;
    MeshCollider fieldOfView;
    void Awake()
    {
        //patroling = true;
        startPos = transform.position;
        destInit = destIndex;
        agent = GetComponent<NavMeshAgent>();
        agent.autoRepath = true;
        agent.autoBraking = true;
        fieldOfView = transform.GetChild(0).GetComponent<MeshCollider>();
        if (fieldOfView == null)
        {
            Debug.LogError("The first object MUST be FOV, otherwise the script will not work correctly. 1");
        }
        check = GameObject.FindObjectOfType<PlayerCheck>();
        anim = GetComponent<Animator>();
    }

    void FixedUpdate()
    {
        if (check == null)
        {
            check = GameObject.FindObjectOfType<PlayerCheck>();
        }

        playerIn = check.playerIn;
        RaycastHit hit;

        if (Physics.Linecast(transform.position, player.position, out hit, ~mask))
        {
            if (!playerIn)
            {
                Debug.DrawLine(transform.position, hit.point, Color.red);
            }
            else if (hit.collider.gameObject != null)
            {
                if (!hit.collider.CompareTag("Player"))
                {
                    Debug.DrawLine(transform.position, hit.point, Color.blue);
                    return;
                }
                else
                {
                    Debug.DrawLine(transform.position, hit.point, Color.green);
                    aggress = true;
                }
            }
        }

        if (aggress)
        {
            Aggro(sawPlayer);
        }

        if (patroling)
        {
            GoToNext();
        }
    }

    void GoToNext()
    {
        patroling = true;
        aggress = false;
        if (wayPoints.Length == 0)
            return;

        if (playerIn)
            return;

        if (agent.remainingDistance < .7f)
        {
            agent.SetDestination(wayPoints[destIndex].position);
            destIndex = (destIndex + 1) % wayPoints.Length;
        }
    }

    void Aggro(string condition)
    {
        if (condition == sawPlayer)
        {
            Chase(player);
        }
    }

    void Chase(Transform transform)
    {
        patroling = false;
        if (playerIn)
        {
            agent.SetDestination(transform.position);
            print("Chasing");
        }
        else
        {
            **Wander(sawPlayer, 15);**
            print("Wander, please");
        }
    }

    **void Wander(string condition, float time)**
    {
        patroling = false;
        print(time);
        wanderTimer += Time.deltaTime;

        print("Wandering");
        //this is where I'm having the most trouble, it will print wandering for 1 //frame then stop and go back to patroling
        //once the player leaves the fov. I'm trying to figure out where the method //stops and why.

        if (condition == sawPlayer)
        {
            if (wanderTimer >= time)
            {
                wanderTimer = 0;
                if (!agent.pathPending && agent.remainingDistance < .5f)
                {
                    GoToNext();
                }
            }
            else
            {
                Vector3 vec;
                vec = new Vector3(Random.Range(agent.destination.x - 10, agent.destination.x), Random.Range(agent.destination.y - 10, agent.destination.y), Random.Range(agent.destination.z - 10, agent.destination.z));
                agent.destination = transform.InverseTransformDirection(vec);

                if (agent.remainingDistance < .3f || wanderTimer > time)
                {
                    GoToNext();
                }
            }
        }
    }
}

0 个答案:

没有答案