aboutsummaryrefslogtreecommitdiff
path: root/sdk/extensions/exporter/source
diff options
context:
space:
mode:
authorBryan Galdrikian <[email protected]>2018-01-22 14:04:16 -0800
committerBryan Galdrikian <[email protected]>2018-01-22 14:04:16 -0800
commit1dc1a87fba520bb45c1ce8165e8ea2c83c0a308d (patch)
tree5f8ca75a6b92c60fb5cf3b14282fc4cc1c127eb2 /sdk/extensions/exporter/source
parentUpdating readme.md to show updated UE4 Blast integration branches (diff)
downloadblast-1dc1a87fba520bb45c1ce8165e8ea2c83c0a308d.tar.xz
blast-1dc1a87fba520bb45c1ce8165e8ea2c83c0a308d.zip
Changes for 1.1.2 release candidate
See README.md, docs/release_notes.txt
Diffstat (limited to 'sdk/extensions/exporter/source')
-rw-r--r--sdk/extensions/exporter/source/NvBlastExtExporterFbxWriter.cpp31
-rw-r--r--sdk/extensions/exporter/source/NvBlastExtExporterFbxWriter.h9
-rw-r--r--sdk/extensions/exporter/source/NvBlastExtExporterObjReader.cpp33
-rw-r--r--sdk/extensions/exporter/source/NvBlastExtExporterObjReader.h14
-rw-r--r--sdk/extensions/exporter/source/NvBlastExtExporterObjWriter.cpp107
-rw-r--r--sdk/extensions/exporter/source/NvBlastExtExporterObjWriter.h11
6 files changed, 174 insertions, 31 deletions
diff --git a/sdk/extensions/exporter/source/NvBlastExtExporterFbxWriter.cpp b/sdk/extensions/exporter/source/NvBlastExtExporterFbxWriter.cpp
index 497c846..d465d65 100644
--- a/sdk/extensions/exporter/source/NvBlastExtExporterFbxWriter.cpp
+++ b/sdk/extensions/exporter/source/NvBlastExtExporterFbxWriter.cpp
@@ -69,6 +69,8 @@ FbxFileWriter::FbxFileWriter():
mRenderLayer = FbxDisplayLayer::Create(mScene, FbxUtils::getRenderGeometryLayerName().c_str());
mRenderLayer->Show.Set(true);
mRenderLayer->Color.Set(FbxDouble3(0.0f, 1.0f, 0.0f));
+
+ mInteriorIndex = -1;
}
void FbxFileWriter::release()
@@ -89,13 +91,19 @@ void FbxFileWriter::createMaterials(const ExporterMeshData& aResult)
for (uint32_t i = 0; i < aResult.submeshCount; ++i)
{
- FbxSurfacePhong* material = FbxSurfacePhong::Create(sdkManager.get(), aResult.submeshNames[i]);
+ FbxSurfacePhong* material = FbxSurfacePhong::Create(sdkManager.get(), aResult.submeshMats[i].name);
material->Diffuse.Set(FbxDouble3(float(rand()) / RAND_MAX , float(rand()) / RAND_MAX, float(rand()) / RAND_MAX));
material->DiffuseFactor.Set(1.0);
mMaterials.push_back(material);
}
}
+void FbxFileWriter::setInteriorIndex(int32_t index)
+{
+ mInteriorIndex = index;
+}
+
+
void FbxFileWriter::createMaterials(const AuthoringResult& aResult)
{
mMaterials.clear();
@@ -113,10 +121,19 @@ void FbxFileWriter::createMaterials(const AuthoringResult& aResult)
material->DiffuseFactor.Set(1.0);
mMaterials.push_back(material);
}
- FbxSurfacePhong* interiorMat = FbxSurfacePhong::Create(sdkManager.get(), "Interior_Material");
- interiorMat->Diffuse.Set(FbxDouble3(1.0, 0.0, 0.5));
- interiorMat->DiffuseFactor.Set(1.0);
- mMaterials.push_back(interiorMat);
+ if (mInteriorIndex == -1) // No material setted. Create new one.
+ {
+ FbxSurfacePhong* interiorMat = FbxSurfacePhong::Create(sdkManager.get(), "Interior_Material");
+ interiorMat->Diffuse.Set(FbxDouble3(1.0, 0.0, 0.5));
+ interiorMat->DiffuseFactor.Set(1.0);
+ mMaterials.push_back(interiorMat);
+ }
+ else
+ {
+ if (mInteriorIndex < 0) mInteriorIndex = 0;
+ if (static_cast<size_t>(mInteriorIndex) >= mMaterials.size()) mInteriorIndex = 0;
+ }
+
}
@@ -416,7 +433,7 @@ uint32_t FbxFileWriter::createChunkRecursive(uint32_t currentCpIdx, uint32_t chu
mesh->AddPolygon(currentCpIdx + cpIdx + 1);
mesh->AddPolygon(currentCpIdx + cpIdx + 2);
mesh->EndPolygon();
- int32_t material = (tri.materialId != MATERIAL_INTERIOR) ? ((tri.materialId < int32_t(mMaterials.size() - 1)) ? tri.materialId : 0) : int32_t(mMaterials.size() - 1);
+ int32_t material = (tri.materialId != MATERIAL_INTERIOR) ? ((tri.materialId < int32_t(mMaterials.size())) ? tri.materialId : 0) : ((mInteriorIndex == -1) ? int32_t(mMaterials.size() - 1): mInteriorIndex);
matElement->GetIndexArray().SetAt(polyCount, material);
if (smElement)
{
@@ -648,7 +665,7 @@ void FbxFileWriter::createChunkRecursiveNonSkinned(const std::string& meshName,
geUV->GetDirectArray().Add(uv);
}
mesh->EndPolygon();
- int32_t material = (geo.materialId != MATERIAL_INTERIOR) ? ((geo.materialId < int32_t(mMaterials.size() - 1))? geo.materialId : 0) : int32_t(mMaterials.size() - 1);
+ int32_t material = (geo.materialId != MATERIAL_INTERIOR) ? ((geo.materialId < int32_t(mMaterials.size()))? geo.materialId : 0) : ((mInteriorIndex == -1)? int32_t(mMaterials.size() - 1) : mInteriorIndex);
matElement->GetIndexArray().SetAt(polyCount, material);
if (smElement)
diff --git a/sdk/extensions/exporter/source/NvBlastExtExporterFbxWriter.h b/sdk/extensions/exporter/source/NvBlastExtExporterFbxWriter.h
index f8490cb..b6d5859 100644
--- a/sdk/extensions/exporter/source/NvBlastExtExporterFbxWriter.h
+++ b/sdk/extensions/exporter/source/NvBlastExtExporterFbxWriter.h
@@ -84,11 +84,16 @@ public:
virtual bool appendMesh(const ExporterMeshData& meshData, const char* assetName, bool nonSkinned) override;
/**
- Save scene to file.
+ Save scene to file.
*/
virtual bool saveToFile(const char* assetName, const char* outputPath) override;
/**
+ Set interior material index.
+ */
+ virtual void setInteriorIndex(int32_t index) override;
+
+ /**
Set true if FBX should be saved in ASCII mode.
*/
bool bOutputFBXAscii;
@@ -129,6 +134,8 @@ private:
void generateSmoothingGroups(fbxsdk::FbxMesh* mesh, FbxSkin* skin);
void removeDuplicateControlPoints(fbxsdk::FbxMesh* mesh, FbxSkin* skin);
+
+ int32_t mInteriorIndex;
};
}
diff --git a/sdk/extensions/exporter/source/NvBlastExtExporterObjReader.cpp b/sdk/extensions/exporter/source/NvBlastExtExporterObjReader.cpp
index fb6e9b3..9eba7d5 100644
--- a/sdk/extensions/exporter/source/NvBlastExtExporterObjReader.cpp
+++ b/sdk/extensions/exporter/source/NvBlastExtExporterObjReader.cpp
@@ -60,7 +60,18 @@ void ObjFileReader::loadFromFile(const char* filename)
std::vector<tinyobj::material_t> mats;
std::string err;
std::string mtlPath;
- bool ret = tinyobj::LoadObj(shapes, mats, err, filename);
+
+ int32_t lastDelimeter = strlen(filename);
+
+ while (lastDelimeter > 0 && filename[lastDelimeter] != '/' && filename[lastDelimeter] != '\\')
+ {
+ lastDelimeter--;
+ }
+ mtlPath = std::string(filename, filename + lastDelimeter);
+ mtlPath += '/';
+
+ bool ret = tinyobj::LoadObj(shapes, mats, err, filename, mtlPath.c_str());
+
// can't load?
if (!ret)
{
@@ -71,6 +82,18 @@ void ObjFileReader::loadFromFile(const char* filename)
std::cout << "Can load only one object per mesh" << std::endl;
}
+ if (!mats.empty())
+ {
+ if (mats.size() == 1 && mats[0].name == "")
+ {
+ mats[0].name = "Default";
+ }
+ for (uint32_t i = 0; i < mats.size(); ++i)
+ {
+ mMaterialNames.push_back(mats[i].name);
+ }
+ }
+
mVertexPositions.clear();
mVertexNormals.clear();
mVertexUv.clear();
@@ -93,6 +116,14 @@ void ObjFileReader::loadFromFile(const char* filename)
}
mIndices = shapes[0].mesh.indices;
+ mPerFaceMatId = shapes[0].mesh.material_ids;
+ for (uint32_t i = 0; i < mPerFaceMatId.size(); ++i)
+ {
+ if (mPerFaceMatId[i] == -1) // TinyOBJ loader sets ID to -1 when .mtl file not found. Set to default 0 material.
+ {
+ mPerFaceMatId[i] = 0;
+ }
+ }
}
diff --git a/sdk/extensions/exporter/source/NvBlastExtExporterObjReader.h b/sdk/extensions/exporter/source/NvBlastExtExporterObjReader.h
index 8990287..2e8c955 100644
--- a/sdk/extensions/exporter/source/NvBlastExtExporterObjReader.h
+++ b/sdk/extensions/exporter/source/NvBlastExtExporterObjReader.h
@@ -90,9 +90,9 @@ public:
virtual uint32_t* getIndexArray() override;
/**
- Get loaded per triangle material ids. Currently not supported by OBJ.
+ Get loaded per triangle material ids.
*/
- int32_t* getMaterialIds() override { return nullptr; };
+ int32_t* getMaterialIds() override { return mPerFaceMatId.data(); };
/**
Get loaded per triangle smoothing groups. Currently not supported by OBJ.
@@ -100,20 +100,24 @@ public:
int32_t* getSmoothingGroups() override { return nullptr; };
/**
- Get material name. Currently not supported by OBJ.
+ Get material name.
*/
- const char* getMaterialName(int32_t id) override { return nullptr; }
+ const char* getMaterialName(int32_t id) override { return mMaterialNames[id].c_str(); }
/**
Get material count.
*/
- int32_t getMaterialCount() { return 0; };
+ int32_t getMaterialCount() { return mMaterialNames.size(); };
private:
std::vector<physx::PxVec3> mVertexPositions;
std::vector<physx::PxVec3> mVertexNormals;
std::vector<physx::PxVec2> mVertexUv;
std::vector<uint32_t> mIndices;
+
+ std::vector<std::string> mMaterialNames;
+ std::vector<int32_t> mPerFaceMatId;
+
};
}
diff --git a/sdk/extensions/exporter/source/NvBlastExtExporterObjWriter.cpp b/sdk/extensions/exporter/source/NvBlastExtExporterObjWriter.cpp
index a49e28f..b453a62 100644
--- a/sdk/extensions/exporter/source/NvBlastExtExporterObjWriter.cpp
+++ b/sdk/extensions/exporter/source/NvBlastExtExporterObjWriter.cpp
@@ -31,6 +31,7 @@
#include <sstream>
#include "NvBlastExtAuthoringTypes.h"
#include "NvBlastExtAuthoringMesh.h"
+#include <algorithm>
using namespace physx;
@@ -43,6 +44,16 @@ void ObjFileWriter::release()
delete this;
}
+void ObjFileWriter::setInteriorIndex(int32_t index)
+{
+ mIntSurfaceMatIndex = index;
+}
+
+bool CompByMaterial(const Triangle& a, const Triangle& b)
+{
+ return a.materialId < b.materialId;
+}
+
bool ObjFileWriter::appendMesh(const AuthoringResult& aResult, const char* /*assetName*/, bool /*nonSkinned*/)
{
mMeshData = std::shared_ptr<ExporterMeshData>(new ExporterMeshData(), [](ExporterMeshData* md)
@@ -55,34 +66,90 @@ bool ObjFileWriter::appendMesh(const AuthoringResult& aResult, const char* /*ass
delete[] md->positions;
delete[] md->submeshOffsets;
//delete[] md->texIndex;
- delete[] md->submeshNames;
+ delete[] md->submeshMats;
delete[] md->uvs;
delete md;
});
+
+
ExporterMeshData& md = *mMeshData.get();
uint32_t triCount = aResult.geometryOffset[aResult.chunkCount];
md.meshCount = aResult.chunkCount;
- md.submeshOffsets = new uint32_t[md.meshCount + 1];
- for (uint32_t i = 0; i < md.meshCount + 1; i++)
- {
- md.submeshOffsets[i] = aResult.geometryOffset[i] * 3;
+ md.submeshCount = aResult.materialCount;
+
+ int32_t additionalMats = 0;
+
+ if (mIntSurfaceMatIndex == -1 || mIntSurfaceMatIndex >= (int32_t)md.submeshCount)
+ {
+ md.submeshCount += 1;
+ mIntSurfaceMatIndex = md.submeshCount - 1;
+ additionalMats = 1;
+ }
+
+ md.submeshOffsets = new uint32_t[md.meshCount * md.submeshCount + 1];
+ md.submeshMats = new Materials[md.submeshCount];
+
+ for (uint32_t i = 0; i < md.submeshCount - additionalMats; ++i)
+ {
+ md.submeshMats[i].name = aResult.materialNames[i];
+ md.submeshMats[i].diffuse_tex = nullptr;
+ }
+
+ if (additionalMats)
+ {
+ md.submeshMats[mIntSurfaceMatIndex].name = interiorNameStr.c_str();
+ md.submeshMats[mIntSurfaceMatIndex].diffuse_tex = nullptr;
}
- //md.submeshOffsets = md.meshOffsets;
- md.submeshCount = 1;
- //md.indicesCount = triCount * 3;
md.positionsCount = triCount * 3;
md.normalsCount = md.positionsCount;
md.uvsCount = md.positionsCount;
md.positions = new PxVec3[md.positionsCount];
md.normals = new PxVec3[md.normalsCount];
md.uvs = new PxVec2[md.uvsCount];
+
md.posIndex = new uint32_t[triCount * 3];
md.normIndex = md.posIndex;
md.texIndex = md.posIndex;
- md.submeshNames = new const char*[1]{ gTexPath };
+
+
+
+ /**
+ Now we need to sort input trianles chunk they belong to, then by material;
+ */
+ std::vector<Triangle> sorted;
+ sorted.reserve(triCount);
+
+
+ int32_t perChunkOffset = 0;
+ for (uint32_t i = 0; i < md.meshCount; ++i)
+ {
+ std::vector<uint32_t> perMaterialCount(md.submeshCount);
+
+ uint32_t first = aResult.geometryOffset[i];
+ uint32_t last = aResult.geometryOffset[i + 1];
+ uint32_t firstInSorted = sorted.size();
+ for (uint32_t t = first; t < last; ++t)
+ {
+ sorted.push_back(aResult.geometry[t]);
+ int32_t cmat = sorted.back().materialId;
+ if (cmat == MATERIAL_INTERIOR)
+ {
+ cmat = mIntSurfaceMatIndex;
+ }
+ perMaterialCount[cmat]++;
+ }
+ for (uint32_t mof = 0; mof < md.submeshCount; ++mof)
+ {
+ md.submeshOffsets[i * md.submeshCount + mof] = perChunkOffset * 3;
+ perChunkOffset += perMaterialCount[mof];
+ }
+ std::sort(sorted.begin() + firstInSorted, sorted.end(), CompByMaterial);
+ }
+ md.submeshOffsets[md.meshCount * md.submeshCount] = perChunkOffset * 3;
+
for (uint32_t vc = 0; vc < triCount; ++vc)
{
- Triangle& tri = aResult.geometry[vc];
+ Triangle& tri = sorted[vc];
uint32_t i = vc * 3;
md.positions[i+0] = tri.a.p;
md.positions[i+1] = tri.b.p;
@@ -129,8 +196,15 @@ bool ObjFileWriter::saveToFile(const char* assetName, const char* outputPath)
for (uint32_t submeshIndex = 0; submeshIndex < md.submeshCount; ++submeshIndex)
{
- fprintf(f, "newmtl mat%d\n", submeshIndex);
- fprintf(f, "\tmap_Kd %s\n", md.submeshNames[submeshIndex]);
+ fprintf(f, "newmtl %s\n", md.submeshMats[submeshIndex].name);
+ if (md.submeshMats[submeshIndex].diffuse_tex != nullptr)
+ {
+ fprintf(f, "\tmap_Kd %s\n", md.submeshMats[submeshIndex].diffuse_tex);
+ }
+ else
+ {
+ fprintf(f, "\tKd %f %f %f\n", float(rand()) / RAND_MAX, float(rand()) / RAND_MAX, float(rand()) / RAND_MAX);
+ }
fprintf(f, "\n");
}
@@ -165,13 +239,16 @@ bool ObjFileWriter::saveToFile(const char* assetName, const char* outputPath)
for (uint32_t chunkIndex = 0; chunkIndex < chunkCount; ++chunkIndex)
{
+ fprintf(f, "g %d \n", chunkIndex);
for (uint32_t submeshIndex = 0; submeshIndex < md.submeshCount; ++submeshIndex)
{
uint32_t firstIdx = md.submeshOffsets[chunkIndex * md.submeshCount + submeshIndex];
uint32_t lastIdx = md.submeshOffsets[chunkIndex * md.submeshCount + submeshIndex + 1];
- fprintf(f, "g %d_%d \n", chunkIndex, submeshIndex);
- fprintf(f, "usemtl mat%d\n", submeshIndex);
-
+ if (firstIdx == lastIdx) // There is no trianlges in this submesh.
+ {
+ continue;
+ }
+ fprintf(f, "usemtl %s\n", md.submeshMats[submeshIndex].name);
for (uint32_t i = firstIdx; i < lastIdx; i += 3)
{
fprintf(f, "f %d/%d/%d ", md.posIndex[i] + 1, md.texIndex[i] + 1, md.normIndex[i] + 1);
diff --git a/sdk/extensions/exporter/source/NvBlastExtExporterObjWriter.h b/sdk/extensions/exporter/source/NvBlastExtExporterObjWriter.h
index 3152d42..65e3f0f 100644
--- a/sdk/extensions/exporter/source/NvBlastExtExporterObjWriter.h
+++ b/sdk/extensions/exporter/source/NvBlastExtExporterObjWriter.h
@@ -34,7 +34,7 @@
#include <vector>
#include <PxVec2.h>
#include <PxVec3.h>
-
+#include <string>
struct NvBlastAsset;
namespace Nv
@@ -46,7 +46,7 @@ class ObjFileWriter : public IMeshFileWriter
{
public:
- ObjFileWriter() {};
+ ObjFileWriter(): mIntSurfaceMatIndex(-1), interiorNameStr("INTERIOR_MATERIAL") { };
~ObjFileWriter() = default;
virtual void release() override;
@@ -63,8 +63,15 @@ public:
*/
virtual bool saveToFile(const char* assetName, const char* outputPath) override;
+ /**
+ Set interior material index. Not supported in OBJ since AuthoringTool doesn't created OBJ with materials currently.
+ */
+ virtual void setInteriorIndex(int32_t index) override;
+
private:
std::shared_ptr<ExporterMeshData> mMeshData;
+ int32_t mIntSurfaceMatIndex;
+ std::string interiorNameStr;
};
}