/* gcc -o szesciany.exe -Wall szesciany.c glut32.lib -lopengl32 -lglu32 -std=c99 */ #include #include #include #include #include #include #define UP 0 #define DOWN 1 #define COLOR1_UP true #define COLOR1_DOWN false #define COLOR2_UP true #define COLOR2_DOWN false #define COLOR3_UP true #define COLOR3_DOWN false int i,j,k; int przycisk = 0.0; float katGlownejOsi = 0.0; float katPobocznychOsi = 0.0; float odlegloscOdSrodka = 1.0; float distance = 0; int direction = 0; float color1R = 0.0; float color1G = 0.0; float color1B = 1.0; float color2R = 0.0; float color2G = 0.0; float color2B = 1.0; float color3R = 0.0; float color3G = 0.0; float color3B = 1.0; float colorChange = 0.001f; int changedColor = 0; bool color1Direction = COLOR1_UP; bool color2Direction = COLOR2_UP; bool color3Direction = COLOR3_UP; void Rysuj() { glEnable(GL_DEPTH_TEST); glClear(GL_COLOR_BUFFER_BIT | GL_DEPTH_BUFFER_BIT); glMatrixMode(GL_MODELVIEW); glColor3f(0.0,0.0,1.0); glTranslatef(0.0,0.0,0.0); switch(przycisk) { case 0: glRotatef(katGlownejOsi,0,1,0); for(i=-1;i<2;i++) { for(j=-1;j<2;j++) { for(k=-1;k<2;k++) { glPushMatrix(); glTranslatef(i,j,k); switch(i) { case -1: glTranslatef(distance, 0, 0); break; case 0: glTranslatef(0, 0, 0); break; case 1: glTranslatef(-distance, 0, 0); break; } switch(j) { case -1: glTranslatef(0, distance, 0); break; case 0: glTranslatef(0, 0, 0); break; case 1: glTranslatef(0, -distance, 0); break; } switch(k) { case -1: glTranslatef(0, 0, distance); break; case 0: glTranslatef(0, 0, 0); break; case 1: glTranslatef(0, 0, -distance); break; } if(changedColor==1) { if(i==-1 && j==1 && k==-1) glColor3f(color1R, color1G, color1B); if(i==0 && j==1 && k==0) glColor3f(color2R, color2G, color2B); if(i==1 && j==1 && k==1) glColor3f(color3R, color3G, color3B); } glRotatef(-katPobocznychOsi,0,1,0); glutSolidCube(0.55); glPopMatrix(); glColor3f(0.0,0.0,1.0); } } } break; /* Obracanie wzgledem osi srodkowej */ case 1: katGlownejOsi += -0.05; glRotatef(katGlownejOsi,0,1,0); for(i=-1;i<2;i++) { for(j=-1;j<2;j++) { for(k=-1;k<2;k++) { glPushMatrix(); glTranslatef(i,j,k); switch(i) { case -1: glTranslatef(distance, 0, 0); break; case 0: glTranslatef(0, 0, 0); break; case 1: glTranslatef(-distance, 0, 0); break; } switch(j) { case -1: glTranslatef(0, distance, 0); break; case 0: glTranslatef(0, 0, 0); break; case 1: glTranslatef(0, -distance, 0); break; } switch(k) { case -1: glTranslatef(0, 0, distance); break; case 0: glTranslatef(0, 0, 0); break; case 1: glTranslatef(0, 0, -distance); break; } if(changedColor==1) { if(i==-1 && j==1 && k==-1) glColor3f(color1R, color1G, color1B); if(i==0 && j==1 && k==0) glColor3f(color2R, color2G, color2B); if(i==1 && j==1 && k==1) glColor3f(color3R, color3G, color3B); } glRotatef(-katPobocznychOsi,0,1,0); glutSolidCube(0.55); glPopMatrix(); glColor3f(0.0,0.0,1.0); } } } break; /* Obracanie wzgledem osi Z dla 3*3 elementow */ case 2: katPobocznychOsi += 0.05; glPushMatrix(); glRotatef(katGlownejOsi,0,1,0); for(i=-1;i<2;i++) { for(j=-1;j<2;j++) { for(k=-1;k<2;k++) { glPushMatrix(); glTranslatef(i,k,j); if(changedColor==1) { if(i==-1 && k==1 && j==-1) glColor3f(color1R, color1G, color1B); if(i==0 && k==1 && j==0) glColor3f(color2R, color2G, color2B); if(i==1 && k==1 && j==1) glColor3f(color3R, color3G, color3B); } switch(i) { case -1: glTranslatef(distance, 0, 0); break; case 0: glTranslatef(0, 0, 0); break; case 1: glTranslatef(-distance, 0, 0); break; } switch(j) { case -1: glTranslatef(0, 0, distance); break; case 0: glTranslatef(0, 0, 0); break; case 1: glTranslatef(0, 0, -distance); break; } switch(k) { case -1: glTranslatef(0, distance, 0); break; case 0: glTranslatef(0, 0, 0); break; case 1: glTranslatef(0, -distance, 0); break; } glRotatef(-katPobocznychOsi,0,1,0); glutSolidCube(0.55); glPopMatrix(); glColor3f(0.0,0.0,1.0); } } } glPopMatrix(); break; /* Rozciaganie od srodka */ case 3: if(distance >= 0.2f) direction = UP; if(distance <= -0.2f) direction = DOWN; if(direction == UP) { distance -= 0.0004f; } else { distance += 0.0004f; } glRotatef(katGlownejOsi,0,1,0); for(i=-1;i<2;i++) { for(j=-1;j<2;j++) { for(k=-1;k<2;k++) { glPushMatrix(); glTranslatef(i,j,k); switch(i) { case -1: glTranslatef(distance, 0, 0); break; case 0: glTranslatef(0, 0, 0); break; case 1: glTranslatef(-distance, 0, 0); break; } switch(j) { case -1: glTranslatef(0, distance, 0); break; case 0: glTranslatef(0, 0, 0); break; case 1: glTranslatef(0, -distance, 0); break; } switch(k) { case -1: glTranslatef(0, 0, distance); break; case 0: glTranslatef(0, 0, 0); break; case 1: glTranslatef(0, 0, -distance); break; } if(changedColor==1) { if(i==-1 && j==1 && k==-1) glColor3f(color1R, color1G, color1B); if(i==0 && j==1 && k==0) glColor3f(color2R, color2G, color2B); if(i==1 && j==1 && k==1) glColor3f(color3R, color3G, color3B); } glRotatef(-katPobocznychOsi,0,1,0); glutSolidCube(0.55); glPopMatrix(); glColor3f(0.0,0.0,1.0); } } } break; /* Zmiany kolorow */ case 4: changedColor = 1; glRotatef(katGlownejOsi,0,1,0); for(i=-1;i<2;i++) { for(j=-1;j<2;j++) { for(k=-1;k<2;k++) { glPushMatrix(); glTranslatef(i,j,k); switch(i) { case -1: glTranslatef(distance, 0, 0); break; case 0: glTranslatef(0, 0, 0); break; case 1: glTranslatef(-distance, 0, 0); break; } switch(j) { case -1: glTranslatef(0, distance, 0); break; case 0: glTranslatef(0, 0, 0); break; case 1: glTranslatef(0, -distance, 0); break; } switch(k) { case -1: glTranslatef(0, 0, distance); break; case 0: glTranslatef(0, 0, 0); break; case 1: glTranslatef(0, 0, -distance); break; } if(i==-1 && j==1 && k==-1) //ZIELONY { if(color1Direction == COLOR1_UP) { glColor3f(color1R, color1G+=colorChange, color1B-=colorChange); if(color1G >= 1.0f) color1Direction = COLOR1_DOWN; } if(color1Direction == COLOR1_DOWN) { glColor3f(color1R, color1G-=colorChange, color1B+=colorChange); if(color1G <= 0.0f) color1Direction = COLOR1_UP; } } //glColor3f(color1R+=0.0001f, color1G+=0.0003f, color1B+=0.0006f); if(i==0 && j==1 && k==0) //CZERWONY { if(color2Direction == COLOR2_UP) { glColor3f(color2R+=colorChange, color2G, color2B); printf("COLOR2_UP -> "); printf("%f\n", color2G); if(color2R >= 1.0f) color2Direction = COLOR2_DOWN; } if(color2Direction == COLOR2_DOWN) { glColor3f(color2R-=colorChange, color2G, color2B); if(color2R <= 0.0f) color2Direction = COLOR2_UP; } } if(i==1 && j==1 && k==1) //ŻÓŁTY { if(color3Direction == COLOR3_UP) { glColor3f(color3R+=colorChange, color3G+=colorChange, color3B-=colorChange); if(color3G >= 1.0f) color3Direction = COLOR3_DOWN; } if(color3Direction == COLOR3_DOWN) { glColor3f(color3R-=colorChange, color3G-=colorChange, color3B+=colorChange); if(color3G <= 0.0f) color3Direction = COLOR3_UP; } } glRotatef(-katPobocznychOsi,0,1,0); glutSolidCube(0.55); glPopMatrix(); glColor3f(0.0,0.0,1.0); } } } break; } /* Sprzatamy */ glPopMatrix(); } /* Funkcja generujaca pojedyncza klatke animacji */ void WyswietlObraz(void) { /* Wyczyszczenie bufora ramki i bufora glebokosci */ glClear(GL_COLOR_BUFFER_BIT|GL_DEPTH_BUFFER_BIT); /* Powielenie macierzy na wierzcholku stosu */ glPushMatrix(); /* Wyznaczenie polozenia obserwatora (przeksztalcenie uladu wspolrzednych, sceny do ukladu wspolrzednych obserwatora). */ glTranslatef(0, 0, -7); glRotatef(20, 1, 0, 0); glRotatef(25,0,1,0); /* Generacja obrazu sceny w niewidocznym buforze ramki */ Rysuj(); /* Usuniecie macierzy lezacej na wierzcholku stosu (powrot do stanu sprzed wywolania funkcji) */ glPopMatrix(); /* Przelaczenie buforow ramki */ glutSwapBuffers(); } /* Funkcja ustawiajaca parametry rzutu perspektywicznego i rozmiary viewportu */ void UstawParametryWidoku(int szerokosc, int wysokosc) { /* Ustawienie parametrow viewportu */ glViewport(0, 0, szerokosc, wysokosc); /* Przejscie w tryb modyfikacji macierzy rzutowania */ glShadeModel(GL_SMOOTH); glClearColor(0, 0, 0, 0); glMatrixMode(GL_PROJECTION); glLoadIdentity(); gluPerspective(40.0, (float)szerokosc/(float)wysokosc, 1.0, 1000.0); /* Przejscie w tryb modyfikacji macierzy przeksztalcen geometrycznych */ glMatrixMode(GL_MODELVIEW); /* Zmiana macierzy znajdujacej sie na wierzcholku stosu na macierz jednostkowa */ glLoadIdentity(); } /* Funkcja obslugi klawiatury */ void ObslugaKlawiatury(unsigned char klawisz, int x, int y) { switch(klawisz) { case '1': przycisk = 1; break; case '2': przycisk = 2; break; case '3': przycisk = 3; break; case '4': przycisk = 4; break; } if(klawisz == 27) exit(0); } /* Glowna funkcja programu */ int main(int argc, char **argv) { /* Zainicjowanie biblioteki GLUT */ glutInit(&argc, argv); /* Ustawienie trybu wyswietlania */ glutInitDisplayMode (GLUT_DOUBLE|GLUT_RGB|GLUT_DEPTH); /* Ustawienie polozenia dolenego lewego rogu okna */ glutInitWindowPosition(100, 100); /* Ustawienie rozmiarow okna */ glutInitWindowSize(600, 400); /* Utworzenie okna */ glutCreateWindow("Cubes"); /* Odblokowanie bufora glebokosci */ glEnable(GL_DEPTH_TEST); glEnable(GL_LIGHTING); glEnable(GL_LIGHT0); glEnable(GL_COLOR_MATERIAL); /* Ustawienie wartosci czyszczacej zawartosc bufora glebokosci */ glClearDepth(1000.0); /* Ustawienie koloru czyszczenia bufora ramki */ glClearColor (0.0, 0.0, 0.0, 0.0); /* Zarejestrowanie funkcji (callback) wyswietlajacej */ glutDisplayFunc(WyswietlObraz); /* Zarejestrowanie funkcji (callback) wywolywanej za kazdym razem kiedy zmieniane sa rozmiary okna */ glutReshapeFunc(UstawParametryWidoku); /* Zarejestrowanie funkcji wykonywanej gdy okno nie obsluguje zadnych zadan */ glutIdleFunc(WyswietlObraz); /* Zarejestrowanie funkcji obslugi klawiatury */ glutKeyboardFunc(ObslugaKlawiatury); /* Obsluga glownej petli programu (wywolywanie zarejestrowanych callbackow w odpowiedzi na odbierane zdarzenia lub obsluga stanu bezczynnosci) */ glutMainLoop(); return 0; }