varying vec2 DepthTextureCoord;
varying float FragLightDepth, ViewDist;

uniform sampler2D Eng_EnvDepthTexture;
uniform vec2 Eng_ShadowNearFar;
uniform vec2 Eng_ShadowFallOffNearFar;
uniform vec2 Eng_ObjID;
uniform vec4 ReceiveFrom;

// TODO:
const float mapSize = _EngDef_ShadowsDepthTextureSize;
const float stepSize = 1.0/_EngDef_ShadowsDepthTextureSize;
const float offset = 0.01;

const vec4 clrShadow = vec4(0.0, 0.0, 0.0, 1.0);
const vec4 clrLight = vec4(1.0, 1.0, 1.0, 0.0);

float GetReceiveFrom(in float index)
{
	if (index < 0.01)
		return ReceiveFrom.x;
	else if (index < 1.01)
		return ReceiveFrom.y;
	else if (index < 2.01)
		return ReceiveFrom.z;
	else if (index < 3.01)
		return ReceiveFrom.w;
	else
		return 1.0;
}

void main()
{
	if ((DepthTextureCoord.x < 0.0) || (DepthTextureCoord.y < 0.0) || (DepthTextureCoord.x > 1.0)  || (DepthTextureCoord.y > 1.0) || (FragLightDepth > 1.0)|| (ViewDist < Eng_ShadowNearFar.x) || (ViewDist > Eng_ShadowNearFar.y))
    	discard;
	else
	{
		vec2 fr = fract(DepthTextureCoord * mapSize);
		vec2 tc1 = floor(DepthTextureCoord * mapSize)/mapSize;
		vec2 tc2 = vec2(tc1.x + stepSize, tc1.y);
		vec2 tc3 = vec2(tc1.x, tc1.y + stepSize);
		vec2 tc4 = vec2(tc1.x + stepSize, tc1.y + stepSize);
		tc1 = vec2(tc1.x - stepSize, tc1.y);


		vec4 DepthTex = texture2D(Eng_EnvDepthTexture, tc1);
		vec4 clr1 = (FragLightDepth > (DepthTex.r + offset)) ? clrShadow + 1.0-GetReceiveFrom((DepthTex.g * 3.0)) : clrLight;
		DepthTex = texture2D(Eng_EnvDepthTexture, tc2);
		vec4 clr2 = (FragLightDepth > (DepthTex.r + offset)) ? clrShadow + 1.0-GetReceiveFrom((DepthTex.g * 3.0)) : clrLight;
		DepthTex = texture2D(Eng_EnvDepthTexture, tc3);
		vec4 clr3 = (FragLightDepth > (DepthTex.r + offset)) ? clrShadow + 1.0-GetReceiveFrom((DepthTex.g * 3.0)) : clrLight;
		DepthTex = texture2D(Eng_EnvDepthTexture, tc4);
		vec4 clr4 = (FragLightDepth > (DepthTex.r + offset)) ? clrShadow + 1.0-GetReceiveFrom((DepthTex.g * 3.0)) : clrLight;

		float MaxDist = (Eng_ShadowFallOffNearFar.y - Eng_ShadowFallOffNearFar.x);
		float fallOff = clamp((ViewDist - Eng_ShadowFallOffNearFar.x) / MaxDist, 0.0, 1.0);

		gl_FragColor = ((clr1 + clr2 + clr3 + clr4) * 0.25) + fallOff;
		gl_FragColor.gb = Eng_ObjID / 255.0;
  		gl_FragColor.a = 1.0-(ViewDist / Eng_ShadowFallOffNearFar.x);
	}
}
