source: GTP/trunk/Lib/Vis/Preprocessing/src/Preprocessor.cpp @ 746

Revision 746, 12.6 KB checked in by bittner, 18 years ago (diff)

visualization of the render cost and pvs sizes for viewcells

Line 
1#include "SceneGraph.h"
2#include "Exporter.h"
3#include "UnigraphicsParser.h"
4#include "X3dParser.h"
5#include "Preprocessor.h"
6#include "ViewCell.h"
7#include "Environment.h"
8#include "ViewCellsManager.h"
9#include "ViewCellBsp.h"
10#include "VspBspTree.h"
11#include "VspKdTree.h"
12#include "RenderSimulator.h"
13#include "GlRenderer.h"
14
15Preprocessor *preprocessor;
16
17Preprocessor::Preprocessor():
18mKdTree(NULL),
19mBspTree(NULL),
20mVspKdTree(NULL),
21mVspBspTree(NULL),
22mViewCellsManager(NULL)
23{
24  environment->GetBoolValue("Preprocessor.useGlRenderer", mUseGlRenderer);
25 
26  // renderer will be constructed when the scene graph and viewcell manager will be known
27  renderer = NULL;
28 
29  environment->GetBoolValue("Preprocessor.useGlDebugger", mUseGlDebugger);
30  environment->GetBoolValue("Preprocessor.loadPolygonsAsMeshes", mLoadPolygonsAsMeshes);
31  environment->GetBoolValue("Preprocessor.quitOnFinish", mQuitOnFinish);
32  environment->GetBoolValue("Preprocessor.computeVisibility", mComputeVisibility);
33  environment->GetBoolValue("Preprocessor.detectEmptyViewSpace", mDetectEmptyViewSpace);
34 
35  Debug << "detect empty view space=" << mDetectEmptyViewSpace << endl;
36  Debug << "load polygons as meshes: " << mLoadPolygonsAsMeshes << endl;
37
38}
39
40
41Preprocessor::~Preprocessor()
42{
43  Debug<<"Deleting view cells manager...\n";
44  DEL_PTR(mViewCellsManager);
45  Debug<<"done.\n";
46  Debug<<"Deleting bsp tree...\n";
47  DEL_PTR(mBspTree);
48  Debug<<"done.\n";
49  Debug<<"Deleting kd tree...\n";
50  DEL_PTR(mKdTree);
51  Debug<<"done.\n";
52  Debug<<"Deleting vspkd tree...\n";
53  DEL_PTR(mVspKdTree);
54  Debug<<"done.\n";
55  Debug<<"Deleting vspbsp tree...\n";
56  DEL_PTR(mVspBspTree);
57  Debug<<"done.\n";
58}
59
60int
61SplitFilenames(const string str, vector<string> &filenames)
62{
63        int pos = 0;
64
65        while(1) {
66                int npos = (int)str.find(';', pos);
67               
68                if (npos < 0 || npos - pos < 1)
69                        break;
70                filenames.push_back(string(str, pos, npos - pos));
71                pos = npos + 1;
72        }
73       
74        filenames.push_back(string(str, pos, str.size() - pos));
75        return (int)filenames.size();
76}
77
78bool
79Preprocessor::LoadScene(const string filename)
80{
81        // use leaf nodes of the original spatial hiearrchy as occludees
82        mSceneGraph = new SceneGraph;
83 
84        Parser *parser;
85        vector<string> filenames;
86        int files = SplitFilenames(filename, filenames);
87        cout << "number of input files: " << files << endl;
88        bool result = false;
89        if (files == 1) {
90               
91                if (strstr(filename.c_str(), ".x3d"))
92                        parser = new X3dParser;
93                else
94                        parser = new UnigraphicsParser;
95
96                cout<<filename<<endl;
97                result = parser->ParseFile(filename, &mSceneGraph->mRoot, mLoadPolygonsAsMeshes);
98
99                delete parser;
100
101        } else {
102                // root for different files
103                mSceneGraph->mRoot = new SceneGraphNode;
104                for (int i= 0; i < filenames.size(); i++) {
105                        if (strstr(filenames[i].c_str(), ".x3d"))
106                                parser = new X3dParser;
107                        else
108                                parser = new UnigraphicsParser;
109                       
110                        SceneGraphNode *node;
111                        if (parser->ParseFile(filenames[i], &node)) {
112                                mSceneGraph->mRoot->mChildren.push_back(node);
113                                // at least one file parsed
114                                result = true;
115                        }
116                        delete parser;
117                }
118        }
119       
120
121        if (result) {
122         
123          mSceneGraph->AssignObjectIds();
124          int intersectables, faces;
125          mSceneGraph->GetStatistics(intersectables, faces);
126          cout<<filename<<" parsed successfully."<<endl;
127          cout<<"#NUM_OBJECTS (Total numner of objects)\n"<<intersectables<<endl;
128          cout<<"#NUM_FACES (Total numner of faces)\n"<<faces<<endl;
129          mSceneGraph->CollectObjects(&mObjects);
130          mSceneGraph->mRoot->UpdateBox();
131
132         /* Exporter *exporter = Exporter::GetExporter("testload.x3d");
133
134          if (exporter)
135          {
136                  exporter->ExportGeometry(mObjects);
137                  delete exporter;
138          }*/
139
140        }
141       
142       
143        return result;
144}
145
146bool
147Preprocessor::ExportPreprocessedData(const string filename)
148{
149  return false;
150}
151
152bool
153Preprocessor::BuildKdTree()
154{
155  mKdTree = new KdTree;
156  // add mesh instances of the scene graph to the root of the tree
157  KdLeaf *root = (KdLeaf *)mKdTree->GetRoot();
158  mSceneGraph->CollectObjects(&root->mObjects);
159 
160  mKdTree->Construct();
161  return true;
162}
163
164void
165Preprocessor::KdTreeStatistics(ostream &s)
166{
167  s<<mKdTree->GetStatistics();
168}
169
170void
171Preprocessor::BspTreeStatistics(ostream &s)
172{
173        s << mBspTree->GetStatistics();
174}
175
176bool
177Preprocessor::Export( const string filename,
178                                          const bool scene,
179                                          const bool kdtree,
180                                          const bool bsptree
181                                          )
182{
183  Exporter *exporter = Exporter::GetExporter(filename);
184       
185  if (exporter) {
186    if (scene)
187      exporter->ExportScene(mSceneGraph->mRoot);
188
189    if (kdtree) {
190      exporter->SetWireframe();
191      exporter->ExportKdTree(*mKdTree);
192    }
193
194        if (bsptree) {
195                //exporter->SetWireframe();
196                exporter->ExportBspTree(*mBspTree);
197        }
198
199    delete exporter;
200    return true;
201  }
202
203  return false;
204}
205
206
207bool Preprocessor::PrepareViewCells()
208{
209        //-- parse view cells construction method
210        environment->GetBoolValue("ViewCells.loadFromFile", mLoadViewCells);
211        char buf[100];
212       
213        if (mLoadViewCells)
214        {
215                environment->GetStringValue("ViewCells.filename", buf);
216                mViewCellsManager = ViewCellsManager::LoadViewCells(buf, &mObjects);
217        }
218        else
219        {
220                //-- parse type of view cell container
221                char viewCellsStr[64];
222                environment->GetStringValue("ViewCells.type", viewCellsStr);
223            mViewCellsManager = CreateViewCellsManager(viewCellsStr);
224        }
225
226        float objRenderCost = 0, vcOverhead = 0, moveSpeed = 0;
227
228        environment->GetFloatValue("Simulation.objRenderCost",objRenderCost);
229        environment->GetFloatValue("Simulation.vcOverhead", vcOverhead);
230        environment->GetFloatValue("Simulation.moveSpeed", moveSpeed);
231       
232        mRenderSimulator =
233                new RenderSimulator(mViewCellsManager, objRenderCost, vcOverhead, moveSpeed);
234
235        mViewCellsManager->SetRenderer(mRenderSimulator);
236
237
238        if (mUseGlRenderer || mUseGlDebugger)
239        {
240                // NOTE: render texture should be power of 2 and square
241                // renderer must be initialised
242                renderer = new GlRendererBuffer(1024, 768, mSceneGraph, mViewCellsManager, mKdTree);
243                //              renderer->makeCurrent();
244               
245        }
246       
247        return true;
248}
249
250
251ViewCellsManager *Preprocessor::CreateViewCellsManager(const char *name)
252{
253        if (strcmp(name, "kdTree") == 0)
254        {
255                mViewCellsManager = new KdViewCellsManager(mKdTree);
256        }
257        else if (strcmp(name, "bspTree") == 0)
258        {
259                Debug << "view cell type: Bsp" << endl;
260
261                mBspTree = new BspTree();
262                mViewCellsManager = new BspViewCellsManager(mBspTree);
263        }
264        else if (strcmp(name, "vspBspTree") == 0)
265        {
266                Debug << "view cell type: VspBsp" << endl;
267
268                mVspBspTree = new VspBspTree();
269                mViewCellsManager = new VspBspViewCellsManager(mVspBspTree);
270        }
271        else if (strcmp(name, "vspKdTree") == 0)
272        {
273                mVspKdTree = new VspKdTree();           
274       
275                mViewCellsManager = new VspKdViewCellsManager(mVspKdTree);
276        }
277        else if (strcmp(name, "sceneDependent") == 0)
278        {
279                //TODO
280                mBspTree = new BspTree();
281
282                Debug << "view cell type: Bsp" << endl;
283               
284                mViewCellsManager = new BspViewCellsManager(mBspTree);
285        }
286        else
287        {
288                cerr << "Wrong view cells type " << name << "!!!" << endl;
289                exit(1);
290        }
291
292        return mViewCellsManager;
293}
294
295
296// use ascii format to store rays
297#define USE_ASCII 0
298
299
300inline bool ilt(Intersectable *obj1, Intersectable *obj2)
301{
302        return obj1->mId < obj2->mId;
303}
304
305
306bool Preprocessor::LoadSamples(VssRayContainer &samples,
307                                                           ObjectContainer &objects) const
308{
309        std::stable_sort(objects.begin(), objects.end(), ilt);
310        char fileName[100];
311        environment->GetStringValue("Preprocessor.samplesFilename", fileName);
312       
313    Vector3 origin, termination;
314        // HACK: needed only for lower_bound algorithm to find the
315        // intersected objects
316        MeshInstance sObj(NULL);
317        MeshInstance tObj(NULL);
318
319#if USE_ASCII
320        ifstream samplesIn(fileName);
321        if (!samplesIn.is_open())
322                return false;
323
324        string buf;
325        while (!(getline(samplesIn, buf)).eof())
326        {
327                sscanf(buf.c_str(), "%f %f %f %f %f %f %d %d",
328                           &origin.x, &origin.y, &origin.z,
329                           &termination.x, &termination.y, &termination.z,
330                           &(sObj.mId), &(tObj.mId));
331               
332                Intersectable *sourceObj = NULL;
333                Intersectable *termObj = NULL;
334               
335                if (sObj.mId >= 0)
336                {
337                        ObjectContainer::iterator oit =
338                                lower_bound(objects.begin(), objects.end(), &sObj, ilt);
339                        sourceObj = *oit;
340                }
341               
342                if (tObj.mId >= 0)
343                {
344                        ObjectContainer::iterator oit =
345                                lower_bound(objects.begin(), objects.end(), &tObj, ilt);
346                        termObj = *oit;
347                }
348
349                samples.push_back(new VssRay(origin, termination, sourceObj, termObj));
350        }
351#else
352        ifstream samplesIn(fileName, ios::binary);
353        if (!samplesIn.is_open())
354                return false;
355
356        while (1)
357        {
358                 samplesIn.read(reinterpret_cast<char *>(&origin), sizeof(Vector3));
359                 samplesIn.read(reinterpret_cast<char *>(&termination), sizeof(Vector3));
360                 samplesIn.read(reinterpret_cast<char *>(&(sObj.mId)), sizeof(int));
361                 samplesIn.read(reinterpret_cast<char *>(&(tObj.mId)), sizeof(int));
362               
363                 if (samplesIn.eof())
364                        break;
365
366                Intersectable *sourceObj = NULL;
367                Intersectable *termObj = NULL;
368               
369                if (sObj.mId >= 0)
370                {
371                        ObjectContainer::iterator oit =
372                                lower_bound(objects.begin(), objects.end(), &sObj, ilt);
373                        sourceObj = *oit;
374                }
375               
376                if (tObj.mId >= 0)
377                {
378                        ObjectContainer::iterator oit =
379                                lower_bound(objects.begin(), objects.end(), &tObj, ilt);
380                        termObj = *oit;
381                }
382
383                samples.push_back(new VssRay(origin, termination, sourceObj, termObj));
384        }
385
386#endif
387        samplesIn.close();
388
389        return true;
390}
391
392
393bool Preprocessor::ExportSamples(const VssRayContainer &samples) const
394{
395        char fileName[100];
396        environment->GetStringValue("Preprocessor.samplesFilename", fileName);
397       
398
399        VssRayContainer::const_iterator it, it_end = samples.end();
400       
401#if USE_ASCII
402        ofstream samplesOut(fileName);
403        if (!samplesOut.is_open())
404                return false;
405
406        for (it = samples.begin(); it != it_end; ++ it)
407        {
408                VssRay *ray = *it;
409                int sourceid = ray->mOriginObject ? ray->mOriginObject->mId : -1;               
410                int termid = ray->mTerminationObject ? ray->mTerminationObject->mId : -1;       
411
412                samplesOut << ray->GetOrigin().x << " " << ray->GetOrigin().y << " " << ray->GetOrigin().z << " "
413                                   << ray->GetTermination().x << " " << ray->GetTermination().y << " " << ray->GetTermination().z << " "
414                                   << sourceid << " " << termid << "\n";
415        }
416#else
417        ofstream samplesOut(fileName, ios::binary);
418        if (!samplesOut.is_open())
419                return false;
420
421        for (it = samples.begin(); it != it_end; ++ it)
422        {       
423                VssRay *ray = *it;
424                Vector3 origin(ray->GetOrigin());
425                Vector3 termination(ray->GetTermination());
426               
427                int sourceid = ray->mOriginObject ? ray->mOriginObject->mId : -1;               
428                int termid = ray->mTerminationObject ? ray->mTerminationObject->mId : -1;               
429
430                samplesOut.write(reinterpret_cast<char *>(&origin), sizeof(Vector3));
431                samplesOut.write(reinterpret_cast<char *>(&termination), sizeof(Vector3));
432                samplesOut.write(reinterpret_cast<char *>(&sourceid), sizeof(int));
433                samplesOut.write(reinterpret_cast<char *>(&termid), sizeof(int));
434    }
435#endif
436        samplesOut.close();
437        return true;
438}
439
440
441
442bool
443Preprocessor::GenerateRays(
444                                                   const int number,
445                                                   const int sampleType,
446                                                   SimpleRayContainer &rays
447                                                   )
448{
449  Vector3 origin, direction;
450  int startSize = rays.size();
451  for (int i=0; rays.size() - startSize  < number; i++) {
452        // now get the direction
453        switch (sampleType) {
454        case OBJECT_BASED_DISTRIBUTION: {
455          mViewCellsManager->GetViewPoint(origin);
456          Vector3 point;
457          Vector3 normal;
458          int i = RandomValue(0, mObjects.size() - 1);
459          Intersectable *object = mObjects[i];
460          object->GetRandomSurfacePoint(point, normal);
461          direction = point - origin;
462        }
463          break;
464        case OBJECT_DIRECTION_BASED_DISTRIBUTION: {
465          int i = RandomValue(0, mObjects.size() - 1);
466          Intersectable *object = mObjects[i];
467          Vector3 normal;
468          object->GetRandomSurfacePoint(origin, normal);
469          direction = UniformRandomVector(normal);
470          origin += 0.1f*direction;
471        }
472          break;
473        case DIRECTION_BASED_DISTRIBUTION:
474          mViewCellsManager->GetViewPoint(origin);
475          direction = UniformRandomVector();
476          break;
477        case DIRECTION_BOX_BASED_DISTRIBUTION: {
478          mViewCellsManager->GetViewPoint(origin);
479          float alpha = RandomValue(0.0f, 2*M_PI);
480          float beta = RandomValue(-M_PI/2, M_PI/2);
481          direction = VssRay::GetDirection(alpha, beta);
482          break;
483        }
484        case SPATIAL_BOX_BASED_DISTRIBUTION:
485          mViewCellsManager->GetViewPoint(origin);
486          direction = mKdTree->GetBox().GetRandomPoint() - origin;
487          break;
488        default:
489          // unsuported distribution type
490          return false;
491        }
492        // $$ jb the pdf is yet not correct for all sampling methods!
493        float pdf = 1.0f;
494        float c = Magnitude(direction);
495        if (c > Limits::Small) {
496          direction*=1.0f/c;
497          rays.AddRay(SimpleRay(origin, direction, pdf));
498        }
499  }
500  return true;
501}
Note: See TracBrowser for help on using the repository browser.