Hello, everyone!
I'm starting to learn OpenGL and I have a problem with linear transformations.
The program is very basic: I want to draw 4 squares and make them move individually (by doing translations and rotation). I understand that I need to stock all the transformation in a matrix, so I can multiply it to the square information to get the good translation and rotation parameters. Unfortunately, the red square (the one missing) doesn't want to print on the screen. I have searched for a long time and I don't know what causes the problem: maybe a bad mode initialize or something else... Can someone help me? I have posted the code below.
N.B: You may need to add some includes for the code to work. My confguration of OpenGL only needs <gl/glut.h>
#include <gl/glut.h>
#include <stdio.h>
/**
This program draws 4 squares and do moves on them (translations, rotations, ...)
*/
GLint windowX;
GLint windowY;
GLdouble redTransformationMatrix[16];
void reshape(GLint x, GLint y)
{
windowX = x;
windowY = y;
glViewport(0,0,windowX,windowY); // Reset The Current Viewport
glMatrixMode(GL_PROJECTION); // Select The Projection Matrix
glLoadIdentity(); // Reset The Projection Matrix
glMatrixMode(GL_MODELVIEW); // Select The Modelview Matrix
glLoadIdentity(); // Reset The Modelview Matrix
}
/**
\brief Initializes transformations.
*/
void init()
{
glMatrixMode(GL_MODELVIEW);
glLoadIdentity();
glGetDoublev(GL_MODELVIEW_MATRIX, redTransformationMatrix); //Sets the red square transformation matrix with an identity matrix.
}
/**
\brief Function that is called when a key is pressed on the keyboard.
\param key The ASCII value of the key.
\param x The x value of the mouse position at the event.
\param y The y value of the mouse position at the event.
*/
void keyboardPressed(unsigned char key, int x, int y)
{
switch (key)
{
case 'D':
case 'd':
{
//Translation of the red square.
glMatrixMode(GL_MODELVIEW);
glLoadMatrixd(redTransformationMatrix);
glTranslated(25.0, 0.0, 0.0);
glGetDoublev(GL_MODELVIEW, redTransformationMatrix);
glutPostRedisplay();
break;
}
}
}
/**
\brief Function that draws a square, knowing the middle point and the length of a side.
\param middleX The X coordinate of the middle point.
\param middleY The Y coordinate of the middle point.
\param sideLength The length of a side of the square.
*/
void DrawSquare(GLdouble middleX, GLdouble middleY, GLdouble sideLength)
{
glBegin(GL_QUADS);
glVertex2d(middleX - (sideLength / 2), middleY + (sideLength / 2));
glVertex2d(middleX + (sideLength / 2), middleY + (sideLength / 2));
glVertex2d(middleX + (sideLength / 2), middleY - (sideLength / 2));
glVertex2d(middleX - (sideLength / 2), middleY - (sideLength / 2));
glEnd();
}
/**
\brief Function that is called for every display on the screen.
*/
void display()
{
glMatrixMode(GL_MODELVIEW);
glClear(GL_COLOR_BUFFER_BIT | GL_DEPTH_BUFFER_BIT);
// Reset the current modelview matrix
glLoadIdentity(); //Makes sure that no affine transformation applies here.
//We need to set the viewport and the orthonormal bounds.
glViewport(0, 0, windowX, windowY);
glOrtho(0.0, windowX, 0.0, windowY, -1.0, 1.0);
//Let's draw the squares.
//Red square -- trying here to apply the transformation matrix on the red square.
glPushMatrix();
glLoadMatrixd(redTransformationMatrix);
glColor3d(1.0, 0.0, 0.0);
DrawSquare(200.0, 600.0, 100.0);
glPopMatrix();
//Green square
glColor3d(0.0, 1.0, 0.0);
DrawSquare(600.0, 600.0, 100.0);
//Blue square
glColor3d(0.0, 0.0, 1.0);
DrawSquare(600.0, 200.0, 100.0);
//Yellow square
glColor3d(1.0, 1.0, 0.0);
DrawSquare(200.0, 200.0, 100.0);
glutSwapBuffers(); //Very important, because we are using double buffers and we want to print.
}
int main(int argc, char** argv)
{
glutInit(&argc, argv);
glClearColor(0.0, 0.0, 0.0, 0.0); //Black background color.
windowX = 800;
windowY = 800;
glutInitWindowPosition(0, 0);
glutInitWindowSize(windowX, windowY);
glutInitDisplayMode(GLUT_RGB | GLUT_DOUBLE);
glutCreateWindow("FourSquares");
//Basic initialize...
init();
glClear(GL_COLOR_BUFFER_BIT | GL_DEPTH_BUFFER_BIT);
glutKeyboardFunc(keyboardPressed);
glutReshapeFunc(reshape);
glutDisplayFunc(display);
//The events may start.
glutMainLoop();
return 0;
}