Index: /GTP/trunk/Lib/Vis/Preprocessing/src/TestPreprocessor.vcproj
===================================================================
--- /GTP/trunk/Lib/Vis/Preprocessing/src/TestPreprocessor.vcproj	(revision 1708)
+++ /GTP/trunk/Lib/Vis/Preprocessing/src/TestPreprocessor.vcproj	(revision 1718)
@@ -206,5 +206,5 @@
 				Name="VCLinkerTool"
 				AdditionalDependencies="xerces-c_2.lib glew32.lib zdll.lib zziplib.lib devil.lib glut32.lib OpenGL32.Lib glu32.lib Preprocessor.lib RTScene.lib RTWorld.lib QtCore4.lib qtmain.lib QtOpenGL4.lib Qt3Support4.lib QtTest4.lib QtGui4.lib QtGlRenderer.lib"
-				OutputFile="../bin/release/Preprocessor.exe"
+				OutputFile="../bin/release/Preprocessor2.exe"
 				LinkIncremental="1"
 				AdditionalLibraryDirectories="..\src\GL;..\lib\release;..\..\Preprocessing\lib\release;..\..\..\..\..\..\NonGTP\Boost\lib;..\..\..\..\..\..\NonGTP\Xerces\xercesc\lib;..\..\..\..\..\..\NonGTP\Zlib\lib;..\..\..\..\..\..\NonGTP\Devil\lib;..\MultiLevelRayTracing\RTScene\Release;..\MultiLevelRayTracing\RTWorld\Release;&quot;$(QTDIR)\lib&quot;;.\QtGlRenderer\Release"
Index: /GTP/trunk/Lib/Vis/Preprocessing/src/HierarchyManager.h
===================================================================
--- /GTP/trunk/Lib/Vis/Preprocessing/src/HierarchyManager.h	(revision 1713)
+++ /GTP/trunk/Lib/Vis/Preprocessing/src/HierarchyManager.h	(revision 1718)
@@ -244,4 +244,6 @@
 
 
+	void CollectObjects(const AxisAlignedBox3 &box, ObjectContainer &objects);
+
 	float mInitialRenderCost;
 
@@ -463,5 +465,7 @@
 						  float &renderCost,
 						  float &memory,
-						  int &pvsEntries);
+						  int &pvsEntries,
+						  int &viewSpaceSplits,
+						  int &objectSpaceSplits);
 
 
Index: /GTP/trunk/Lib/Vis/Preprocessing/src/BvHierarchy.cpp
===================================================================
--- /GTP/trunk/Lib/Vis/Preprocessing/src/BvHierarchy.cpp	(revision 1717)
+++ /GTP/trunk/Lib/Vis/Preprocessing/src/BvHierarchy.cpp	(revision 1718)
@@ -838,13 +838,10 @@
   
 	const AxisAlignedBox3 nodeBbox = tData.mNode->GetBoundingBox();
-
-	const float minBox = nodeBbox.Min(axis);
-	const float maxBox = nodeBbox.Max(axis);
 	const float boxArea = nodeBbox.SurfaceArea();
 
 	float minSum = 1e20f;
   
-	float minBorder = maxBox;
-	float maxBorder = minBox;
+	float minBorder = nodeBbox.Max(axis);
+	float maxBorder = nodeBbox.Min(axis);
 	float areaLeft = 0, areaRight = 0;
 
@@ -854,29 +851,26 @@
 	vector<float> bordersRight;
 
-	if (mUseBboxAreaForSah)
-	{
-		// we keep track of both borders of the bounding boxes =>
-		// store the events in descending order
-
-		bordersRight.resize(mSubdivisionCandidates->size());
-
-		SortableEntryContainer::reverse_iterator rcit = 
-			mSubdivisionCandidates->rbegin(), rcit_end = 
-			mSubdivisionCandidates->rend();
-	
-		vector<float>::reverse_iterator rbit = bordersRight.rbegin();
-	
-		for (; rcit != rcit_end; ++ rcit, ++ rbit) 
-		{
-			Intersectable *obj = (*rcit).mObject;
-			const AxisAlignedBox3 obox = obj->GetBox();
-
-			if (obox.Min(axis) < minBorder)
-			{
-				minBorder = obox.Min(axis);
-			}
-
-			(*rbit) = minBorder;
-		}
+	// we keep track of both borders of the bounding boxes =>
+	// store the events in descending order
+
+	bordersRight.resize(mSubdivisionCandidates->size());
+
+	SortableEntryContainer::reverse_iterator rcit = 
+		mSubdivisionCandidates->rbegin(), rcit_end = 
+		mSubdivisionCandidates->rend();
+
+	vector<float>::reverse_iterator rbit = bordersRight.rbegin();
+
+	for (; rcit != rcit_end; ++ rcit, ++ rbit) 
+	{
+		Intersectable *obj = (*rcit).mObject;
+		const AxisAlignedBox3 obox = obj->GetBox();
+
+		if (obox.Min(axis) < minBorder)
+		{
+			minBorder = obox.Min(axis);
+		}
+
+		(*rbit) = minBorder;
 	}
 
@@ -899,36 +893,22 @@
 		const AxisAlignedBox3 obox = obj->GetBox();
 
-		if (mUseBboxAreaForSah)
-		{
-			AxisAlignedBox3 lbox = nodeBbox;
-			AxisAlignedBox3 rbox = nodeBbox;
-	
-			// the borders of the bounding boxes have changed
-			if (obox.Max(axis) > maxBorder)
-			{
-				maxBorder = obox.Max(axis);
-			}
-
-			minBorder = (*bit);
-
-			lbox.SetMax(axis, maxBorder);
-			rbox.SetMin(axis, minBorder);
-	
-			al = lbox.SurfaceArea();
-			ar = rbox.SurfaceArea();
-		}
-		else
-		{
-			// just add up areas of the objects itself
-			// As we are not sampling volumetric visibility,
-			// this should provide better heuristics
-			const float area = obj->GetArea();//obox.SurfaceArea();
-
-			al += area;
-			ar -= area;
-		}
+		// the borders of the bounding boxes have changed
+		if (obox.Max(axis) > maxBorder)
+		{
+			maxBorder = obox.Max(axis);
+		}
+
+		minBorder = (*bit);
+
+		AxisAlignedBox3 lbox = nodeBbox;
+		AxisAlignedBox3 rbox = nodeBbox;
+
+		lbox.SetMax(axis, maxBorder);
+		rbox.SetMin(axis, minBorder);
+
+		al = lbox.SurfaceArea();
+		ar = rbox.SurfaceArea();
 
 		const bool noValidSplit = ((objectsLeft <= Limits::Small) || (objectsRight <= Limits::Small));
-
 		const float sum =  noValidSplit ? 1e25 : objectsLeft * al + objectsRight * ar;
       
@@ -1054,5 +1034,5 @@
 		AxisAlignedBox3 rbox = nodeBbox;
 	
-		// the borders of the bounding boxes have changed
+		// the borders of the left bounding box have changed
 		for (int i = 0; i < 3; ++ i)
 		{
@@ -2386,3 +2366,44 @@
 
 
-}
+void BvHierarchy::CollectObjects(const AxisAlignedBox3 &box, ObjectContainer &objects)
+{
+	stack<BvhNode *> nodeStack;
+
+	nodeStack.push(mRoot);
+
+	while (!nodeStack.empty()) 
+	{
+		BvhNode *node = nodeStack.top();
+
+		nodeStack.pop();
+
+		if (node->IsLeaf()) 
+		{
+			BvhLeaf *leaf = (BvhLeaf *)node;
+
+			ObjectContainer::const_iterator oit, oit_end = leaf->mObjects.end();
+
+			for (oit = leaf->mObjects.begin(); oit != oit_end; ++oit) 
+			{
+				Intersectable *object = *oit;
+				if (Overlap(box, object->GetBox())) 
+				{
+					object->Mail();
+					objects.push_back(object);
+				}
+			}
+		} 
+		else 
+		{
+			BvhInterior *interior = (BvhInterior *)node;
+
+			if (Overlap(box, interior->GetBoundingBox()))
+				nodeStack.push(interior->GetFront());
+
+			if (Overlap(box, interior->GetBoundingBox()))
+				nodeStack.push(interior->GetBack());
+		}
+	}
+}
+
+}
Index: /GTP/trunk/Lib/Vis/Preprocessing/src/ViewCellsManager.cpp
===================================================================
--- /GTP/trunk/Lib/Vis/Preprocessing/src/ViewCellsManager.cpp	(revision 1717)
+++ /GTP/trunk/Lib/Vis/Preprocessing/src/ViewCellsManager.cpp	(revision 1718)
@@ -2628,9 +2628,8 @@
 
 
-void
-ViewCellsManager::UpdatePvsForEvaluation()
-{
-  ObjectPvs objPvs;
-  UpdatePvsForEvaluation(mViewCellsTree->GetRoot(), objPvs);
+void ViewCellsManager::UpdatePvsForEvaluation()
+{
+	ObjectPvs objPvs;
+	UpdatePvsForEvaluation(mViewCellsTree->GetRoot(), objPvs);
 }
 
@@ -5725,85 +5724,4 @@
 
 #if 1
-#if TEST_EVALUATION
-void VspOspViewCellsManager::EvalViewCellPartition()
-{
-	const int castSamples = (int)storedRays.size();
-	char s[64]; 
-	char statsPrefix[100];
-
-	Environment::GetSingleton()->GetStringValue("ViewCells.Evaluation.statsPrefix", statsPrefix);
-
-	Debug << "view cell stats prefix: " << statsPrefix << endl;
-
-	// should directional sampling be used?
-	const bool dirSamples = (mEvaluationSamplingType == SamplingStrategy::DIRECTION_BASED_DISTRIBUTION);
-
-	cout << "reseting pvs ... ";
-	const bool startFromZero = true;
-
-	if (startFromZero)
-	{
-		// reset pvs and start over from zero
-		mViewCellsTree->ResetPvs();
-	}
-	else 
-	{
-		// statistics before casting more samples
-		cout << "compute new statistics ... ";
-		sprintf(s, "-%09d-eval.log", castSamples);
-		string fName = string(statsPrefix) + string(s);
-
-		mViewCellsTree->ExportStats(fName);
-		cout << "finished" << endl;
-	}
-	cout << "finished" << endl;
-
-    cout << "Evaluating view cell partition ... " << endl;
-
-	VssRayContainer evaluationSamples = storedRays;
-	const int samplingType = mEvaluationSamplingType;
-	
-	cout << "computing sample contributions of " << (int)evaluationSamples.size()  << " samples ... ";
-	
-	ComputeSampleContributions(evaluationSamples, true, false);
-	
-	cout << "finished" << endl;
-	
-	cout << "compute new statistics ... ";
-	
-	// propagate pvs or pvs size information
-	ObjectPvs pvs;
-	UpdatePvsForEvaluation(mViewCellsTree->GetRoot(), pvs);
-
-
-	/////////////////////
-	// $§temporary matt: test render cost
-
-	sprintf(s, "-%09d-eval.log", castSamples);
-	string fileName = string(statsPrefix) + string(s);
-
-	ViewCellContainer leaves;
-
-	mViewCellsTree->CollectLeaves(mViewCellsTree->GetRoot(), leaves);
-	float rc = 0;
-
-	ViewCellContainer::const_iterator vit, vit_end = leaves.end();
-	
-	for (vit = leaves.begin(); vit != vit_end; ++ vit)
-	{
-		ViewCell *vc = *vit;
-		const float pvsCost = vc->GetPvs().EvalPvsCost();
-		const float vol = vc->GetVolume();
-		rc += pvsCost * vol;
-	}
-
-	Debug << "\nrendercost hack: " << rc / mViewSpaceBox.GetVolume() << endl;
-	mViewCellsTree->ExportStats(fileName);
-	cout << "finished" << endl;
-
-	disposeRays(evaluationSamples, NULL);
-}
-
-#else
 
 void VspOspViewCellsManager::EvalViewCellPartition()
@@ -5812,40 +5730,31 @@
 	int numSamples;
 	int castSamples = 0;
+	int oldSamples = 0;
+	int samplesForStats;
+	char statsPrefix[100];
+	char suffix[100];
 	int splitsStepSize;
 
-	char str[64]; 
-	
+
 	Environment::GetSingleton()->GetIntValue("ViewCells.Evaluation.samplesPerPass", samplesPerPass);
+	Environment::GetSingleton()->GetIntValue("ViewCells.Evaluation.samplesForStats", samplesForStats);
 	Environment::GetSingleton()->GetIntValue("ViewCells.Evaluation.samples", numSamples);
+	Environment::GetSingleton()->GetStringValue("ViewCells.Evaluation.statsPrefix", statsPrefix);
 	Environment::GetSingleton()->GetIntValue("ViewCells.Evaluation.stepSize", splitsStepSize);
-
-	char statsPrefix[100];
-	Environment::GetSingleton()->GetStringValue("ViewCells.Evaluation.statsPrefix", statsPrefix);
-
+	
+	Debug << "step size: " << splitsStepSize << endl;
 	Debug << "view cell evaluation samples per pass: " << samplesPerPass << endl;
 	Debug << "view cell evaluation samples: " << numSamples << endl;
 	Debug << "view cell stats prefix: " << statsPrefix << endl;
-	Debug << "step size: " << splitsStepSize << endl;
+
+	// should directional sampling be used?
+	bool dirSamples = 
+		(mEvaluationSamplingType == SamplingStrategy::DIRECTION_BASED_DISTRIBUTION);
 
 	cout << "reseting pvs ... ";
 		
-	const bool startFromZero = true;
-
 	// reset pvs and start over from zero
-	if (startFromZero)
-	{
-		mViewCellsTree->ResetPvs();
-	}
-	else // start from current sampless
-	{
-		// statistics before casting more samples
-		cout << "compute new statistics ... ";
-		sprintf(str, "-%09d-eval.log", castSamples);
-		string fName = string(statsPrefix) + string(str);
-
-		mViewCellsTree->ExportStats(fName);
-		cout << "finished" << endl;
-	}
-
+	mViewCellsTree->ResetPvs();
+	
 	cout << "finished" << endl;
     cout << "Evaluating view cell partition ... " << endl;
@@ -5853,10 +5762,8 @@
 	while (castSamples < numSamples)
 	{		
-		VssRayContainer evaluationSamples;
-
 		///////////////
 		//-- we have to use uniform sampling strategy for construction rays
 
-		//VssRayContainer evaluationSamples;
+		VssRayContainer evaluationSamples;
 		const int samplingType = mEvaluationSamplingType;
 
@@ -5871,8 +5778,9 @@
 
 		Real timeDiff = TimeDiff(startTime, GetTime());
-		Debug << "finished in " << timeDiff * 1e-3 << " secs" << endl;
-		cout << "finished in " << timeDiff * 1e-3 << " secs" << endl;
-
+		
+		cout << "finished in " << timeDiff * 1e-3f << " secs" << endl;
 		cout << "computing sample contributions of " << (int)evaluationSamples.size()  << " samples ... ";
+		
+		Debug << "finished in " << timeDiff * 1e-3f << " secs" << endl;
 		Debug << "computing sample contributions of " << (int)evaluationSamples.size()  << " samples ... ";
 
@@ -5885,24 +5793,46 @@
 		Debug << "finished in " << timeDiff * 1e-3 << " secs" << endl;
 
-		startTime = GetTime();
-		cout << "compute new statistics ... " << endl;
-
-		///////////
-		//-- output stats
-
-		sprintf(str, "-%09d-eval.log", castSamples);
-		const string splitsFilename = string(statsPrefix) + string(str);
-
-		ofstream splitsStr(splitsFilename.c_str());
-		mHierarchyManager->EvaluateSubdivision2(splitsStr, splitsStepSize);
-
-		timeDiff = TimeDiff(startTime, GetTime());
-		cout << "finished in " << timeDiff * 1e-3 << " secs" << endl;
-		Debug << "statistics computed in " << timeDiff * 1e-3 << " secs" << endl;
-	
+		if ((castSamples >= samplesForStats + oldSamples) || (castSamples >= numSamples))
+		{
+			oldSamples += samplesForStats;
+
+			///////////
+			//-- output stats
+
+			sprintf(suffix, "-%09d-eval.log", castSamples);
+			const string filename = string(statsPrefix) + string(suffix);
+
+			startTime = GetTime();
+			cout << "compute new statistics ... " << endl;
+
+			ofstream ofstr(filename.c_str());
+			mHierarchyManager->EvaluateSubdivision2(ofstr, splitsStepSize);
+
+			timeDiff = TimeDiff(startTime, GetTime());
+			cout << "finished in " << timeDiff * 1e-3 << " secs" << endl;
+			Debug << "statistics computed in " << timeDiff * 1e-3 << " secs" << endl;
+
+			// only for debugging purpose
+			if (1)
+			{
+				ViewCellContainer viewCells;
+				mViewCellsTree->CollectLeaves(mViewCellsTree->GetRoot(), viewCells);
+
+				ViewCellContainer::const_iterator vit, vit_end = viewCells.end();
+				int pvsSize = 0;
+
+				for (vit = viewCells.begin(); vit != vit_end; ++ vit)
+				{
+					pvsSize += (*vit)->GetPvs().GetSize();
+				}
+
+				cout << "debug entries: " << pvsSize << ", memcost: " << (float)pvsSize * ObjectPvs::GetEntrySize() << endl;
+			}
+		}
+
 		disposeRays(evaluationSamples, NULL);
 	}
+	
 }
 #endif
-#endif
-}
+}
Index: /GTP/trunk/Lib/Vis/Preprocessing/src/BvHierarchy.h
===================================================================
--- /GTP/trunk/Lib/Vis/Preprocessing/src/BvHierarchy.h	(revision 1707)
+++ /GTP/trunk/Lib/Vis/Preprocessing/src/BvHierarchy.h	(revision 1718)
@@ -613,4 +613,5 @@
 	static float EvalAbsCost(const ObjectContainer &objects);
 
+	void CollectObjects(const AxisAlignedBox3 &box, ObjectContainer &objects);
 
 protected:
Index: /GTP/trunk/Lib/Vis/Preprocessing/src/HierarchyManager.cpp
===================================================================
--- /GTP/trunk/Lib/Vis/Preprocessing/src/HierarchyManager.cpp	(revision 1715)
+++ /GTP/trunk/Lib/Vis/Preprocessing/src/HierarchyManager.cpp	(revision 1718)
@@ -1607,5 +1607,6 @@
 						const int entriesInPvs,
 						const float memoryCost,
-						const bool vsp)
+						const int viewSpaceSplits,
+						const int objectSpaceSplits)
 {
 	stats << "#Pass\n" << 0 << endl
@@ -1614,5 +1615,7 @@
 		   << "#TotalEntriesInPvs\n" << entriesInPvs << endl
 		   << "#Memory\n" << memoryCost << endl
-		   << "#Vsp\n" << (vsp ? 1 : 0) << endl
+		   << "#ViewSpaceSplits\n" << viewSpaceSplits << endl
+		   << "#ObjectSpaceSplits\n" << objectSpaceSplits << endl
+		   << "#VspOspRatio\n" << (float)viewSpaceSplits / (float)objectSpaceSplits << endl
 		   << endl;
 }
@@ -1782,5 +1785,7 @@
 										float &renderCost,
 										float &memory,
-										int &pvsEntries)
+										int &pvsEntries,
+										int &viewSpaceSplits,
+										int &objectSpaceSplits)
 {
 	ViewCellContainer viewCells;
@@ -1844,4 +1849,8 @@
 
 	memory = pvsEntries * ObjectPvs::GetEntrySize();
+
+	viewSpaceSplits = (int)viewCells.size();
+	objectSpaceSplits = (int)bvhNodes.size();
+
 	//cout << "viewCells: " << (int)viewCells.size() << " nodes: " << (int)bvhNodes.size() << " rc: " << renderCost << " entries: " << pvsEntries << endl;
 
@@ -1857,4 +1866,6 @@
 	int entriesInPvs = 1;
 	int steps = 0;
+	int viewSpaceSplits = 0;
+	int objectSpaceSplits = 0;
 
 	cout << "exporting vsposp stats ... " << endl;
@@ -1864,5 +1875,5 @@
 	//-- first view cell
 
-	UpdateStats(stats, 2, totalRenderCost, entriesInPvs, memoryCost, true);
+	UpdateStats(stats, 2, totalRenderCost, entriesInPvs, memoryCost, viewSpaceSplits, objectSpaceSplits);
 
 	//-- go through tree in the order of render cost decrease
@@ -1907,8 +1918,14 @@
 			entriesInPvs += entriesIncr;
 			// if (rcDecr <= 0)
-			if (nextCandidate->Type() == SubdivisionCandidate::VIEW_SPACE) 
+			if (nextCandidate->Type() == SubdivisionCandidate::VIEW_SPACE)
+			{
+				++ viewSpaceSplits;
 				cout << "v";//cout << "vsp t: " << timeStamp << " rc: " << rcDecr << " pvs: " << entriesIncr << endl;
+			}
 			else
+			{
+				++ objectSpaceSplits;
 				cout << "o";//"osp t: " << timeStamp << " rc: " << rcDecr << " pvs: " << entriesIncr << endl;
+			}
 
 			++ steps;
@@ -1916,6 +1933,7 @@
 			if ((steps % 500) == 499)
 				cout << steps << " steps taken" << endl;
+
 			const float memoryCost = (float)entriesInPvs * (float)ObjectPvs::GetEntrySize();
-			UpdateStats(stats, steps, totalRenderCost, entriesInPvs, memoryCost, false);
+			UpdateStats(stats, steps, totalRenderCost, entriesInPvs, memoryCost, viewSpaceSplits, objectSpaceSplits);
 		}
 
@@ -2010,10 +2028,25 @@
 	float memory;
 	int pvsEntries;
+	int viewSpaceSplits;
+	int objectSpaceSplits;
 
 	while (1)
 	{
-		const int numSplits = ExtractStatistics(splits, 99999.0, renderCost, memory, pvsEntries);
+		const int numSplits = ExtractStatistics(splits, 
+												99999.0, 
+												renderCost, 
+												memory, 
+												pvsEntries,
+												viewSpaceSplits,
+												objectSpaceSplits);
 		
-		UpdateStats(splitsStats, numSplits, renderCost, pvsEntries, memory, 0);
+		UpdateStats(splitsStats, 
+					numSplits, 
+					renderCost, 
+					pvsEntries, 
+					memory, 
+					viewSpaceSplits, 
+					objectSpaceSplits);
+
 		splits += splitsStepSize;
 
@@ -2023,3 +2056,8 @@
 }
 
-}
+
+void HierarchyManager::CollectObjects(const AxisAlignedBox3 &box, ObjectContainer &objects)
+{
+}
+
+}
