Assignment 2 - Hierarchical Transforms

Due Wednesday 2/12 at 11:59 pm. You must work individually.


Learn and apply hierarchical 3D transformations using the matrix stack.

Associated Labs


Write a program that allows you to create a robot that you can manipulate with the keyboard. You are free to create your own robotic character, but there should be at least 10 components in the robot, and the hierarchy should not be flat. For example, in the figures below, we have the following hierarchy:

When a parent component is transformed, all of its descendants should be transformed appropriately. The keyboard control should be as follows:

By pressing the period and comma keys, you should be able to select different components in the hierarchy. You must draw the selected component so that it is distinguishable from unselected components. The x/X, y/Y, and z/Z keys should change the rotation angle of the selected component. In the left figure above, the torso is the selected component, and in the right figure, one of the lower legs is the selected component. Here, the selected component is drawn darker than the unselected components, but you can color it the way you want or draw it slightly bigger.

Step 1

Start from your Lab 0 code base.

  1. Create your A2 project folder and copy the L00 files and folders into it.
  2. Modify CMakeLists.txt to change the project name (line 4).
  3. Add GLM calls so that you can draw transformed squares. (If you’re not sure how to do this, you may want to start with Lab 4.) You should go through the various helper classes (e.g., Shape, Program, etc.) to understand roughly what they are doing.
  4. Add support for keyboard input (x/X, y/Y, z/Z) by using the glfwSetCharCallback() function.

Step 2

Create a class that represents a component. This class should contain the necessary member variables so that you can make a tree data structure out of these components. The root of the tree should represent the torso, which means that transforming the torso transforms everything else.

In addition to the member variables required for the tree hierarchy, the class should also have the following:

The drawing code should be recursive - in other words, in the render() function in main.cpp, there should be a single draw call on the root component, and all the other components should be drawn recursively from the root. In the main render() function, you should create an instance of the matrix stack class and pass it to the root component’s drawing function. Make sure to pass the matrix stack by reference or as a (smart) pointer.

The component’s rendering method should simply take the current state of the component and draw it. You should not create the robot hierarchy in this method. In other words, the scene setup must be done in main’s init() rather than in main’s render(). Whenever the keyboard is pressed, the char_callback() function is called. Update the robot’s joint angles inside this function.

For this assignment, the 3D rotation of the joint should be represented simply as a concatenation of three separate rotation matrices about the x-, y-, and z-axes: Rx * Ry * Rz. The position of the joint should not be at the center of the box. For example, the elbow joint should be positioned between the upper and lower arms.

You must draw the selected component differently from unselected components. For example, in the images above, the selected component is darker than the other components. You can either change the color (like above) or change the size.

The traversal of the tree with the period and comma keys should be in depth-first or breadth-first order. Do not hardcode this traversal order - your code should be set up so that it works with any tree.

HINT: Debugging OpenGL & GLSL


Point breakdown

Total: 105 points

What to hand in

Failing to follow these points may decrease your “general execution” score. On Linux/Mac, make sure that your code compiles and runs by typing:

> mkdir build
> cd build
> cmake ..
> make
> ./A2 ../resources

If you’re on Windows, make sure that you can build your code using the same procedure as in Lab 0.

Generated on Fri Apr 24 08:43:58 CDT 2020