- Home /
How to stop objects spawning on top of each other
Im making a darts game where you have to pop some balloons that are floating upwards. The problem im having is that the balloons asre spawning on top of each other here is my code currently. The general idea i have found so far is to create a list and then add the objects to the list and for each instantiate check the positions of the objects. How would i check through the list for the positions of the objects and then use that information to find a new position for the object?
if(Time.time >= _NextSpawn){
int objectsToSpawn = balloons;
for(int i = 0; i < objectsToSpawn; i++){
int randomX = Random.Range(minX, maxX);
int randomY = Random.Range(minY, maxY);
int randomZ = Random.Range(minZ, maxZ);
Vector3 pos = new Vector3(randomX, randomY, randomZ);
balloons.Add(Instantiate(balloon, pos, rot));
}
Answer by robertbu · Mar 13, 2013 at 04:21 PM
The easiest is a brute force approach of generating random position and comparing them to the positions of the object until you find a position that works. Example untested code:
Vector3 FindPos()
{
for (int i = 0; i < 1000; i++)
{
float randomX = Random.Range(minX, maxX);
float randomY = Random.Range(minY, maxY);
float randomZ = Random.Range(minZ, maxZ);
Vector3 pos = new Vector3(randomX, randomY, randomZ);
int j;
for (j = 0; j < balloons.count; j++) {
if (Vector3.Distance(pos, balloons[j].transform.position) < threshold)
break;
}
if (j >= balloons.count)
return pos;
}
return pos;
}
Since sometimes there is no solution (too many object in too small a space), you want to limit the number of times you try. Here the limit is 1000.
Answer by serinth · Mar 13, 2013 at 05:16 PM
Where should i put this code in my script? As of right now my code spawns 10 balloons every 10 seconds but im not sure how to utilise the code you have provided
void Update () {
if(Time.time >= _NextSpawn){
int objectsToSpawn = redballoons;
for(int i = 0; i < objectsToSpawn; i++){
int randomX = Random.Range(minX, maxX);
int randomY = Random.Range(minY, maxY);
int randomZ = Random.Range(minZ, maxZ);
Vector3 pos = new Vector3(randomX, randomY, randomZ);
Instantiate(balloon, pos, rot);
}
That is the full update method i have created i can sort of see what your doing in that code you provided but as im not a very good scripter im finding it difficult to figure out where and how to apply it
As mentioned, the code is untested, but here is how you would use it.
void Update () {
if(Time.time >= _NextSpawn){
int objectsToSpawn = redballoons;
for(int i = 0; i < objectsToSpawn; i++){
Instantiate(balloon, FindPos(), rot);
}
}
}
Note I'm assu$$anonymous$$g your 'balloons' is a list that remain current with the balloons in the scene.
Balloons was a list i created to add the balloons to when they were created since i found out that i could check the postions by adding them to a list then checking for those positions so the balloons would not instantiate at those positions Where would i place your code in the script? in the update or start methods or somewhere different?
I put what I knew of your script together with the new code I provided. You will have to look at this and then merge in the parts you did not post. It compiles, but I did not test it. For this to work, you need to give all your balloons the "Balloon" tag.
using UnityEngine;
using System.Collections;
public class Balloons : $$anonymous$$onoBehaviour {
public GameObject balloon;
private GameObject[] argo;
private Quaternion rot = Quaternion.identity;
private float _NextSpawn;
private int redballoons = 10;
public float $$anonymous$$X;
public float maxX;
public float $$anonymous$$Y;
public float maxY;
public float $$anonymous$$Z;
public float maxZ;
private float threshold = 0.75f;
void Update () {
if(Time.time >= _NextSpawn){
int objectsToSpawn = redballoons;
argo = GameObject.FindGameObjectsWithTag ("Balloon");
for(int i = 0; i < objectsToSpawn; i++){
Instantiate(balloon, FindPos(), rot);
}
_NextSpawn = Time.time + 10.0f;
}
}
Vector3 FindPos()
{
Vector3 pos = Vector3.zero;
for (int i = 0; i < 1000; i++)
{
float randomX = Random.Range($$anonymous$$X, maxX);
float randomY = Random.Range($$anonymous$$Y, maxY);
float randomZ = Random.Range($$anonymous$$Z, maxZ);
pos = new Vector3(randomX, randomY, randomZ);
int j;
for (j = 0; j < argo.Length; j++) {
if (Vector3.Distance(pos, argo[j].transform.position) < threshold)
break;
}
if (j >= argo.Length)
return pos;
}
return pos;
}
}
This code doesn't stop the objects spawning on top of each other or spawning partway through each other. At the moment the objects spawn fine and in the target area but i need them to stop spawning on or partway through each other
Your answer
