I wrote a simple Phong shader with two directional lights for a project, and noticed an unpleasant artifact in the lighting. Where both lights are illuminating the same region, dark bands appear at the light terminators where N.L reaches zero. At first I thought it must be a bug in my code, but a quick test revealed the Unity standard shader has the exact same problem.

my shader unity shader

My best guess is that this is some form of the Mach effect, and our retinas are overshooting where the brightness plateaus. Does anyone know any tricks to mitigate this effect?


Here are two more images to illustrate the effect better - one with my shader, and one with Unity's diffuse shader, with the lights at 90 degrees and all specular and ambient contributions removed.


You can clearly see the dark bands around the top right quadrant where one light's terminator intersects the other's area of effect (well, I can anyway, YMMV). I've run an eyedropper over it and confirmed it's a perceptual effect, the pixels do not in fact get darker.

  • 1
    $\begingroup$ Is it rendered in linear colour space ? $\endgroup$
    – PaulHK
    Dec 20 '17 at 12:46
  • $\begingroup$ Do you actually have two lights 180 degrees apart? It should get dark at the light terminator but it wouldn't normally get light again on the other side unless you have two-sided lighting turned on and shadows turned off, or two lights on opposite sides. $\endgroup$
    – Dan Hulme
    Dec 20 '17 at 13:28
  • $\begingroup$ PaulHK, tried it with both and the effect persists, although it's a little less pronounced in linear. $\endgroup$
    – russ
    Dec 20 '17 at 13:32
  • $\begingroup$ Dan, check out the pics. The lights are more like 60 degrees apart, the problem is when one light's contribution reaches zero, it appears to have a negative contribution to the other light - probably just a perceptual artifact but still annoying. $\endgroup$
    – russ
    Dec 20 '17 at 13:35
  • 3
    $\begingroup$ Unfortunately, this is the correct result of the Lambertian lighting model. The physically valid way of getting rid of it is to replace your point light sources with area lights. Alternatively, if you don't care about correctness you could replace the $\max(n\cdot\ell,0)$ step with a different function that smooths over the kink at $n\cdot\ell=0$. $\endgroup$
    – user106
    Dec 22 '17 at 2:11

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service, privacy policy and cookie policy

Browse other questions tagged or ask your own question.