But I've run into a problem... My Inverse Kinematics spider is setup to have 8 legs, with 6 'bones' in each leg. At the end of each joint (except for the last one) there is a joint - represented by a single 'angle vector' - i.e a vector containing the current angle of rotation around each of the 3 axis. Each bone is connected to the end point of the last one (at the position of the 'joint'). By providing each bone on initialization with a length, an angle of rotation and its maximum and minimum rotation I am able to construct a 'limb'. Each frame, (as described in Hugo Elias' page), a small angle is calculated and added to each joint, so that by the following frame, the tip of the limb is closer to the target. Now a spider leg is made up of 6 bones (in my slightly simplified model). The first bone (i.e the one that connects the leg to the body) rotates around two axis (lets call them x and z), whilst all the other bones only rotate around the x axis (i.e they are hinges, like your knee. The 1st joint can therefore be called a 'ball and socket' joint, as it moves both forward and backwards and up and down. Now in my IK implementation, each joint is only capable of rotating around a single axis. To create a 'ball and socket joint' (i.e the first joint), I simply create two bones of length 1 (tiny), which rotate around the two axis I need (x and z). This works, up to a point. If you look at the images below, you can see the problem.
The image above left shows a single limb which is STRAIGHT. The first joint is on the right, and is slightly elivated (as a spider's body is always off the ground). The leg tip is on the left, and is currently touching the BLUE target. On the right we see the same limb from the top, and its STRAIGHT. Because the target and first joint (where the ball and socket is located) are in a straight line.
The image above shows the same leg, only the target has moved backward - the ball and socket joint (i.e one x and one z axis joint) allows for the spider to move its legs forward and backwards. Now the tip of the leg reaches the target correctly, the problem is (as you can see in the top down view), that the leg is CROOKED. A screenshot of a full spider with 8 legs shows why this is a major problem :
Above is a screenshot of a spider in movement. The legs at the side are ok, because their angle of rotation along the z axis (backwards and forwards) are pretty small. The legs at the back, and more so the legs at the front, have a much larger angle of rotation, and as you can see the legs aren't straight as they should be. Now the way I've implemented the IK is that when an angle is added to a hinge joint (i.e 5/6 of the bones), that angle only rotates the bone it's attached to (its a local rotation). I.e the joints that move the bones up and down to lift the leg off the ground only affect that perticular bone. HOWEVER, when an angle is added to the joint which rotates the leg forwards and backwards (i.e ONE joint in the limb), the angle is ALSO added to all other child joints (in this case, all the other joints).
//Loop through joints (clue = they are at Bone.startPoint)
//Calculate the amount to rotate the joint for the next frame
for(int p = numberOfBones-1; p >= 0; p--)
{
CVector3 rot = CalculateJointRotationAmount(test_bone[p].GetEndPoint(),
test_bone[p].GetStartPoint(),
test_bone[p].GetAxisOfRotation(),
test_bone[p].GetFlexSpeed()
);
//If current joint has an influencial rotation axis
if(test_bone[p].GetAxisOfRotation() == "z-axis")
//Loop through all child joints
for(int q = p+1; q < numberOfBones; q++)
{
//add influencial rotation
test_bone[q].IncrementAngle(rot,
test_bone[p].GetAxisOfRotation(),
test_bone[p].GetMaxAngle(),
test_bone[p].GetMinAngle()
);
}
//Apply joint rotation to current bone
test_bone[p].IncrementAngle(rot,
test_bone[p].GetAxisOfRotation(),
test_bone[p].GetMaxAngle(),
test_bone[p].GetMinAngle()
);
}
Above is the source code for the part which increments the angle of each joint, each frame. As you can see, when the joint which rotates around the z-axis' angle is imcremented, all the child (x-axis) joints are also rotated around the z-axis by that amount.
I'm just wondering wether any of you can spot a flaw in my logic here. Is adding the same z-axis rotation to each x-axis joint the correct thing to do?
If you are interested in having a look at my spider walking, feel free to download this (95k) demo :
Inverse Kinematics Spider Demo
The spider walks through the wall, plus there are a few bugs in it (no pun intended ), including the little 'slip' each leg does before moving forward, plus that some of the joints detach slightly at times, but hey, I only started this 2 weeks ago!
If you look from the front or from the top, you can clearly see the problem I have. The legs should be STRAIGHT! Not bent like some Gorilla-Spider!
Anyway, I would be Very grateful for any help you can give me!
Cheers,
SFA.
llyrapcenydd@yahoo.co.uk
[edited by - SFA on May 7, 2004 12:04:41 PM]