Part of the Khronos Group
OpenGL.org

The Industry's Foundation for High Performance Graphics

from games to virtual reality, mobile phones to supercomputers

Results 1 to 4 of 4

Thread: Moving a Light Source

Hybrid View

  1. #1
    Junior Member Newbie
    Join Date
    Nov 2012
    Posts
    5

    Moving a Light Source

    Hello all,

    I've been browsing the forums for a while and I've found some useful stuff, so I thought I'd ask a few questions of my own.

    My first question pertains to how I would go about moving a light source. I want the camera position to stay constant, but I'd like to be able to use the keyboard to move where the light is shining from and update my shading accordingly. Here's how I'm currently doing it, to no avail:
    I have a handler in my main source file which takes three vertices where the light should be positioned.
    Code :
    //from main
     
    //declaring the handler
    GLint h_aLight;
     
    //globals for light position
    float lightX = 5;
    float lightY = 5;
    float lightZ = 5;
     
    //inside my function to install the shaders
    h_aLight = safe_glGetAttribLocation(ShadeProg, "aLight");
     
    //inside my draw function, after I've done the appropriate model transforms
    //set the light position in the shader
          glUniform3f(h_aLight, lightX, lightY, lightZ);

    I'm not worrying about applying the transforms yet, I know I need to multiply the model matrix by the normals, but that's a problem for later. Those values are passed off to a variable in my vertex shader, which is used to calculate the direction of the light by created by subtracting the position of the object from the points passed to my light handler to create a vector.

    Code :
    //vertex shader
     
    //declaring the variable
    varying vec3 lightPos;
     
    void main(){
    //...
     
    //creating the vector
    lightPos = vec3(aLight.x - vPosition.x, aLight.y - vPosition.y, aLight.z - vPosition.z);
     
    //shading calculations based on the light vector
    }

    Because my light direction is updated here and all the shading calculations are done AFTER this point, I would assume that updating the values passed to the light handler would result in a new light direction vector that my calculations would use for brand new calculations. However, I don't see any difference in the picture at all. I make sure that the global variables are getting updated with a printf() right after glUniform3f(h_aLight, lightX, lightY, lightZ); that displays the values of lightX, lightY, and lightZ.

    Any help would be appreciated

  2. #2
    Super Moderator OpenGL Guru dorbie's Avatar
    Join Date
    Jul 2000
    Location
    Bay Area, CA, USA
    Posts
    3,946
    Your light is just a uniform. The light position will not change unless you transform it. The specified light position will be in the space in which you use it for your relative position.

    In your case you are calculating your light position in object space.

    If you want your light to be in world space relative to the object then transform vPosition through the object matrix first.

    If you want eye space then transform vPosition through the modelview.

    A common convention if to transform vPosition through your modelview matrix and to manually transform your light into eyespace in your application. This matches OpenGL's fixed function pipeline convention but does not impose a split modelview matrix nor a retransformation of the light per vertex.

    So:

    1) transform light to eyespace then set the light position uniform.
    2) calculate the modelview matrix and specify it as a uniform matrix
    3) in the vertex shader transform vPosition through the modelview matrix THEN perform the lighting relative position subtraction.
    Last edited by dorbie; 11-05-2012 at 04:27 PM.

  3. #3
    Junior Member Newbie
    Join Date
    Nov 2012
    Posts
    5
    Quote Originally Posted by dorbie View Post
    1) transform light to eyespace then set the light position uniform.
    2) calculate the modelview matrix and specify it as a uniform matrix
    3) in the vertex shader transform vPosition through the modelview matrix THEN perform the lighting relative position subtraction.
    I've already done steps 2 and 3. In my shader I already have three uniform matrices declared, the ModelMatrix, ViewMatrix, and ProjectionMatrix.
    Code :
    //declaring the matrices in my VS
    uniform mat4 uProjMatrix;
    uniform mat4 uViewMatrix;
    uniform mat4 uModelMatrix;
     
    //inside main
    vPosition = uModelMatrix* vec4(aPosition.x, aPosition.y, aPosition.z, 1);
    vPosition = uViewMatrix* vPosition;

    It's after this that I do the subtraction to get the light vector. I feel like my only problem is transforming light to eyespace. Following what it sounded like you were saying, I transformed light to eyespace in my main source file. I multiplied it by the ModelView to get it in eyespace in the same manner as vPosition.
    Code :
    //in my main source file
     
    //globals for light position
    float lightX = 5;
    float lightY = 5;
    float lightZ = 5;
    float homo = 0;
    glm::vec4 eyeLight = glm::vec4(lightX,lightY,lightZ, homo);
    glm::mat4 ModelMat; //holds value of ModelMatrix
    glm::mat4 ViewMat; //holds value of ViewMatrix
    glm::mat4 ProjMat; //holds value of ProjectionMatrix
     
    //in my draw function, after model transforms, but before i pop the matrix
    //set the light position in the shader
          eyeLight = ModelMat * eyeLight;
          eyeLight = ViewMat * eyeLight;
          glUniform4f(h_aLight, eyeLight[0], eyeLight[1], eyeLight[2], eyeLight[3]);

    Now lighting kinda works... it at least responds to where I initially set it. If I move the camera or try to rotate the object, the lighting changes, but it looks like it circulates between 5 different stages of light movement before it starts the loop over, no matter how I move the object. Another issue I notice is that no matter how I move the camera, whether it's in a circle or just forward or backward, this loop continues. This problem also happens when I simply translate or scale the object. Also, I still can't change the position of the light using key presses like I wanted
    Last edited by synhyborex; 11-05-2012 at 06:48 PM.

  4. #4
    Junior Member Newbie
    Join Date
    Nov 2012
    Posts
    5
    After a bunch of reading, I figured it out, and it now works as intended

    The problem was just that I was doing the transformation to eyespace inside my main source file rather than my shader...and to think I originally thought I needed to calculate it in the shader anyway.

    Thanks for the help!

Posting Permissions

  • You may not post new threads
  • You may not post replies
  • You may not post attachments
  • You may not edit your posts
  •