source: GTP/trunk/App/Demos/Vis/FriendlyCulling/VisibilitySolutionConverter/VisibilitySolutionConverter.cpp @ 3246

Revision 3246, 20.3 KB checked in by mattausch, 15 years ago (diff)
Line 
1#include "VisibilitySolutionConverter.h"
2#include "Triangle3.h"
3#include "Vector3.h"
4#include "gzstream.h"
5#include <iostream>
6#include <queue>
7#include <stack>
8
9
10using namespace std;
11
12// MAGIC of all bin exports
13#ifndef MAGIC
14#define MAGIC 0x827923
15#endif
16
17#define BVH_VERSION 2.1
18
19#define TYPE_INTERIOR -2
20#define TYPE_LEAF -3
21
22
23static const float sScale = 0.05f;
24
25
26static string ReplaceSuffix(const string &str,
27                                                        const string &a,
28                                                        const string &b)
29{
30        string result = str;
31
32        int pos = (int)str.rfind(a, (int)str.size() - 1);
33        if (pos == str.size() - a.size())
34        {
35                result.replace(pos, a.size(), b);
36        }
37
38        return result;
39}
40
41
42static void LoadIndices(char *str,
43                                                const VertexArray &vertices,
44                                                const VertexArray &normals,
45                                                const vector<pair<float, float> > &texCoords,
46                                                VertexArray &faceVertices,
47                                                VertexArray &faceNormals,
48                                                vector<TexCoord> &faceTexCoords
49                                                )
50{
51        vector<string> triples;
52
53        char *next_token;
54
55        // extract the triples of the form v/t/n v/t/n ...
56        char *pch = strtok_s(str + 1, " ", &next_token);
57
58        while (pch)
59        {
60                string s(pch);
61                //s += "\n",
62                triples.push_back(s);
63               
64                pch = strtok_s(NULL, " ", &next_token);   
65        }
66
67        vector<int> indices;
68        vector<int> nIndices;
69        vector<int> tIndices;
70
71        char seps[] = " /\t\n";
72
73        for (size_t i = 0; i < triples.size(); ++ i)
74        {
75                static int dummy = 0;
76
77                size_t found;
78                found = triples[i].find_first_of(seps);
79                size_t prevfound = 0;
80                // vertex, normal, texture indices
81                string str = triples[i].substr(prevfound, found);
82
83                int index = (int)strtol(str.c_str(), NULL, 10) - 1;
84
85                int tIndex = index;
86                int nIndex = index;     
87               
88                prevfound = found;
89                found = triples[i].find_first_of(seps, found + 1); 
90
91                if (found != string::npos)
92                {
93                        str = triples[i].substr(prevfound, found);
94
95                        int idx = (int)strtol(str.c_str(), NULL, 10) - 1;
96                        if (idx > 0) tIndex = idx;
97                }
98
99                if ((found + 1) < triples[i].size())
100                {
101                        str = triples[i].substr(found + 1);
102
103                        int idx = (int)strtol(str.c_str(), NULL, 10) - 1;
104                        if (idx > 0) nIndex = idx;
105                }
106
107                // store indices
108                if (index >= 0)
109                {
110                        indices.push_back(index);
111                        nIndices.push_back(nIndex);
112                        tIndices.push_back(tIndex);
113                }
114
115                // new triangle found
116                if (indices.size() > 2)
117                {
118                        int idx1 = 0;
119                        int idx2 = (int)indices.size() - 2;
120                        int idx3 = (int)indices.size() - 1;
121
122                        faceVertices.push_back(vertices[indices[idx1]]);
123                        faceVertices.push_back(vertices[indices[idx2]]);
124                        faceVertices.push_back(vertices[indices[idx3]]);
125
126
127                        /*if (!normals.empty())
128                        {
129                                faceNormals.push_back(normals[nIndices[idx1]]);
130                                faceNormals.push_back(normals[nIndices[idx2]]);
131                                faceNormals.push_back(normals[nIndices[idx3]]);
132                        }
133                        else
134                        {
135                                // no face normals? => create normals
136                                const CHCDemoEngine::Triangle3
137                                        tri(vertices[indices[idx1]],
138                                            vertices[indices[idx2]],
139                                                vertices[indices[idx3]]);
140
141                                const CHCDemoEngine::Vector3 n = tri.GetNormal();
142
143                                faceNormals.push_back(n);
144                                faceNormals.push_back(n);
145                                faceNormals.push_back(n);
146                        }*/
147
148                        if (!texCoords.empty())
149                        {
150                                faceTexCoords.push_back(texCoords[tIndices[idx1]]);
151                                faceTexCoords.push_back(texCoords[tIndices[idx2]]);
152                                faceTexCoords.push_back(texCoords[tIndices[idx3]]);
153                        }
154                }
155        }
156}
157
158
159VisibilitySolutionConverter::VisibilitySolutionConverter()
160{}
161
162
163VisibilitySolutionConverter::~VisibilitySolutionConverter()
164{
165        for (size_t i = 0; i < mGeometry.size(); ++ i)
166        {
167                delete [] mGeometry[i]->mVertices;
168                delete [] mGeometry[i]->mNormals;
169                delete [] mGeometry[i]->mTexCoords;
170
171                delete mGeometry[i];
172        }
173       
174        mGeometry.clear();
175}
176
177
178void VisibilitySolutionConverter::LoadShape(const VertexArray &vertices,
179                                                                                        const VertexArray &normals,
180                                                                                        const vector<TexCoord> &texCoords)
181{
182        int numElements = (int)vertices.size();
183        Geometry *geom = new Geometry();
184
185        // convert the triangles to geometry
186        geom->mVertices = new CHCDemoEngine::Vector3[numElements];
187        geom->mNormals = new CHCDemoEngine::Vector3[numElements];
188        geom->mTexCoords = new TexCoord[numElements];
189
190        geom->mVertexCount = numElements;
191        geom->mTexcoordCount = (int)texCoords.size();
192
193        //cout << "number of vertices=" << numElements << endl;
194
195        for (int i = 0; i < numElements; ++ i)
196        {
197                // convert to our camera system: change y and z
198                geom->mVertices[i] =  vertices[i];
199                geom->mNormals[i] =  normals[i];
200               
201                if (i < geom->mTexcoordCount)
202                {
203                        geom->mTexCoords[i].first = texCoords[i].first;
204                        geom->mTexCoords[i].second = texCoords[i].second;
205                }
206        }
207
208        mGeometry.push_back(geom);
209}
210
211
212bool VisibilitySolutionConverter::Convert(const std::string &sceneInputFilename,
213                                                                                  const std::string &sceneOutputFilename,
214                                                                                  const std::string &bvhInputFilename,
215                                                                                  const std::string &bvhOutputFilename)
216{
217        mNumShapes = 0;
218       
219        // delete previous geometry
220        for (size_t i = 0; i < mGeometry.size(); ++ i)
221        {
222                delete [] mGeometry[i]->mVertices;
223                delete [] mGeometry[i]->mNormals;
224                delete [] mGeometry[i]->mTexCoords;
225
226                delete mGeometry[i];
227        }
228       
229        mGeometry.clear();
230
231        if (!LoadSolution(bvhInputFilename))
232        {
233                cerr << "could not read solution file" << endl;
234                return false;
235        }
236
237        if (!ReadScene(sceneInputFilename))
238        {
239                cerr << "could not read file" << endl;
240                return false;
241        }
242
243        // update bvh bounding boxes with loaded geometry
244        UpdateBvh(mRoot);
245
246        cout << "loading bvh, bb: " << mRoot->box << endl;
247
248        cout << "writing scene" << endl;
249
250        if (!WriteScene(sceneOutputFilename))
251        {
252                cerr << "could not write file" << endl;
253                return false;
254        }
255
256        cout << "writing bvh" << endl;
257
258        if (!WriteBvh(bvhOutputFilename))
259        {
260                cerr << "could not write bvh!" << endl;
261                return false;
262        }
263
264        return true;
265}
266
267
268bool VisibilitySolutionConverter::ReadScene(const string &filename)
269{
270        VertexArray vertices;
271        VertexArray normals;
272        vector<TexCoord> texCoords;
273
274        //if (ReadSimpleObj(filename, vertices, normals, texCoords))
275        if (ReadObj(filename, vertices, normals, texCoords))
276        {
277                ConstructBvhObjects(vertices, normals, texCoords);
278                return true;
279        }
280
281        return false;
282}
283
284
285bool VisibilitySolutionConverter::ReadObj(const string &filename,
286                                                                                  VertexArray &vertices,
287                                                                                  VertexArray &normals,
288                                                                                  vector<TexCoord> &texcoords)
289{
290        FILE *file;
291
292        if ((file = fopen(filename.c_str(), "r")) == NULL) return false;
293       
294        VertexArray tempVertices;
295        //tempVertices.reserve(11000000);
296        //tempVertices.reserve(13000000 * 3);
297
298        VertexArray tempNormals;
299        vector<TexCoord> tempTexcoords;
300
301        vector<int> indices;
302
303        int line = 0;
304        const int len = 10000;
305        char str[len];
306
307        const string binFilename = ReplaceSuffix(filename, ".obj", ".bn");
308
309        if (!ReadBinObj(binFilename, vertices))
310        {
311                cout << "binary dump " << binFilename << " not available, loading ascii obj" << endl;
312
313                while (fgets(str, len, file) != NULL)
314                {
315                        if (line % 500000 == 0)
316                                cout << line << " " << str;
317
318                        ++ line;
319
320                        switch (str[0])
321                        {
322                        case 'v': // vertex or normal
323                                {
324                                        float x, y, z;
325
326                                        //if (tempVertices.size() >= maxVertices * 3) continue;
327
328                                        switch (str[1])
329                                        {
330                                        case 'n' :
331                                                sscanf(str + 2, "%f %f %f", &x, &y, &z);
332                                                tempNormals.push_back(CHCDemoEngine::Vector3(x, -z, y));
333                                                break;
334                                        case 't':
335                                                sscanf(str + 2, "%f %f", &x, &y);
336                                                tempTexcoords.push_back(pair<float, float>(x, y));
337                                                break;
338                                        default:
339                                                sscanf(str + 1, "%f %f %f", &x, &y, &z);
340                                               
341                                                CHCDemoEngine::Vector3 v = CHCDemoEngine::Vector3(x, -z, y) * sScale;
342                                                tempVertices.push_back(v);
343                                                //cout <<"v " << x << " " << y << " "<< z << " ";
344                                        }
345                                        break;
346                                }
347                        case 'f':
348                                {
349                                        //////////
350                                        //-- indices in the current line
351
352                                        //if (tempVertices.size() >= maxVertices * 3) continue;
353                                        LoadIndices(str,
354                                                tempVertices, tempNormals, tempTexcoords,
355                                                vertices, normals, texcoords);
356
357                                        break;
358                                } 
359                                break;
360                        default:
361                                // throw away line
362                                break;
363                        }
364                }
365
366                ExportBinObj(binFilename, vertices);
367        }
368        else if (0)
369        {
370                cout << "creating normals" << endl;
371                normals.reserve(vertices.size());
372
373                for (size_t i = 0; i < vertices.size(); i += 3)
374                {
375                        // no face normals? => create normals
376                        const CHCDemoEngine::Triangle3
377                                tri(vertices[i], vertices[i + 1], vertices[i + 2]);
378
379                        const CHCDemoEngine::Vector3 n = tri.GetNormal();
380
381                        normals.push_back(n);
382                        normals.push_back(n);
383                        normals.push_back(n);
384                }
385        }
386
387        cout << "finished creating normals" << endl;
388
389        fclose(file);
390
391        return !vertices.empty();
392}
393
394
395static inline float RandomColor(float x)
396{
397        return x + (1.0f - x) * (float)rand() / RAND_MAX;
398}
399
400
401void VisibilitySolutionConverter::WriteGeometry(ogzstream &str, Geometry *geom)
402{
403        int vertexCount = geom->mVertexCount;
404        str.write(reinterpret_cast<char *>(&vertexCount), sizeof(int));
405 
406        str.write(reinterpret_cast<char *>(geom->mVertices), sizeof(CHCDemoEngine::Vector3) * vertexCount);
407        str.write(reinterpret_cast<char *>(geom->mNormals), sizeof(CHCDemoEngine::Vector3) * vertexCount);
408
409        int texCoordCount = 0;//geom->mTexcoordCount;
410        str.write(reinterpret_cast<char *>(&texCoordCount), sizeof(int));
411
412        if (texCoordCount)
413        {
414                str.write(reinterpret_cast<char *>(geom->mTexCoords), sizeof(float) * texCoordCount * 2);
415        }
416
417        ///////
418        //-- texture
419
420        int texId = -1;
421        str.write(reinterpret_cast<char *>(&texId), sizeof(int));
422
423        bool alphaTestEnabled = false;
424        bool cullFaceEnabled = true;
425
426        str.write(reinterpret_cast<char *>(&alphaTestEnabled), sizeof(bool));
427        str.write(reinterpret_cast<char *>(&cullFaceEnabled), sizeof(bool));
428
429        // material
430        bool hasMaterial = true;
431       
432        str.write(reinterpret_cast<char *>(&hasMaterial), sizeof(bool));
433       
434        if (hasMaterial)
435        {
436                CHCDemoEngine::Vector3 ambient, diffuse, spec, emm;
437
438                ambient.x = ambient.y = ambient.z = 0.2f;
439                //diffuse.x = diffuse.y = diffuse.z = 1.0f;
440
441                diffuse.x = RandomColor(0.5f);
442                diffuse.y = RandomColor(0.5f);
443                diffuse.z = RandomColor(0.5f);
444
445                spec.x = spec.y = spec.z = .0f;
446                emm = spec;
447
448                // only write rgb part of the material
449                str.write(reinterpret_cast<char *>(&ambient), sizeof(CHCDemoEngine::Vector3));
450                str.write(reinterpret_cast<char *>(&diffuse), sizeof(CHCDemoEngine::Vector3));
451                str.write(reinterpret_cast<char *>(&spec), sizeof(CHCDemoEngine::Vector3));
452                str.write(reinterpret_cast<char *>(&emm), sizeof(CHCDemoEngine::Vector3));
453        }
454}
455
456
457bool VisibilitySolutionConverter::WriteScene(const string &filename)
458{
459        ogzstream ofile(filename.c_str());
460
461        if (!ofile.is_open()) return false;
462       
463        int textureCount = 0;
464        ofile.write(reinterpret_cast<char *>(&textureCount), sizeof(int));
465
466
467        ///////////
468        //-- write shapes
469
470        int numShapes = (int)mGeometry.size();
471        ofile.write(reinterpret_cast<char *>(&numShapes), sizeof(int));
472
473        vector<Geometry *>::const_iterator it, it_end = mGeometry.end();
474
475        for (it = mGeometry.begin(); it != it_end; ++ it)
476        {
477                WriteGeometry(ofile, *it);
478        }
479
480
481        int entityCount = numShapes;
482        ofile.write(reinterpret_cast<char *>(&entityCount), sizeof(int));
483
484
485        //////////
486        //-- write single scene entity for each shape
487
488        // all shapes belong to this scene entity
489        for (int i = 0; i < numShapes; ++ i)
490        {
491                // no transformation
492                bool hasTrafo = false;
493                ofile.write(reinterpret_cast<char *>(&hasTrafo), sizeof(bool));
494
495                // a dummy lod
496                int numLODs = 1;
497                ofile.write(reinterpret_cast<char *>(&numLODs), sizeof(int));
498
499                float dist = 0;
500                ofile.write(reinterpret_cast<char *>(&dist), sizeof(float));
501
502                int shapesPerEntity = 1;
503                ofile.write(reinterpret_cast<char *>(&shapesPerEntity), sizeof(int));
504
505                int shapeId = i;
506                ofile.write(reinterpret_cast<char *>(&shapeId), sizeof(int));
507        }
508
509        return true;
510}
511
512
513void VisibilitySolutionConverter::ConstructBvhObjects(const VertexArray &vertices,
514                                                                                                          const VertexArray &normals,
515                                                                                                          const vector<TexCoord> &texCoords)
516{
517        CHCDemoEngine::AxisAlignedBox3 testBox;
518        testBox.Initialize();
519
520        for (int i = 0; i < vertices.size(); ++ i)
521        {
522                testBox.Include(vertices[i]);
523        }
524
525        cout << "geometry bounds: " << testBox << endl;
526
527        mGeometry.reserve(mBvhLeaves.size());
528
529        mNumShapes = (int)mBvhLeaves.size();
530
531        for (size_t i = 0; i < mBvhLeaves.size(); ++ i)
532        {
533                BvhLeaf *node = mBvhLeaves[i];
534
535                VertexArray _vertices; 
536                VertexArray _normals;
537                vector<TexCoord> _texCoords;
538
539                const int size = node->last - node->first + 1;
540
541                _vertices.reserve(size);
542                _normals.reserve(size);
543
544                //cout << "vtx: " << size << endl;
545                for (int j = node->first; j <= node->last; ++ j)
546                {
547                        const int idx = 3 * mGlobalTriangleIds[j];
548
549                        for (int k = 0; k < 3; ++ k)
550                        {
551                                _vertices.push_back(vertices[idx + k]);
552                                //_normals.push_back(normals[idx + k]);
553                                //_texCoords.push_back(texCoords[idx + k]);
554                        }
555
556                        // no face normals? => create normals
557                        const CHCDemoEngine::Triangle3
558                                tri(vertices[idx], vertices[idx + 1], vertices[idx + 2]);
559
560                        const CHCDemoEngine::Vector3 n = tri.GetNormal();
561
562                        _normals.push_back(n);
563                        _normals.push_back(n);
564                        _normals.push_back(n);
565                }
566
567                LoadShape(_vertices, _normals, _texCoords);
568               
569                // we store geometry in our bvh => change first and last pointer
570                // fromt triangles to geometry
571                node->first = (int)mGeometry.size() - 1;
572                node->last = (int)mGeometry.size() - 1;
573
574                //_vertices.clear();
575                //_normals.clear();
576                //_texCoords.clear();
577        }
578}
579
580
581bool VisibilitySolutionConverter::ReadBvh(FILE *fr)
582{
583        int buffer[6];
584        fread(buffer, sizeof(int), 6, fr);
585
586        if (buffer[0] != MAGIC)
587        {
588                cerr << "Error: Wrong file type" << endl;
589                return false;
590        }
591
592        if (buffer[1] != (int)(1000 * BVH_VERSION))
593        {
594                cerr << "Error: Wrong BVH version" << endl;
595                return false;
596        }
597
598        // load triangle ids
599        size_t numTriangles = buffer[2];
600        mGlobalTriangleIds.reserve(numTriangles);
601
602        for (size_t i = 0; i < numTriangles; ++i)
603        {
604                int id;
605                fread(&id, sizeof(int), 1, fr);
606                mGlobalTriangleIds.push_back(id);
607                //triangles[i] = scene->triangles[id];
608        }
609
610        const size_t numNodes = buffer[5];
611
612        mNumNodes = 0; // this was set to 1 in constructor!
613
614        mRoot = LoadNode(fr, 0);
615
616        if (mNumNodes != numNodes)
617        {
618                cerr << "Warning: Loaded " << mNumNodes <<
619                            " bvh nodes instead of " << buffer[5] << endl;
620        }
621
622        fclose(fr);
623       
624        return true;
625}
626
627
628void VisibilitySolutionConverter::UpdateLeafBox(BvhLeaf *leaf)
629{
630        leaf->box.Initialize();
631
632        Geometry *geom = mGeometry[leaf->first];
633
634        for (size_t i = 0; i < geom->mVertexCount; ++ i)
635        {
636                CHCDemoEngine::Vector3 v = geom->mVertices[i];
637                leaf->box.Include(v);
638        }
639}
640
641
642BvhNode *VisibilitySolutionConverter::LoadNode(FILE *fr, int depth)
643{
644        ++ mNumNodes;
645       
646        int buffer[4];
647        fread(buffer, sizeof(int), 4, fr);
648
649        if (buffer[2] != -1)
650        {
651                BvhInterior *interior = new BvhInterior();
652               
653                interior->first = buffer[0];
654                interior->last  = buffer[1];
655                interior->axis  = buffer[2];
656                interior->id    = buffer[3];
657                interior->depth = depth;
658
659                BvhNode *front, *back;
660
661                front = LoadNode(fr, depth + 1);
662                back  = LoadNode(fr, depth + 1);
663
664                front->parent = interior;
665                back->parent = interior;
666
667                interior->front = front;
668                interior->back = back;
669       
670                return (BvhNode *)interior;
671        }
672        else
673        {
674                // leaf
675                BvhLeaf *leaf = new BvhLeaf();
676
677                leaf->first = buffer[0];
678                leaf->last  = buffer[1];
679                leaf->axis  = buffer[2];
680                leaf->id    = buffer[3];
681
682                leaf->depth = depth;
683
684                mBvhLeaves.push_back(leaf);
685       
686                return (BvhNode *)leaf;
687        }
688}
689
690
691bool VisibilitySolutionConverter::ReadDummyTree(FILE *fr)
692{
693        int buffer[256];
694        fread(buffer, sizeof(int), 3, fr);
695
696        // read dummy bounding box
697        float dummy[6];
698        fread(dummy, sizeof(float) * 6, 1, fr);
699
700        int stack = 1;
701
702        // read dummy tree
703        while (stack)
704        {
705                int axis;
706                fread(&axis, sizeof(int), 1, fr);
707                -- stack;
708
709                if (axis != - 1)
710                {
711                        float dummy;
712                        fread(&dummy, sizeof(float), 1, fr);
713                       
714                        stack += 2;
715                }
716        }
717 
718        return true;
719}
720
721
722
723bool VisibilitySolutionConverter::LoadSolution(const string &filename)
724{
725        FILE *fr = fopen(filename.c_str(), "rb");
726
727        cerr << "Info: Loading visibility solution from file '" + filename + "'" << endl;
728 
729        if (fr == NULL)
730        {
731                cerr << "Error: Cannot open file for reading" << endl;
732                return false;
733        }
734
735        float totalSamples, totalTime;
736
737        fread(&totalSamples, sizeof(float), 1, fr);
738        fread(&totalTime, sizeof(float), 1, fr);
739
740        // just need to convert objects => read dummy visibility tree
741        bool ok = ReadDummyTree(fr);
742
743        // read bvh to determine objects (= the leaves of the bvh)
744        if (ok) ok = ReadBvh(fr);
745
746        fclose(fr);
747       
748        if (ok)
749                cout << "Info: visibility solution loaded" << endl;
750        else
751                cout << "Info: loading visibility solution failed" << endl;
752 
753        return true;
754}
755
756
757bool VisibilitySolutionConverter::ReadBinObj(const string &filename,
758                                                                                         VertexArray &vertices
759                                                                                         )
760{
761        igzstream inStream(filename.c_str());
762       
763        if (!inStream.is_open()) return false;
764
765        cout << "binary obj dump available, loading " << filename.c_str() << endl;
766       
767        // read in triangle size
768        int numTriangles;
769
770        const int t = 500000;
771        inStream.read(reinterpret_cast<char *>(&numTriangles), sizeof(int));
772        vertices.reserve(numTriangles * 3);
773        cout << "loading " << numTriangles * 3 << " vertices ("
774                << numTriangles * 3 * sizeof(CHCDemoEngine::Vector3) / (1024 * 1024) << " MB)" << endl;
775
776        int i = 0;
777
778        while (1)
779        {
780                CHCDemoEngine::Vector3 v;
781                inStream.read(reinterpret_cast<char *>(&v), sizeof(CHCDemoEngine::Vector3));
782
783                // end of file reached
784                if (inStream.eof())     break;
785               
786                //v *= scale;
787                vertices.push_back(v);
788
789                if (((i ++) % t) == 0)
790                         cout << "\r" << i << "/" << numTriangles * 3 << "\r";
791        }
792       
793        cout << "finished loading vertices" << endl;
794
795        if (i != numTriangles * 3)
796                cerr << "warning: " << numTriangles * 3 << " != " << i << endl;
797
798        inStream.close();
799
800        return true;
801}
802
803
804bool VisibilitySolutionConverter::ExportBinObj(const string &filename,
805                                                                                           const VertexArray &vertices)
806{       
807        ogzstream ofile(filename.c_str());
808        if (!ofile.is_open()) return false;
809
810        int numTriangles = (int)vertices.size() / 3;
811
812        ofile.write(reinterpret_cast<char *>(&numTriangles), sizeof(int));
813
814        VertexArray::const_iterator it, it_end = vertices.end();
815
816        for (it = vertices.begin(); it != it_end; ++ it)
817        {
818                CHCDemoEngine::Vector3 v = *it;
819                ofile.write(reinterpret_cast<char *>(&v), sizeof(CHCDemoEngine::Vector3));
820        }
821
822        cout << "exported " << numTriangles * 3 << " vertices" << endl;
823
824        ofile.close();
825
826        return true;
827}
828
829
830void VisibilitySolutionConverter::WriteNextNode(ogzstream &stream,
831                                                                                                BvhNode *node)
832{
833        int nodeType;
834
835        if (node->IsLeaf())
836                nodeType = TYPE_LEAF;
837        else
838                nodeType = TYPE_INTERIOR;
839               
840        stream.write(reinterpret_cast<char *>(&nodeType), sizeof(int));
841
842        CHCDemoEngine::AxisAlignedBox3 box = node->box;
843        //box.Scale(sScale);
844
845        CHCDemoEngine::Vector3 bMin = box.Min();
846        CHCDemoEngine::Vector3 bMax = box.Max();
847
848        stream.write(reinterpret_cast<char *>(&(node->first)), sizeof(int));
849        stream.write(reinterpret_cast<char *>(&(node->last)), sizeof(int));
850
851        stream.write(reinterpret_cast<char *>(&bMin), sizeof(CHCDemoEngine::Vector3));
852        stream.write(reinterpret_cast<char *>(&bMax), sizeof(CHCDemoEngine::Vector3));
853}
854
855
856void VisibilitySolutionConverter::UpdateBvh(BvhNode *node)
857{
858        if (!node->IsLeaf())
859        {
860                BvhInterior *interior = (BvhInterior *)node;
861
862                UpdateBvh(interior->front);
863                UpdateBvh(interior->back);
864
865                interior->first = min(interior->front->first, interior->back->first);
866                interior->last = max(interior->front->last, interior->back->last);
867               
868                node->box = Union(interior->front->box, interior->back->box);
869        }
870        else
871        {
872                UpdateLeafBox((BvhLeaf *)node);
873                //cout << "bb: " << node->box << endl;
874        }
875}
876
877
878bool VisibilitySolutionConverter::WriteBvh(const string &filename)
879{
880        std::queue<BvhNode *> tQueue;
881        ogzstream stream(filename.c_str());
882
883        if (!stream.is_open()) return NULL;
884
885        WriteNextNode(stream, mRoot);
886
887        tQueue.push(mRoot);
888       
889        while (!tQueue.empty())
890        {
891                BvhNode *node = tQueue.front();
892                tQueue.pop();
893
894                if (!node->IsLeaf())
895                {
896                        BvhInterior *interior = static_cast<BvhInterior *>(node);
897
898                        BvhNode *front = interior->front;
899                        BvhNode *back = interior->back;
900
901                        WriteNextNode(stream, front);
902                        WriteNextNode(stream, back);
903
904                        tQueue.push(front);                     
905                        tQueue.push(back);
906                }
907        }
908
909        return true;
910}
Note: See TracBrowser for help on using the repository browser.