How to choose a random point only once?

I’m creating an enemy that has four random points as children. When he moves, he should move to one of those points randomly. I have the following code which sort of works, but instead of choosing the random point once it repeats. I’ve confirmed this with Debug.Log. How do I make it only choose the random point once?

    bool isCharging = false;

void Update(){
	if(isCharging){
		StartCoroutine(Charge());
	}
}

    void OnTriggerEnter2D(Collider2D col){

	if(col.gameObject.name == "Player" && (Time.time - lastChargeTime) > 5){
		isCharging = true;
            }
}

IEnumerator MovetoRandomPoint(Vector3 targetPos, float moveDuration){
	float timer = 0.0f;
	Vector3 startPos = transform.position;

	while(timer < moveDuration){
		timer += Time.deltaTime;
		float t = timer / moveDuration;
		t = t * t * t * (t * (6f * t - 15f) + 10f);
		transform.position = Vector3.Lerp(startPos, targetPos, t);
		yield return null;
	}

	yield return null;
}

IEnumerator Charge(){
	pathscript.enabled = false;
	GetComponent<AIDestinationSetter>().enabled = false;
	index = Random.Range(0, pointArray.Length);
	currentPoint = pointArray[index];
	StartCoroutine(MovetoRandomPoint(currentPoint, 10f));
	Debug.Log("current point is:" + currentPoint);
	yield return new WaitForSeconds(1);
	isCharging = false;		
	lastChargeTime = Time.time;
}

This is happening because you are calling StartCoroutine(Charge()) every frame (in the Update method). Within the Charge() coroutine itself, you are setting a random point, therefore you are setting a random point every frame. You need to bring the StartCoroutine() out of the Update() function (it only needs to be called once and it will run the whole thing over time, no need to call it every frame anyway).

If you have anymore questions please ask, and if this solved it for you please mark it as answered, thank you :slight_smile:

I think

lastPoint = currentPoint; while (currentPoint == lastPoint) { index = Random.Range(0, pointArray.Length); currentPoint = pointArray[index]; }

In you IEnumerator Charge() method, look at these two lines:

	index = Random.Range(0, pointArray.Length);
	currentPoint = pointArray[index];

Random.Range can draw the same point a couple of times in a row. There is no check for that. I would rebuild it a bit. Delete those two lines, and replace them with that:

	currentPoint = SelectThePoint();

And somewhere in your class, add a new method:

	Vector3 SelectThePoint(){
		index = Random.Range(0, pointArray.Length - 1);
		
		Vector3 temp = pointArray[index];
		pointArray[index] = pointArray[pointArray.Length - 1];;
		pointArray[pointArray.Length - 1] = temp;
		
		return pointArray[index];
	}

It takes random number (index) from the array, but it excludes the last element. Subsequently it replaces drawn element with the last element in the array, and returns the point at the index. The reason the last element is bypassed in the calculation is that this element is the point at which your gameobject is actually positioned, and you don’t want it to be drawn once again in a row.

And the next thing. Look at the IEnumerator Charge(). Find this statement:

     isCharging = false;

Move it from the end of the coroutine to the beginning, because it can be the source of your problems.