Exploide GameObjects Into BrokenParts : Unity

Hello Everyone,

I have created brokenparts(head , leg , hand , heart) and all gameobject is having rigidbody , all are child of parent object…

Now on explosion i am adding velocity to rigidbody of that broken parts.

when my projectile collides with healthy gameobject at that time OnCollisionEnter() will be called. Below script i have attached to my projectile…

#pragma strict
public var bloodPrefab : GameObject;
public var brokenPartsPrefab : GameObject;

private var healthbarScript1 : healthBar1;
private var healthbarScript2 : healthBar2;
private var cowboyShootScript : cowboyShoot;
private var curHealth : int;
private var collisionPosition : Vector3;
private var objectExplode : boolean = false;
private var explosionRadius = 5.0;    //The starting radius of the explosion
private var explosionPower = 10.0;

function Start () {
	cowboyShootScript = GameObject.Find("cowboy").GetComponent("cowboyShoot");
}

function Update () {
	transform.Translate(cowboyShootScript.hitPoint.x * 2 * Time.deltaTime , cowboyShootScript.hitPoint.y * 2 * Time.deltaTime , 0 , Space.World);
	if(transform.position.x > 12.0f)
	{
		Destroy(gameObject);
	} 
}


function OnCollisionEnter(collision : Collision)
{
	
	collision.rigidbody.constraints = RigidbodyConstraints.FreezeAll;
	
	if(collision.gameObject.tag == "zombie")
	{
		
		collisionPosition = collision.gameObject.transform.position;
		if(collision.gameObject.GetComponent("healthBar1"))
		{
			healthbarScript1 = collision.gameObject.GetComponent("healthBar1");
			healthbarScript1.curHealth -= 1;
			curHealth = healthbarScript1.curHealth;			
		}
		else if(collision.gameObject.GetComponent("healthBar2"))
		{
			healthbarScript2 = collision.gameObject.GetComponent("healthBar2");
			healthbarScript2.curHealth -= 1;
			curHealth = healthbarScript2.curHealth;			
		}
		
		if(curHealth == 0)
		{
			Destroy(collision.gameObject);
			
			Instantiate(brokenPartsPrefab, collisionPosition , Quaternion.identity);
			var brokenParts = [];
    		brokenParts = GameObject.Find("brokenParts(Clone)").GetComponentsInChildren(Rigidbody);
    		
    		for(var rbChild : Rigidbody in brokenParts)
    		{
      			rbChild.velocity = rbChild.rigidbody.velocity/2;
      			rbChild.angularVelocity = rbChild.rigidbody.angularVelocity;
    		}
	
			objectExplode = true;
		}
		
		Instantiate( bloodPrefab , collision.contacts[0].point, bloodPrefab.transform.rotation );
		Destroy(gameObject);
		
		objectExplode = false;
	}
}

function OnCollisionExit(collision : Collision)
{
	collision.rigidbody.constraints = RigidbodyConstraints.FreezeRotation | RigidbodyConstraints.FreezePositionY | RigidbodyConstraints.FreezeRotationZ;
}

function FixedUpdate() {
    if (objectExplode == true) {
 
       // Apply an explosion force to all nearby rigidbodies
       if (explosionRadius<18) {
          explosionRadius+=0.5;
 
          var explosionPos : Vector3 = collisionPosition;
          var colliders : Collider[] = Physics.OverlapSphere (explosionPos, explosionRadius);
 
          for (var hit : Collider in colliders) {
          if (!hit)
          continue;
 
          if (hit.rigidbody) {
              hit.rigidbody.AddExplosionForce(explosionPower, explosionPos, explosionRadius, 3.0);
              }
          }
       }
    } else {explosionRadius=5.0;}
}

But my brokenparts are not exploiding in the air… What is wrong in this script?? Or if you guys are having another idea then guide me…

Thanks in advance for your help and support…

function OnCollisionEnter(collision : Collision)
{
collision.rigidbody.constraints = RigidbodyConstraints.FreezeAll;

and

function OnCollisionExit(collision : Collision)
{
collision.rigidbody.constraints = RigidbodyConstraints.FreezeRotation | RigidbodyConstraints.FreezePositionY | RigidbodyConstraints.FreezeRotationZ;
}

If the thing you hit was a zombie, the projectile will destroy itself and never unfreeze the zombie’s constraints.

I can’t fathom why you would want to do that. Maybe you have a good reason but I certainly can’t see it.

if(curHealth == 0)
{
    Destroy(collision.gameObject);

If your health is 0, destroy the object you collided with? Is this what you intended?

Instantiate(brokenPartsPrefab, collisionPosition , Quaternion.identity);
var brokenParts = [];
brokenParts = GameObject.Find("brokenParts(Clone)").GetComponentsInChildren(Rigidbody);

That is the weirdest way of instantiating something I’ve ever seen. Instantiate() returns the game object it instantiated. So a much better way of doing it would be:

var brokenParts = Instantiate(brokenPartsPrefab, collisionPosition , Quaternion.identity);
var bodies = brokenParts.GetComponentsInChildren(Rigidbody);
  1. This is your first problem:

    for(var rbChild : Rigidbody in brokenParts)
    {
    rbChild.velocity = rbChild.rigidbody.velocity/2;//This is halving the velocity of each child, which would be 0 anyway because they were just instantiated.
    rbChild.angularVelocity = rbChild.rigidbody.angularVelocity;//This does absolutely nothing. You’re setting a number to itself.
    }

I don’t know what you actually want to set the velocity to, but I’m guessing the desired result isn’t half of 0.

  1. This is your second problem.

    objectExplode = true;
    }

    //Ignore this line//Instantiate( bloodPrefab , collision.contacts[0].point, bloodPrefab.transform.rotation );
    Destroy(gameObject);

    objectExplode = false;

Not only will objectExplode always be false at the end of the function, but you are also destroying the projectile, which means that even if you weren’t setting objectExplode to false, FixedUpdate() would never even do its thing anyway.

if (explosionRadius<18) {
explosionRadius+=0.5;

You’re increasing the radius by 0.5 every frame, meaning it will get from 5 to 18 in 26 frames. It works but its certainly not the way I’d do it. I’d do something more along the lines of explosionRadius += 13 * Time.deltaTime; which would increase it from 5 to 18 over a second, regardless of how fast you have physics set to run.

 for (var hit : Collider in colliders) {
if (!hit)
continue;

There is no reason to null check the array you were given by Physics.OverlapSphere. Its not gonna tell you it hit things that don’t exist.