uniform sampler2D 	depthmap,
					normalmap,
					rippleTex;

uniform mat4		eyeToWorld;
uniform mat4		worldToEye;
uniform vec3		campos;

uniform float		rippleScale;
uniform float 		currentTime;
uniform float 		rainIntensity;
uniform float 		humidity;

varying vec2	VPOS;
varying vec2 	texcoord;

float PI=3.141592653589;
float MAX_DIST=6000.0;
float FADE_RANGE=3000.0;

vec4 TimeMul = vec4(1.0, 0.85, 0.93, 1.13); 
vec4 TimeAdd = vec4(0.0, 0.2, 0.45, 0.7);
vec4 Times = fract((currentTime * TimeMul + TimeAdd) * 1.6);

uniform vec4	TM0,
				TM1,
				TM3;

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;
}

vec2 encode (vec3 n)
{
	n=normalize(n);
    float f = sqrt(8.0*n.z+8.0);
    return n.xy / f + 0.5;
}

vec4 ComputeRipple(vec2 UV, float time, float Weight)
{
    vec4 Ripple = texture2D(rippleTex, UV);
    Ripple.yz = Ripple.yz * 2 - 1; // Decompress perturbation

    float DropFrac = fract(Ripple.w + time); // Apply time shift
    float TimeFrac = DropFrac - 1.0 + Ripple.x;
    float DropFactor = clamp(0.2 + Weight * 0.8 - DropFrac,0.0,1.0);
    float FinalFactor = DropFactor * Ripple.x * 
                        sin( clamp(TimeFrac * 9.0, 0.0, 3.0) * PI);
	Ripple.yz=Ripple.yz * FinalFactor * 0.35;
    return vec4(Ripple.y, 1.0, Ripple.z,DropFactor*Ripple.x);
}

void main()
{
	vec4 pos;
	pos.z = texture2D(depthmap,texcoord.st).r;
	vec4 encoded=texture2D(normalmap,texcoord.st);
	vec4 normal = decode(encoded);
	vec4 rippleColor=vec4(0.0,0.0,0.0,0.0);
	
	if(-pos.z<MAX_DIST)
	{
		// compute world position
		pos.xy=VPOS*-pos.z;
		pos.w=1.0;
		/*vec3 Wpos;
		Wpos=(VPOS.xyz*-pos.z)+campos;*/
		vec4	XYproj;	
		vec3 	projcoords;
		
		// COMPUTE LIGHT TEXTURE PROJECTION + ATTENUATION
		XYproj.x = dot(pos,TM0);
		XYproj.y = dot(pos,TM1);
		XYproj.w = dot(pos,TM3);
		projcoords.xy=(XYproj.xy/XYproj.w);
		vec2 coords0=projcoords.xy;//*220.0 - ofs;
		
		// convert normal to world space
		normal.w=0.0;
		vec4 WSnormal=eyeToWorld*normal;
		float facing=clamp(dot(WSnormal.xyz,vec3(0.0,1.0,0.0)),0.0,1.0);
		facing = max((facing-0.5),0.0)*2.0;
		
		// We enable one layer by quarter intensity and progressively blend in the
		// current layer
		vec4 Weights = min(rainIntensity/*3.0*/,1.0) - vec4(0.0, 0.25, 0.5, 0.75);
		Weights = clamp(Weights * 4.0,0.0,1.0);
		
		// Generate four shifted layer of animated circle
		vec2 UVRipple = /*Wpos.xz*/coords0;//*vec2(rippleScale);
		vec4 Ripple1 = ComputeRipple(UVRipple + vec2( 0.25,0.0),Times.x, Weights.x);
		vec4 Ripple2 = ComputeRipple(UVRipple + vec2(-0.55,0.3), Times.y, Weights.y);
		vec4 Ripple3 = ComputeRipple(UVRipple + vec2(0.6, 0.85), Times.z, Weights.z);
		vec4 Ripple4 = ComputeRipple(UVRipple + vec2(0.5,-0.75), Times.w, Weights.w);
		
		float Ripple=clamp(Ripple1.w+Ripple2.w+Ripple3.w+Ripple4.w,0.0,1.0);
		
		vec4 Z = mix(vec4(1.0), vec4(Ripple1.y, Ripple2.y, Ripple3.y, Ripple4.y), Weights);
		vec2 vWR=Weights.x * Ripple1.xz + Weights.y * Ripple2.xz + Weights.z * Ripple3.xz + Weights.w * Ripple4.xz;
		
		vec4 outNormal = vec4(vWR.x*4.0,Z.x * Z.y * Z.z * Z.w,vWR.y*4.0,0);
		outNormal=worldToEye*outNormal;
		
		MAX_DIST-=FADE_RANGE;
		float fadeToDist=1.0-clamp(((-pos.z)-MAX_DIST)/MAX_DIST,0.0,1.0);
		outNormal.xyz=mix(normal.xyz,outNormal.xyz,Ripple*facing*fadeToDist);
										
		rippleColor=vec4(encode(outNormal.xyz),0.0/*encoded.z-(rainIntensity*facing)*/,clamp(/*facing*/min(rainIntensity,1.0),0.0,1.0));
	}
	gl_FragColor=rippleColor;
}
