UnityRef is currently in early development. Some features may be incomplete and/or not functioning.

UNITYREF

Your Pit Stop For Solving ANYTHING in Unity

physics

[2D Physics] Fix Child Objects Detaching During bodyType Instantiation

Solution

physicsrigidbodysimulationkinematics

Unity 2021.x - Unity 6.3.x

Published 14 days ago

Issue

 An object instantiated as a child of another object using Instantiate does not remain attached to its parent or follow its movement. Attempts to instantiate the object using either Transform.localPosition or Transform.position result in the child appearing detached and stationary relative to the parent or at an incorrect global position.

Additionally, the instantiated object may render incorrectly, appearing as a primitive shape instead of its intended visual representation.

To ensure an instantiated child object moves with its parent, set its Rigidbody2D.bodyType property to Kinematic. For releasing the object, change its bodyType to Dynamic and clear its parent transform.

Explanation

When instantiating a GameObject that needs to move with its parent, particularly if physics components are involved, the Rigidbody2D.bodyType property of the child object is crucial. If the child object possesses a Rigidbody2D component and is intended to be carried by a parent, its Rigidbody2D.bodyType should be set to Kinematic. This configuration allows the object to be moved directly via its Transform component, preventing physics forces from acting upon it independently and ensuring it follows the parent’s movement.

  1. Access the Rigidbody2D component immediately after calling Instantiate on your prefab.
  2. Set the bodyType to RigidbodyType2D.Kinematic to disable simulation while the object is parented.
  3. To release the object and restore physics interactions (e.g. for a projectile), switch the bodyType back to RigidbodyType2D.Dynamic.
  4. Call transform.SetParent(null) to detach the object from the parent hierarchy.

Regarding the object appearing as a rectangle, this typically indicates an issue with rendering components. Verify that the instantiated GameObject’s prefab has a properly configured SpriteRenderer or MeshRenderer with an assigned asset.

Additional Tips

  • Use transform.SetParent(parent, false) to maintain local scale and position during instantiation.
  • For Unity 6, ensure you are using linearVelocity instead of the legacy velocity property for more consistent physics behavior.
  • Check that the Simulated property on the Rigidbody2D is enabled, or the object will not trigger collisions even when bodyType is updated.

Copy


using UnityEngine;

public class ProjectileLauncher : MonoBehaviour
{
    [SerializeField] private Transform shootPoint;
    [SerializeField] private GameObject ballPrefab;

    private GameObject currentBall;

    void Start()
    {
        // Instantiate the ball prefab as a child of this object
        currentBall = Instantiate(ballPrefab, shootPoint.position, shootPoint.rotation, transform);

        // Set bodyType to Kinematic so it follows parent movement
        if (currentBall.TryGetComponent<Rigidbody2D>(out Rigidbody2D rb))
        {
            rb.bodyType = RigidbodyType2D.Kinematic;
        }
    }

    public void Launch()
    {
        if (currentBall != null)
        {
            // Detach and restore Dynamic physics
            currentBall.transform.SetParent(null);
            if (currentBall.TryGetComponent<Rigidbody2D>(out Rigidbody2D rb))
            {
                rb.bodyType = RigidbodyType2D.Dynamic;
                rb.linearVelocity = transform.right * 10f;
            }
        }
    }
}

Related Posts Haven't quite found a solution to your problem? We think these posts might help you.

Content inspired by a Unity discussion post.