# Finding random position in torus?

Hello,

I am trying to finding a random position in torus.

Actually I found a method that finding torus iteratively. But it includes while loop and I don’t want to use while loop in a method while it slows down update duration.

Are there any algorithm for my purpose.

Here is the code that I wrote

``````Vector3 GetARandomPositionInTorus(Vector3 center)
{

Vector3 dest = transform.position;

while (Vector3.Distance(dest, transform.position) < newCirclePositionMinDistance)
{
Vector3 randomPosition = Random.insideUnitSphere * newCirclePositionMaxDistance;
randomPosition = new Vector3(randomPosition.x, transform.position.y, randomPosition.z);
dest = randomPosition + center;
}

return dest;
``````

}

This is more of a math problem than a Unity problem.

Imagine the torus as a necklace; a bunch of spheres connected with a string through their centers, and aligned in a ring.

Get a random angle around that ring.

Find the position of the string.

Imagine a sphere there.

Get a random point in that sphere.

Now you have a point that lies within the torus \o/

Here’s some code to demonstrate. I have not factored in the position and orientation of the torus, this is just to show the above steps in practice. Attach to an empty gameObject in a new scene. Hit Play. Left-click in the scene view and change the inspector values while playing.

``````using UnityEngine;
using System.Collections;
using System.Collections.Generic;

public class RandomPosInTorus : MonoBehaviour
{
[Space(20)]
public int iterations = 1000;
public GameObject markerObject;

private List< GameObject > markerList; // object pool. for testing purposes

void Start()
{
markerList = new List< GameObject >();
Generate();
}

void Update()
{
if ( Input.GetKeyDown( KeyCode.Mouse0 ) )
Generate();
}

void Generate()
{
// object pool. for testing purposes. remove old markers each time Generate is called
if ( markerList.Count > 0 )
foreach ( GameObject marker in markerList )
Destroy( marker );

markerList = new List< GameObject >();

float ringRadius = wallRadius + innerRadius; // ( ( max - min ) / 2 ) + min

for ( int i = 0; i < iterations; i ++ )
{
// create marker object
GameObject go;
if ( !markerObject )
{
go = GameObject.CreatePrimitive( PrimitiveType.Sphere );
go.transform.localScale = Vector3.one * 0.05f;
}
else
go = (GameObject)Instantiate( markerObject );
go.name = "Sphere_" + i.ToString();

// position marker object
Transform tx = go.transform;
tx.parent = transform;
}
}

{
// get a random angle around the ring
float rndAngle = Random.value * 6.28f; // use radians, saves converting degrees to radians

// determine position
float cX = Mathf.Sin( rndAngle );
float cZ = Mathf.Cos( rndAngle );

Vector3 ringPos = new Vector3( cX, 0, cZ );