ActionWander.cs 3.7 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116
  1. using UnityEngine;
  2. namespace BehaviorDesigner.Runtime.Tasks.Movement
  3. {
  4. [TaskDescription("Wander using the Unity NavMesh.")]
  5. [TaskCategory("Movement")]
  6. [HelpURL("http://www.opsive.com/assets/BehaviorDesigner/Movement/documentation.php?id=9")]
  7. [TaskIcon("Assets/Behavior Designer Movement/Editor/Icons/{SkinColor}WanderIcon.png")]
  8. public class ActionWander : Action
  9. {
  10. [Tooltip("The speed of the agent")]
  11. public SharedFloat speed;
  12. [Tooltip("Angular speed of the agent")]
  13. public SharedFloat angularSpeed;
  14. [Tooltip("How far ahead of the current position to look ahead for a wander")]
  15. public SharedFloat wanderDistance = 20;
  16. [Tooltip("The amount that the agent rotates direction")]
  17. public SharedFloat wanderRate = 2;
  18. [Tooltip("The amount that the wander count,0 forver")]
  19. public SharedInt wanderCount = 1;
  20. /// <summary>
  21. /// 最大游荡时间
  22. /// </summary>
  23. public float maxWanderTime = 3.0f;
  24. // A cache of the NavMeshAgent
  25. private UnityEngine.AI.NavMeshAgent navMeshAgent;
  26. private int curCount = 0;
  27. private Vector3 targetPos = Vector3.zero;
  28. private Vector3 livePos = Vector3.zero;
  29. private float curWanderTime = 0;
  30. public override void OnAwake()
  31. {
  32. // cache for quick lookup
  33. navMeshAgent = gameObject.GetComponent<UnityEngine.AI.NavMeshAgent>();
  34. livePos = transform.position;
  35. }
  36. public override void OnStart()
  37. {
  38. if (navMeshAgent == null)
  39. {
  40. navMeshAgent = gameObject.GetComponent<UnityEngine.AI.NavMeshAgent>();
  41. }
  42. // set the speed, angular speed, and destination then enable the agent
  43. navMeshAgent.speed = speed.Value;
  44. navMeshAgent.angularSpeed = angularSpeed.Value;
  45. navMeshAgent.enabled = true;
  46. navMeshAgent.destination = Target();
  47. curCount = wanderCount.Value;
  48. curWanderTime = maxWanderTime;
  49. }
  50. // There is no success or fail state with wander - the agent will just keep wandering
  51. public override TaskStatus OnUpdate()
  52. {
  53. // 游荡时间结束
  54. curWanderTime -= Time.deltaTime;
  55. if(curWanderTime <= 0)
  56. {
  57. return TaskStatus.Success;
  58. }
  59. if (curCount < 0)
  60. {
  61. return TaskStatus.Success;
  62. }
  63. if (navMeshAgent.destination != targetPos)
  64. {
  65. navMeshAgent.destination = Target();
  66. }
  67. else
  68. {
  69. if (wanderCount.Value > 0)
  70. {
  71. if (navMeshAgent.remainingDistance <= navMeshAgent.stoppingDistance)
  72. {
  73. curCount--;
  74. }
  75. }
  76. }
  77. return TaskStatus.Running;
  78. }
  79. public override void OnEnd()
  80. {
  81. // Disable the nav mesh
  82. navMeshAgent.enabled = false;
  83. }
  84. // Return targetPosition if targetTransform is null
  85. private Vector3 Target()
  86. {
  87. // point in a new random direction and then multiply that by the wander distance
  88. var direction = transform.forward + Random.insideUnitSphere * wanderRate.Value;
  89. targetPos = livePos + direction.normalized * wanderDistance.Value;
  90. targetPos.y = navMeshAgent.destination.y;
  91. return targetPos;
  92. }
  93. // Reset the public variables
  94. public override void OnReset()
  95. {
  96. wanderDistance = 20;
  97. wanderRate = 2;
  98. maxWanderTime = 3.0f;
  99. }
  100. }
  101. }