uniform sampler2D 	colorTex,
					normalTex,
					matTex,
					posTex;
uniform sampler2D 	skyOcclusion;

uniform samplerCube	envCube;
varying vec2 		texcoord;
uniform vec4		ambientColor;		
varying vec2		VPOS;
uniform mat4		eyeToWorld;
uniform float		ambientScatter;
uniform float		cubeLod;
uniform float 		saturation;

uniform vec3 scatterPalette[8];

float Pi=3.14159265359;

vec4 decode(vec4 enc)
{
    vec2 fenc = enc.xy*4.0-2.0;
    float f = dot(fenc,fenc);
    float g = sqrt(1.0-f/4.0);
    vec4 n;
    n.xy = fenc.xy*g;
    n.z = 1.0-f/2.0;
	n.w=enc.w;
    return n;
}

vec4 RGBMDecode( vec4 rgbm ) {
  return vec4(6.0 * rgbm.rgb * rgbm.a,1.0);
}

float phong_diffuse()
{
	return (1.0 / Pi);
}

void main()
{
	vec4 finalcolor=vec4(0.0,0.0,0.0,0.0);

	float sky=texture2D(skyOcclusion,texcoord.st).r;
	vec4 ambient = texture2D(colorTex,texcoord.st);
	vec4 encoded = texture2D(normalTex,texcoord.st);
	vec4 normal = decode(encoded);
	vec4 pos;
	pos.z = texture2D(posTex,texcoord.st).r;
	//float metal = texture2D(matTex,texcoord.st).r*step(ambient.a,0.0);	// if(scatter=ambient.a > 0) metal = 0
	
	vec4 mat = texture2D(matTex,texcoord.st);
	float metal=mat.x*step(ambient.a,0.0);// if(scatter=ambient.a > 0) metal = 0

	// get colors
	int i1=int(mat.x*256.0);
	int i2=i1;
	i1=i1/8;	// specular index
	i2=i2-(i1*8);
	vec4 scatterColor=vec4(pow(scatterPalette[i2],vec3(2.2))*ambientScatter,ambientScatter);
	
	
	pos.xy=VPOS.xy*-pos.z;
	pos.w=1.0;
	pos=eyeToWorld*pos;
	
	vec4 N=eyeToWorld*vec4(normal.xyz,0.0);
	
	/*vec4 diffuse = RGBMDecode(textureCubeLod(envCube,-N.xyz,6.0));
	diffuse = (diffuse+vec4(ambient.a+ambientScatter))/vec4(1+ambient.a+ambientScatter);
	*/
	// IBL diffuse
	vec4 IBLdiffuse = RGBMDecode(textureCubeLod(envCube,-N.xyz,cubeLod));
	
	float lum=dot(IBLdiffuse.rgb,vec3(0.3,0.59,0.11));
	IBLdiffuse.rgb=mix(vec3(lum),IBLdiffuse.rgb,/*sqrt(*/clamp(0.4*log(sky)+1.0,0.0,1.0)/*)*/);
	
	//vec4 diffuse =  IBLdiffuse * phong_diffuse();	
	vec4 diffuse = /*mix(*/IBLdiffuse*(phong_diffuse()+vec4(ambient.a+scatterColor/*ambientScatter*/))/vec4(1+ambient.a+scatterColor/*ambientScatter*/)/*,diffuse,metal)*/;
	
	// energy conservation
	finalcolor = mix(ambient,vec4(0.0),metal)*ambientColor*diffuse;//ambientColor*ambient*diffuse*(1.0-metal); 
	
	// DESATURATE
	//=0.5;
	lum=dot(finalcolor.rgb,vec3(0.3,0.59,0.11));
	finalcolor.rgb=mix(vec3(lum),finalcolor.rgb,saturation);
	
	gl_FragColor=max(finalcolor,0.0);
}
