using System.Collections.Generic; using NodeCanvas.Framework; using ParadoxNotion.Design; using UnityEngine; using NavMeshAgent = UnityEngine.AI.NavMeshAgent; namespace NodeCanvas.Tasks.Actions { [Category("Movement/Pathfinding")] [Description("Move Randomly or Progressively between various game object positions taken from the list provided")] public class Patrol : ActionTask { public enum PatrolMode { Progressive, Random } [RequiredField, Tooltip("A list of gameobjects patrol points.")] public BBParameter> targetList; [Tooltip("The mode to use for patrol (progressive or random)")] public BBParameter patrolMode = PatrolMode.Random; public BBParameter speed = 4; public BBParameter keepDistance = 0.1f; private int index = -1; private Vector3? lastRequest; protected override string info { get { return string.Format("{0} Patrol {1}", patrolMode, targetList); } } protected override void OnExecute() { if ( targetList.value.Count == 0 ) { EndAction(false); return; } if ( targetList.value.Count == 1 ) { index = 0; } else { if ( patrolMode.value == PatrolMode.Random ) { var newIndex = index; while ( newIndex == index ) { newIndex = Random.Range(0, targetList.value.Count); } index = newIndex; } if ( patrolMode.value == PatrolMode.Progressive ) { index = (int)Mathf.Repeat(index + 1, targetList.value.Count); } } var targetGo = targetList.value[index]; if ( targetGo == null ) { ParadoxNotion.Services.Logger.LogWarning("List game object is null on Patrol Action Task.", LogTag.EXECUTION, this); EndAction(false); return; } var targetPos = targetGo.transform.position; agent.speed = speed.value; if ( ( agent.transform.position - targetPos ).magnitude < agent.stoppingDistance + keepDistance.value ) { EndAction(true); return; } } protected override void OnUpdate() { var targetPos = targetList.value[index].transform.position; if ( lastRequest != targetPos ) { if ( !agent.SetDestination(targetPos) ) { EndAction(false); return; } } lastRequest = targetPos; if ( !agent.pathPending && agent.remainingDistance <= agent.stoppingDistance + keepDistance.value ) { EndAction(true); } } protected override void OnPause() { OnStop(); } protected override void OnStop() { if ( lastRequest != null && agent.gameObject.activeSelf ) { agent.ResetPath(); } lastRequest = null; } public override void OnDrawGizmosSelected() { if ( agent && targetList.value != null ) { foreach ( var go in targetList.value ) { if ( go != null ) { Gizmos.DrawSphere(go.transform.position, 0.1f); } } } } } }