- Home /
Making a Script that places Objects at random possition but not at the same as a taken position
I want to make a script for a game that places a set of Objects at random positions in a grid. The spawningprocess and grid are already set up but my problem is that sometimes objects spawn at the same possition. I roll a random X and a random Z position (Y is always 0), round that to conform with the grid and then create the Object at the end position. Is there any way to prevent the objects from spawning at the same position? I would just make one of the objects respawn at a different possition if it detects that it spawned inside another object but that seems very inefficient seeing how the game could end up randomly generating the object at a taken position again and could in theory take forever to find an empty spot
In the Awake Function:
for (int x = amountOfCoalSpawned; x < amountOfCoal; x++)
{
Vector3 PositionToPlace;
PositionToPlace.x = Random.Range(grid.minX, grid.maxX);
PositionToPlace.y = 0;
PositionToPlace.z = Random.Range(grid.minZ, grid.maxZ);
SpawnCoal(PositionToPlace);
Debug.Log("Coal");
}
SpawnCoal Function:
void SpawnCoal(Vector3 clickPoint)
{
Vector3 endPosition = grid.GetNearestPointOnGrid(clickPoint);
Debug.Log("Passing Coal Position");
Instantiate(CoalObject, endPosition, Quaternion.identity);
}
The grid.GetNearestPointOnGrid function simply takes the x and z values and rounds them to full intertures and passes them back.
Like i said, the script works but i dont know how to prevent objects spawning within eachother if i make it spawn multiple ones
Answer by Larry-Dietz · Dec 08, 2019 at 04:02 PM
Assuming that your "coal" has a collider attached, something like this should work.
for (int x = amountOfCoalSpawned; x < amountOfCoal; x++)
{
Vector3 PositionToPlace;
bool Placed=false;
int Count=0;
while(!Placed)
{
if(count++>100)
break;
PositionToPlace.x = Random.Range(grid.minX, grid.maxX);
PositionToPlace.y = 0;
PositionToPlace.z = Random.Range(grid.minZ, grid.maxZ);
if(Physics2D.OverlapCircle(PositionToPlace, .01f == null)
Placed=true;
}
SpawnCoal(PositionToPlace);
Debug.Log("Coal");
}
What this is doing, is repeating your random position code until it is not able to find a collider at the position, then calling your spawn method.
The count variable is to stop an infinite loop, in the case that it can't find a place to spawn, at which point, it will go ahead and spawn over top of something. Change the 100 to however many attempts you want it to make before giving up.
I typed this directly in the answer, so no guarantees against typos :)
Hope it helps, -Larry
Your answer
Follow this Question
Related Questions
A node in a childnode? 1 Answer
Why does List
Argument out of range 0 Answers
Using List.Count on Unity iPhone 2 Answers