Laboratorium Grafiki Komputerowej3, Studia PK, Inne - serwer Nexus, Dydaktyka, ZaoczniGK, OpenGL-lab3


Opracował: mgr inż. Paweł Macioł

Laboratorium Grafiki Komputerowej

Ćwiczenie 3 - „Perspektywa. Sterowanie położeniem obserwatora”

W tym ćwiczeniu zapoznamy się ze sposobami perspektywicznej projekcji 3D. Zostanie pokazany sposób prostej interakcji użytkownika mającej wpływ na położenie obserwatora oraz oglądanych obiektów.

Przestrzeń obiektu (inaczej przestrzeń modelu) - jest to układ współrzędnych obiektu, w którym ten obiekt jest definiowany. Przykładowo: dla sfery jej przestrzenią obiektu może być układ współrzędnych, którego środek jest środkiem sfery; dla walca środek układu może leżeć w środku podstawy, a kierunek osi z jest zgodny z kierunkiem osi symetrii tego walca. Położenie wierzchołków w przestrzeni obiektów jest określone jako wektor [x, y, z].

Współrzędne homogeniczne - to czteroelementowy wektor postaci [x, y, z, w], w którym pierwsze 3 składniki określają położenie w przestrzeni 3D, a czwarty to dodatkowy parametr w. Jeśli wektor położenia zostaje wyrażony za pomocą wektora 3-elementowego to zakłada się, że w = 1. Matematyczne znaczenie parametru w jest takie, że jest to wartość przez którą należy podzielić x, y i z by uzyskać położenie w postaci tradycyjnej. Tak więc jest to pewien współczynnik skali:

Przestrzeń świata - przestrzeń konkretnego obiektu nie ma związku z innymi obiektami posiadającymi własne przestrzenie. Przestrzeń świata definiuje pewien bezwzględny punkt odniesienia dla wszystkich obiektów sceny. Jeśli przyjmiemy że przestrzenią świata jest sala laboratoryjna, to obiekty w niej występujące (komputery, stoły, krzesła) mają różne położenie i ukierunkowanie.

Przekształcenie modelu - opisuje sposób w jaki obiekt w przestrzeni modelu jest transformowany do przestrzeni świata. Na przykład, musimy obrócić, przeskalować i przesunąć stolik by znalazł się on w odpowiednim miejsu w laboratorium. Wszystkie te przekształcenia można zapisać matematycznie jako macierze 4x4 i składać je w jedną macierz transformacji, co jest istotne dla wydajności programu. Mnożąc położenie punktu w postaci homogenicznej (w = 1) w przestrzeni modelu przez macierz 4x4 reprezentującą przekształcenie modelu w przestrzeń świata, otrzymamy to samo położenie opisane w przestrzeni świata.

Przestrzeń oka (inaczej przestrzeń widoku) - to przestrzeń obserwatora, czyli układ współrzędnych obserwatora względem, którego opisujemy położenie obserwowanych obiektów w scenie. W standardzie OpenGL przyjęło się, że domyślnie obserwator („oko”) znajduje się w początku swojego układu współrzędnych, a kierunek patrzenia na scenę jest zgodny z kierunkiem osi z i biegnie wzdłuż jej ujemnych wartości.

Przekształcenie widoku - konwertuje położenie w przestrzeni świata na położenie w przestrzeni obserwatora. To przekształcenie da się zestawić w postaci macierzy 4x4 i nazywane jest macierzą model-widok. Jest to macierz, która łaczy w sobie przekształcenie modelu i przekształcenie widoku.

Przestrzeń przycięcia - kiedy położenia znajdują się już w przestrzeni oka, kolejnym krokiem jest określenie, które z nich znajduje się w widocznym obszarze. Zatem kolejnym układem po przestrzeni oka jest przestrzeń przycięcia. Wyjaśnienie tej techniki można prześledzić obserwując działanie funkcji np. glOrtho().

Przekształcenie, które konwertuje współrzędne przestrzeni oka do przestrzeni przycięcia jest nazywane przekształceniem rzutowania. To przekształcenie definiuje obszar przestrzeni oka, w którym znajdują się widoczne obikety. W OpenGL wszystko co ma być widoczne musi się znajdować w sześcianie, którego każdy punkt spełnia nierówności: -w ≤ x ≤ w, -w ≤ y ≤ w, -w ≤ z ≤ w. Przekształcenie to podobnie jak wcześniej wymienione da się zestawić w postaci tzw. macierzy rzutowania o rozmiarach 4x4.

Znormalizowane współrzędne przycięcia - współrzędne przycięcia maja postać homogeniczną [x, y, z, w], lecz koniecznym jest aby uzyskać położenie w przestrzeni dwu-wymiarowej (x,y) wraz zadaną wartością głębi. Uzyskuje się to dzieląc składowe wektora x, y, z przez składnik w. W ten sposób otrzymane współrzędne noszą nazwę znormalizowanych współrzędnych urządzenia. Na ostatnim etapie następuje transformacja znormalizowanych współrzędnych urządzenia na współrzędne okna, które mierzone są w pikselach.

  1. Dodaj dom kodu z ćwiczenia 2 następującej definicji globalnej zmiennej:

/* Pozycja obserwatora */

GLfloat viewer_pos[] = { 0.0, 0.0, 10.0 };

  1. Dokonaj modyfikacji kodu z ćwiczenia 2 tak aby na ekranie uzyskać poniższy rysunek:

0x01 graphic

  1. W pomocy VS znajdź informacje na temat funkcji glPerspective() Zmodyfikuj ciała funkcji ReshapeWindow() oraz RenderScene() zgodnie z poniższym.

/* Tę funkcję wywołuje system w momencie gdy uytkownik zmieni myszą

* rozmiar głownego okna. jej zadaniem jest zachowanie propocji wymiarów

* rysowanych obiektów niezależnie od wymiarów okna.

*/

void ReshapeWindow(int width, int height)

{

// Ustawiamy układ współrzędnych obserwatora

glMatrixMode(GL_PROJECTION);

// Resetujemy macierz projkecji

glLoadIdentity();

// Ustawiamy perspektywę

gluPerspective(70.0, 1.0, 1.0, 20.0);

// Korekta

if(width <= height)

glViewport(0, (height - width)/2, width, width);

else

glViewport((width - height)/2, 0, height, height);

// Ustawiamy macierz modelu

glMatrixMode(GL_MODELVIEW);

// Resetujemy macierz modelu

glLoadIdentity();

}

/* W tej funkcji określamy to co ma byc narysowane na ekranie.

* Jest wywoływana zawsze wtedy, gdy trzeba przerysować ekran - bufor ramki.

*/

void DrawScene(void)

{

// Czyścimy okno aktualnym (domyślnym) kolorem oraz resetujemy bufor głębi

glClear(GL_COLOR_BUFFER_BIT | GL_DEPTH_BUFFER_BIT);

// Resetujemy bieżącą macierz

glLoadIdentity();

// Definiujemy położenie obserwatora

gluLookAt(viewer_pos[0],viewer_pos[1],viewer_pos[2],

0.0, 0.0, 0.0, 0.0, 1.0, 0.0);

// Rysujemy osie układu

DrawSceneAxes();

// Zamieniamy bufory ramki

glutSwapBuffers();

}

  1. W powyższym przypadku obserwator znajduje się w punkcie (0,0,10). Zmień tę pozycję na (4, -4, 10). Ustaw współrzędne wektora zenitu na [1, 1, 0]. Jak zmiany te wpłyną na rzutowanie?

Interakcja z obiektem w scenie poprzez użycie myszy

Kolejnym zadaniem jest wzbogacenie naszego programu o funkcjonalność, która będzie polegała na tym, że przy wciśniętym lewym klawiszu myszy i jednoczesnym jej ruchu w lewo bądź w prawo, czajnik wykona stosowny obrót w danym kierunku względem osi y.

  1. W sekcji przeznaczonej na definicję zmiennych globalnych dodaj następujące definicje:

/* Kat obrotu czajnika */

GLfloat theta = 0.0f;

/* Przelicznik pixeli na kąt */

GLfloat pixels2angle = 0.0;

/* Status lewego przycisku myszy:

0- zwolniony

1- wciśnięty */

GLint lbutton_status = 0;

/* Ostatnia pozycja kursora myszy */

GLint x_last_pos = 0;

/* Przemieszczenie kursora */

GLint x_delta = 0;

  1. W funkcji main() dodaj rejestracje funkcji:

// Rejestracja funkcji odpowiedzialnej stan myszy

glutMouseFunc(MouseFunc);

// Rejestracja funkcji odpowiedzialnej za ruch myszy

glutMotionFunc(MouseMotion);

  1. Zaimplementuj zarejestrowane funkcje:

/* Funkcja obsługująca mysz - bada stan klawiszy

* i ustawia odpowiednie zmienne

*/

void MouseFunc(int button, int state, int x, int y)

{

if(button == GLUT_LEFT_BUTTON && state == GLUT_DOWN)

{

// Zapamętujemy obecne położenie myszy

x_last_pos = x;

// Przycisk lewy wcisnięty

lbutton_status = 1;

} else {

// Przycisk jest zwolniony

lbutton_status = 0;

}

}

/* Funkcja monitoruje położenie myszy i ustala odpowiednie zmienne */

void MouseMotion(GLsizei x, GLsizei y)

{

// Wyliczamy aktualne przemieszczenie

x_delta = x - x_last_pos;

// Zapamiętujemy aktualne położenie

x_last_pos = x;

// Odświeżamy okno

glutPostRedisplay();

}

  1. Tuż przed rysowaniem dzbanka dodaj:

// Jeśli wciśnięto lewy klawisz myszy

if(lbutton_status = 1)

{

// Zwiększ kąt

theta += x_delta*pixels2angle;

}

// Obrót w okół osi y

glRotatef(theta,0.0f, 1.0f, 0.0f);

  1. W na początku funkcji ReshapeWindow() dodaj przeliczenie pikseli na stopnie:

// Przeliczamy piksele na stopnie

pixels2angle = 360.0f/(float)width;

  1. Skopiuj i uruchom program.

  2. Zmodyfikuj program dodając obrót w około osi x.

  3. Dodaj funkcjonalność prawego klawisza myszy, którego wciśnięcie i ruch w kierunku pionowym powoduje zbliżanie/oddalanie się od obiektu.

  4. Odwróćmy problem. Teraz niech dzbanek będzie nieruchomy i będzie się rysował w początku układu współrzędnych. Położenie obserwatora względem obiektu (względem początku układu współrzędnych) można zapisać we współrzędnych biegunowych:

0x01 graphic
,

gdzie: θ,φ- to odpowiednie kąty przy wektorze wodzącym o długości R



Wyszukiwarka

Podobne podstrony:
grafika-okno2, Studia PK, Inne - serwer Nexus, Dydaktyka, GK, OpenGL-lab1, AplikacjaWindows
grafika rastrowa, Studia PK, Inne - serwer Nexus, Dydaktyka, ZaoczniGK, Photoshop
1- Interfejs, Studia PK, Inne - serwer Nexus, Dydaktyka, ZaoczniGK, Rastrowa, grafika rastrowa 1
Opis ćwiczenia3, Studia PK, Inne - serwer Nexus, Dydaktyka, GK, grafika rastrowa 3
Opis ćwiczenia2, Studia PK, Inne - serwer Nexus, Dydaktyka, GK, grafika rastrowa 2
Wydział Inżynierii Elektrycznej i Komputerowej 02, studia, PK - WIŚ -UCZ, Semestr I, Fizyka
SPR-ANKI, Studia, WAT Informatyka, s3 - GK - lab grafika komputerowa, Lab2
Zadanie IY4S1, Studia, WAT Informatyka, s3 - GK - grafika komputerowa, LAB2
sprawozdanie3, Studia, WAT Informatyka, s3 - GK - lab grafika komputerowa, Lab4
sprawozdanie oswietlenie, Studia, WAT Informatyka, s3 - GK - lab grafika komputerowa, Lab3
Rzezba Lab4, Studia, WAT Informatyka, s3 - GK - grafika komputerowa, LAB4
GK LAB3, Studia, WAT Informatyka, s3 - GK - grafika komputerowa, LAB4
KWADRYKI, Studia, WAT Informatyka, s3 - GK - lab grafika komputerowa, Lab2
Laboratorium3 PGK zadania, WAT, semestr III, Grafika komputerowa
OpenGl, Studia, WAT Informatyka, s3 - GK - lab grafika komputerowa, Lab4
Glony(1), Studia, PK OŚ, biologia, laboratorium
Zadania L3 I6X4S1, Studia, WAT Informatyka, s3 - GK - lab grafika komputerowa, Lab4
Zadania L3 I6Y3S1, Studia, WAT Informatyka, s3 - GK - lab grafika komputerowa, Lab3

więcej podobnych podstron