Goal: Learn about lighting by modifying our OpenGL program.
Action:
GLfloat white[] = {1,1,1,1}; // light color GLfloat lightPosition[]={-1,1,1,1}; // light position glLightfv(GL_LIGHT0, GL_POSITION, lightPosition); // setlight position glLightfv(GL_LIGHT0, GL_DIFFUSE, white); // set diffuse light color glLightfv(GL_LIGHT0, GL_SPECULAR, white); // set specular light color glEnable(GL_LIGHT0);The glLightfv() command takes three arguments. The first is the light number, which should be one of the OpenGL constants GL_LIGHTi. The number of lights depends on the implementation, but at least 8 lights are supported. The second is the lighting parameter to be set, also one of the OpenGL constants. The final argument is the value the parameter should be set to. In this case, the value is a vector of floats, as specified by the fv (f for float and v for vector) in the command glLightfv(). (See Woo for a full description of argument specifications.) Note that OpenGL lighting is more flexible than the model we used for raytracing in that a light can provide different colors for diffuse and specular. (For more details on the possible parameters see Woo chapter 5.)
GLfloat white[] = {1,1,1,1}; // white GLfloat purple[] = {1,0,1,1}; // purple glMaterialfv(GL_FRONT, GL_DIFFUSE, purple); glMaterialfv(GL_FRONT, GL_DIFFUSE, white); glMateriali(GL_FRONT,GL_SHININESS,50);Just as with colors, the most recently defined properties apply to an object when it is drawn. (Why? think state machine...)
glEnable(GL_LIGHTING);
float const=1.0; // constant attenuation float linear=1.0; // linear attenuation float quadratic=0.5; // quadratic attenuation glLightf(GL_LIGHT0, GL_CONSTANT_ATTENUATION, const); // set diffuse light color glLightf(GL_LIGHT0, GL_LINEAR_ATTENUATION, const); // set diffuse light color glLightf(GL_LIGHT0, GL_QUQADRATIC_ATTENUATION, const); // set diffuse light colorNote that we are using glLightf, where the f signifies a float argument.
glBegin(GL_TRIANGLE_STRIP); glVertexf(-20.0,-5.0,-40.0); glVertexf(-20.0,-5.0,0.0); glVertexf(20.0,-5.0,-40.0); glVertexf(20.0,-5.0,0.0); glEnd();Recompile and run your program.
There are several issues with the current code that need to be fixed. First, you need to set the material properties
for the floor. Use similar code as for the sphere but make the floor a different color. Next, OpenGL needs surface normals
in order to compute the lighting (just as you did in the ray tracer). You can define a normal by glNormalf(vx,vy,vz).
OpenGL keeps track of the the most recently defined normal, let's call it currNormal. When you create a vertex
by a call like glVertexf(-10,-5,10), OpenGL assumes the normal at that point on the surface is currNormal. Since
the normal to our floor is <0,1,0> it suffices to call glNormalf(0,1,0) immediately before the call to glBegin(GL_TRIANGLE,STRIP).
Make these changes and recompile your program.
Deliverables: Email a your OpenGL.cpp to me and hand in a hard-copy in class next Tuesday. If you haven't handed in a file for Lab 4, you can hand in one file for both.