Bringing Static Models to Life

To see definitions relevant to this tutorial click here

This tutorial shows how to turn an imported VRML static model, made by any 3d editor, into a dynamic multi-part animated model.

This tutorial is written to accompany the robot demo bring static model to life

This demo requires first that the contents of the files_for_demos.zip file be manually unzipped and put in the folder:

My Documents\Seamless3d\Application Data For Seamless3d\For Robot Demos Only

To see this demo, move the mouse to the top left corner of the 3d window and select:

 

The demo shows all the actions needed to make the static model ready to be animated.

The same Interpolator nodes, ROUTEs and or scripts used for animating standard type vrml models that are made from multiple Transform and Shape nodes, can also be used to animate this model when it is ready to be animated.

The example static model used here is a model made by Seamless3d that has been converted to a file containing only a single VRML Shape node which contains all the geometry and texture mapping but nothing else (no scripts). If the static model is opened in a VRML browser, the geometry will not be collapsed.

Though the static model could have been made by any 3d editor, note that the model made by Seamless3d has been made specially suited for single skin mesh animation, extra vertices have been created for the shoulders, elbows, knees etc. to improve the quality of the joints when they bend.

A big advantage of using build nodes is there is no problem in accidently messing up the model because the source static model can be re-imported at any time. Build nodes offer more freedom with what can be done with our work. Once the build nodes have been set up they can be re-used to import any static model that has the same basic shape.

The Basic Idea


The static model is imported into a single part and then the vertices are transferred to the rest of the parts using a transparent cylinder to select the vertices. When this is done the pivot points are moved to the correct location for each part so that the parts can then be animated.

Begin

Start the robot demo:

bring static model to life

All of the titles for the robot demo operations will be shown here in bold beginning with the operation number followed by the title itself. Any comments  for the operation will be explained under the title.

0. Create A New Seamless File


1. Import Empty Skeleton of Parts
Begin with a pre-made skeleton of empty parts.

Part names that begin with l_ are the left parts and names that begin with r_ are the right parts. To avoid using double names for a part, the part for the upper arm for example is referred to by it's joint (shoulder) that attaches it to it's ancestor part.

Part Includes
shoulder upper arm
elbow forearm
wrist hand
hip thigh
knee shin & calf
ankle foot

2. Replace ColorEffect with TextureEffect


 

Because the static model uses textures we must first replace the ColorEffect node with a TextureEffect node. If this is not done before importing the model into a part node, all of the texture mapping will be lost. This operation should not be done if the model being imported does not use textures such as when the Shape uses "color per vertex" or when the Shape uses only the Material node to colour the geometry.

3. Import Static Model Into a Part
An immediate blue part named model_source is created to contain all the triangles imported from the file, static_model.wrl

This part will be the 1st source of the vertices for the model and will not be modified by any build nodes so it will always contain the original number of vertices.

A "build cycle" is the term used for when ever the build nodes run. (much the same as executing a macro). A build cycle happens automatically each time we modify a field belonging to a build node. In a build cycle each build node runs it's "doBuild" function in sequential order from top to bottom. Collapsing nodes in the scene tree has no affect over a build cycle.

The static model has it's arms straight out horizontally which makes it easiest to select the vertices around the shoulder for the arm parts but if the model is to be used strictly for the H-Anim standard, the arms in the static model must rest downwards.

4. Copy All of the Triangles to the Pelvis
Because TransferBCyl nodes will be used to transfer the ownership of vertices from a part that contains the source vertices to the rest of the parts and because this will result in the source part being modified (loosing ownership of vertices results in loosing vertices), instead of transferring the vertices directly from the 1st source, all of the vertices will first be copied to another part (the pelvis) to be used as the direct source for the TransferBCycle nodes. This is done using a CopyPart node. Note that the demo robot drags the Part nodes from the skeleton to the CopyPart node while holding down the Alt key so that the Parts are dragged as references. Also note that the source node is dropped to the upper half (and to the right) of the CopyPart's icon so that it is dropped as a source node and that the destination part is dragged to the lower half of the icon so that it is dragged as the destination part. The source part is differentiated from the destination part in the scene tree by the blue dot to the left of the referenced part's icon:

The part model_source is hidden from here on so that the only triangles that will be visible, will be contained in the parts used for the actual model.

5. Place the Avatar to the Floor
This is a floor set to the height of -1.75 meters which is suitable for an avatar to be used in a blaxxun multi-user world.

If the model is to be used strictly for the H-Anim standard, a floor height of zero should be used instead.

6. Zoom in View to l_shoulder
Shows how to center the view to the position of the selected vertex and then zoom in on this point.

7. Transfer from pelvis to 1st group for shoulder
Here the first TransferBCyl node is added. TransferBCyl nodes are set the task of selecting vertices from the source part node (the upper reference part with the blue dot) and transferring them to the dest(ination) part (the lower reference part without the blue dot). The position of the vertices does not change because all part nodes at this stage are centred at the same location (0,0,0) and so only the ownership of the vertices changes from the transfer. The vertices from the source (pelvis) are selected using a semi transparent cylinder. The cylinder's proportions are specified by the TransferBCyl's radius and height fields. The cylinder is positioned using the location and orientation fields. The cylinder is visible in the 3d window when TransferBCyl node is selected and while the in field is checked. The indices for the selected vertices are put in the vertex field. Therefore the length property for the vertex field shows how many vertices have been selected.

The robot un-checks the in field after each TransferBCyl node is added only to speed up the build cycles because with in unchecked the transfer does not have do the time consuming task of measuring which vertices fit within the cylinder thanks to the vertex field remembering which vertices to transfer.

When a part like the shoulder bends during animation, we can improve the quality of the joint by making it so that different groups of vertices at the joint rotate fractions of the full amount of the rotation field for the part.
Here we see how the shoulder and elbow would look if all the vertices for these parts are allowed to all bend the full amount of the part's rotation field:



and here we see:



how the shoulder and elbow will look with the first 1st and 2nd ring of vertices bending only 1/3rd, the and 2/3rds the full amount of the part's rotation field.
Grouping the vertices into 3 different groups for the l_shoulder part is achieved by using 3 TransferBCyl nodes, with each one of the TransferBCyl node's cylinder set to select each group for the l_shoulder.
The group field is set to 0 so that the coordGroup field for the destination part is set to the number of vertices for the first group (coordGroup element at index 0).
The TransferBCyl node takes care of the work of sorting out the indices of the coords for us but because the groups are specified by the range of the indices (from coord 0 to coord 9 for the 1st group and from coord 10 to coord 19 for the second group), it is important that we do the first ring for the shoulder first and then the next ring second in line for the build cycle. Otherwise the groups will not be sorted in the order intended during animation.

After the TransferBCyl fields are set the part l_shoulder's weight field is set to .333 (weight element at index 0) to specify the first group to rotate 1/3rd the full rotation (1 = the full amount) during animation.

Note: the TransferBCyl's group field can be left to the default value of -1 (will not change the part's coordGroup with this value), if we manually specify the part's coordGroup field to the number of vertices we want for the group but it makes us less likely to add a bug if we let the TransferBCyl node write in the number of vertices it has selected from the cylinder.


8. Transfer from pelvis to 2nd group for shoulder
Because this is for the second group for the l_shoulder part, the group field is set to 1 and the part's weight field at index 1 is set to .333 to specify the second group rotate 2/3rds the full rotation during animation.

Note how instead of adding a new TransferBCyl node from the new node bar, a copy of the previous node is made by holding down the control key while dragging the previous TransferBCyl node to the GroupBuild node. This has the advantage of beginning with a new node whose fields are set to the values of the previous node.

9. Transfer Vertices from pelvis to rest of shoulder
Because this is for the 3rd and last group for the l_shoulder, there is no need to set the group field to 2 and the part's weight field to 1 because this last group can be left to rotate to the default full amount.


10. Transfer from pelvis to 1st group for l_elbow
11. Transfer from pelvis to 2nd group for l_elbow
12. Transfer Vertices from pelvis to rest of l_elbow
13. Transfer from pelvis to 1st group for l_wrist
14. Transfer Vertices from pelvis to rest of l_wrist
15. Transfer Vertices for the Right Arm
Because the model is symmetrical, the right arm TransferBCyl nodes are exactly the same as the left TransferBCyl nodes except for the location and orientation for the cylinders. Because these fields are set to mirror the left side, all that has to be done is add a minus sign for the x components for the location fields and to rotate the orientation fields half a revolution. The control key is held down while the orientation field buttons are clicked, so that the orientation value will rotate at clean right angles.

16. Transfer pelvis to 1st group for l_hip
17. Transfer from pelvis to 2nd group for l_hip
18. Transfer Vertices from pelvis to rest of l_hip
19. Transfer from pelvis to 1st group for l_knee
20. Transfer from pelvis to 2nd group for l_knee
21. Transfer Vertices from pelvis to rest of l_knee
22. Transfer from pelvis to 1st group for l_ankle
23. Transfer Vertices from pelvis to rest of l_ankle
24. Transfer Vertices for the Right Leg

25. Transfer pelvis to tummy0
Because the parts, tummy0, tummy1 thorax, neck0, neck1 and head are parts for the spine and bend much the same as snake joints (each part only needs to bend in small amounts), these parts will not be divided into smaller groups like the parts were for the limbs.

26. Transfer pelvis to tummy1
27. Transfer pelvis to thorax
28. Transfer pelvis to neck0
29. Transfer pelvis to neck1
30. Transfer pelvis to head
With the last lot of vertices transferred to the head, the pelvis is left with only the triangles that are intended to stay owned by the pelvis.

31. Move the Pivot Points
Here the parts are centered so that when they are rotated by their rotation fields during animation, the pivot point for each part will be at the correct position. For all except the CenterJoint node that references the pelvis, the CenterJoint nodes numOf field is used to average the first ring of the vertices to create the location of the pivot point. This works out nicely because all of the part's first ring of vertices are indexed from 0 to 1 less than the number of vertices contained in the first ring.

Although Seamless3d naturally builds models with vertices that are indexed in an ordered fashion in accordance to their position, it would not matter at this stage if the vertices in our static model were ordered randomly because the TransferBCyl sorts the vertices index order so that they can be grouped. When the first ring is selected by the TransferBCyl node's cylinder, the coords for this ring can be grouped by their index range and for parts like the pelvis, head and thorax that do not have the first ring individually selected by the cylinder, it does not matter anyway because the TransferBCyl node's indexPosition field was left checked for all of the parts which causes the vertices to be sorted in order of the height of the vertex in relation to the orientation of the cylinder. (if the cylinder is orientated to be horizontal then the vertices are ordered horizontally).

Note indexPosition left unchecked will significantly speed up the TransferBCyl for a build cycle when the in field is checked. However because most of the parts will have the in field unchecked at any one time in this demo, little difference if any will be noticed by unchecking the indexPosition field for parts where it is not required and so this field has been left checked for all of the parts in this demo.

Demo Completed

Animating The Model

After moving the pivot points the model is ready to be animated. Because animating this model will be the same as it is for animating the model made in the build avatar demo,

 

the same demo operations beginning at operation 26 Setup Animation, will show how to animate this model.

Making Modifications to the TransferBCyl Fields at a Later Date

One of the great advantages of using build nodes is one can go back in time and make modifications to one's work. However this freedom comes with the possibility of one being able to write bugs that cause a build cycle to malfunction. For example if a TransferBCyl's in field is unchecked and the cylinder is changed to select different vertices and there are other TransferBCyl nodes that come after in the build cycle which have their in fields unchecked, they are likely to no longer be locked into relevant vertices which can result in them indexing vertices that do not exist by the time they get their turn to function. This problem is easily avoided however if before modifying a TransferBCyl node's fields, the user right clicks on the build node and selects:

This causes the selected node and all build nodes that come after in the build cycle to have their in field checked if they have one.

A full build cycle will make things slower (only for editing) but the in fields can be all unchecked back just as easily by right clicking on the same build node and selecting fast build. If your computer is fast or if you prefer to always play it safe, consider permanently leaving the in fields checked so that indexing will always adjust dynamically when ever changes are made, any where in the build cycle. If you take this approach, it is worth un-checking the indexPosition field for parts that do not need it.


Copyright © 2000-2006 Graham Perrett thyme@seamless3d.com