Attaching configurable joint(s) at runtime resulting in erratic movements

Hello,

First time posting so I hope I’m providing sufficient details about the issue I’m facing.

I’m working on an active ragdoll character with multiple configurable joints, using XYZ position spring values to stay in place. The character’s limbs also mimic the rotations of a separate, animated version of the same character model.

Now I’m trying to add the functionality for the ragdoll’s hands to grab specific objects. I do this by adding a configurable joint to the grabbed object and set its connected body to the rigidbody of the hand. Here is the method used to do this:

    private void OnCollisionEnter(Collision col)
    {
        Grabbable grabbable = col.collider.GetComponent<Grabbable>();

        if (grabbable && !grabbedObject && Input.GetMouseButton(grabButton))
        {
            this.grabbedObject = grabbable;
            grabbedObjectCollider = col.collider;

            Physics.IgnoreCollision(myCollider, grabbedObjectCollider, true);

            grabJoint = grabbable.gameObject.AddComponent<ConfigurableJoint>();

            grabJoint.connectedBody = this.myRB;
            grabJoint.breakForce = this.grabStrength;

            grabJoint.xMotion = ConfigurableJointMotion.Locked;
            grabJoint.yMotion = ConfigurableJointMotion.Locked;
            grabJoint.zMotion = ConfigurableJointMotion.Locked;

            grabJoint.angularXMotion = ConfigurableJointMotion.Locked;
            grabJoint.angularYMotion = ConfigurableJointMotion.Locked;
            grabJoint.angularZMotion = ConfigurableJointMotion.Locked;

            StartCoroutine(WaitForGrabRelease());
        }
    }

However this causes very unpredictable results. Objects that are grabbed sometimes spazz out. Other times the ragdoll spazzes out. And every now and then it seems to work. Generally it appears that objects with a higher mass value tend to be more problematic.

Here are a few examples of what happens:

I have read up on similar problems, though I cannot seem to find a workaround or explanation of what might be the culprit.

Is there something specific that stands out in this scenario which could cause these kinds of problems?

Would be happy to provide additional details if necessary.

Hi, and welcome to Unity forums!

I don’t know the specific cause for that, but my gut feeling is that creating the joint and spawning a coroutine within OnCollisionEnter is not a good idea. I’d try using OnCollisionEnter only to store the collided object, then moving all other code to FixedUpdate. Something like this in your MonoBehaviour:

Grabbable m_grabbable = null;

void OnCollisionEnter (Collision col)
{
    m_grabbable = col.collider.GetComponent<Grabbable>();
}

void FixedUpdate ()
{
    if (m_grabbable != null)
    {
        // Check for grabbedObject, create joint, spawn coroutine
        ...
    }

    m_grabbable = null;
}

Thanks for responding.

I’ve moved everything but the storing of the collider to a separate method that is called on each fixed update, though unfortunately the issue still persists.

Not so much related to the original question, but is your suggestion mainly to improve code structure?

After a lot more testing I’ve come to find something peculiar.

These issues appear more often than not. But when they don’t, they don’t happen at all, without a single change to the code or in the editor.

No matter how wild the interaction, every now and then it all just works flawlessly: