I have studied coroutines from wikipedia,Unity documentation and this unite 2013 1.
Now the problem is as Wikipedia explains Coroutines are able to save states(including local variables).In the video Devin Horsman shows that a state machine can be implemented using Coroutines at 7:54 in the video he shows implementation of a coroutine setup to work as a state machine.He explains that coroutines can “remember state” which is useful as it avoids having class level variables and avoid having cluttered code.
So I tried implementing a very basic follower where the follows the enemy while in range and then goes to wait if out of range using coroutines as-
using UnityEngine;
using System.Collections;
public class Enemy : MonoBehaviour
{
private GameObject player;
private float DangerDistance = 8.0f;
public float EnemySpeed = 1.0f;
// Use this for initialization
void Awake()
{
player = GameObject.FindGameObjectWithTag("playerBall");
}
bool inDangerDistance()
{
Vector2 playerpos = new Vector2(player.transform.position.x,player.transform.position.z);
Vector2 mine = new Vector2(transform.position.x,transform.position.z);
Vector2 dotter = new Vector2(transform.forward.x,transform.forward.z);
//Debug.Log(Vector2.Dot((playerpos-mine).normalized,dotter.normalized));
return Vector2.Distance(playerpos,mine)<=DangerDistance && nearEquals(Vector2.Dot((playerpos-mine).normalized,dotter.normalized),1);
}
bool nearEquals(float first,float second)
{
return Mathf.Abs(first-second)<=0.2f;
}
IEnumerator search()
{
while(true)
{
if(inDangerDistance())
{
yield return StartCoroutine(follow());
}
transform.Rotate(0,90*Time.deltaTime,0);
yield return null;
}
}
IEnumerator follow()
{
Vector2 playerpos = new Vector2(player.transform.position.x,player.transform.position.z);
Vector2 mine = new Vector2(transform.position.x,transform.position.z);
while(true)
{
while(inDangerDistance())
{
playerpos.x = player.transform.position.x;
playerpos.y = player.transform.position.z;
mine.x = transform.position.x;
mine.y = transform.position.z;
Vector3 v1 = new Vector3(playerpos.x,0,playerpos.y)-new Vector3(mine.x,0,mine.y);
transform.forward = v1;
transform.Translate((playerpos.x-mine.x)*Time.deltaTime*EnemySpeed,0,(playerpos.y-mine.y)*Time.deltaTime*EnemySpeed,relativeTo:Space.World);
yield return null;
}
yield return StartCoroutine(search());
Debug.Log("yoohoo");
}
}
void Start()
{
StartCoroutine(search());
}
}
Now the problem I notice with this approach is there is no actual State preserved as I switch from search to follow and vice versa as StartCoroutine builds a new Coroutine object and defeats the purpose of preservation(“yoohoo” is never printed in follow()).So what advantage really Coroutines have other than using WaitforSeconds() if they could not preserve state or there is something wrong in the video or I am completely wrong?Thanks for help.