CSCI 384 Computer Graphics

    College of the Holy Cross, Fall 2003

    Home | | Syllabus | | Assignments | | Documentation

    Assignment 4

    Due: Thursday, October 23, in class


    Problem 1:
    In this problem, you will use openGL functions to create a 3-Dimensional object that rotates about different axes depending on a key-press. You will first create a simple 3D box, open at the top and bottom, then you will add the code that allows it to rotate. Finally, you will write a program that recursively divides each of the quadrilateral faces into two new quads, generating the approximation of a cylinder (that is open at the top and bottom).

    Part a. A spinning box.
    Write a program similar to the example program for a spinning 3D pyramid demonstrated in lecture 12. This program should create a box, with 4 quadrilateral faces (instead of the square-based pyramid that was demonstrated in lecture) that is open at the top and bottom. Make your box centered on the origin. You should create the faces of the box so that the "outward" face is toward the outside of the object. (Use the right-hand rule to make sure you list the vertices in the correct order to accomplish this). Alternate the colors of the sides between red and blue so that you can see the three-dimensionality of the box. Use an idle function to rotate the box about the x or y axis so that you can see the different sides of it (just as we did in lecture). Save this file as username_box.c. The following image shows the tetrahedron viewed at an angle from the top:

    Part b. Add a user interface
    Save the program you wrote in part a in a new file called, username_spin.c. Modify this program to include a user-interface that detects a keypress. A press of the 'f' key should cause the tetrahedron to spin about the x axis. The 'j' key should cause spin about the y axis and the 'k' key should cause spin about the z axis. To respond to a keypress, use the function: glutKeyboard(keys), where keys() is the callback function for a keypress. An example of responding to a keypress is in the Moving Viewer program in appendix A.12 of the textbook. That program also has a mouse function that controls spin about an axis with a mouse-click. You will need to use the same logic in your keys() function that controls the spin axis with a keypress. Save the code for this part in a file called username_spin.c

    Part c. Approximating a cylinder
    One way to generate a sphere in openGL, is by successively dividing triangular faces of a polyhedron into more triangles, and normalizing all the vertices so that they lie on the surface of a sphere. An example of this approach is described in the textbook in section 6.6 and the program is given in appendix A.13> In this part of the problem, you will use a recursive strategy similar to that in example A.13 of the textbook (the Sphere program) to approximate a cylinder. Instead of using the divide_triangle function to recursively divide the object into triangular faces, you will write a recursive divide_quad() function that will recursively divide the quadrilateral faces of your box into 2 new quadrilateral faces. Save the code from part b in a new file, called username_cylinder.c. First, you will need to normalize the vertices of your box so that they all lie an equal distance from the y axis. If a vertex is at position (x, y, z), and you want it to be a distance, d, from the y axis, you can normalize by multiplying each component by d/(sqrt(x*x + z*z)). Make sure none of your vertices is at the point (0, 0, 0) before doing this!. Second, create a recursive function, divide_quad(), that takes four vertices and an integer counter as parameters. divide_quad() should calculate two new vertices from the four given as parameters, one at the center of the top edge and one at the center of the bottom edge. These new vertices should then be normalized to be at the same distance from the y axis as the others. The new vertices, along with pairs of the other four vertices, define 2 new quadrilaterals as shown below.

    If the recursive counting variable is greater than zero, these two new quads should be divided (by calling divide_quad with the new sets of vertices). This is then repeated for as many levels as defined by the counter. (I recommend trying small numbers, like 0, 1 and 2 levels, to test it out). When the counter reaches zero, render the current quadrilateral from the four vertex parameters. Below is the resulting object for m=1, viewed at an angle from the top.

    You will need to specify a unique color for each face of your cylinder. I recommend alternating the color between two primary colors such as red and blue. You can do this by setting the color to red before one call to divide_quad() and to blue before the second call to divide_quad(), and so on.

    Part d. Optional Extra Credit (worth up to 20 pts)
    Modify your program from part c to either create a more interesting object than a tetrahedron box, cylinder or sphere (worth 1 pt) or to make the tetrahedron (or object) do a more interesting animation than simply rotating around an axis when you hit the 'd' key (worth 1 pt). For example, it could do a little dance or it could turn on its head and hop around. I will base the score on good programming technique and originality. Have some fun with this part. Save your program in a file called username_extraCredit.c.


    Problem 2: Gimbal Lock
    If you followed the example given in A.12 of the book to make your box rotate about the three different coordinate axes, you will notice that the rotations are performed about each of the axes in turn:

      glRotatef(theta[0], 1.0, 0.0, 0.0); //Rotate about X axis glRotatef(theta[1], 0.0, 1.0, 0.0); //Rotate about Y axis glRotatef(theta[2], 0.0, 0.0, 1.0); //Rotate about Z axis

    This implementation leads to an interesting phenomenon, known as gimbal lock, which occurs in the following situation. If the user presses a key (the 'j' key) to rotate the object by 90 deg about the Y axis, then subsequent rotations about the X or Z axis will appear to have the same effect--i.e. the object will appear to rotate about the same axis for either key press. (The rotation is actually in opposite directions, but it is hard to see that with the 3D box or cylinder). What is going on here?

    Your task is to show that gimbal lock is a direct consequence of the calls to glRotatef() in the display function. Note that the program will perform the rotations in the same order (First about Z, then about Y and finally about X) when drawing the object, independent of the order in which the user pressed the keys. Use the matrix equations for the transformations involved in the three glRotatef() calls to show that the sequence Rz(theta)Ry(90)Rx(0) is equivalent to the sequence Rz(0)Ry(90)Rx(-theta). (You need to do the matrix multiplication on this one to show that the results are the same). Write out the matrix equations and their solutions.


    Problem 3: Camera Position based on Yaw, Pitch and Roll.
    In section 5.3.4 of the textbook, the concept of Yaw, Pitch and Roll are defined in terms of an aircraft. If the airplane is pointing along the Z axis, then yaw is a rotation about the y axis, pitch is rotation about the x axis and roll is rotation about the z axis. Note that the "camera" in this case is in the nose of the plane, which is not centered at the origin. Given three angles, theta1, theta2, and theta3 that define the amount of yaw, pitch and roll, respectively, and a distance d of the nose of the airplane from its center of mass (located at the origin), write the matrix multiplication equation that sets up the camera in the viewing position that corresponds to the yaw, pitch and roll (in that order). Hand in the equation, showing the complete matrices that are multiplied together. You do not need to multiply out these matrices.


    Turning in this assignment

    Turn in a hardcopy of the C code for problem 1, and your solutions for problems 2 and 3. This is due in class, Thursday, October 23.

    In addition, email a copy of the files containing your C code to me at croyden@mathcs.holycross.edu. The subject line should read "Graphics Assignment 4". There should be 3 files named "username_box.c", "username_spin.c", "username_cylinder.c" and (if you have it) "username_extraCredit.c". This should be dropped before the due date.


    Home | | Syllabus | | Assignments | | Documentation


    Constance Royden--croyden@mathcs.holycross.edu.edu
    Computer Science 384
    Date Created: August 17, 1999
    Last Modified: October 14, 2003
    Page Expires: August 17, 2004