There is a slight problem with the BlinnPhong lighting model and OpenGLES. If you check the source code of the Mobile shaders, you will see that they provide an alternative lighting model “MobileBlinnPhong”.
I was able to isolate the issue to these lines in BlinnPhong:
inline fixed4 LightingBlinnPhong (SurfaceOutput s, fixed3 lightDir, fixed3 viewDir, fixed atten)
{
fixed3 h = normalize (lightDir + viewDir); //normalize light direction added to the view direction
fixed diff = max (0, dot (s.Normal, lightDir));
float nh = max (0, dot (s.Normal, h)); //calculate the dot product of the surface normal and our normalized light+view, then make sure it is no smaller than 0 (black)
float spec = pow (nh, s.Specular*128.0) * s.Gloss;
fixed4 c;
c.rgb = (s.Albedo * _LightColor0.rgb * diff + _LightColor0.rgb * _SpecColor.rgb * spec) * (atten * 2);
c.a = s.Alpha + _LightColor0.a * _SpecColor.a * spec * atten;
return c;
}
The mobile version MobileBlinnPhong:
inline fixed4 LightingMobileBlinnPhong (SurfaceOutput s, fixed3 lightDir, fixed3 halfDir, fixed atten)
{
fixed diff = max (0, dot (s.Normal, lightDir));
fixed nh = max (0, dot (s.Normal, halfDir)); //Instead of injecting the normalized light+view, we just inject view, which is provided as halfasview in the initial surface shader CG parameters
fixed spec = pow (nh, s.Specular*128) * s.Gloss;
fixed4 c;
c.rgb = (s.Albedo * _LightColor0.rgb * diff + _LightColor0.rgb * spec) * (atten*2);
c.a = 0.0;
return c;
}
So by comparison we can see that the GPU seems to fumble on the standard BlinnPhong model, and UT’s mobile version accounts for and corrects it.
For a quick fix, I suggest that any time you use OpenGLES (either 1.1 or 2.0) use a shader which employs the mobile-safe version of BlinnPhong lighting model as opposed to the standard.
If you need me to I’ll go more in-depth, I just wanted to get this out quickly.
Hope this helps!
==