Consideriamo il seguente problema:
Il problema implica una traduzione fra sistemi di coordinate:
Nel passare dagli oggetti all'immagine, le coordinate dei punti subiscono una serie di trasformazioni (pipeline): trasformazioni di modellazione, di vista, di proiezione, di workstation.
+--------+ +--------+ |coord.di| trasf.di trasf.di trasf.di trasf.di |coord. | |model- | --------> --------> --------> --------> |pixel | |lazione | modellaz. vista proiez. workst. |finestra| +--------+ +--------+Per risalire dall'immagine agli oggetti dobbiamo eseguire la serie di trasformazioni inversa.
In OpenGL i parametri di queste trasformazioni sono memorizzati in tre variabili di stato:
Quando specifichiamo una primitiva con glBegin(...); glVertex(...) ... glEnd(); le coordinate dei vertici, scritte in coordinate di modellazione, vengono tradotte in coordinate di finestra da OpenGL usando la viewport e le matrici projection e modelview presenti nello stato corrente.
OpenGL mette a disposizione la funzione gluUnProject
che esegue la traduzione inversa da coordinate della finestra in
coordinate di modellazione.
A questa funzione dobbiamo passare la viewport e le due matrici
projection e modelview che sono state usate nella traduzione diretta.
gluUnProject(x, y, z, modelview_mat, projection_mat, viewport, &xx, &yy, &zz);
La viewport e le due matrici projection e modelview sono parte dello stato di OpenGL. In generale lo stato di OpenGL si puo' interrogare con l'istruzione glGet che esiste in forme diverse a seconda del tipo dei parametri di stato che chiediamo.
Per variabili di stato a valori interi: glGetIntegerv(nome, ptr);
Per variabili di stato a valori double: glGetDoublev(nome, ptr);
Prevedere una struttura dati globale al programma, per esempio un array, in cui memorizzare i punti immessi.
La mia primitiva usera' i vertici presi dall'array.
Nel punto del codice in cui e' scritta la primitiva
salvare la viewport e le matrici modelview e projection
in variabili globali al programma.
Questo salva esattamente lo stato di trasformazioni
in cui OpenGL si trova quando disegna la primtiva.
Definire una mouse callback che preleva le coordinate Glut del punto cliccato, le traduce in coordinate di modellazione usando la viewport e le matrici salvate, aggiunge il punto cosi' tradotto all'array, ed invoca tramite glutPostRedisplay il ridisegnamento della finestra.
Nel ridisegno dopo eseguita la mouse callback, la primitiva trovera' un vertice in piu' nell'array...