Ball appears to pass through brick intermittently

Started by
17 comments, last by Scouting Ninja 5 years, 10 months ago

How should I handle that then? Loop through the array before clearing it and if it's not null, then destroy it? Also, a note on this. I'm never actually spawning, destroying them all, then calling this again. Not yet at least. As of now, once the initially spawned bricks are destroyed, the game is over. So it shouldn't be calling this and getting an error for pre-existing bricks, because there shouldn't be any pre-existing bricks. 

Advertisement
8 hours ago, ethancodes said:

Also, a note on this. I'm never actually spawning

Then this is probably not your problem either. You will now have to check all the bricks to see that they are destroying them self correctly.

The problem is that debugging a game without the full game is impossible.

 

The only advice I can give you is that the error has something to do with objects being destroyed. More importantly something is trying to destroy the transform part; when it should be targeting the GameObject instead.

 

The transform part of a Unity game object is the primary part it goes in this order: Transform->GameObjects->Component.

Destroying the transform shouldn't be possible, because there could still be code and stuff attached. Instead Destroy(GameObject) removes the game object and components; then when all attached code to the transform is no longer needed; Unity will remove the transform by it self.

 

Check all your code and look for a place where you are deleting or destroying a none GameObject; that would be the cause of the bug.

Are there other ways of destroying things other than using the Destroy method? I searched the entire solution and went through every single Destroy call, all of them are destroying gameObject. I'm curious if there could be something else that is trying to destroy something and I'm just not seeing it because it's not using the Destroy method.

Ok, so I figured out where the error is coming from. In the following code, on the last line I have brickHolder.transform. This part is setting the brickHolder as the parent object of the bricks. The problem is it takes a Transform for some reason, not a GameObject. I'm assuming the brickHolder is getting destroyed as the game is stopped (hence why the errors only show up when I stop the game), but it is trying to destroy the transform since that's what is passed in here. How can I stop this? I think somewhere in the code I should be able to put Destroy(FindbyName"brickHolder") or something like that, to ensure it gets destroyed before the game tries to destroy it by the transform. I just don't know where I would put it or if that is even the right idea.

 


		//LayoutObjectAtRandom accepts an array of game objects to choose from along with a minimum and maximum range for the number of objects to create.
		void LayoutObjectAtRandom (int brickCount)
		{
			bricks.Add(oneHitBrick);
			bricks.Add(twoHitBrick);
			bricks.Add(threeHitBrick);
			bricks.Add(explodingBarrel);

			//Instantiate objects until the randomly chosen limit objectCount is reached
			for(int i = 0; i < brickCount; i++)
			{
				//Choose a position for randomPosition by getting a random position from our list of available Vector3s stored in gridPosition
				GridSquare selectedPosition = RandomPosition();

				GameObject brick = bricks[Random.Range(0,bricks.Count)];

				//Instantiate tileChoice at the position returned by RandomPosition with no change in rotation
				selectedPosition.AssociatedBrick = Instantiate(brick, selectedPosition.GridPosition, Quaternion.identity, brickHolder.transform);

			}
		}

 

3 hours ago, ethancodes said:

Destroy(FindbyName"brickHolder") or something like that, to ensure it gets destroyed before the game tries to destroy it by the transform.

You can try this. Just make a simple code for it. However I don't know if it will work because the way you are using Instantiate is correct.

Edit:

The brickHolder it isn't a brick, right? There isn't any code trying to destroy it?

The brick holder is just a prefab of an empty gameobject with nothing but a transform and a rigidbody on it. I instantiate it here:


	public GameObject brickHolder;

void Awake ()
		{
			brickHolder = Instantiate(brickHolder, Vector3.zero,Quaternion.identity) as GameObject;
		}

I move it here:


void Update ()
		{
			brickHolder.transform.position = Vector3.MoveTowards(brickHolder.transform.position, target.transform.position , speed * Time.deltaTime);
		}

 

And the only other place it is mentioned in code is here, where the bricks get instantiated:


//LayoutObjectAtRandom accepts an array of game objects to choose from along with a minimum and maximum range for the number of objects to create.
		void LayoutObjectAtRandom (int brickCount)
		{
			bricks.Add(oneHitBrick);
			bricks.Add(twoHitBrick);
			bricks.Add(threeHitBrick);
			bricks.Add(explodingBarrel);

			//Instantiate objects until the randomly chosen limit objectCount is reached
			for(int i = 0; i < brickCount; i++)
			{
				//Choose a position for randomPosition by getting a random position from our list of available Vector3s stored in gridPosition
				GridSquare selectedPosition = RandomPosition();

				GameObject brick = bricks[Random.Range(0,bricks.Count)];

				//Instantiate tileChoice at the position returned by RandomPosition with no change in rotation
				selectedPosition.AssociatedBrick = Instantiate(brick, selectedPosition.GridPosition, Quaternion.identity, brickHolder.transform);
			}
		}

 

 

2 hours ago, ethancodes said:

he brick holder is just a prefab of an empty gameobject with nothing but a transform and a rigidbody on it. I instantiate it here:

You can remove this instantiate. It's a mono script so just place a object in the scene and attach that script. Dragging a object into the editor is the same as using instantiate.

The only time you want to call instantiate is to make a clone of something.

 

Doesn't look like this is it either. Can you post the full error?

Post it as a spoiler by using the eye icon in the forum editor here. It's right next to the code <> icon.

Well I don't know what it was but I fixed it. lol. I had this set up so that the Boardmanager class was also moving the bricks. That's all this code we've been working on. Well, you mentioned just attaching the script to an instance of the brickHolder in the hierarchy. I didn't think it would be good practice to attach the Boardmanager script to it, so I removed all logic regarding brick movement and put it in a new script which got assigned to the brickHolder object. I was still having issues though because the bricks were not spawning for some reason. I finally found that if I change the Instantiation of the bricks to this:

 


selectedPosition.AssociatedBrick = Instantiate(brick, selectedPosition.GridPosition, Quaternion.identity, GameObject.Find("BrickHolder").transform);

Suddenly it worked fine! I ran it about 20 times, no errors. I test played, win and lose. Hit single and multiple explosive bricks. All looks good! And the code is much cleaner and easier to read as well!

17 minutes ago, ethancodes said:

I finally found that if I change the Instantiation of the bricks to this:

That is kind of how Unity wants you to do it. A even more effective way would be to make a public GameObject variable at the top, then in the editor you drag your BrikcHolder in and reference that.

What you are doing here is also OK.

This topic is closed to new replies.

Advertisement