Index: GTP/trunk/App/Demos/Vis/FriendlyCulling/src/FrameBufferObject.cpp
===================================================================
--- GTP/trunk/App/Demos/Vis/FriendlyCulling/src/FrameBufferObject.cpp	(revision 2965)
+++ GTP/trunk/App/Demos/Vis/FriendlyCulling/src/FrameBufferObject.cpp	(revision 2976)
@@ -162,5 +162,9 @@
 	glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_WRAP_T, wrapParam);
 
-	if (useMipMap) glGenerateMipmapEXT(GL_TEXTURE_2D);
+	if (useMipMap) 
+	{
+		//glTexParameteri(GL_TEXTURE_2D, GL_GENERATE_MIPMAP, GL_FALSE);
+		glGenerateMipmapEXT(GL_TEXTURE_2D);
+	}
 
 	// print status
@@ -186,14 +190,39 @@
 	}
 
-	unsigned char *data = new unsigned char[bytes * 4 * mWidth * mHeight];
-
+	glBindTexture(GL_TEXTURE_2D, 0);
+	glFlush();
+	glFinish();
 	glEnable(GL_TEXTURE_2D);
 	glBindTexture(GL_TEXTURE_2D, mTexId);
-
-	glGetTexImage(GL_TEXTURE_2D, 0, GL_RGBA, mGlFormat, data);
+	//glBindTexture(GL_TEXTURE_2D, mTexId);
+	GLint width, height;
+
+	glGetTexLevelParameteriv(GL_TEXTURE_2D, 1, GL_TEXTURE_WIDTH, &width);
+	glGetTexLevelParameteriv(GL_TEXTURE_2D, 1, GL_TEXTURE_HEIGHT, &height);
+
+	cout << "w: " << width << "h: " << height << endl;
+
+	/*glGetTexLevelParameteriv(GL_TEXTURE_2D, 0, GL_TEXTURE_WIDTH, &width);
+	glGetTexLevelParameteriv(GL_TEXTURE_2D, 0, GL_TEXTURE_HEIGHT, &height);
+
+	cout << "w: " << width << "h: " << height << endl;
+*/
+	unsigned char *data = new unsigned char[bytes * 4 * width * height];
+
+
+	glGetTexImage(GL_TEXTURE_2D, 1, GL_RGBA, GL_FLOAT, data);
+	//glGetTexImage(GL_TEXTURE_RECTANGLE_EXT, 0, GL_LUMINANCE, GL_UNSIGNED_BYTE, (void *)data);
 
 	glBindTexture(GL_TEXTURE_2D, 0);
 	glDisable(GL_TEXTURE_2D);
 
+	float *d = (float *)data;
+
+	/*for (int i = 0; i < 10000; ++ i)
+	{
+		if (i % 100 == 0)
+		cout << "x: " << d[i];
+	}*/
+	//cout << endl << endl;
 	return data;
 }
Index: GTP/trunk/App/Demos/Vis/FriendlyCulling/src/shaders/deferred.cg
===================================================================
--- GTP/trunk/App/Demos/Vis/FriendlyCulling/src/shaders/deferred.cg	(revision 2975)
+++ GTP/trunk/App/Demos/Vis/FriendlyCulling/src/shaders/deferred.cg	(revision 2976)
@@ -64,5 +64,6 @@
 		   uniform sampler2D positions,
 		   uniform sampler2D normals,
-		   uniform float3 lightDir
+		   uniform float3 lightDir,
+		   uniform sampler2D oldColors
 		   )
 {
@@ -86,4 +87,6 @@
 	//-- write out logaritmic luminance for tone mapping
 
+	float4 oldColor = tex2Dlod(colors, float4(IN.texCoord.xy, 0, 99));
+
 	const float3 w = float3(0.299f, 0.587f, 0.114f);
 
@@ -94,5 +97,7 @@
 	float logLumScaled = logLum * INV_LOGLUM_RANGE - logLumOffset;
 
-	OUT.color.w = logLumScaled;
+	const static float factor = 0.2f;
+	
+	OUT.color.w = lerp(oldColor.w, logLumScaled, factor);
 
 	return OUT;
Index: GTP/trunk/App/Demos/Vis/FriendlyCulling/src/shaders/antialiasing.cg
===================================================================
--- GTP/trunk/App/Demos/Vis/FriendlyCulling/src/shaders/antialiasing.cg	(revision 2974)
+++ GTP/trunk/App/Demos/Vis/FriendlyCulling/src/shaders/antialiasing.cg	(revision 2976)
@@ -87,8 +87,10 @@
 	float4 s3 = tex2Dlod(colors, float4(offset + IN.lb.xy * w, 0, 0));
 
-	float4 sc = tex2Dlod(colors, float4(IN.c.xy, 0, 0));
+	float4 centerColor = tex2Dlod(colors, float4(IN.c.xy, 0, 0));
 
-	float4 col = (s0 + s1 + s2 + s3 + sc) * 0.2f;
+	float4 col = (s0 + s1 + s2 + s3 + centerColor) * 0.2f;
 	//return (s0 + s1 + s2 + s3) * 0.25f;
+
+	col.w = centerColor.w;
 
 	return col;
Index: GTP/trunk/App/Demos/Vis/FriendlyCulling/src/shaders/globillum.cg
===================================================================
--- GTP/trunk/App/Demos/Vis/FriendlyCulling/src/shaders/globillum.cg	(revision 2975)
+++ GTP/trunk/App/Demos/Vis/FriendlyCulling/src/shaders/globillum.cg	(revision 2976)
@@ -189,5 +189,5 @@
 		// check if something changed in the surrounding area
 		&& (oldNumSamples > 0.2 * gi.ao.y)
-		&& (oldAvgDepth / newAvgDepth > 0.99)
+		//&& (oldAvgDepth / newAvgDepth > 0.99)
 		)
 	{
Index: GTP/trunk/App/Demos/Vis/FriendlyCulling/src/glInterface.h
===================================================================
--- GTP/trunk/App/Demos/Vis/FriendlyCulling/src/glInterface.h	(revision 2899)
+++ GTP/trunk/App/Demos/Vis/FriendlyCulling/src/glInterface.h	(revision 2976)
@@ -23,5 +23,9 @@
 #endif	
 
-static GLenum mrt[] = {GL_COLOR_ATTACHMENT0_EXT, GL_COLOR_ATTACHMENT1_EXT, GL_COLOR_ATTACHMENT2_EXT, GL_COLOR_ATTACHMENT3_EXT};
+static GLenum mrt[] = 
+{GL_COLOR_ATTACHMENT0_EXT, GL_COLOR_ATTACHMENT1_EXT, GL_COLOR_ATTACHMENT2_EXT, GL_COLOR_ATTACHMENT3_EXT};
+
+static GLenum mrt2[] =
+{GL_COLOR_ATTACHMENT3_EXT, GL_COLOR_ATTACHMENT1_EXT, GL_COLOR_ATTACHMENT2_EXT, GL_COLOR_ATTACHMENT0_EXT};
 
 
Index: GTP/trunk/App/Demos/Vis/FriendlyCulling/src/DeferredRenderer.h
===================================================================
--- GTP/trunk/App/Demos/Vis/FriendlyCulling/src/DeferredRenderer.h	(revision 2973)
+++ GTP/trunk/App/Demos/Vis/FriendlyCulling/src/DeferredRenderer.h	(revision 2976)
@@ -61,4 +61,5 @@
 
 	void SetShadingMethod(SHADING_METHOD s);
+	static int colorBufferIdx;
 
 protected:
@@ -112,4 +113,5 @@
 
 	bool mRegenerateSamples;
+
 };
 
Index: GTP/trunk/App/Demos/Vis/FriendlyCulling/src/chcdemo.cpp
===================================================================
--- GTP/trunk/App/Demos/Vis/FriendlyCulling/src/chcdemo.cpp	(revision 2974)
+++ GTP/trunk/App/Demos/Vis/FriendlyCulling/src/chcdemo.cpp	(revision 2976)
@@ -168,5 +168,5 @@
 PerfTimer frameTimer, algTimer;
 
-
+static int sCurrentMrtSet = 0;
 
 /// the used render type for this render pass
@@ -617,5 +617,5 @@
 
 	// the diffuse color buffer
-	fbo->AddColorBuffer(ColorBufferObject::BUFFER_FLOAT_32, ColorBufferObject::WRAP_CLAMP_TO_EDGE, ColorBufferObject::FILTER_NEAREST, ColorBufferObject::FILTER_NEAREST);
+	fbo->AddColorBuffer(ColorBufferObject::BUFFER_FLOAT_32, ColorBufferObject::WRAP_CLAMP_TO_EDGE, ColorBufferObject::FILTER_LINEAR, ColorBufferObject::FILTER_LINEAR);
 
 	// the positions buffer
@@ -626,5 +626,5 @@
 
 	// another color buffer
-	fbo->AddColorBuffer(ColorBufferObject::BUFFER_FLOAT_32, ColorBufferObject::WRAP_CLAMP_TO_EDGE, ColorBufferObject::FILTER_NEAREST, ColorBufferObject::FILTER_NEAREST);
+	fbo->AddColorBuffer(ColorBufferObject::BUFFER_FLOAT_32, ColorBufferObject::WRAP_CLAMP_TO_EDGE, ColorBufferObject::FILTER_LINEAR, ColorBufferObject::FILTER_LINEAR);
 
 	PrintGLerror("fbo");
@@ -1053,5 +1053,15 @@
 		// draw to 3 color buffers
 		// a color, normal, and positions buffer
-		glDrawBuffers(4, mrt);
+		if (sCurrentMrtSet == 0)
+		{
+			DeferredRenderer::colorBufferIdx = 0;
+			glDrawBuffers(3, mrt);
+		}
+		else 
+		{
+			DeferredRenderer::colorBufferIdx = 3;
+			glDrawBuffers(3, mrt2);
+		}
+		sCurrentMrtSet = 1 - sCurrentMrtSet;
 
 		glEnableClientState(GL_NORMAL_ARRAY);
Index: GTP/trunk/App/Demos/Vis/FriendlyCulling/src/DeferredRenderer.cpp
===================================================================
--- GTP/trunk/App/Demos/Vis/FriendlyCulling/src/DeferredRenderer.cpp	(revision 2975)
+++ GTP/trunk/App/Demos/Vis/FriendlyCulling/src/DeferredRenderer.cpp	(revision 2976)
@@ -28,4 +28,6 @@
 
 static CGparameter sColorsTexDeferredParam;
+static CGparameter sOldColorsTexDeferredParam;
+
 static CGparameter sPositionsTexDeferredParam;
 static CGparameter sNormalsTexDeferredParam;
@@ -111,6 +113,7 @@
 static CGparameter sIntensityTexDownSampleParam;
 
-
-
+static unsigned int pbo[] = {0, 0};
+
+static unsigned int sCurrentPBOIdx = 0;
 //#define USE_3D_SSAO
 
@@ -128,5 +131,5 @@
 Sample2 pcfSamples[NUM_PCF_TABS];
 
-static int colorBufferIdx = 0;
+int DeferredRenderer::colorBufferIdx = 0;
 
 static void PrintGLerror(char *msg)
@@ -141,4 +144,17 @@
 	}
 }
+
+static int computeSize(int level)
+{
+	// Compute total image size.
+	float w = 1024;
+	float h = 768;
+
+	int mipmapSize = max(1, w / (1 << level) ) * 
+		             max(1, h / (1 << level) ) * sizeof(float) * 4;
+
+	return mipmapSize;
+}
+
 
 
@@ -257,4 +273,15 @@
 	mFbo->AddColorBuffer(ColorBufferObject::BUFFER_FLOAT_32, ColorBufferObject::WRAP_CLAMP_TO_EDGE, ColorBufferObject::FILTER_LINEAR);
 	mFbo->AddColorBuffer(ColorBufferObject::BUFFER_FLOAT_32, ColorBufferObject::WRAP_CLAMP_TO_EDGE, ColorBufferObject::FILTER_LINEAR);
+
+	glGenBuffersARB(2, pbo);
+
+	int dataSize = 1024 * 1768 * 4 * sizeof(float);
+
+	glBindBufferARB(GL_PIXEL_PACK_BUFFER_ARB, pbo[0]);
+	glBufferDataARB(GL_PIXEL_PACK_BUFFER_ARB, dataSize, 0, GL_STREAM_READ_ARB);
+	glBindBufferARB(GL_PIXEL_PACK_BUFFER_ARB, pbo[1]);
+	glBufferDataARB(GL_PIXEL_PACK_BUFFER_ARB, dataSize, 0, GL_STREAM_READ_ARB);
+
+	glBindBufferARB(GL_PIXEL_PACK_BUFFER_ARB, 0);
 }
 
@@ -297,4 +324,5 @@
 		sPositionsTexDeferredParam = cgGetNamedParameter(sCgDeferredProgram, "positions");  
 		sColorsTexDeferredParam = cgGetNamedParameter(sCgDeferredProgram, "colors");  
+		sOldColorsTexDeferredParam = cgGetNamedParameter(sCgDeferredProgram, "oldColors");
 		sNormalsTexDeferredParam = cgGetNamedParameter(sCgDeferredProgram, "normals");
 		
@@ -521,6 +549,5 @@
 
 	mFboIndex = 2 - mFboIndex;
-	//swap(mNewFbo, mOldFbo);	
-
+	
 	FrameBufferObject::Release();
 
@@ -537,6 +564,4 @@
 	glPushMatrix();
 	glLoadIdentity();
-
-	colorBufferIdx = 0;
 
 	const float offs = 0.5f;
@@ -551,5 +576,4 @@
 	else
 		FirstPass(fbo, light);
-
 
 	switch (mShadingMethod)
@@ -570,8 +594,9 @@
 	float imageKey, whiteLum, middleGrey;
 
-	// generate mip map levels of position texture
+	glPixelStorei(GL_PACK_ALIGNMENT, 1);
+	// generate mip map levels for average loglum and tone mapping 
 	glBindTexture(GL_TEXTURE_2D, fbo->GetColorBuffer(colorBufferIdx)->GetTexture());
 	glGenerateMipmapEXT(GL_TEXTURE_2D);
-
+	
 	ComputeToneParameters(fbo, light, imageKey, whiteLum, middleGrey);
 	ToneMap(fbo, light, imageKey, whiteLum, middleGrey);
@@ -770,4 +795,5 @@
 {
 	GLuint colorsTex = fbo->GetColorBuffer(colorBufferIdx)->GetTexture();
+	GLuint oldColorsTex = fbo->GetColorBuffer(3 - colorBufferIdx)->GetTexture();
 	GLuint positionsTex = fbo->GetColorBuffer(1)->GetTexture();
 	GLuint normalsTex = fbo->GetColorBuffer(2)->GetTexture();
@@ -786,4 +812,7 @@
 	cgGLSetTextureParameter(sColorsTexDeferredParam, colorsTex);
 	cgGLEnableTextureParameter(sColorsTexDeferredParam);
+
+	cgGLSetTextureParameter(sOldColorsTexDeferredParam, oldColorsTex);
+	cgGLEnableTextureParameter(sOldColorsTexDeferredParam);
 
 	cgGLSetTextureParameter(sPositionsTexDeferredParam, positionsTex);
@@ -811,4 +840,5 @@
 
 	cgGLDisableTextureParameter(sColorsTexDeferredParam);
+	cgGLDisableTextureParameter(sOldColorsTexDeferredParam);
 	cgGLDisableTextureParameter(sPositionsTexDeferredParam);
 	cgGLDisableTextureParameter(sNormalsTexDeferredParam);
@@ -1129,4 +1159,42 @@
 											 float &middleGrey)
 {
+	// read pixels from framebuffer to PBO
+/*	glBindBufferARB(GL_PIXEL_PACK_BUFFER_ARB, pbo[sCurrentPBOIdx]);
+	
+	glBindTexture(GL_TEXTURE_2D, fbo->GetColorBuffer(colorBufferIdx)->GetTexture());
+	glGetTexImage(GL_TEXTURE_2D, 0, GL_RGBA, GL_FLOAT, NULL);
+
+	/////////////
+	//-- map the PBO to process its data by CPU
+
+	sCurrentPBOIdx = 1 - sCurrentPBOIdx;
+
+	glBindBufferARB(GL_PIXEL_PACK_BUFFER_ARB, pbo[sCurrentPBOIdx]);
+	GLfloat *ptr = (GLfloat *)glMapBufferARB(GL_PIXEL_PACK_BUFFER_ARB, GL_READ_ONLY_ARB);
+
+	if (ptr)
+	{
+		float lumScaled = ptr[4 * 2 - 1];
+		float logLum = lumScaled * LOGLUM_RANGE + MINLOGLUM;
+		imageKey = exp(logLum);
+
+		cout << "key: " << imageKey << " " << lumScaled << endl;
+		glUnmapBufferARB(GL_PIXEL_PACK_BUFFER_ARB);
+	}
+*/
+	float *pixels = (float *)fbo->GetColorBuffer(colorBufferIdx)->ReadTexture();
+
+	float lumScaled = pixels[3];//4 * 2 - 1];
+	
+	float logLum = lumScaled * LOGLUM_RANGE + MINLOGLUM;
+	imageKey = exp(logLum);
+	
+	delete [] pixels;
+	cout << "key: " << imageKey << " " << lumScaled << endl;
+
+	// back to conventional pixel operation
+	glBindBufferARB(GL_PIXEL_PACK_BUFFER_ARB, 0);
+
+
 	// hack: estimate value where sky burns out
 	whiteLum = log(1e4f);
