#include "BvhExporter.h" using namespace std; // MAGIC of all bin exports #ifndef MAGIC #define MAGIC 0x827923 #endif #define BVH_VERSION 2.1 namespace CHCDemoEngine { static int currentIdx = 0; void BvhExporter::SaveNode(BvhNode *node, FILE *fw) { if (!node) return; int buffer[4]; if (node->IsLeaf()) { BvhLeaf *leaf = (BvhLeaf*)node; buffer[0] = mTriangleRangeMap[leaf].first; buffer[1] = mTriangleRangeMap[leaf].second; buffer[2] = -1;//leaf->GetAxis(); buffer[3] = currentIdx ++; fwrite(buffer, sizeof(int), 4, fw); } else { BvhInterior *interior = (BvhInterior *)node; buffer[0] = interior->mFirst; buffer[1] = interior->mLast; buffer[2] = 0;//interior->mAxis; buffer[3] = currentIdx ++; fwrite(buffer, sizeof(int), 4, fw); SaveNode(interior->GetFront(), fw); SaveNode(interior->GetBack(), fw); } } void BvhExporter::ConstructTriangleRangeMap(Bvh *bvh, BvhNode *node, int &first, int &last) { if (!node->IsLeaf()) { int m; BvhInterior *interior = static_cast(node); ConstructTriangleRangeMap(bvh, interior->GetFront(), first, m); ConstructTriangleRangeMap(bvh, interior->GetBack(), m, last); mTriangleRangeMap[node] = pair(first, last); } else { //first = currentIdx; last = first + bvh->CountTriangles(node); //currentIdx = last; mTriangleRangeMap[node] = pair(first, last); } } bool BvhExporter::ExportToFile(const string &filename, Bvh *bvh) { cout << "Info: Exporting to file '" << filename.c_str() << "'" << endl; FILE *fw = fopen(filename.c_str(), "wb"); if (fw == NULL) { cerr << "Error: Cannot open file for writing" << endl; return false; } int buffer[6]; buffer[0] = MAGIC; buffer[1] = BVH_VERSION * 1000; //buffer[2] = triangles.size(); buffer[3] = 0; // construction method buffer[4] = 1; // termination leaves buffer[5] = bvh->CountNumNodes(bvh->GetStaticRoot()); fwrite(buffer, sizeof(int), 6, fw); int first, last; ConstructTriangleRangeMap(bvh, bvh->GetStaticRoot(), first, last); BvhNodeContainer nodes; bvh->CollectNodes(bvh->GetStaticRoot(), nodes); vector triangles; BvhNodeContainer::const_iterator it, it_end = nodes.end(); for (it = nodes.begin(); it != it_end; ++ it) { BvhNode *node = *it; int f = mTriangleRangeMap[node].first; int b = mTriangleRangeMap[node].second; for (int i = f; i < b; ++ i) { triangles.push_back(i); } } // export sorted triangle IDs for (int i = 0; i < triangles.size(); ++i) { fwrite(&triangles[i], sizeof(int), 1, fw); } SaveNode(bvh->GetStaticRoot(), fw); cout << "successfully exported bvh" << endl; fclose(fw); return true; } }