00001
00002
00003
00004
00005
00006
00007
00008
00009
00010
00011
00012 #ifndef EXPLICIT_HIERARCHICAL_MESH_H
00013 #define EXPLICIT_HIERARCHICAL_MESH_H
00014
00015 #include "foundation/Px.h"
00016 #include "IProgressListener.h"
00017 #include "RenderMeshAsset.h"
00018 #include "ConvexHullMethod.h"
00019 #include "foundation/PxPlane.h"
00020
00021 namespace nvidia
00022 {
00023 namespace apex
00024 {
00025
00026 PX_PUSH_PACK_DEFAULT
00027
00033 struct ExplicitVertexFormat
00034 {
00036 uint32_t mWinding;
00037
00039 bool mHasStaticPositions;
00040
00042 bool mHasStaticNormals;
00043
00045 bool mHasStaticTangents;
00046
00048 bool mHasStaticBinormals;
00049
00051 bool mHasStaticColors;
00052
00054 bool mHasStaticSeparateBoneBuffer;
00055
00057 bool mHasStaticDisplacements;
00058
00060 bool mHasDynamicPositions;
00061
00063 bool mHasDynamicNormals;
00064
00066 bool mHasDynamicTangents;
00067
00069 bool mHasDynamicBinormals;
00070
00072 bool mHasDynamicColors;
00073
00075 bool mHasDynamicSeparateBoneBuffer;
00076
00078 bool mHasDynamicDisplacements;
00079
00081 uint32_t mUVCount;
00082
00084 uint32_t mBonesPerVertex;
00085
00087 ExplicitVertexFormat()
00088 {
00089 clear();
00090 }
00091
00113 void clear()
00114 {
00115 mWinding = RenderCullMode::CLOCKWISE;
00116 mHasStaticPositions = false;
00117 mHasStaticNormals = false;
00118 mHasStaticTangents = false;
00119 mHasStaticBinormals = false;
00120 mHasStaticColors = false;
00121 mHasStaticSeparateBoneBuffer = false;
00122 mHasStaticDisplacements = false;
00123 mHasDynamicPositions = false;
00124 mHasDynamicNormals = false;
00125 mHasDynamicTangents = false;
00126 mHasDynamicBinormals = false;
00127 mHasDynamicColors = false;
00128 mHasDynamicSeparateBoneBuffer = false;
00129 mHasDynamicDisplacements = false;
00130 mUVCount = 0;
00131 mBonesPerVertex = 0;
00132 }
00133
00137 bool operator == (const ExplicitVertexFormat& data) const
00138 {
00139 if (mWinding != data.mWinding)
00140 {
00141 return false;
00142 }
00143 if (mHasStaticPositions != data.mHasStaticPositions ||
00144 mHasStaticNormals != data.mHasStaticNormals ||
00145 mHasStaticTangents != data.mHasStaticTangents ||
00146 mHasStaticBinormals != data.mHasStaticBinormals ||
00147 mHasStaticColors != data.mHasStaticColors ||
00148 mHasStaticSeparateBoneBuffer != data.mHasStaticSeparateBoneBuffer ||
00149 mHasStaticDisplacements != data.mHasStaticDisplacements)
00150 {
00151 return false;
00152 }
00153 if (mHasDynamicPositions != data.mHasDynamicPositions ||
00154 mHasDynamicNormals != data.mHasDynamicNormals ||
00155 mHasDynamicTangents != data.mHasDynamicTangents ||
00156 mHasDynamicBinormals != data.mHasDynamicBinormals ||
00157 mHasDynamicColors != data.mHasDynamicColors ||
00158 mHasDynamicSeparateBoneBuffer != data.mHasDynamicSeparateBoneBuffer ||
00159 mHasDynamicDisplacements != data.mHasDynamicDisplacements)
00160 {
00161 return false;
00162 }
00163 if (mUVCount != data.mUVCount)
00164 {
00165 return false;
00166 }
00167 return true;
00168 }
00169
00173 bool operator != (const ExplicitVertexFormat& data) const
00174 {
00175 return !(*this == data);
00176 }
00177
00181 void copyToVertexFormat(VertexFormat* format) const
00182 {
00183 format->reset();
00184 uint32_t bi;
00185 if (mHasStaticPositions)
00186 {
00187 bi = (uint32_t)format->addBuffer(format->getSemanticName(RenderVertexSemantic::POSITION));
00188 format->setBufferFormat(bi, RenderDataFormat::FLOAT3);
00189 format->setBufferAccess(bi, mHasDynamicPositions ? RenderDataAccess::DYNAMIC : RenderDataAccess::STATIC);
00190 }
00191 if (mHasStaticNormals)
00192 {
00193 bi = (uint32_t)format->addBuffer(format->getSemanticName(RenderVertexSemantic::NORMAL));
00194 format->setBufferFormat(bi, RenderDataFormat::FLOAT3);
00195 format->setBufferAccess(bi, mHasDynamicNormals ? RenderDataAccess::DYNAMIC : RenderDataAccess::STATIC);
00196 }
00197 if (mHasStaticTangents)
00198 {
00199 bi = (uint32_t)format->addBuffer(format->getSemanticName(RenderVertexSemantic::TANGENT));
00200 format->setBufferFormat(bi, RenderDataFormat::FLOAT3);
00201 format->setBufferAccess(bi, mHasDynamicTangents ? RenderDataAccess::DYNAMIC : RenderDataAccess::STATIC);
00202 }
00203 if (mHasStaticBinormals)
00204 {
00205 bi = (uint32_t)format->addBuffer(format->getSemanticName(RenderVertexSemantic::BINORMAL));
00206 format->setBufferFormat(bi, RenderDataFormat::FLOAT3);
00207 format->setBufferAccess(bi, mHasDynamicBinormals ? RenderDataAccess::DYNAMIC : RenderDataAccess::STATIC);
00208 }
00209 if (mHasStaticDisplacements)
00210 {
00211 bi = (uint32_t)format->addBuffer(format->getSemanticName(RenderVertexSemantic::DISPLACEMENT_TEXCOORD));
00212 format->setBufferFormat(bi, RenderDataFormat::FLOAT3);
00213 format->setBufferAccess(bi, mHasDynamicDisplacements ? RenderDataAccess::DYNAMIC : RenderDataAccess::STATIC);
00214 bi = (uint32_t)format->addBuffer(format->getSemanticName(RenderVertexSemantic::DISPLACEMENT_FLAGS));
00215 format->setBufferFormat(bi, RenderDataFormat::UINT1);
00216 format->setBufferAccess(bi, mHasDynamicDisplacements ? RenderDataAccess::DYNAMIC : RenderDataAccess::STATIC);
00217 }
00218 if (mUVCount > 0)
00219 {
00220 bi = (uint32_t)format->addBuffer(format->getSemanticName(RenderVertexSemantic::TEXCOORD0));
00221 format->setBufferFormat(bi, RenderDataFormat::FLOAT2);
00222 }
00223 if (mUVCount > 1)
00224 {
00225 bi = (uint32_t)format->addBuffer(format->getSemanticName(RenderVertexSemantic::TEXCOORD1));
00226 format->setBufferFormat(bi, RenderDataFormat::FLOAT2);
00227 }
00228 if (mUVCount > 2)
00229 {
00230 bi = (uint32_t)format->addBuffer(format->getSemanticName(RenderVertexSemantic::TEXCOORD2));
00231 format->setBufferFormat(bi, RenderDataFormat::FLOAT2);
00232 }
00233 if (mUVCount > 3)
00234 {
00235 bi = (uint32_t)format->addBuffer(format->getSemanticName(RenderVertexSemantic::TEXCOORD3));
00236 format->setBufferFormat(bi, RenderDataFormat::FLOAT2);
00237 }
00238 switch (mBonesPerVertex)
00239 {
00240 case 1:
00241 bi = (uint32_t)format->addBuffer(format->getSemanticName(RenderVertexSemantic::BONE_INDEX));
00242 format->setBufferFormat(bi, RenderDataFormat::USHORT1);
00243 break;
00244 case 2:
00245 bi = (uint32_t)format->addBuffer(format->getSemanticName(RenderVertexSemantic::BONE_INDEX));
00246 format->setBufferFormat(bi, RenderDataFormat::USHORT2);
00247 bi = (uint32_t)format->addBuffer(format->getSemanticName(RenderVertexSemantic::BONE_WEIGHT));
00248 format->setBufferFormat(bi, RenderDataFormat::FLOAT2);
00249 break;
00250 case 3:
00251 bi = (uint32_t)format->addBuffer(format->getSemanticName(RenderVertexSemantic::BONE_INDEX));
00252 format->setBufferFormat(bi, RenderDataFormat::USHORT3);
00253 bi = (uint32_t)format->addBuffer(format->getSemanticName(RenderVertexSemantic::BONE_WEIGHT));
00254 format->setBufferFormat(bi, RenderDataFormat::FLOAT3);
00255 break;
00256 case 4:
00257 bi = (uint32_t)format->addBuffer(format->getSemanticName(RenderVertexSemantic::BONE_INDEX));
00258 format->setBufferFormat(bi, RenderDataFormat::USHORT4);
00259 bi = (uint32_t)format->addBuffer(format->getSemanticName(RenderVertexSemantic::BONE_WEIGHT));
00260 format->setBufferFormat(bi, RenderDataFormat::FLOAT4);
00261 break;
00262 }
00263
00264 format->setHasSeparateBoneBuffer(mHasStaticSeparateBoneBuffer);
00265 format->setWinding((RenderCullMode::Enum)mWinding);
00266 }
00267 };
00268
00269
00277 struct ExplicitSubmeshData
00278 {
00282 enum
00283 {
00284 MaterialNameBufferSize = 1024
00285 };
00286
00290 char mMaterialName[MaterialNameBufferSize];
00291
00296 ExplicitVertexFormat mVertexFormat;
00297
00301 bool operator == (const ExplicitSubmeshData& data) const
00302 {
00303 return !::strcmp(mMaterialName, data.mMaterialName) && mVertexFormat == data.mVertexFormat;
00304 }
00305
00309 bool operator != (const ExplicitSubmeshData& data) const
00310 {
00311 return !(*this == data);
00312 }
00313 };
00314
00315
00319 struct CollisionVolumeDesc
00320 {
00321 CollisionVolumeDesc()
00322 {
00323 setToDefault();
00324 }
00325
00329 void setToDefault()
00330 {
00331 mHullMethod = ConvexHullMethod::CONVEX_DECOMPOSITION;
00332 mConcavityPercent = 4.0f;
00333 mMergeThreshold = 4.0f;
00334 mRecursionDepth = 0;
00335 mMaxVertexCount = 0;
00336 mMaxEdgeCount = 0;
00337 mMaxFaceCount = 0;
00338 }
00339
00344 ConvexHullMethod::Enum mHullMethod;
00345
00350 float mConcavityPercent;
00351
00356 float mMergeThreshold;
00357
00364 uint32_t mRecursionDepth;
00365
00370 uint32_t mMaxVertexCount;
00371
00376 uint32_t mMaxEdgeCount;
00377
00382 uint32_t mMaxFaceCount;
00383 };
00384
00385
00389 struct CollisionDesc
00390 {
00400 unsigned mDepthCount;
00401
00405 CollisionVolumeDesc* mVolumeDescs;
00406
00412 float mMaximumTrimming;
00413
00415 CollisionDesc()
00416 {
00417 setToDefault();
00418 }
00419
00423 void setToDefault()
00424 {
00425 mDepthCount = 0;
00426 mVolumeDescs = NULL;
00427 mMaximumTrimming = 0.2f;
00428 }
00429 };
00430
00431
00436 struct FractureMethod
00437 {
00441 enum Enum
00442 {
00443 Unknown,
00444 Slice,
00445 Cutout,
00446 Voronoi,
00447
00448 FractureMethodCount
00449 };
00450 };
00451
00452
00458 struct FractureMaterialDesc
00459 {
00463 PxVec2 uvScale;
00464
00468 PxVec2 uvOffset;
00469
00474 PxVec3 tangent;
00475
00479 float uAngle;
00480
00485 uint32_t interiorSubmeshIndex;
00486
00488 FractureMaterialDesc()
00489 {
00490 setToDefault();
00491 }
00492
00501 void setToDefault()
00502 {
00503 uvScale = PxVec2(1.0f);
00504 uvOffset = PxVec2(0.0f);
00505 tangent = PxVec3(0.0f);
00506 uAngle = 0.0f;
00507 interiorSubmeshIndex = 0;
00508 }
00509 };
00510
00511
00516 struct MaterialFrame
00517 {
00518 MaterialFrame() :
00519 mCoordinateSystem(PxVec4(1.0f)),
00520 mUVPlane(PxVec3(0.0f, 0.0f, 1.0f), 0.0f),
00521 mUVScale(1.0f),
00522 mUVOffset(0.0f),
00523 mFractureMethod(FractureMethod::Unknown),
00524 mFractureIndex(-1),
00525 mSliceDepth(0)
00526 {
00527 }
00528
00532 void buildCoordinateSystemFromMaterialDesc(const nvidia::FractureMaterialDesc& materialDesc, const PxPlane& plane)
00533 {
00534 PxVec3 zAxis = plane.n;
00535 zAxis.normalize();
00536 PxVec3 xAxis = materialDesc.tangent;
00537 PxVec3 yAxis = zAxis.cross(xAxis);
00538 const float l2 = yAxis.magnitudeSquared();
00539 if (l2 > PX_EPS_F32*PX_EPS_F32)
00540 {
00541 yAxis *= PxRecipSqrt(l2);
00542 }
00543 else
00544 {
00545 uint32_t maxDir = PxAbs(plane.n.x) > PxAbs(plane.n.y) ?
00546 (PxAbs(plane.n.x) > PxAbs(plane.n.z) ? 0u : 2u) :
00547 (PxAbs(plane.n.y) > PxAbs(plane.n.z) ? 1u : 2u);
00548 xAxis = PxMat33(PxIdentity)[(maxDir + 1) % 3];
00549 yAxis = zAxis.cross(xAxis);
00550 yAxis.normalize();
00551 }
00552 xAxis = yAxis.cross(zAxis);
00553
00554 const float c = PxCos(materialDesc.uAngle);
00555 const float s = PxSin(materialDesc.uAngle);
00556
00557 mCoordinateSystem.column0 = PxVec4(c*xAxis + s*yAxis, 0.0f);
00558 mCoordinateSystem.column1 = PxVec4(c*yAxis - s*xAxis, 0.0f);
00559 mCoordinateSystem.column2 = PxVec4(zAxis, 0.0f);
00560 mCoordinateSystem.setPosition(plane.project(PxVec3(0.0f)));
00561
00562 mUVPlane = plane;
00563 mUVScale = materialDesc.uvScale;
00564 mUVOffset = materialDesc.uvOffset;
00565 }
00566
00567 PxMat44 mCoordinateSystem;
00568 PxPlane mUVPlane;
00569 PxVec2 mUVScale;
00570 PxVec2 mUVOffset;
00571 uint32_t mFractureMethod;
00572 int32_t mFractureIndex;
00573 uint32_t mSliceDepth;
00574 };
00575
00576
00587 class DisplacementMapVolume
00588 {
00589 public:
00596 virtual void getData(uint32_t& width, uint32_t& height, uint32_t& depth, uint32_t& size, unsigned char const** ppData) const = 0;
00597
00598 virtual ~DisplacementMapVolume() { }
00599 };
00600
00601
00609 struct BSPOpenMode
00610 {
00614 enum Enum
00615 {
00616 Automatic,
00617 Closed,
00618 Open,
00619
00620 BSPOpenModeCount
00621 };
00622 };
00623
00624
00633 class ExplicitHierarchicalMesh
00634 {
00635 public:
00637 enum Enum
00638 {
00643 VisualizeMeshBSPOutsideRegions = (1 << 0),
00644
00649 VisualizeMeshBSPInsideRegions = (1 << 1),
00650
00656 VisualizeMeshBSPSingleRegion = (1 << 8),
00657
00659 VisualizeSliceBSPOutsideRegions = (1 << 16),
00660
00662 VisualizeSliceBSPInsideRegions = (1 << 17),
00663
00665 VisualizeSliceBSPSingleRegion = (1 << 24),
00666
00667 VisualizeMeshBSPAllRegions = VisualizeMeshBSPOutsideRegions | VisualizeMeshBSPInsideRegions
00668 };
00669
00675 class Embedding
00676 {
00677 public:
00681 enum DataType
00682 {
00683 MaterialLibrary
00684 };
00685
00689 virtual void serialize(PxFileBuf& stream, Embedding::DataType type) const = 0;
00690
00694 virtual void deserialize(PxFileBuf& stream, Embedding::DataType type, uint32_t version) = 0;
00695 };
00696
00700 class ConvexHull
00701 {
00702 protected:
00703 ConvexHull()
00704 {
00705 }
00706
00707 virtual ~ConvexHull()
00708 {
00709 }
00710
00711 public:
00715 virtual void buildFromPoints(const void* points, uint32_t numPoints, uint32_t pointStrideBytes) = 0;
00716
00720 virtual const PxBounds3& getBounds() const = 0;
00721
00725 virtual float getVolume() const = 0;
00726
00730 virtual uint32_t getVertexCount() const = 0;
00731
00736 virtual PxVec3 getVertex(uint32_t vertexIndex) const = 0;
00737
00741 virtual uint32_t getEdgeCount() const = 0;
00742
00748 virtual PxVec3 getEdgeEndpoint(uint32_t edgeIndex, uint32_t whichEndpoint) const = 0;
00749
00753 virtual uint32_t getPlaneCount() const = 0;
00754
00759 virtual PxPlane getPlane(uint32_t planeIndex) const = 0;
00760
00788 virtual bool rayCast(float& in, float& out, const PxVec3& orig, const PxVec3& dir,
00789 const PxTransform& localToWorldRT, const PxVec3& scale, PxVec3* normal = NULL) const = 0;
00798 virtual bool reduceHull(uint32_t maxVertexCount, uint32_t maxEdgeCount, uint32_t maxFaceCount, bool inflated) = 0;
00799
00803 virtual void release() = 0;
00804 };
00805
00813 virtual void clear(bool keepRoot = false) = 0;
00814
00819 virtual int32_t maxDepth() const = 0;
00820
00824 virtual uint32_t partCount() const = 0;
00825
00829 virtual uint32_t chunkCount() const = 0;
00830
00835 virtual int32_t* parentIndex(uint32_t chunkIndex) = 0;
00836
00841 virtual uint64_t chunkUniqueID(uint32_t chunkIndex) = 0;
00842
00846 virtual int32_t* partIndex(uint32_t chunkIndex) = 0;
00847
00851 virtual PxVec3* instancedPositionOffset(uint32_t chunkIndex) = 0;
00852
00856 virtual PxVec2* instancedUVOffset(uint32_t chunkIndex) = 0;
00857
00862 virtual uint32_t meshTriangleCount(uint32_t partIndex) const = 0;
00863
00868 virtual ExplicitRenderTriangle* meshTriangles(uint32_t partIndex) = 0;
00869
00873 virtual PxBounds3 meshBounds(uint32_t partIndex) const = 0;
00874
00878 virtual PxBounds3 chunkBounds(uint32_t chunkIndex) const = 0;
00879
00884 virtual uint32_t* chunkFlags(uint32_t chunkIndex) const = 0;
00885
00889 virtual void buildCollisionGeometryForPart(uint32_t partIndex, const CollisionVolumeDesc& desc) = 0;
00890
00898 virtual void buildCollisionGeometryForRootChunkParts(const CollisionDesc& desc, bool aggregateRootChunkParentCollision = true) = 0;
00899
00903 virtual void reduceHulls(const CollisionDesc& desc, bool inflated) = 0;
00904
00908 virtual uint32_t convexHullCount(uint32_t partIndex) const = 0;
00909
00913 virtual const ConvexHull** convexHulls(uint32_t partIndex) const = 0;
00914
00918 virtual PxVec3* surfaceNormal(uint32_t partIndex) = 0;
00919
00923 virtual const DisplacementMapVolume& displacementMapVolume() const = 0;
00924
00930 virtual uint32_t submeshCount() const = 0;
00931
00935 virtual ExplicitSubmeshData* submeshData(uint32_t submeshIndex) = 0;
00936
00941 virtual uint32_t addSubmesh(const ExplicitSubmeshData& submeshData) = 0;
00942
00951 virtual uint32_t getMaterialFrameCount() const = 0;
00952 virtual nvidia::MaterialFrame getMaterialFrame(uint32_t index) const = 0;
00953 virtual void setMaterialFrame(uint32_t index, const nvidia::MaterialFrame& materialFrame) = 0;
00954 virtual uint32_t addMaterialFrame() = 0;
00955
00960 virtual void serialize(PxFileBuf& stream, Embedding& embedding) const = 0;
00961
00966 virtual void deserialize(PxFileBuf& stream, Embedding& embedding) = 0;
00967
00971 virtual void set(const ExplicitHierarchicalMesh& mesh) = 0;
00972
00981 virtual void calculateMeshBSP(uint32_t randomSeed, IProgressListener* progressListener = NULL, const uint32_t* microgridSize = NULL, BSPOpenMode::Enum meshMode = BSPOpenMode::Automatic) = 0;
00982
00986 virtual void replaceInteriorSubmeshes(uint32_t partIndex, uint32_t frameCount, uint32_t* frameIndices, uint32_t submeshIndex) = 0;
00987
00993 virtual void visualize(RenderDebugInterface& debugRender, uint32_t flags, uint32_t index = 0) const = 0;
00994
00998 virtual void release() = 0;
00999
01000 protected:
01006 ExplicitHierarchicalMesh() {}
01007 virtual ~ExplicitHierarchicalMesh() {}
01008
01009 private:
01011 ExplicitHierarchicalMesh& operator = (const ExplicitHierarchicalMesh&)
01012 {
01013 return *this;
01014 }
01015 };
01016
01017
01018 PX_POP_PACK
01019
01020 }
01021 }
01022
01023
01024 #endif // EXPLICIT_HIERARCHICAL_MESH_H