Rotation Hierarchy w/Quaternions
I''m trying to set up a heirarchy of rotations. For example, take a rotaing jack-in-the box. The box is spinning. The little crank is also rotating, on the side of the box as the box is rotating. The little handle on the end of the crank is rotating... well, you get the idea. I couldn''t seem to locate anything like that around here. Maybe I''m just missing it.
To get the rotational orientation of each object would I just multiply each child object''s quaternion by all of its parents, like: box_quat*crank_quat*handle_quat? I tried to do this, but the handle ended up going in all sorts of whack directions...
___________________________________Digital Paint: Paintball 2.0jitspoe's joint
For your last question first (about the Quaternion Multiplication), I am not sure if they are able to be concatinated in a similar manor as Matrices. What you would actually use the Quaternion for is to accomplish the rotation, THEN you convert it into a matrix which you can concatinate.
As for what you where asking about for about a rotation hierarchy, what you are actually refering to is a transformation hierarchy or as some like to call it, a Scene Graph. Gamedev just a an article on it: http://www.gamedev.net/columns/gameengineering/oosm/
So you could do it like this. You have your scene graph with all the elements of the scene. Here is how the tree would look.
Jack in Box
|
<transform matrix>
Box Jack Crank
|
<transform matrix>
Handle
Kinda see??? So to sum up, Quaternions use to rotate on arbitrary axis, once rotated, convert to matrix and store as. As you go down tranformations, you multiply by previous mat (not too efficent, but it's what you're asking). Make sense...?
fix- damnit, html cut out some of my psuedo code there. There is an entity list below the transform node. And a bunch of spaces too but it killed the. Tell me if you don't get the idea.
[edited by - Dirge on May 28, 2002 10:07:50 AM]
As for what you where asking about for about a rotation hierarchy, what you are actually refering to is a transformation hierarchy or as some like to call it, a Scene Graph. Gamedev just a an article on it: http://www.gamedev.net/columns/gameengineering/oosm/
So you could do it like this. You have your scene graph with all the elements of the scene. Here is how the tree would look.
Jack in Box
|
<transform matrix>
Box Jack Crank
|
<transform matrix>
Handle
Kinda see??? So to sum up, Quaternions use to rotate on arbitrary axis, once rotated, convert to matrix and store as. As you go down tranformations, you multiply by previous mat (not too efficent, but it's what you're asking). Make sense...?
fix- damnit, html cut out some of my psuedo code there. There is an entity list below the transform node. And a bunch of spaces too but it killed the. Tell me if you don't get the idea.
[edited by - Dirge on May 28, 2002 10:07:50 AM]
"Artificial Intelligence: the art of making computers that behave like the ones in movies."www.CodeFortress.com
Is there a way to do it without transform matrices? I would think there would be a way to do it with just quaternions and offsets.
___________________________________Digital Paint: Paintball 2.0jitspoe's joint
If you have some vector v in 3d space it can be represented by a quaternion as p = (0,v)
A rotation represented by the quaternion q rotates v like this
p -> q p q-1
If you follow this by another rotation represented by the quaternion r then this happens
q p q-1 -> r q p q-1 r-1
Which has the same effect on p as a rotation by the quaternion rq
So in short, yes you just multiply them
A rotation represented by the quaternion q rotates v like this
p -> q p q-1
If you follow this by another rotation represented by the quaternion r then this happens
q p q-1 -> r q p q-1 r-1
Which has the same effect on p as a rotation by the quaternion rq
So in short, yes you just multiply them

quaternions can be concatenated just like matrices, and it is a faster operation. To rotate unit quaternion q1 by unit quaternion q2:
q1 = q2*q1;
simple as that. Note that the order of multiplication is important. Quaternion multiplication is well documented so this should be easy to implement.
You don't want to go around converting to matrices until you really have to. It's an expensive operation.
To describe a hierarchy as you mentioned above I use a tree data structure. These are pretty cool - they take care of memory management and hierarchy maintenance for you. You just add or remove data at whatever position in the hierarchy then you can read or write to it whenever you want. The recursive nature of a tree data structure can be used to accumulate the transformations for you. An example in psuedo code to follow... an iterator is a type of smart pointer btw.
In this way each object need only store its own local transformation - its accumulated transformation is defined by it's position in the hierarchy. I'm currently working on applying all this to skeletal animation.
There is a tree tutorial somewhere on this site. Not sure if it uses iterators or not. Does this make sense? feel free to ask if not.
-
Geocyte Has Committed Suicide.
edit - put psuedo code in source box
[edited by - geocyte on May 28, 2002 9:30:40 PM]
q1 = q2*q1;
simple as that. Note that the order of multiplication is important. Quaternion multiplication is well documented so this should be easy to implement.
You don't want to go around converting to matrices until you really have to. It's an expensive operation.
To describe a hierarchy as you mentioned above I use a tree data structure. These are pretty cool - they take care of memory management and hierarchy maintenance for you. You just add or remove data at whatever position in the hierarchy then you can read or write to it whenever you want. The recursive nature of a tree data structure can be used to accumulate the transformations for you. An example in psuedo code to follow... an iterator is a type of smart pointer btw.
void draw_tree(treeIterator<an_object> itor) { glPushMatrix(); // saves the current gl matrix glMultMatrixf(itor->matrix.m);//transform by object matrix for(treeIterator<an_object> tmp_itor = itor.firstChild(); tmp_itor != itor.lastChild(); ) { draw_tree(tmp_itor++); } glPopMatrix(); // restores the matrix we saved earlier}
In this way each object need only store its own local transformation - its accumulated transformation is defined by it's position in the hierarchy. I'm currently working on applying all this to skeletal animation.
There is a tree tutorial somewhere on this site. Not sure if it uses iterators or not. Does this make sense? feel free to ask if not.
-
Geocyte Has Committed Suicide.
edit - put psuedo code in source box
[edited by - geocyte on May 28, 2002 9:30:40 PM]
Geocyte Has Committed Suicide.
Ok, I added some mouse control and now I can see the problem a little more clearly...
It looks as though the crank is rotating on the same axis (relative to the origin), rather than on an axis relative to the parent rotation. From a top view, the axis is always horizontal and the crank handle is moving up and down vertically as it orbits the box.
Am I multiplying my quaternions in the wrong order, or what's the deal here?
[edited by - jitspoe on May 29, 2002 3:29:51 AM]
It looks as though the crank is rotating on the same axis (relative to the origin), rather than on an axis relative to the parent rotation. From a top view, the axis is always horizontal and the crank handle is moving up and down vertically as it orbits the box.
Am I multiplying my quaternions in the wrong order, or what's the deal here?
[edited by - jitspoe on May 29, 2002 3:29:51 AM]
___________________________________Digital Paint: Paintball 2.0jitspoe's joint
I''m not sure about other people but I''d need a little more detail to answer that

Yeah, I was going to provide more detail, but then I had a better idea of what was going on, so I went to play with it. Turns out: a) quaternions were multiplied in the wrong order (should have been child*parent, not parent*child), and b) the offset was being calculated between unrotated and rotated coordinates, so it was doing all kinds of weird stuff. I was fixing code someone else started and there actually wasn''t enough data passed to the function calculate the proper offset.
It all works now th, yay! :D
It all works now th, yay! :D
___________________________________Digital Paint: Paintball 2.0jitspoe's joint
This topic is closed to new replies.
Advertisement
Popular Topics
Advertisement
Recommended Tutorials
Advertisement