0

I am try to implement a basic spotlight using OpenGL and Fragment Shader. However, I notice that there is a distinct black border artifact at the periphery of the spotlight. I expect to see a hard cut-off between the color inside the spotlight circle and outside the spotlight circle.

.

The teapot has plain grey color (0.75,0.75,0.75), it is illuminated by :

  1. a blue point light between the body and the handle
  2. a red directional light from top right pointing toward the teapot centre
  3. a green spotlight from the camera toward the body

Here is the fragment shader code (assuming the transformations are done properly in vertex shader and CPU-side):

#version 330 compatibility
#extension GL_ARB_separate_shader_objects : enable

in vec3   oNormal;
in vec3   oPos;
out vec4  Color;

uniform vec3 light0Pos;
uniform vec3 light0Color;
uniform vec3 light1Dir;
uniform vec3 light1Color;
uniform vec3 light2Pos;
uniform vec3 light2Color;
uniform vec3 light2SpotDir;
uniform float light2SpotExp;
uniform float light2SpotCut;

void main()
{
  vec3 nNormal = normalize(oNormal);
  vec3 surfaceColor = vec3(0.75, 0.75, 0.75);
  vec3 tempColor = vec3 (0.0, 0.0, 0.0);

  //first light: point light
  float w = max(dot(nNormal, normalize(light0Pos - oPos)), 0.0);
  tempColor = surfaceColor * vec3(w) * light0Color.xyz;

  //second light: directional light
  w = max(dot(nNormal, normalize(light1Dir) * vec3(-1.0)), 0.0);
  tempColor = tempColor + max(vec3(0.0),surfaceColor * vec3(w) * light1Color.xyz);

  //third light: spotlight
  vec3 spotDir = normalize(vec3(light2SpotDir));
  vec3 light2Dir = normalize(oPos - light2Pos);
  w = dot(spotDir, light2Dir);
  float c = step(cos(radians(light2SpotCut * 0.5)),w);
  w = c * pow(w,light2SpotExp) * max(dot(nNormal, normalize(light2Dir) * vec3(-1.0)), 0.0);
  tempColor = tempColor + max(vec3(0.0),surfaceColor * vec3(w) * light2Color.xyz);

  Color = vec4(tempColor, 1.0);
}

I suspect there is an interpolation issue. If I check the pixel values, the red pixel which is outside spotlight and near the border has color (87, 0, 0) and the green/yellow pixel which is inside spotlight and near the border has color (83, 66, 0). If it is because of interpolation, the border should have the color like (80, 30, 0). However, the border has color (17, 9, 0) instead...The red channel should not be interpolated.

Thanks!

Rabbid76
  • 202,892
  • 27
  • 131
  • 174
  • light2SpotExp is 29.66, if I am not wrong, and light2SpotCut is 40.0. Of course, if I make the exponent value to be very big (around 300), the spotlight will become very small and we will not see the black border anymore. – OenFriste Sep 14 '18 at 13:08
  • My apology, the problem is solved. I forgot that there are some other post-processing effects in the pipeline which cause edges to appear. – OenFriste Sep 19 '18 at 06:51

0 Answers0