O objetivo desta aula é testar na prática os conceitos de Computação Gráfica
estudados em aula. Serão utilizadas apenas as bibliotecas OpenGL, GLU e GLUT, de maneira que o
programa fique portável e possa ser executado tanto no ambiente Windows como no ambiente
Linux
Para implementação de aplicações OpenGL é necessário criar um projeto para
linkar as bibliotecas. Descompacte o arquivo Quadrado.zip para um diretório e abra o arquivo
Depois, compile e execute o programa que abrirá uma janela com fundo preto e um quadrado colorido, conforme
mostra a próxima figura.
Observe atentamente o código para entender o seu funcionamento, considerando a
estrutura básica de um programa OpenGL:
- Função main, onde a comunicação com a OpenGL é estabelecida e são disparadas as inicializações
necessárias, que inclui a definição das funções callback;
- Função que contém as inicializações relativas à exibição (Inicializa);
- Função callback (Desenha) responsável pelo desenho;
- Função callback (AlteraTamanhoJanela) que é chamada sempre que a janela for redimensionada.
Agora altere o código fonte conforme descrito a seguir e, a cada alteração,
compile e execute novamente o programa para verificar os resultados obtidos. Em caso de dúvida, consulte a professora
ou o tuturial de introdução à OpenGL disponível em
http://www.inf.pucrs.br/~manssour/OpenGL/Tutorial.html.
- Troque a cor de fundo da janela, modificando os argumentos da chamada da função
glClearColor(0.0f, 0.0f, 0.0f, 1.0f), e as cores do desenho (glColor3f(1.0f, 0.0f, 0.0f););
-
Altere o nome, o tamanho e a posição da janela GLUT nas
funções de inicialização chamadas na main;
- Por enquanto, elimine o cálculo para correção da razão do aspecto (coloque apenas gluOrtho2D (-250.0f, 250.0f, -250.0f, 250.0f);,
que faz com que a origem do sistema de referência fique no centro da window)
- Desenhe duas linhas que representem os eixos cartesianos do universo (use glBegin(GL_LINES) e glEnd(),
acrescentando os quatro vértices necessários para o desenho dos eixos);
Importante: todas as rotinas de desenho devem ser chamadas na função Desenha;
- Substitua a chamada à função glBegin(GL_QUADS);....glEnd();
pelo desenho de um triângulo e de um quadrado, que devem ser
definidos de maneira a formar uma casinha, como mostra a próxima
figura. Os comandos para desenhar a casinha
são:
glLineWidth(3);
glBegin(GL_TRIANGLES);
glColor3f(0.0f, 0.0f, 1.0f);
glVertex2i(50,100);
glColor3f(1.0f, 0.0f, 0.0f);
glVertex2i(100,150);
glColor3f(0.0f, 0.0f, 1.0f);
glVertex2i(150,100);
glEnd();
glBegin(GL_LINE_LOOP);
glVertex2i(50,1);
glVertex2i(50,99);
glVertex2i(150,99);
glVertex2i(150,1);
glEnd();
-
Aplique uma tranformação geométrica de 45 graus de
rotação na casinha (importante: a rotação,
bem como as transformações
de escala e translação, deve ser aplicada antes que a casinha seja desenhada);
- Altere o ângulo de rotação de 45 para 90 graus e veja o que acontece;
-
Altere a posição da casinha de maneira que ela seja
rotacionada em torno do seu ponto central e não troque de
"quadrante". Neste caso, troque os valores dos vértices de tal
maneira que o centro da casinha fique na posição (0,0).
Como fazer para interagir com o programa sem que seja necessário
compilar o código cada vez que o objeto, por exemplo, é
rotacionado com um ângulo diferente? Neste caso, pode ser
definida uma
função callback para gerenciar eventos do teclado. Para isto, inicialmente, registre esta função callback
acrestando a seguinte linha de código na função main, antes da chamada para a função Inicializa():
glutSpecialFunc(TeclasEspeciais);
Em seguida, declare as seguintes variáveis globais (logo após os includes):
GLint tx, ty, angulo;
GLfloat ex,ey;
Inicialize estas variáveis na função Inicializa() com os seguintes valores:
tx = 0;
ty = 0;
angulo = 0;
ex = 1;
ey = 1;
Agora acrescente os comandos abaixo na função Desenha, no lugar do comando
glRotatef colocado anteriormente:
glTranslatef(tx, ty, 0);
glScalef(ex, ey, 1);
glRotatef(angulo, 0, 0, 1);
Finalmente, para fazer o tratamento dos eventos, inclua e termine de implementar a
função callback TeclasEspeciais descrita abaixo. Complete código desta função de maneira a permitir:
- rotacionar o objeto para esquerda cada vez o usuário pressiona a tecla PageUp (incremente a variável global angulo);
- rotacionar o objeto para direita cada vez o usuário pressiona a tecla PageDn (decremente a variável global angulo);
- aumentar o tamanho do objeto cada vez que o usuário pressiona a tecla Home (incremente ex e ey);
- diminuir o tamanho do objeto cada vez que o usuário pressiona a tecla End (decremente ex e ey);
- transladar o objeto para cima, para baixo, para a esquerda e para a direita sempre que o
usuário pressionar cada uma das teclas de setas (incremente e decremente as variáveis tx e ty).
void TeclasEspeciais(int key, int x, int y) { switch (key) { case GLUT_KEY_PAGE_UP: break; case GLUT_KEY_PAGE_DOWN: break; case GLUT_KEY_HOME: break; case GLUT_KEY_END: break; case GLUT_KEY_UP: break; case GLUT_KEY_DOWN: break; case GLUT_KEY_LEFT: break; case GLUT_KEY_RIGHT: break; } glutPostRedisplay(); }
Para outras informações sobre o tratamento de eventos, consulte o tutorial de
OpenGL (http://www.inf.pucrs.br/~manssour/OpenGL/Eventos.html).
|