//---------------------------------------------------------------------
// Ukazkovy priklad k serii clanku o graficke knihovne OpenGL a GLU
//
// Autor: Pavel Tisnovsky
// Cislo clanku: 20
// Cislo prikladu: 1
//
// Program otevre jedno hlavni okno a vykresli do nej slozitejsi
// polygon vytvoreny pomoci teselatoru. Okno (a tim i celou aplikaci)
// lze ukoncit stiskem klavesy ESC.
//---------------------------------------------------------------------
#include <GL/gl.h>
#include <GL/glu.h>
#include <GL/glut.h> // hlavickovy soubor funkci GLUTu
#include <stdlib.h>
#include <stdio.h>
#define WINDOW_WIDTH 450 // velikost okna
#define WINDOW_HEIGHT 250
#define WINDOW_TITLE "OpenGL a GLU, priklad 20.1"// titulek okna
#ifndef CALLBACK
#define CALLBACK
#endif
GLdouble currentWinding = GLU_TESS_WINDING_ODD;
GLUtesselator *gluTessObject;
//---------------------------------------------------------------------
// Nastaveni souradneho systemu v zavislosti na velikosti okna
//---------------------------------------------------------------------
void onResize(int w, int h) // w a h reprezentuje novou velikost okna
{
glViewport(0, 0, w, h); // viditelna oblast pres cele okno
glMatrixMode(GL_PROJECTION); // zacatek modifikace projekcni matice
glLoadIdentity(); // vymazani projekcni matice (=identita)
glOrtho(0, w, 0, h, -1, 1); // mapovani abstraktnich souradnic do souradnic okna
glTranslatef(0.0, h, 0.0);
glScalef(1.0, -1.0, 1.0);
glMatrixMode(GL_MODELVIEW);
glLoadIdentity();
}
//---------------------------------------------------------------------
// Callback funkce volana pri zahajeni vykreslovani graficke primitivy
//---------------------------------------------------------------------
void CALLBACK callbackBegin(GLenum which)
{
glBegin(which);
}
//---------------------------------------------------------------------
// Callback funkce volana pri ukonceni vykreslovani graficke primitivy
//---------------------------------------------------------------------
void CALLBACK callbackEnd(void)
{
glEnd();
}
//---------------------------------------------------------------------
// Callback funkce volana pri vyskytu chyby
//---------------------------------------------------------------------
void CALLBACK callbackError(GLenum errorCode)
{
const GLubyte *s=gluErrorString(errorCode);
fprintf(stderr, "chyba pri teselaci: %s\n", s);
exit(0);
}
//---------------------------------------------------------------------
// Tato funkce je volana pri kazdem prekresleni okna
//---------------------------------------------------------------------
void onDisplay(void)
{
glClearColor(0.0, 0.0, 0.0, 0.0); // nastaveni mazaci barvy na cernou
glClear(GL_COLOR_BUFFER_BIT); // vymazani bitovych rovin barvoveho bufferu
glShadeModel(GL_FLAT);
glPolygonMode(GL_FRONT_AND_BACK, GL_LINE); // rezim vykreslovani polygonu
glColor3f(1.0f, 1.0f, 1.0f); // nastaveni barvy pro kresleni
glBegin(GL_POLYGON); // vykresleni konvexniho polygonu
glVertex2i( 50, 100);
glVertex2i(100, 50);
glVertex2i(150, 50);
glVertex2i(200, 100);
glVertex2i(200, 150);
glVertex2i(150, 200);
glVertex2i(100, 200);
glVertex2i( 50, 150);
glEnd();
gluTessObject=gluNewTess(); // vytvoreni objektu pro teselaci
gluTessCallback(gluTessObject, GLU_TESS_VERTEX, glVertex3dv);
gluTessCallback(gluTessObject, GLU_TESS_BEGIN, callbackBegin);
gluTessCallback(gluTessObject, GLU_TESS_END, callbackEnd);
gluTessCallback(gluTessObject, GLU_TESS_ERROR, callbackError);
gluTessProperty(gluTessObject, GLU_TESS_WINDING_RULE, currentWinding);
gluTessBeginPolygon(gluTessObject, NULL); // zahajeni noveho polygonu
gluTessBeginContour(gluTessObject); // zahajeni nove kontury
GLdouble vertex[][3]={
{250, 100},
{300, 50},
{350, 50},
{400, 100},
{400, 150},
{350, 200},
{300, 200},
{250, 150}
};
// specifikace jednotlivych vrcholu kontury
gluTessVertex(gluTessObject, vertex[0], vertex[0]);
gluTessVertex(gluTessObject, vertex[1], vertex[1]);
gluTessVertex(gluTessObject, vertex[2], vertex[2]);
gluTessVertex(gluTessObject, vertex[3], vertex[3]);
gluTessVertex(gluTessObject, vertex[4], vertex[4]);
gluTessVertex(gluTessObject, vertex[5], vertex[5]);
gluTessVertex(gluTessObject, vertex[6], vertex[6]);
gluTessVertex(gluTessObject, vertex[7], vertex[7]);
gluTessEndContour(gluTessObject); // konec specifikace kontury
gluTessEndPolygon(gluTessObject); // konec specifikace polygonu
gluDeleteTess(gluTessObject); // zruseni objektu teselatoru
glFlush(); // provedeni a vykresleni zmen
}
//---------------------------------------------------------------------
// Tato funkce je volana pri stlaceni ASCII klavesy
//---------------------------------------------------------------------
void onKeyboard(unsigned char key, int x, int y)
{
if (key==27) exit(0); // pokud byla stlacena klavesa ESC, konec programu
}
//---------------------------------------------------------------------
// Hlavni funkce konzolove aplikace
//---------------------------------------------------------------------
int main(int argc, char **argv)
{
glutInit(&argc, argv); // inicializace knihovny GLUT
glutInitDisplayMode(GLUT_SINGLE | GLUT_RGB); // nastaveni jednoho barvoveho bufferu
glutInitWindowPosition(30, 30); // pocatecni pozice leveho horniho rohu okna
glutInitWindowSize(WINDOW_WIDTH, WINDOW_HEIGHT);// pocatecni velikost okna
glutCreateWindow(WINDOW_TITLE); // vytvoreni okna pro kresleni
glutDisplayFunc(onDisplay); // registrace funkce volane pri prekreslovani okna
glutReshapeFunc(onResize); // registrace funkce volane pri zmene velikosti okna
glutKeyboardFunc(onKeyboard); // registrace funkce volane pri stlaceni klavesy
glutMainLoop(); // nekonecna smycka, kde se volaji zaregistrovane funkce
return 0; // navratova hodnota vracena operacnimu systemu
}
//---------------------------------------------------------------------
// Konec zdrojoveho souboru
//---------------------------------------------------------------------