DirectX 10 – Geometry Shaders Go to the module webpage and download this week's lab materials. Extract the contents of the zip file to a work folder. There are two projects in this week's lab. Basic Geometry Shader Geometry shaders sit between the vertex shader and the pixel shader. Their input is the primitive currently being rendered, usually a triangle, but can be a line or a point if that is what is being rendered. The output of a geometry shader is a *stream* of primitives, typically a triangle strip, but can be a line strip or a list of points even. The basic use of a geometry shader is to update the vertices in a triangle based on information about the triangle. A vertex shader can only work on a single vertex at a time, the geometry shader has the data for all three vertices of a triangle to work with. A geometry shader can output one or more triangles (lines or points), or none at all. So the geometry shader can create new geometry or destroy it prior to rendering. Although adding too much geometry can be a performance problem A Simple Geometry shader Here we will demonstrate a geometry shader to "explode" a model by calculating the face normals. The face normals are derived from multiple vertices in a triangle, so this technique is best done in a geometry shader Open and run the GeometryShader project. You will see an exploded sphere. This application uses a geometry shader to move each triangle outwards in the direction of its face normal. The face normals are calculated by looking at the edges of each triangle. This is only possible in a geometry shader, which operates on each triangle and has access to the three vertices at once. Look at the geometry shader itself (called "ExplodeTriangles" in "GeometryShader.fx"). It is like a vertex shader, but there are important differences in the input/output First, see how the function is prefixed by a line that indicates the maximum vertices output by the shader. This shader inputs one triangle and doesn't add or remove any, so it will always output 3 vertices Two structures are defined for the input and output as with other shaders, but the parameters to the main function, representing the input and output are different. Read the comments explaining these parameters Finally note how the output is produced: Vertices are generated, one at a time, and added to the output stream with Append. This continues as long as you are creating a single triangle strip. So the second and subsequent triangles are defined by just one vertex. When the triangle strip ends or a new one is needed then call RestartStrip Exercises Adjust the explode amount (set from a float near the top of "GeometryShader.cpp") CO3303 - Maths and Technologies for Games, Week 6 Lab Worksheet 1-1 Experiment with different models. Try the teapot or troll provided in the project folder. You will want to adjust the explode amount and the model scaling ("InitScene" in "GeometryShader.cpp") o Optional: You could vary the explode amount on a sine wave ("UpdateScene") Output a second triangle which isn't exploded at all - i.e. the original triangle is kept and the exploded one is added o You will need to change the max vertices output by the shader o The two triangles output are not connected and can't be made into a single triangle strip, so RestartStrip needs to be called between the two triangles ouput as well as at the end Advanced - A single triangle can be split into four by joining the three vertices to a new vertex at the centre. This is a form of tessellation. Change the shader so it outputs four triangles like this. Note: it is not normally recommended to tessellate like this in a geometry shader o Only move the centre vertex by the explode amount. Leave the original three where they are Geometry Shaders - Silhouettes The next project illustrates another use for a geometry shader – the generation of silhouettes (note: it doesn’t work yet). Finding which edges of a model form the outline is a task often assigned to the CPU when required. With geometry shaders we can do it efficiently on the GPU. This could be the silhouette from the point of view of the viewer (perhaps for an edge-based drawing effect), or perhaps from the silhouette from a light (for shadow effects). The process is relatively straightforward The majority of the code is the same the first geometry shader project This geometry shader though takes as input a triangle with adjacency information. The shader gets an array of 6 vertices to work with. The three vertices of the triangle are stored in positions 0, 2 & 4. The extra three vertices are those vertices (elsewhere in the mesh) that are adjacent to the edges of this triangle. See the lecture notes for a diagram This additional adjacency information must be calculated on importing the mesh. The model class in this application has been updated to optionally do this With the adjacent vertices, we can form the adjacent triangles. The geometry shader can now use the same technique as the last lab to calculate the face normals for the main triangle and its three adjacent triangles These face normals are tested against the direction to the camera, to see if they face towards or away o Testing if the main triangle faces towards the triangle is basically the back-face culling test we have often used before. This is now programmable with geometry shaders CO3303 - Maths and Technologies for Games, Week 6 Lab Worksheet 1-2 If the main triangle faces the camera, and an adjacent triangle faces away, then the edge between these triangles must be a silhouette edge. The geometry shader tests each edge and outputs a line for each one that meets this condition The result is an outline for the geometry Exercises The geometry shader has missing sections, fill them in to make the project work o Refer to the previous exercise and the lecture notes Experiment with the different models provided Advanced - This could turned into part of a high quality cell shading technique. Instead of outputting lines expand the lines into long thin rectangles, and output two triangles for each. Render these black, or use a brush stroke texture on them. Use a second pass to render the polygon faces themselves with some simple coloured technique. CO3303 - Maths and Technologies for Games, Week 6 Lab Worksheet 1-3