1 / 44

OpenGL 4 shaderek, GLSL Valasek Gábor

OpenGL 4 shaderek, GLSL Valasek Gábor. OpenGL 4. A következő programozható fázisok vannak a 4.x-es OpenGL-ben: Vertex shader Tesselation control shader Tesselation evaluation shader Geometry shader Fragment shader. OpenGL 4 pipeline. Vertex és pixel shader. Vertex shader.

akira
Download Presentation

OpenGL 4 shaderek, GLSL Valasek Gábor

An Image/Link below is provided (as is) to download presentation Download Policy: Content on the Website is provided to you AS IS for your information and personal use and may not be sold / licensed / shared on other websites without getting consent from its author. Content is provided to you AS IS for your information and personal use only. Download presentation by click this link. While downloading, if for some reason you are not able to download a presentation, the publisher may have deleted the file from their server. During download, if you can't get a presentation, the file might be deleted by the publisher.

E N D

Presentation Transcript


  1. OpenGL 4 shaderek, GLSL Valasek Gábor

  2. OpenGL 4 • A következő programozható fázisok vannak a 4.x-es OpenGL-ben: • Vertex shader • Tesselation control shader • Tesselation evaluation shader • Geometry shader • Fragment shader

  3. OpenGL 4 pipeline

  4. Vertex és pixel shader

  5. Vertex shader • A vertex shader programunkban végezzük el a bejövő geometria csúcspontjainak transzformációját • glDrawArrays/glDrawElements hívásban hivatkozott csúcspontok lesznek a bemenetei • A vertex shader bemeneti változóihoz (in módosító) a hozzárendelést a programból csináljuk • A csúcspontbeli attribútumoknál ritkábban változó bemenetet uniform változókon keresztül adhatjuk át (uniform = a kirajzolás hívás idejére konstans)

  6. Vertex shader • A bejövő csúcspont koordinátáit clip space-be ( -1 <= x,y,z <= 1) kell transzformálni és a beépített gl_Position változónak átadni – ezt a pipeline nem programozható részeinek is kell • gl_Position = gl_MVPMatrix * bejövő_vertex_pos4 • Ezen kívül azt csinálunk „amit akarunk” (minden out-tal megjelölt változónak adhatunk értéket és továbbküldhetjük a következő programozható fázisnak)

  7. Vertex shader • A következő beépített kimeneti változók írhatóak a vertex shaderből: • vec4 gl_Position: a transzformált homogén koordinátái a bejövő vertex-nek. Ebbe írnia kell a VS-nek. • float gl_PointSize: a kirajzolandó pont mérete pixelben (point sprite-okhoz). Opcionális. • vec4 gl_ClipVertex: felhasználói vágósíkokhoz. Opcionális. • És ezeken kívül minden, amit mi is felveszünk...

  8. Fragment shader • vec4 gl_FragColor: a fragment színe, de ha nem írun bele viszont van kimeneti vec4, az lesz ez • vec4 glFragData[gl_MaxDrawBuffers]: ha több color attachment-je van az aktív FBO-nak, akkor ezen keresztül írhatunk rájuk • float gl_FragDepth: fragment mélységi értéke (ha módosítanánk, mint a raycasterben) • vec4 gl_FragCoord: csak olvasható, a fragment homogén koordinátái (4. koord 1/w) • bool gl_FrontFacing: előrefelé néz-e a fragment lapja

  9. Vertex shader #version 400 invec3 VertexPosition; invec3 VertexColor; outvec3 Color; void main() { Color = VertexColor; gl_Position = vec4(VertexPosition,1.0); }

  10. Fragment shader #version 400 in vec3 Color; outvec4 FragColor; void main() { FragColor = vec4(Color, 1.0); }

  11. Program-shader megfeleltetések • Vertex attribútumok és a shader bemeneti változóinak összerendelés: glBindAttribLocation( programHandle, // shader prog 0, // index "VertexPosition"); // sh-s nev glBindAttribLocation( programHandle, 1, "VertexColor");

  12. Program-shader megfeleltetések glGenVertexArrays( 1, &vaoHandle ); glBindVertexArray(vaoHandle); glEnableVertexAttribArray(0); // Vertex position glEnableVertexAttribArray(1); // Vertex color glBindBuffer(GL_ARRAY_BUFFER, positionBufferHandle); glVertexAttribPointer( 0, 3, GL_FLOAT, GL_FALSE, 0, (GLubyte *)NULL ); glBindBuffer(GL_ARRAY_BUFFER, colorBufferHandle); glVertexAttribPointer( 1, 3, GL_FLOAT, GL_FALSE, 0, (GLubyte *)NULL );

  13. Program-shader megfeleltetések • Lényegében tehát általános, indexekkel azonosított csatornákon keresztül megy az információátadás • A csatornák száma a GL_MAX_VERTEX_ATTRIBS segítségével kérhetőek le

  14. Layout • A shader oldalon is megcsinálhatjuk a bejövő csatornák „index-esítését”, és nem kell bind-olni az attrib location-öket: layout (location = 0) in vec3 VertexPosition; layout (location = 1) in vec3 VertexColor; • Ezt a kimeneti változóknál is lehet használni: layout (location = 0) out vec4 FragColor;

  15. Uniform változók • A shaderen belül read-only-k (konstansok), de kezdeti értéket kaphatnak • uniform mat4 MVP • Típusok:, n = 2,3,4 • mat<n>: n x n-es mátrix • vec<n>: n dim vektor

  16. Uniform változók • Először meg kell tudnunk az OpenGL-es azonosítóját a uniform változónak: • GLuint mvpInShader = glGetUniformLocation( programHandle, "MVP"); • Ezután már típusának megfelelő fv-vel értéket adhatunk neki: • GlUniformMatrix4fv( mvpInShader, 1, GL_FALSE, &app_mvp[0][0]); • Többiek: http://www.opengl.org/sdk/docs/man/xhtml/glUniform.xml

  17. Uniform változók • Alaptípusok tömbjét is megjelölhetünk uniform-ként • Ekkor pl. egy mátrixtömb konkrét indexen lévő mátrixának azonosítóját megkapjuk így: • GLuint location = glGetUniformLocation( programHandle, "MyArray[1]" );

  18. Uniform block • Több shader változó használhatja a program szempontjából ugyanazon uniform változókat • Ezeket mégis külön-külön kellene feltöltenünk stb., mert ugyanannak a uniform változónak más lesz a címe a különböző shader programokban • A uniform block segítségével ezen segíthetünk (csak használjunk shared layout-ot)

  19. Uniform block – a shaderben uniform BlobSettings { vec4 InnerColor; vec4 OuterColor; float RadiusInner; float RadiusOuter; };

  20. Uniform block • A uniform változók adatait tartalmazó puffer objektum a uniform buffer object • A változókra hivatkozásnál elég az adattag nevét írni, nem kell prefixelni az UBO nevével (tehát pl. elég az InnerColor, nem kell BlobSettings.InnerColor)

  21. Uniform block GLuint blockIndex = glGetUniformBlockIndex( programHandle, "BlobSettings"); GLint blockSize; glGetActiveUniformBlockiv( programHandle, blockIndex, GL_UNIFORM_BLOCK_DATA_SIZE, &blockSize); GLubyte * blockBuffer= (GLubyte *)malloc(blockSize);

  22. Uniform block constGLchar *names[] = { "InnerColor", "OuterColor", "RadiusInner", "RadiusOuter" }; GLuint indices[4]; glGetUniformIndices( programHandle, 4, names, indices); GLint offset[4]; glGetActiveUniformsiv( programHandle, 4, indices, GL_UNIFORM_OFFSET, offset);

  23. Uniform block GLfloat outerColor[] = {0.0f, 0.0f, 0.0f, 0.0f}; GLfloat innerColor[] = {1.0f, 1.0f, 0.75f, 1.0f}; GLfloat innerRadius = 0.25f, outerRadius = 0.45f; memcpy(blockBuffer + offset[0], innerColor, 4 * sizeof(GLfloat)); memcpy(blockBuffer + offset[1], outerColor, 4 * sizeof(GLfloat)); memcpy(blockBuffer + offset[2], &innerRadius, sizeof(GLfloat)); memcpy(blockBuffer + offset[3], &outerRadius, sizeof(GLfloat));

  24. Uniform block GLuint uboHandle; glGenBuffers( 1, &uboHandle ); glBindBuffer( GL_UNIFORM_BUFFER, uboHandle ); glBufferData( GL_UNIFORM_BUFFER, blockSize, blockBuffer, GL_DYNAMIC_DRAW ); glBindBufferBase( GL_UNIFORM_BUFFER, blockIndex, uboHandle );

  25. Fragment shader #version 400 invec3 Color; outvec4 FragColor; void main() { FragColor = vec4(Color, 1.0); }

  26. Az összes shader

  27. Az összes shader • Az összes shader opcionális, pass-through-ként működnek ha nincs saját hozzárendelve • Ha van akár geometry, akár tesszelációs shader, akkor kell legyen vertex shader is

  28. Geometry shader • Meglévő geometria módosítására, törlésére, bővítésére • Bemenete a transzformált vertexekből képezett primitívekből áll • Kimenete 0, 1, vagy több primitív • A kimenő primitív típus különbözhet a bejövőtől! • De csak egyféle típusú lehet a kimenet

  29. Geometry shader • Minden primitívre egyszer fut le • A primitív összes csúcspontját eléri, a csúcspontokban tárolt összes információval együtt • Lehet akár culling-ot is csinálni benne

  30. Geometry shader • EmitVertex: ha kész vagyunk a primitív egyik csúcspontjához tartozó attribútumok kitöltésével, ezzel az utasítással adhatjuk tovább a pipeline-nak • Ha nincs EmitVertex, akkor implicit eldobódik csúcspont • EmitPrimitive: ha elkészült a primitív összes csúcspontja, akkor EmitPrimitive-vel tudjuk visszadobni a pipeline-ba • Ha nincs EmitPrimitive, akkor a GS lefutásakor implicit hívódik egy

  31. Tesszelációs shader • Ha aktiválva van, akkor csak egyetlen rajzolási primitívünk van: GL_PATCHES • A patch primitív tetszőleges geometriai és egyéb információk halmaza, ami alapján a tesszelációs shader az inkrementális képszintézisnek megfelelő primitíveket hoz létre • Maximális „csúcsok” száma egy patch-ben: GL_MAX_PATCH_VERTICES

  32. Tesszelációs shader • A kirajzolandó patch-adathalmaz csúcspontjainak száma: • glPatchParameteri( GL_PATCH_VERTICES, num); • Például Bézier kontrollpontok száma

  33. Tesszelációs shader • A patch primitívet nem rajzoljuk ki, a tesselation control és tesselation evaluator számára szolgáltat adatokat • A tényleges pipeline-ba bekerülő primitíveket a tesselation primitive generator állítja elő (ez a TCS és TES között van a pipelineban)

  34. TCS • A TPG-t konfigurálja, hogy az miképp készítsen primitíveket (mennyit és melyik beépített algoritmussal) • Ezen kívül per-vertex kimeneti attribútumokat állíthat elő

  35. TES • A TPG által létrehozott primitívek minden egyes (paramétertérbeli) csúcspontjára meghívódik • Lényegében: a görbe- vagy felületséma kiértékelése a feladata • Fő feladat: a pozíció meghatározása

  36. Geometry shader példa

  37. Geometry shader - bemenet • A következő típusú bemenetek lehetnek: points (1) lines (2) lines_adjacency (4) triangles (3) triangles_adjacency (6) Primitívenként 1, 2, 4, 3, 6 csúcspontokkal

  38. Geometry shader - bemenet A szomszédossági adatos primitívek OpenGL kliens oldali kódjában a következők: GL_LINES_ADJACENCY GL_LINE_STRIP_ADJACENCY GL_TRIANGLES_ADJACENCY GL_TRIANGLE_STRIP_ADJECENCY

  39. Geometry shader - bemenet • A többi primitív típusból pedig a pipeline csinálja meg a GS bemenetet • Ami tehát mindig 1 primitívből áll, amihez tartozhat szomszédossági információ is • Hogyan kapja ezt meg?

  40. Geometry shader - bemenet

  41. Geometry shader - bemenet

  42. Geometry shader - bemenet

  43. Geometry shader - bemenet

  44. Geometry shader – bemenet, kimenet

More Related