How to detect child object collisions on parent

Hi,
I have a parent object with a rigidbody2D and a collider. In code I instantiate a second object from a prefab and make it a child of the first object. This child has a collider but no rigidbody. On the parent object I am using void OnCollisionEnter2D(Collision2D coll) to detect collisions between the parent and other objects.

My problem is that this does not detect collisions that the child object has with other objects, it only catches those that directly collide with the parent’s collider. The parent’s OnCollisionEnter2D doesn’t run when the child hits something. Is there a way to catch child collisions as well without putting scripts on the child object?

Add a script to child and inside it have a reference of script of parent object. Now write 3 methods in parent script like ( OnCollisionEnter2DChild , OnCollisionStay2DChild , OnCollisionExit2DChild ) and called respective method from the methods (OnCollisionEnter2D , OnCollisionStay2D , OnCollisionExit2D) which are in child object script by passing the collision object.

I ran into the same problem. It turns out that Rigidbody2D does not fire the OnCollision2D messages. A compound collider works for the physics aspects but not the messaging. Only the colliders fire the OnCollision message, and only to the monobehaviours that are on the same gameobject as the collider. The Collider2D does have a reference to the rigidbody so you can force the call up by placing this script on a child collider gameobject if you want the parent with the rigidbody to handle all the collision logic.

public class ChildCollider : MonoBehaviour {
 
    // Use this for initialization
    void Start () {
 
    }
 
    // Update is called once per frame
    void Update () {
 
    }
 
    void OnCollisionEnter2D( Collision2D collision) {
       this.collider2D.attachedRigidbody.SendMessage("OnCollisionEnter2D",collision);
    }
}

So it does look like a script is necessary but with this script you won’t need to manually set the parent script as reference by dragging it onto a public variable, and this will also send the oncollision message to all Monobehaviours on the same gameobject as the RigidBody2D in case you have multiple scripts on the parent doing stuff when a collision happens.

I have found a different solution that may be useful in some cases: Trigger in child object calls OnTriggerEnter in parent object - Unity Answers

That link talks about how in some cases, a child object can call the OnTrigger or OnCollision function of the parent. If your child is a trigger, like for attack hit boxes, this might be useful. I have found it is for me.

void OnTriggerEnter(Collider other)
    {      
        if (other.gameObject.tag == "CrystalNode")
        {
            print("Hitting Crystal");
            Damage(other.gameObject);
        }

        if (other.gameObject.tag == "OreNode")
        {
            print("Hitting Ore");
            Damage(other.gameObject);
        }
    }

I have found that the above code being on the parent, correctly calls the correct print function depending on what the child trigger is overlapping. If your child had a rigid body, though, you may get weird physics behaviours, so this is probably best for triggers.

Note: I didn’t notice this working initially when the child had no script attached. When I attached a script to my child and called OnTrigger, I noticed it working on the parent as well. I removed the script from the child and it continued calling on the parent. So, assuming it wasn’t a bug, you don’t need a script on the child at all.

@NJML