Computer Graphics Università dell Insubria Corso di Laurea in Informatica Anno Accademico 2014/15 Marco Tarini comporre una scena con la Model Transform Stack di matrici di modellaione: reminder! (vedi le 13) gerarchia di matrici di modellaione: albero in testa: spaio mondo nei nodi: spai oggetti sugli archi: trasformaioni locali per scendere nella gerarchia: preliminare: «push» (per ricorarsi dello stato del padre) poi, le comporre le trasformaioni locali cioè quelle per andare da: spaio figlio a: spaio del padre regola intuitiva: l ultima transf che aggiungo è la prima che viene eseguita per ritornare al padre: «pop» Stack di matrici di modellaione Una oggetto che contiene lo stack di matrici di modellaione un singleton, per semplicità Funioni: /* the MODEL stack of matrices */ var model = { } init: function() { }, // uno stack con 1 solo elemento: l identità top: function() { }, // restituisce la matrice in cima allo stack push: function() { }, // duplica l elemento in cima allo stack pop: function() { }, // rimuove l elemento in cima allo stack /* funioni che comulano una nuova trasformaione all elemento top: */ scale: function( s, s, s ) { }, translate: function( t, t, t ) { }, rotatex: function( degrees ) { }, Note implementative implementare lo stack con un arra JavaScript di matrici Three.js campo ( privato )data top: ultimo elemento dell arra (quello in posiione lenght ) push e pop: allungare / accorciare dinamicamente l arra (in coda!) coi metodi push e pop degli arra java funioni che cumuluano la trasformaione: creano la matrice della nuova trasf, moltiplicano l elemento top con essa, a destra 1
Un possibile baco: il problema Un possibile baco: il fi /* the MODEL stack of matrices */ var model = { data : [], // l arra top : function() { return this.data[ this.lenght - 1 ]; }, /* the MODEL stack of matrices */ var model = { data : [], // l arra top : function() { return this.data[ this.lenght - 1 ]; }, } // duplica l elemento in cima allo stack push: function() { this.data.push( this.top() ); }, } // duplica l elemento in cima allo stack push: function() { var tmp = new THREE.Matri4(); tmp.cop( this.top() ) ; this.data.push( tmp ); }, push push una Matri4 una Matri4 una Matri4 una Matri4 una Matri4 (con gli stessi valori) Una gerarchia: Una gerarchia: pareti T A spaio mondo (stana) T B T C T D T E 1 2 3 3 T 0 base (cilindro chiuso) Colonna i T 1 T 2 T3 T 4 fusto A (cono) fusto B (cono) piedistallo (cilindro chiuso) bunn (in cima) 2
Trasformaioni: comporre una Trasformaioni: piedistallo T 3 =? = H = H-2 = H = H-2-8 0 +8 Spaio Colonna = 2 = 0-4 0 +4 Spaio Colonna Spaio Cilindro Chiuso Trasformaione del fusto A Trasformaione del fusto B T 1 =? T 2 =? = H-2 = H-2-3 0 +3 = 2 Spaio Cono -3 0 +3 = H/2 = 2 Spaio Cono Spaio Colonna Spaio Colonna 3
Scomporre T 2 in una sequena di aioni Trasformaioni: da piedistallo a cilindro 1. Inverti verticalmente (sulla Y) model.scale(,, ); problema! det. negativo () inverte gli orientamenti delle facce model.scale(,, ); model.ratatez( 180 ); 2. Riscala da: altea 2 (da a ) ad: altea H-4 da: larghea 2 a: larghea 6 (da -3 a +3) model.scale( 3, (H-4)/2, 3); 3. Transla di H/2 in su model.translate( 0, H/2, 0); ok oppure: ok (è la stessa matrice!) (verificare) ordine concettuale / temporale delle trasfr. ordine in cui compaiono nel codice circa 0 2.5 Spaio Colonna T 4 =? = H circa +0.18 circa +0.03 circa +0.05 Spaio Bunn (spaio oggetto dell oggetto Bunn) (vedere la mesh) Soluione (sbrigativa) per ottenere cilindri chiusi Idea (sbrigativa) per le basi: usare coni appiattiti cilindro chiuso T a T b T c base inferiore sup laterale base superiore T c =? Spaio Cilindro Chuiso Spaio Cono (mesh procedurale) 4
T c (da cono a base sup): sequena di aioni Traccia di altre scelte implementative 1. Appiattisci verticalmente (sulla Y, a 0) model.scale( 1, 0, 1); problema! det 0 matrice non invertibile (ci serve invertirla per la dir. luce) model.scale( 1, 0.001, 1 ); ok (indistinguibile, ma invertibile) 2. Transla di 1 in su (sulla Y) model.translate( 0, 1, 0); ordine concettuale / temporale delle trasfr. ordine in cui compaiono nel codice Usare 4 LoD diversi del coniglio, uno su ciascuna (di altea crescente) 4 mesh separate, prese dal sito di Stanford, come la prima 4 file JSON (ottenute con meshlab) 4 elementi di un vettore JavaScript di GPU mesh Geometria stana: presa in rete una mesh di un angolo interno replicata due volte per comporre una stana di 4 pareti Traccia di altre scelte implementative Matrice di vista un metodo di trackball ora la restituisce allungata la distana a seconda del (seno dell ) angolo phi per ottenere una traiettoria ellittica invece che circolare della camera limiti ad-hoc all angolo theta per evitare di far sparire la camera sotto il pavimento / sopra il soffitto Traccia di altre scelte implementative Base color (lambertiano) del modello di illuminaione uno uniform negli shader non più un const colore (per mesh) attuale: delle var Javascript settata con funione setcolor( r, g, b ) passata come uniform agli shader (nella senduniform) 5
Per i dettagli, vedere l implementaione sul sito (come al solito): le 24op 6