Sunday, October 26, 2014

How to implement basic transformations on objects


I have taught CGV under Visvesvaraya Technological University more than six times and you may ask did I not get bored? Yes I did. Three times in the 1998/2002 scheme and three times in the 2006/2010 scheme. There is a vast difference between the syllabus of the earlier scheme and that of the 2006 scheme and onwards. Earlier scheme relied on textbook by James D Foley and others. The 2006 scheme follows Edward Angel and has introduced OpenGL to computer science students.
Students of yesteryears including me learn’t the now obsolete graphics.h library. I still remember those says when I had purchased a computer and was hunting for the EGAVGA.BGI file from my computer assembler. Coming to the topic It might strike you late but the importance of mathematics in Computer Graphics and Visualization is as Breath is to Life.
I will take you on a journey into a bit of transformations and how to realize them. “Your geometry lessons in schools will help you learn to write Graphics Programs”. Yes you heard it right.

Translation

One of the first things that a student of computer graphics learns is to move an object from one place to another. Actually, We draw an object at a particular place. So all we need to do to move it is to erase the object from that place and draw it at a new place (position). Place/position is measured with respect to a co-ordinate system. It may be 2-D or 3D coordinate system with x,y and z axis. A point may have three values like this:
int p1x,p1y,p1z; // non object oriented way
or
class point // object oriented way
{
int x,y,z;
};
point p1;
Now comes the most interesting part…. In OpenGL, transformations are implemented as functions. So if you want to apply any transformation on an object calling the transformation function before drawing the object will be sufficient to apply that transformation on that object.
So we have a function called glTranslatef to translate an object from one place to another. This function changes the position where objects are drawn.
Look at this code:
glTranslatef(4.0,3.0,0);
drawtriangle();
It draws a triangle at current raster position. That position is moved by glTranslatef() function to 4 units right(x axis) and three units up(y axis).

Rotation

All students of CSE/MCA would want to implement rotation in their projects but would not know how to rotate a particular object in the scene. Suppose I have drawn a line on the screen like this:
glBegin(GL_LINES);
glVertex2f(p1x,p1y);
glVertex2f(p2x,p2y);
glEnd();
This piece of code is present somewhere in the display function or any other function which is called from within display.

I want to rotate this line with respect to its centre. How to I do that?

You would have studied in your course about glPushMatrix(); and glPopMatrix(); functions. There is something called as the current transformation matrix (CTM). All objects going through the pipeline undergo these transformations. So if you want to apply a transformation to only the object you selected you just need to save the current transformation matrix somewhere so that it can be retrieved later. No better place than the stack to save it. PushMatrix saves the CTM on the stack and PopMatrix pops it from the stack and makes it the CTM.

To rotate this line we need to write the following code:
glPushMatrix();
glTranslatef((p1x+p2x)/2,(p1y+p2y)/2)); // go to a position at the center of the line 
glRotatef(10,0,1,0); // Rotate by 10 degrees the line wrt y-axis(0,1,0)
glTranslatef(-(p1x+p2x)/2,-(p1y+p2y)/2)); // go to a position at the center of the line
glBegin(GL_LINES);
glVertex2f(p1x,p1y);
glVertex2f(p2x,p2y);
glEnd();
glPopMatrix();

This code will draw the line in a rotated position. If you want continuous rotation you will need to increment this angle ‘10’ continuously by substituting a variable in its place. Here is the entire program to draw a rotating line while another object(teapot) nearby is stationary.
This snapshot represents the output:

Scaling:

Similar to rotation you would want objects to become big and small. Scaling an object involves calling the function glScalef();
So it it’s a 3D object like a teapot then glutSolidTeapot() is used to draw a teapot. To draw a teapot of different size we would
….. // here you would move the raster position to where
….. // you want to draw the teapot
glPushMatrix();
glScalef(2,2,2);
glutSolidTeapot();
glPopMatrix();

Here is a program where there is a rotating line and a teapot drawn with varying sizes and another nearby object(line) is not scaled but slowly rotating.
 Snapshot:

I hope your problem of applying transformations to selected objects is solved now. Happy Coding.

Wednesday, September 24, 2014

Tetra Turns into a Sphere and Viceversa

You may be aware of how a tetrahedron looks like. It is a polyhedra made up of four equilateral triangles.
 In this program all the equilateral triangles have a sierpinski gasket on them. Sierpinski gasket is a fractal drawn recursively by dividing the edges of the triangle and then inscribing a triangle with vertices at the center of each edge. Except the inscribed triangle all other triangles are repeatedly subdivided. Here is how a Sierpinski gasket looks like...
In my program that is the first one where the tetra turns into a sphere....i have colored the triangles inside the tetrahedron using Red, Green, Blue and Black Colors.
I will show a snippet of code which is doing this magic.
Here is the source.
 In the function normalize i have added the following code:(See comments)
void normalize(GLfloat *p)
{ double d=0.0;
int i;
for(i=0;i<3;i++) d+=p[i]*p[i]; //find the length of the vector
d=sqrt(d); // starting from origin to face of tetra
d=d+(1-d)*sf; // sf(scaling factor) has abs of sine wave 
                           // which is set in idle function
 if(max<d) max=d; // this statement i guess is not needed
if(d>0.0)
for(i=0;i<3;i++) p[i]/=d;//divide the vector components by the
}                                            // newly required length in d
Here is the idle function
void idle()
{ sf=fabs(sin(angle)); // as mentioned abs of sine wave
angle+=0.0004; // increment angle
if(angle>=360) angle=0; // if angle overflows
glutPostRedisplay(); // call display every possible moment
}
Happy Coding!
Small modification now the up and down arrow increases or decreases the angle and hence the scaling factor which decides the difference between the tetra and the sphere. Here is the modified code.

Tuesday, September 23, 2014

Another modification to the tetra program

Another modification to the tetra program that i made my poor students do were to add a timer to the program. In the timer function the color of the four faces of the tetra are changed. Its a glittering program where the tetra changes color every second. Some may say i went crazy making the students do these modifications. They were begging me to explain the code and i could just mumble that you will not understand now. When i covered the topic on timers i guess they understood.

Here are the snapshots:



Here is the source.

Modification to house rotation program

This program asks for initial rotation angle and starting from that orientation keeps rotating the house about the pivot point. Meaning less modification you may say but this is what i taught the students in the lab.

Snapshots:




Here is the source.

Modifications made to Cylinder and Parallelepiped

Modifications made to Cylinder and Parallelepiped program. The scene has been made to rotate on mouse input.
Several modifications need to be made in code to achieve this.

Snapshots:






Here is the source.

Program to draw a teapot over a table and rotate the scene using mouse

Program to draw a teapot over a table and rotate the scene using mouse input. This is the same program as the teapot program. The only modifications done are color of the teapot and the walls are changed. The scene is rotated using mouse input(on dragging the mouse).

Here are the snapshots:








Here is the source.

Drawing a sphere using a tetrahedron in OpenGL

This is a program in the seventh unit of Computer Graphics & Visualization (14CS65) of 6th semester CSE branch in VTU. This program has been modified to rotate the scene using mouse input. It asks for number of divisions. Once that is entered it draws a sphere using the same program to draw a tetra. A brief explanation of the code will follow soon.

Here are the snapshots:







Here is the source. Have a look at an animation of the above transformation where the tetra turns into a sphere and vice-versa. In another modification I have created a tetra with colors of sides changing every second. Both the above modifications require us to use a timer and an idle function.