A More Complete Robot Example
Here's a similar example, applied to a more complete figure. The Stickman sample program displays a stick figure robot (see Figure 6). The sliders let you turn the robot’s head and move its left and right shoulders, elbows, hips, and knees.
The basic idea for building Stickman's transformations is the same as the one used by the RobotArm program. The top-level group contains the robot’s base (which in this case is its head), spine, shoulder group, and hip group.
The shoulder group contains the shoulders and groups for the left and right upper arms. Each upper arm group contains the actual upper arm plus the lower arm.
Similarly the hip group contains the hips and groups for the left and right upper legs. The upper leg groups contain the upper and lower legs.
Unlike the RobotArm program, this example builds its robot out of spheres and cylinders. All together, those shapes contain thousands of triangles, so building the whole thing in XAML code is impractical; instead, the program uses code-behind to build its shapes. That introduces a new technique: binding a transformation to a slider's value at run time.
The following code shows how the program builds the robot’s right forearm.
// Right forearm.
GeometryModel3D rforearm_model = null;
Material rforearm_material =
MeshGeometry3D rforearm_mesh = null;
MakeCylinder(TheModel, ref rforearm_model, ref rforearm_mesh,
0, -6, 3, 0, -9, 3,
0, 0, 1, 1, 0.5, 0.5, 20);
The code creates GeometryModel3D, Material, and MeshGeometry3D objects for the forearm, and then calls the MakeCylinder method to create a cylinder representing the forearm.
The following code shows how the program bends the robot’s right elbow.
// Right forearm transformation.
AxisAngleRotation3D relbow_rotation =
relbow_rotation.Axis = new Vector3D(0, 0, 1);
Binding relbow_binding = new Binding("Value");
relbow_binding.Source = sliRElbow;
RotateTransform3D relbow_rot =
new RotateTransform3D(relbow_rotation, 0, -6, 3);
Transform3DGroup rforearm_transform = new Transform3DGroup();
rforearm_model.Transform = rforearm_transform;
The code first instantiates an AxisAngleRotation3D object to represent rotation around the Z-axis. (The robot’s initial position is standing in the YZ plane facing in the positive X direction, so the shoulders and elbows rotate parallel to the Z-axis.)
The code then creates a Binding object that binds to a Value property. It sets the Binding’s Source to the appropriate slider, and calls SetBinding to bind the AxisAngleRotation3D object’s Angle property.
It then uses the AxisAngleRotation3D object to make a new RotateTransform object that rotates around the point (0, -6, 3), the elbow’s location in the robot’s initial position.
Finally the code makes a Transform3DGroup, adds the elbow and shoulder transformations to it, and applies the result to the forearm’s model.
The Stickman program demonstrates the basic techniques you need to build robots, but you could go a long way toward making it more realistic. For example, you could add textures to improve the realism of the surfaces; or extend the model, adding facial features, hands, feet, fingers, and toes. However, if you did that, the program would become hopelessly cluttered with sliders.
The Stickman example allows only fairly simple transformations. For example, the upper arms bend only forward and backward relative to the shoulders—but a real shoulder joint is a ball-and-socket joint that allows much more freedom of movement. Similarly, to improve the realism, the hips should allow greater range of motion, and the lower arms and legs should allow some twist. This robot will never do the Macarena, but it does show how to use simple transformations.
Download the examples and experiment with them. Add some extra degrees of freedom at the joints and see if you can build a more flexible robot that can dance and do yoga. Once you’ve mastered using transformations to provide joints, you can move on to more complex models such as spiders, snakes, and octopi.