• entries
743
1924
• views
581838

# Hinges

1162 views

In my preparation for rag doll animation, something has been troubling me.

What I will want to do is start the rag doll in whatever pose the character is from the animation system, then allow the physics to take over. Have been thinking about this in relation to the constraints (hinges and cone twists) and trying to figure out how this should work.

It occurred to me that if I create the bodies in the posed positions, the constraints will then be created with their limits relative to the body orientations, rather than the limits being global to the bind pose.

In English, I want the knee hinge to always be across the X axis in model space, constraining the leg to be, for example, straight or at a 90 degree angle bent in the logical direction for a knee. If I create the upper and lower leg parts in an already slightly rotated position relative to each other, then create the constraint, surely that slight rotated position will be the upper end of the limit and it will bend too far in the other way? If you see what I mean? Hard to explain.

I've just finished some experiments here. Turns out my suspicion was correct. What I've had to do instead is create the bodies in what will be equivalent to the model bind pose, then create the constraints, then modify the world transform of the body parts afterwards. Feels a bit wrong to be directly setting the world transform of a physics body, but seems to work okay.

In the video, you can see several "legs" that are spawned in various different initial poses, but the hinge limits are correctly between fully straight and 90 degree bent, in the correct direction. It looks a little bit like this. JoinedShape is just a testing class by the way, so no points for criticising my use of that static variable:

JoinedShape::JoinedShape(Events &events, Graphics &graphics, Physics &physics, Scene &scene, const Vec3 &position) : press(false){ delegate.connect(this, &JoinedShape::keyDown, events.keyDown); static int x = 0; Color color[] = { makeColor(255, 0, 0), makeColor(0, 255, 0), makeColor(0, 0, 255), makeColor(255, 255, 0) }; Buffer buffer = debugAddSolidCapsuleToBuffer(1, 4, color[x]); graphics.resources.add(mesh, new Mesh(graphics.device, buffer, VertexType::Color, D3DPOOL_MANAGED)); nodeA = scene.addNode(new StaticMeshNode(mesh.id(), RenderType::Color, translationMatrix(position))); nodeB = scene.addNode(new StaticMeshNode(mesh.id(), RenderType::Color, translationMatrix(position + Vec3(0, 4, 0)))); bodyA = physics.createBody(new Capsule(1, 4), translationMatrix(position), 1); bodyB = physics.createBody(new Capsule(1, 4), translationMatrix(position + Vec3(0, 4, 0)), 1); constraint = physics.createHingeConstraint(bodyA.ref(), bodyB.ref(), Vec3(0, 2, 0), Vec3(0, -2, 0), Vec3(0, 0, -1), 0, pi() / 2); Matrix b; switch(x) { case 1: b = translationMatrix(Vec3(0, 2, 0)) * rotationZMatrix(pi() / 2) * translationMatrix(Vec3(0, -2, 0)); break; case 2: b = translationMatrix(Vec3(0, 2, 0)) * rotationZMatrix(pi() / 4) * translationMatrix(Vec3(0, -2, 0)); break; default: b = identityMatrix(); break; } bodyB->setTransform(b * bodyB->transform()); ++x; if(x == 4) x = 0;}In other words, create the shapes with the upper one sitting on top of the lower, rotated the same, then create the constraint with the limits set to the requried values, then modify the world transform of the upper shape to rotate it away from the bind pose.

So in theory, unless I'm missing something, when I come to create the rag doll for my character, I'll create the bodies based on the bind pose positions of the joints, then create the constraints, then when it has been created, apply the transforms from the animation's current matrix palette to the bodies to move it into the current pose.

Hmm. Maybe. We shall see.

I'm going to have a standard format for my humanoid rag doll, and use standard naming for the joints in the editor so I can, for example, look up "Left Hip" and "Left Knee" and use these points to create the upper leg capsule. I think I should be able to generalise this to any human skeleton then.

Feeling a bit like my journals are a little impenetrable lately and possibly not easy to understand or interesting to read, but I enjoy putting these up so thanks for stopping by.

## 1 Comment

heh, even if people do the TL:DR thing, you still have a nice video illustrating things =)