- Home /
[c#] While loop not exiting, I have no idea why
What I'm trying to do is make sure that there isn't already a gameObject in the spot I'm trying to spawn my gameObject.
To the best of my knowledge I've accounted for all possible outcomes and am also using the raycast correctly.
public void SpawnAttackShip(){
bool spawned = false;
while(spawned == false){
Vector3 position = new Vector3(Random.Range(screenLeft.x, screenRight.x), screenTop.y, 0);
Ray ray = Camera.main.ViewportPointToRay(Camera.main.WorldToViewportPoint(position));
RaycastHit hit;
if(Physics.Raycast(ray, out hit)){
if((hit.transform.tag == "Enemy")){
spawned = false;
}
if((hit.transform.tag == null)){
GameObject attackShip = (GameObject)Instantiate(theAttackShip, position, Quaternion.identity);
spawned = true;
}
}
else{
GameObject attackShip = (GameObject)Instantiate(theAttackShip, position, Quaternion.identity);
spawned = true;
}
}
}
I've been trying to troubleshoot it but its tough because it makes unity crash in the infinite loop.
Answer by Baste · Feb 09, 2015 at 11:09 PM
Troubleshooting infinite loops is a bit tricky - the best way is often to either open a debugger, or go for the cheap option:
int safety = 0;
while(spawned == false && safety < 100)
safety++;
...
}
Generally, having an while-loop run until some randomly generated value gets a favorable value is not ideal. In your case, it seems that your raycast is always hitting something with the Enemy tag - which might mean that you've tagged some background with "Enemy", or that your rays are not doing what you think they are. A quick solution (that probably should be in anyways) would be to just give up after a bunch of iterations, and try again later.
Also, please, use while(!spawned) instead of while(spawned == false). It reads better - "I want to run the loop while the ship has not spawned" rather than "I want to run the loop while the ship having spawned is false".
Have to say I generally prefer the == false
way of doing it, because it jumps out as a negative condition more easily when scanning code quickly. Not that I'd tell anyone else that it's the right way of doing it. I think this one's a matter of taste.
I love that this answer is the one that got accepted... when I actually found why he was getting an infinite loop. ;)
This isn't really an "answer". And to tell a novice that !spawned
reads better than spawned == false
.. come now! I bet you're fun at parties! I personally DO use the shorthand version ("!" ins$$anonymous$$d of "== false"). I could go on about beginners missing the "!", a million ways to skin a cat, the fact that you've assumed English as the way to vocalise the code segment, but I'm not here to start a flame war.
But the worst bit of advice you gave, and the reason why I even commented here, is to $$anonymous$$ch a novice about ways to circumvent correct code, by putting in a "safety net". Ins$$anonymous$$d of finding out WHY the code looped infinitely, your suggestion is to cover it up, and hope it goes away. How many novice programmers are going to start implementing this kind of code in every program, in every loop, they code?
In fairness, the one bit of good advice was to use a debugger. I can't stress that enough.
Answer by DanSuperGP · Feb 10, 2015 at 12:04 AM
if((hit.transform.tag == null)){
Tag generally never equals null. If you haven't tagged something it has the tag string "Untagged".
This is why you're getting an infinite loop. Neither of your conditions can ever cause spawned to equal true.
That was only part of the problem, I didn't have a background and the ray wasn't hitting anything at all. I figured it would just return nothing, but I was totally wrong. In the end I make a background and tagged it background to make everything work properly. I Put the other answer above as the answer because it helped me stop unity from crashing so I could debug the problem myself.
Your answer
Follow this Question
Related Questions
Raycast returns null for no apparent reason 0 Answers
Need Help with RayCast. No Vector? 1 Answer
Raycast goes through 1 Answer
Shoot off multiple raycasts from 1 object? 2 Answers
set ray.point as x, y and z float 1 Answer