Project 4: Lighting and Shading
This project is on OpenGL lighting and shading, and includes GLSL shader programs.
This project is due on Friday, November 2nd at 1:30pm. It will be introduced in lab 260 by Sid on Monday, October 29th at 2:30pm.
Note that while you are welcome to start working on this project immediately, we will not have covered all the material in class until Tuesday, October 23rd.
For Windows and Linux users, in order to expose OpenGL extensions, you must download GLee and add the glee.h and glee.c files to your project files, or tell the linker to link with the GLee library (glee.lib or glee.dll for Windows, or libglee.a/libglee.so for Linux). OSX users will not need GLee, as OpenGL extensions are available by default.
1. Lighting (50 points)
We provide source code to help you get started with the project. The code displays two spheres on the screen, deliberately at a low tessellation level (i.e., few triangles) to make the lighting effects you are implementing more obvious.
You should start by replacing the matrix class in the base code with your own. Then you should write classes to manage light and material properties (Light and Material). You will also need to add your mouse control code from Project 3 to your application. It does not have to work perfectly, but needs to at least somehow rotate the spheres around and allow the user to zoom in.
Then you need to do the following things:
- Display the two spheres from the starter code and and give them material properties: one of them should be shiny and diffuse, the other one only diffuse (5 points).
- Your mouse control routines from Project 3 affect the location of the two spheres (5 points).
- Create a point light. Position it so that its effect can be seen on both spheres (15 points).
- Create a spot light. By default, it should point to at least one of the spheres. The spot diameter should be smaller than that sphere so that the outline of it can be seen on the sphere, as well as the brightness gradient at the edge of it. (15 points)
- Support two keyboard keys: 'p' and 's': The 'p' key turns the point light on and off, the 's' key turns the spot light on and off, so that you can demonstrate the functionality of each light individually, as well as their combination. (5 points)
- Allow the user to move the light sources by applying your mouse control routines to them: whichever light source is enabled with the 'p' and 's' keys should be affected by the mouse. If no light source is enabled, the mouse should move the spheres. Similar to Project 3, the 'r' key should reset the positions of all spheres and light sources. (5 points)
This URL provides a good summary of OpenGL lighting and materials.
Note that OpenGL multiplies light position and direction with the Modelview matrix when they are set. Therefore, you need to modify the Modelview matrix with your mouse control routines to rotate the light sources, independently for each light source.
Note: The spheres are generated by the glutSolidSphere routine, which automatically generates normal vectors. To ascertain that your normal vectors will survive scale operations correctly, you should use the following OpenGL commands:
glEnable(GL_NORMALIZE); glLightModelf(GL_LIGHT_MODEL_LOCAL_VIEWER, GL_TRUE);
2. Shader Programs (50 points)
In this part of the project, you will need to add support for per-pixel shading of the effect of your light sources from part 1 on the spheres, which will significantly improve the visual appearance of the light reflections on the spheres.
We provide a sample shader class and three sample combinations of vertex and fragment shaders for you to get familiar with GLSL shader programming. For this part of the project, extend the diffuse_shading shader to perform per-pixel Phong shading. The shader should use the properties of your light sources and materials. These properties can be accessed in the shader through the predefined gl_LightSource and gl_FrontMaterial variables.
- Create GLSL vertex and fragment shaders for the point light (15 points).
- Create GLSL vertex and fragment shaders for the spot light (15 points).
- Create GLSL vertex and fragment shaders which support both light sources concurrently (10 points).
- Demonstrate the scene with the two spheres from Part 1 with optional per-pixel shading: add support for the 'g' key to toggle your GLSL shaders on or off, to demonstrate the difference between OpenGL's built-in (per vertex) shading and your custom per-pixel shading. (10 points)
- While most CSE lab computers do, some older computers or simpler graphics cards do not support GLSL. Be aware that this might be a problem with your personal computer.
- It is more efficient to compute the reflection vector in the vertex shader. Then you pass it to the fragment shader as a varying parameter. OpenGL will automatically interpolate the vector at each pixel. However, you will have to re-normalize it in the fragment shader to make sure it is a unit vector.
- For this project it is sufficient to support just one concurrent light source. However, you will need to support the point light as well as the spot light in your scene, just assume that they will never be enabled at the same time.
Here are a few URLs with tutorials on how to write GLSL shader code. The tutorial at the first URL contains detailed instructions for how to do per-pixel shading for point and spot lights, including sample shader code.
- Lighthouse3D GLSL tutorials
- Clockworkcoders GLSL tutorials
- GLSL quick reference
- GLSL reference documentation
4. Extra Credit (10 points)