1

I'm seeking help as I'm having a hard time trying to draw a fixed spot light in my mesh renderer. I'm currently doing something like:

gluLookAt(...)
DrawMesh(...)
float pos[] = {0, 500, 0, 1};
glLightfv(GL_LIGHT0, GL_POSITION, pos);

where I init the light with:

float ambient_light[] = {1, 1, 1, 1.0};
glLightfv(GL_LIGHT0, GL_AMBIENT, ambient_light);

GLfloat cutoffAngle = 30.0f;
glLightf(GL_LIGHT0, GL_SPOT_CUTOFF, cutoffAngle);

GLfloat spotDirection[3] = {0.0f, -1.0f, 0.0f};
glLightfv(GL_LIGHT0, GL_SPOT_DIRECTION, spotDirection);

GLfloat exponentValue = 10.0f;  // Example value
glLightf(GL_LIGHT0, GL_SPOT_EXPONENT, exponentValue);

Defining the light after transformations should provide a fixed light relative to my camera PoV. The problem is that the spot light is still with respect to camera traslations, but changes with camera rotation/orientation!. Here's a gif of whats happening. It's been 2 days and I haven't been able to get over this issue! I will happily share more code if needed. Thanks for reading this.

(note that I'm forced to stick to legacy opengl due to this being an academic project)

I already tried changing the order of modelview function and light calls, setting different light properties and playing with mesh normals. The expected behaviour should consist of the light staying still even when moving the camera orientation.

Tides
  • 17
  • 4

2 Answers2

2

According to the specification:

The position is transformed by the modelview matrix when glLight is called (just as if it were a point), and it is stored in eye coordinates. Blockquote

So your issue here is that the light position gets transformed by your modelview matrix, which is created by gluLookAt(). You can reset your modelview matrix by calling glLoadIdentity(). You may want to use glPushMatrix() and glPopMatrix() to restore the matrix if you want to render more stuff later.

Suppose there are some translations in your modelview matrix to get the objects into eye space, eg. gluLookAt() with non-zero eye coordinate. You might need to restore that translation after glLoadIdentity().

  • The answer was actually the opposite. The light SHOULD be affected by transformations for it to be static with regard to camera position. My problem was simply that I forgot to move the GL_SPOT_DIRECTION setting inside the drawing routine; that caused the light direction to not being updated by the modelview matrix resulting in the situation I described. Thank you anyway for trying – Tides Jul 22 '23 at 14:13
0

Quoting an answer from reddit which solved my problem:

I think the problem is that all of the glLightfv() calls that take a vector use the current ModelViewMatrix. Since your call that sets the spotlight direction is outside the draw loop, the MVM is likely identity at that time. Try moving the GL_SPOT_DIRECTION setting inside draw() next to where you set the position. Or maybe both calls have to be outside, I'm not sure how the matrices work in this mode. In any case, having them set at different places is almost certainly part of the problem.

Tides
  • 17
  • 4