#version 120 


// herp derp hax hax

uniform sampler2D depthTex;
uniform sampler2D aoTex;
uniform sampler2D srcTex;

uniform vec4 ScreenRes;
uniform vec4 ScreenInv;
uniform vec4 dUV;

const float near = 1.0;
const float far = 1000.0;



/*
vec3 cPos( vec2 sPos ) {
	float d = texture2D (depthTex, sPos).a;
	d =  (2 * near) / (far + near - d * (far - near));

	//d = 1 - 1/(d+1);
	float y = sPos.y * ScreenRes.w;
	float x = sPos.x;
	vec2 s = (vec2(x, y) - 0.5 ) * ( d ) * 0.76;
	return vec3(s.x, s.y, d);
}*/

//const vec2 dUV = vec2( 1.0/400.0, 1.0/300.0 );


float sampD( vec2 sPos ) {
	float d = texture2D (depthTex, sPos).a;
	d =  (2 * near) / (far + near - d * (far - near));	
	return d;
}

float sat( float v ) {
	//return clamp( v, 0.0, 1.0);
	return min( 1.0, max( 0.0, v));
}

void main()
{
	//col = cPos( gl_TexCoord[0].st ).x;
	
	
/*	vec3 pV = cPos( sp + vec2( 0, dUV.y )*1 );
	
	vec3 dpV = pV - cV;
	
	vec3 ndpV = normalize( dpV );
	
	ao = saturate ( dot( -cnV, ndpV ) );
//	ao = ndpV.x ;
	
	*/
	
//	col =  ao * 1.5;
		
//	col = abs( cV.z )*10;
	
//	col = ScreenRes.w;
	
//	float d = cV.z;
	
	
//	if (d > 0.95 && d < 1 ) 
//		col = 1;
//	else
//	col = 0;
//	col = d;
//	col = sat( ( d - 0.95 ) * 20 );

//	gl_FragColor = vec4( 0.127, 0.11, 0.096, col);	

	vec2 sp = gl_TexCoord[0].st;
	
	float cD = sampD( sp );



	bool fog = true;
	vec3 fogCol = vec3( 0.99608, 0.92157, 0.85490);
	//vec3 fogCol = vec3( 244.0/255.0, 217.0/255.0, 144.0/255.0);
	//vec3 fogCol = vec3( 144.0/255.0, 235.0/255.0, 246.0/255.0);
	float fogFactor = 0.0;
	
	if ( fog ) {
		float fogStart = 0.1;
		float fogStop = 0.2;

		fogFactor = sat( ( cD - fogStart ) / ( fogStop - fogStart ) );
	}

	if ( fogFactor > 0.999 ) {
		gl_FragColor = vec4( fogCol, 1);
			return;
	}




	const int blurSize = 5;
	float sumW = 0.0;
	float sumAO = 0.0;
	
	
	for ( int x=-blurSize/2; x < blurSize/2 +1; x++) {
		for ( int y=-blurSize/2; y < blurSize/2 +1; y++) {
			vec2 uvSamp = sp + vec2(dUV.x*x, dUV.y*y);
			float aoSamp = texture2D ( aoTex, uvSamp ).r;
			float ao = aoSamp;
			
			float d = sampD( uvSamp );
						
			if ( abs( cD - d ) < 0.001 ) {
				sumAO += ao;
				sumW += 1;
			}
		}		
	}

	float ao = 0;
	if ( sumW > 0 ) {
		ao = sumAO / sumW;
	} else {
		ao = texture2D ( aoTex, sp ).r;
	}
	
	ao = ao*1.0;


	
	const bool dof = true;
	const bool farOnly = true;
	
	vec3 dofCol = vec3( 0.0 );
	float dofW = 0.0;
	float dofFocus = 0.075;
	
	float dofDir = 1.0;
	
	if ( !farOnly && cD < dofFocus ) {
		dofDir = -1.0;
	}
	const int dofBlurSize = 5;
	if ( dof && ( !farOnly || cD > dofFocus  ) ) {
		for ( int x=-dofBlurSize/2; x < dofBlurSize/2 +1; x++) {
			for ( int y=-dofBlurSize/2; y < dofBlurSize/2 +1; y++) {
				vec2 uvSamp = sp + vec2(dUV.x*(x*2-0.5*sign(float(x))), dUV.y*(y*2-0.5*sign(float(y))));
				float d = sampD( uvSamp );
				
				
				float w = sat((10 - (abs( float(x) ) + abs( float(y) ))) / 10.0);
				//w = 1.0;
				//if ( ( cD - d )*dofDir < 0.01 ){ //|| d > dofFocus ) {
				//if ( ( dofFocus - d )*dofDir < 0.01 ){
				if ( ( d > dofFocus *dofDir ) ){
					dofCol += texture2D( srcTex, uvSamp ).rgb*w;
					dofW += 1.0*w;
//					dofCol += vec3(1,0,0);
				}// else {
				//	dofW += 1.0;
				//	dofCol += vec3(0,1,0);
				//}
				
			}		
		}
	}
	
	vec3 dofTexel = vec3( 0.0 );
	
	if ( dofW > 0 ) {
		dofTexel = dofCol*(1.0/dofW);
	} else  {
		//	dofTexel = texture2D( srcTex, sp ).rgb;
	}
	
	
	vec3 srcTexel = texture2D( srcTex, sp ).rgb;
	
	if ( dof ) {
		if ( !farOnly || cD > dofFocus ) {
			float diff = cD - dofFocus;
			float factor = sat(abs(diff)*50);
			srcTexel = srcTexel * (1-factor) + dofTexel*factor;
		}
	}
	
	if ( dofDir > 0 ) {
		//srcTexel = vec3( 0.0 );
	}
	
	//ao = 0.0;
	vec3 res = srcTexel * ( 1.0f - ao ) + vec3( 0.127, 0.11, 0.096 ) * ao;
	
	res = res * ( 1.0 - fogFactor) + fogCol *fogFactor;
	
	//res = vec3(texture2D ( aoTex, sp ).r );
	
	gl_FragColor.rgba = vec4( res, 1);
	
	//gl_FragColor.rgba = vec4(ao, ao, ao, 1);
	//gl_FragColor.rgba = vec4( 1,1, 1, ao);
	
	
	//gl_FragColor = vec4( srcTexel, 1);
	
	//gl_FragColor = vec4( cV.z, 0, 0, 1);
	
}
