Differences

This shows you the differences between two versions of the page.

Link to this comparison view

pgapi:laboratoare:02 [2024/10/08 11:59]
florica.moldoveanu [Suprafețe de rotație]
pgapi:laboratoare:02 [2024/10/09 10:05] (current)
andrei.lambru [Cerințe laborator]
Line 1: Line 1:
 ====== Laboratorul 02 ====== ====== Laboratorul 02 ======
- 
 ===== Suprafețe generate ===== ===== Suprafețe generate =====
  
-În multe cazuri, putem cunoaște propietățile unei suprafețe ​fără a-i cunoaște geometria explicită. Putem genera această suprafață folosind o geometrie ​generatoare ​și un proces ​de generare. ​În acest laborator, vom explora câteva din metodele ​de generare ​existente.+Definim o suprafață generată sub forma unei suprafețe ​create printr-o metodă de multiplicare a unei geometrii suportProcesul de creare a unei astfel de suprafețe necesită
 +  * O geometrie ​generator, ce este definită explicit ​și pe baza căreia are loc procesul ​de generare. 
 +  * Un algoritm ​de generare. Acesta poate fi bazat pe un proces de replicare, urmat de o transformare de translație,​ rotație sau orice alt tip de transformare.
  
-Orice suprafață generată are: +Procesul de generare decurge astfelîntâi se desenează geometria ​generator, pe baza căreia ​este construită suprafața generată. După aceastase desenează un număde instanțe ale geometriei generatorfiecare transformată de funcția de generare într-un mod progresiv. Rezultatul final este obținut prin combinarea topologică a acestor instanțe.
-  * Un generator, ​adică o geometrie explicit definită ​pe baza căreia ​are loc procesul de generare +
-  * Un algoritm de generare. Acesta poate fi bazat pe rotațietranslație sau pe orice fel de curbă definită prin puncte ​de control (ex: BezierHermite, etc)+
  
-Procesul ​de generare decurge astfel: întâi se desenează geometria generator, pe baza căreia va fi construită suprafațgenerată. ​După aceasta, se desenează un număde instanțe ale geometriei ​generatorfiecare ​transformată de funcția de generare într-un mod progresivRezultatul final este obținut prin combinarea topologică a acestor ​instanțe.+==== Suprafețe ​de translație ==== 
 + 
 +O suprafață de translație este o suprafață generată ​prin instanțierea unui obiect generatorFiecare instanță a generatorului suferă o transformare de translație. O suprafață de translație poate fi definită prin instanțierea unui generator ​cu fiecare ​instanță translatată progresiv dupa o funcție. 
 + 
 +Un exemplu ​de suprafață translatată este: 
 + 
 +{{ :​ppbg:​laboratoare:​translation-surface.png?600 |}} 
 + 
 +==== Suprafețe de rotație ==== 
 + 
 +O suprafață de rotație ​este o suprafață generată ​prin instanțierea unui obiect generator. Fiecare instanță a generatorului suferă o transformare de rotație. Aceasta poate fi definită prin instanțierea unui generator cu fiecare instanță rotită progresiv dupa o funcție. 
 + 
 +{{ :​ppbg:​laboratoare:​rotation-surface.png?600 |}} 
 + 
 +===== Laborator =====
  
-===== Diferite tipuri de instanțiere ===== 
  
 Instanțierea reprezintă un mecanism prin care se amplifică numărul de primitive trimise la banda grafică. Această amplificare este fie explicită (programată de utilizator în shader), fie implicită (generată prin comenzi OpenGL). Instanțierea reprezintă un mecanism prin care se amplifică numărul de primitive trimise la banda grafică. Această amplificare este fie explicită (programată de utilizator în shader), fie implicită (generată prin comenzi OpenGL).
Line 18: Line 30:
  
 <code cpp> <code cpp>
-glDrawElementsInstanced(topologie, ​nr_indecsi, tip_data, offset, instante).+glDrawElementsInstanced(topologie, ​nr_indici, tip_data, offset, instante).
 </​code>​ </​code>​
  
-De exemplu, dacă aș dori să desenez ​de 1540 de ori (instanțe) ​un obiect cu 99 de indecși, format din triunghiuri din buffer-ul de indecși, legat curent la banda grafică, atunci comanda ar fi:+De exemplu, dacă se doreste desenarea ​de 1540 de ori (instanțe) ​ale unui obiect cu 99 de indici, format din triunghiuri din buffer-ul de indici, legat curent la banda grafică, atunci comanda ar fi:
  
 <code cpp> <code cpp>
Line 27: Line 39:
 </​code>​ </​code>​
  
-Instanțierea explicită se face în shader, generând geometrie nouă prin comenzi ​glsl, în acest caz prin comenzi de geometry shader: +Instanțierea explicită se face în shader, generând geometrie nouă prin comenzi ​GLSL, în acest caz prin comenzi de geometry shader: 
-<​code ​cpp+<​code ​glsl
-gl_Position = P*V*M*vec4(p1,​ 1);​ EmitVertex();​ +for (int i=0;​i<​10;​i++) { 
-gl_Position = P*V*M*vec4(p2,​ 1);​ EmitVertex();​ +    ​gl_Position = P*V*M*vec4(p1,​ 1);​ EmitVertex();​ 
-gl_Position = P*V*M*vec4(p3,​ 1);​ EmitVertex();​+    gl_Position = P*V*M*vec4(p2,​ 1);​ EmitVertex();​ 
 +    gl_Position = P*V*M*vec4(p3,​ 1);​ EmitVertex();​
 EndPrimitive();​ EndPrimitive();​
 +
 +}
 </​code>​ </​code>​
-Instanțirea oferă posibilitatea ușoară de a crește rapid numărul de obiecte din scenă, dacă obiectele sunt identice. Ex: copaci, tile-uri de teren, unități într-un rts, etc. 
  
-Pentru a lucra cu suprafețe de translație,​ rotație și/sau interpolare,​ vom folosi ​instanțiere. Totușichiar dacă avem N instanțe ​de geometrie generatornu avem topologia necesară pentru a lega instanțeledeoarece generatorul este o curbă (topologie 2D), iar suprafața generată necesită topologie 3D.+În situația în care se utilizează ​instanțiere ​implicităîn programul ​de tip vertex shaderse poate obține numărul de ordine al instanței din care face parte vârful procesatprin utilizarea atributului de intrare implicit ''​gl_InstanceID''​.
  
-{{ :pgapi:​laboratoare:​poza_suprafete.png?​nolink |}}+<note important>​ 
 +În cadrul acestui laborator, se utilizează numărul de ordine al instanței din care face parte linia primită la intrare de către programul de tip geometry shader. Implicit, standardul OpenGL nu permite accesul la atributul de intrare ''​gl_InstanceID''​ în geometry shader. Din acest motiv, a fost creat un atribut de ieșire din vertex shader cu numele ''​instance''​ ce este primit sub forma de atribut de intrare în geometry shader cu tipul de date vector de 2 componente ''​instance[2]'',​ conform codului GLSL de mai jos:
  
-Din figură se observă clar cum avem mai multe tipuri de obiecte: +<code glsl> 
-  - Obiectul generator (prima linie neagră din stânga) +// Vertex Shader 
-  - Obiectul nou generat (2 instanțe ale generatorului și topologie de legatură între linii) +... 
-  - Suprafața finală generată+out int instance;
  
-Dacă nu am fi folosit acest proces, atunci prin instanțiere am fi obținut liniile instanțiate,​ dar nu și topologia de legatură între linii, adică exact ca în următoarea imagine:+void main() 
 +
 +    instance = gl_InstanceID;​ 
 +    ... 
 +
 +</​code>​
  
-{{ :​pgapi:​laboratoare:​poza_curbe.png?nolink |}}+<code glsl> 
 +// Geometry Shader 
 +in int instance[2];​ 
 +... 
 +</​code>​
  
-===== Suprafețe ​de translație =====+Ambele valori ale vectorului sunt identice și reprezintă numărul ​de ordine al instanței din care face parte linia de la intrarea programului de tip geometry shader. 
 +</​note>​
  
-O suprafață de translație este o suprafață generată prin instanțierea unui obiect generator. Fiecare instanță a generatorului suferă o transformare de translațieO suprafață ​de translație poate fi definită prin instanțierea unui generator cu fiecare instanță translatată progresiv dupa o funcție.+Instanțirea oferă posibilitatea ușoară de a crește rapid numărul de obiecte din scenă, dacă obiectele sunt identiceEx: copaci, tile-uri ​de teren, unități într-un rts, etc.
  
-Un exemplu ​de suprafață translatată este:+Pentru a lucra cu suprafețe ​de translație, rotație și/sau interpolare,​ se utilizeaza instanțiere. Totuși, chiar dacă avem N instanțe de geometrie generator, nu avem topologia necesară pentru a lega instanțele,​ deoarece generatorul ​este o curbă (topologie 2D), iar suprafața generată necesită topologie 3D.
  
-{{ :​pgapi:​laboratoare:​suprafata_translatie.png?nolink ​|}}+{{ :​pgapi:​laboratoare:​poza_suprafete.png?600 |}}
  
-===== Suprafețe de rotație =====+Din imagine se observă clar cum avem mai multe tipuri de obiecte: 
 +  - Obiectul generator (prima linie neagră din stânga) 
 +  - Obiectul nou generat (2 instanțe ale generatorului și topologie ​de legatură între linii) 
 +  - Suprafața finală generată
  
-O suprafață de rotație este o suprafață generată prin instanțierea unui obiect generator. Fiecare instanță a generatorului suferă o transformare de rotație. Aceasta poate fi definită prin instanțierea unui generator cu fiecare ​instanță rotită progresiv dupa o funcție. +Dacă nu am fi folosit acest proces, atunci ​prin instanțiere am fi obținut liniile ​instanțiate, dar nu și topologia ​de legatură între ​liniiadică exact ca în următoarea imagine:
- +
-{{ :​pgapi:​laboratoare:​suprafata_rotatie.png?​nolink |}} +
- +
-<​del><​del>​===== Curbe și suprafețe de formă liberă ===== +
- +
-Curbele și suprafețele de formă liberă sunt generate plecând de la niște puncte de control și generând alte puncte pe baza acestor puncte de control, care apoi sunt legate prin topologie pentru a crea suprafața. Există mai multe tipuri de curbe de control: Hermite, Bezier, etc. Dacă folosim câte o curbă de control pentru fiecare dimensiune, obținem metode de generare de suprafețe (petice), de volume sau de forme multidimensionale. În acest laborator vom lucra cu o curba de control Bezier, dar vom descrie pe scurt și un petic Bezier. +
- +
-<​del>​Formal,​ o curbă Bezier este construită pe baza a N puncte, numite puncte ​de control. Ecuația unui punct generat, pe baza acestor puncte de control, este:</​del>​ +
- +
-{{ :​pgapi:​laboratoare:​formula bezier 1.png?​nolink |}} +
- +
-<​del>​Unde B(t) este noul punct generat, iar t reprezint distanța parametrică între ​primul punct de control și ultimul punct de control. +
- +
-În cazul comun, în care N = 4, ecuația devine: +
- +
-{{ :​pgapi:​laboratoare:​formula bezier 2.png?​nolink |}} +
- +
-O reprezentare vizuală a procesului de generare de puncte pe baza punctelor de control: +
- +
-{{ :​pgapi:​laboratoare:​bezier.png?​nolink |}} +
- +
-unde punctele albe sunt punctele de control, iar punctele roșii sunt cele generate. +
- +
-<​del>​Procesul poate fi extins cu ușurință la 2 dimensiuni prin utilizarea unei petic Bezier. În cazul particular, dar comun al unui petic cu 16 puncte (4x4), acesta poate arăta astfel: +
- +
-{{ :​pgapi:​laboratoare:​bezier_suprafata.png?​nolink |}} +
- +
-<<​del>​hidden>​ +
-===Ce inseamnă, de fapt, din punct de vedere geometric, o curbă Bezier? === +
-În imaginea alaturată putem observa cum toate segementele P0P1, P1P2, P2P3, A1A2, A2A3 si B1B2 sunt taiate la un t% predefinit. Acesta este t-ul din ecuatia de interpolare liniara. Astfel A1 este interpolarea liniara intre P0 si P1, A2 intre P1 si P2, B1 intre A2 si A1, samd. Punctul final C este rezultatul acestui sir de interpolari. Daca as avea N segmente de control, procesul de determinare al punctului de pe curba ar include N-1 + N-2 + N-3 + …. +2+ 1 interpolari. Acelasi proces este aplicabil pentru toate familiile de curbe, singurele diferente fiind ca nu se mai interpoleaza doar dupa pozitie, adica operatia de interpolare este mai complicata (include tangente, directii, unghiuri, etc).+
  
-{{ :​pgapi:​laboratoare:​capture.png?nolink&​800 ​|}}+{{ :​pgapi:​laboratoare:​poza_curbe.png?300 |}}
  
-? 
-{{ :​pgapi:​laboratoare:​bezier_explicatii.png?​nolink |}} 
-</​hidden>​ 
-</​del>​ 
-</​del><​del>​Strike-through Text</​del></​del></​del></​del>​ 
 ===== Cerințe laborator ==== ===== Cerințe laborator ====
  
Line 105: Line 98:
  
 <note important>​ <note important>​
 +  * //Geometria suport trimisă către shader este o linie, ce leagă primul și ultimul punct de control.// Punctele de control sunt accesabile în geometry shader sub numele ''​control_p1'',​ ''​control_p2'',​ ''​control_p3'',​ ''​control_p4''​. ​
   * În laborator, geometria suport pentru curbă este deja definită. Există două tipuri de instanțieri:​   * În laborator, geometria suport pentru curbă este deja definită. Există două tipuri de instanțieri:​
       * Instanțierea implicită, facută cu comanda glDrawElementsInstanced,​ care este deja implementată și care generează geometria suport de N ori       * Instanțierea implicită, facută cu comanda glDrawElementsInstanced,​ care este deja implementată și care generează geometria suport de N ori
       * Instanțierea explicită, care va fi implementată în geometry shader.       * Instanțierea explicită, care va fi implementată în geometry shader.
-  * //Geometria suport trimisă către shader este o linie, ce leagă primul și ultimul punct de control.// Punctele de control sunt accesabile în geometry shader sub numele ''​control_p1'',​ ''​control_p2'',​ ''​control_p3'',​ ''​control_p4''​. ​ 
 </​note>​ </​note>​
  
Line 114: Line 107:
   - Trimiteți către shader numărul de puncte generate pe o curbă bezier (''​no_of_generated_points''​) și controlați de la tastatură atât acest număr (''​no_of_generated_points''​),​ cât și numărul de instanțe (''​no_of_instances''​).   - Trimiteți către shader numărul de puncte generate pe o curbă bezier (''​no_of_generated_points''​) și controlați de la tastatură atât acest număr (''​no_of_generated_points''​),​ cât și numărul de instanțe (''​no_of_instances''​).
   - Modificați fișierul ''​GeometryShader.glsl''​ pentru a desena o curbă Bézier pe baza a 4 puncte de control.   - Modificați fișierul ''​GeometryShader.glsl''​ pentru a desena o curbă Bézier pe baza a 4 puncte de control.
-    * Desenați o bandă de linii, pe baza tipului de geometrie de ieșire ''​line_strip'',​ prin emiterea mai multor vârfuri ale căror poziții se obțin prin eșantionarea curbei Bézier. +    * Desenați o polinie, pe baza tipului de geometrie de ieșire ''​line_strip'',​ prin emiterea mai multor vârfuri ale căror poziții se obțin prin eșantionarea curbei Bézier. 
-    * Permiteți modificarea de la tastatură a numărului de vârfuri ce descriu ​banda de linii. Acest număr trebuie să poată fi scăzut și crescut.+    * Permiteți modificarea de la tastatură a numărului de vârfuri ce descriu ​polilinii. Acest număr trebuie să poată fi scăzut și crescut.
     * După acest pas, rezultatul pe care ar trebui să îl obțineti este următorul: \\ {{ :​ppbg:​laboratoare:​bezier-animation.gif?​600 |}}     * După acest pas, rezultatul pe care ar trebui să îl obțineti este următorul: \\ {{ :​ppbg:​laboratoare:​bezier-animation.gif?​600 |}}
   - Modificați fisierul ''​GeometryShader.glsl''​ pentru a desena o suprafață de translație,​ pe baza curbei Bézier obținute anterior.   - Modificați fisierul ''​GeometryShader.glsl''​ pentru a desena o suprafață de translație,​ pe baza curbei Bézier obținute anterior.
pgapi/laboratoare/02.1728377956.txt.gz · Last modified: 2024/10/08 11:59 by florica.moldoveanu
CC Attribution-Share Alike 3.0 Unported
www.chimeric.de Valid CSS Driven by DokuWiki do yourself a favour and use a real browser - get firefox!! Recent changes RSS feed Valid XHTML 1.0