From c7814cf50a04a6e8ad6f11b4c7fb0be04648cbf1 Mon Sep 17 00:00:00 2001 From: Michael PLATINGS Date: Tue, 3 May 2011 09:11:04 +0000 Subject: [PATCH] Updated to use FBX SDK 2012.1 --- src/osgPlugins/fbx/CMakeLists.txt | 2 - src/osgPlugins/fbx/ReaderWriterFBX.cpp | 19 +- src/osgPlugins/fbx/ReaderWriterFBX.h | 7 +- src/osgPlugins/fbx/WriterNodeVisitor.cpp | 21 +-- src/osgPlugins/fbx/WriterNodeVisitor.h | 5 +- .../fbx/fbxMaterialToOsgStateSet.cpp | 54 +++--- src/osgPlugins/fbx/fbxMaterialToOsgStateSet.h | 3 +- src/osgPlugins/fbx/fbxRAnimation.cpp | 1 + src/osgPlugins/fbx/fbxRCamera.cpp | 3 +- src/osgPlugins/fbx/fbxRLight.cpp | 3 +- src/osgPlugins/fbx/fbxRMesh.cpp | 176 ++++++++++-------- src/osgPlugins/fbx/fbxRNode.cpp | 78 +++++--- src/osgPlugins/fbx/fbxReader.h | 6 +- 13 files changed, 223 insertions(+), 155 deletions(-) diff --git a/src/osgPlugins/fbx/CMakeLists.txt b/src/osgPlugins/fbx/CMakeLists.txt index 5e311a657..a2d4b2ad7 100644 --- a/src/osgPlugins/fbx/CMakeLists.txt +++ b/src/osgPlugins/fbx/CMakeLists.txt @@ -20,8 +20,6 @@ SET(TARGET_H WriterNodeVisitor.h ) -ADD_DEFINITIONS(-DKFBX_PLUGIN -DKFBX_FBXSDK -DKFBX_NODLL) - IF(WIN32) SET(TARGET_EXTERNAL_LIBRARIES wininet) ENDIF(WIN32) diff --git a/src/osgPlugins/fbx/ReaderWriterFBX.cpp b/src/osgPlugins/fbx/ReaderWriterFBX.cpp index f6e869778..71b8f76ba 100644 --- a/src/osgPlugins/fbx/ReaderWriterFBX.cpp +++ b/src/osgPlugins/fbx/ReaderWriterFBX.cpp @@ -23,6 +23,7 @@ #if defined(_MSC_VER) #pragma warning( disable : 4505 ) + #pragma warning( default : 4996 ) #endif #include @@ -103,7 +104,7 @@ public: //them from the nodes that skin deformers linked to. void findLinkedFbxSkeletonNodes(KFbxNode* pNode, std::set& fbxSkeletons) { - if (const KFbxGeometry* pMesh = dynamic_cast(pNode->GetNodeAttribute())) + if (const KFbxGeometry* pMesh = KFbxCast(pNode->GetNodeAttribute())) { for (int i = 0; i < pMesh->GetDeformerCount(KFbxDeformer::eSKIN); ++i) { @@ -239,10 +240,8 @@ ReaderWriterFBX::readNode(const std::string& filenameInit, return ReadResult::ERROR_IN_READING_FILE; } - for (int i = 0; i < lImporter->GetTakeCount(); i++) + for (int i = 0; KFbxTakeInfo* lTakeInfo = lImporter->GetTakeInfo(i); i++) { - KFbxTakeInfo* lTakeInfo = lImporter->GetTakeInfo(i); - lTakeInfo->mSelect = true; } @@ -255,8 +254,6 @@ ReaderWriterFBX::readNode(const std::string& filenameInit, if (KFbxNode* pNode = pScene->GetRootNode()) { - pScene->SetCurrentTake(pScene->GetCurrentTakeName()); - bool useFbxRoot = false; bool lightmapTextures = false; bool tessellatePolygons = false; @@ -274,10 +271,10 @@ ReaderWriterFBX::readNode(const std::string& filenameInit, { lightmapTextures = true; } - if (opt == "TessellatePolygons") - { - tessellatePolygons = true; - } + if (opt == "TessellatePolygons") + { + tessellatePolygons = true; + } } } @@ -336,7 +333,7 @@ ReaderWriterFBX::readNode(const std::string& filenameInit, *localOptions, authoringTool, lightmapTextures, - tessellatePolygons); + tessellatePolygons); ReadResult res = reader.readFbxNode(pNode, bIsBone, nLightCount); diff --git a/src/osgPlugins/fbx/ReaderWriterFBX.h b/src/osgPlugins/fbx/ReaderWriterFBX.h index 8db463300..73738090c 100644 --- a/src/osgPlugins/fbx/ReaderWriterFBX.h +++ b/src/osgPlugins/fbx/ReaderWriterFBX.h @@ -2,11 +2,16 @@ #define READERWRITERFBX_H #include +#include /////////////////////////////////////////////////////////////////////////// // OSG reader plugin for the ".fbx" format. // See http://www.autodesk.com/fbx -// This plugin requires the FBX SDK version 2011.3.1 (Static Libraries) +// This plugin requires the FBX SDK version 2012.1 + +#if FBXSDK_VERSION_MAJOR != 2012 || FBXSDK_VERSION_MINOR != 1 +#error Wrong FBX SDK version +#endif class ReaderWriterFBX : public osgDB::ReaderWriter { diff --git a/src/osgPlugins/fbx/WriterNodeVisitor.cpp b/src/osgPlugins/fbx/WriterNodeVisitor.cpp index b3d424313..0b8884e34 100644 --- a/src/osgPlugins/fbx/WriterNodeVisitor.cpp +++ b/src/osgPlugins/fbx/WriterNodeVisitor.cpp @@ -333,30 +333,30 @@ WriterNodeVisitor::Material::Material(WriterNodeVisitor& writerNodeVisitor, _fbxMaterial = KFbxSurfacePhong::Create(pSdkManager, mat->getName().c_str()); if (_fbxMaterial) { - _fbxMaterial->GetDiffuseFactor().Set(1, true); - _fbxMaterial->GetDiffuseColor().Set(fbxDouble3( + _fbxMaterial->DiffuseFactor.Set(1, true); + _fbxMaterial->Diffuse.Set(fbxDouble3( diffuse.x(), diffuse.y(), diffuse.z())); - _fbxMaterial->GetTransparencyFactor().Set(transparency); + _fbxMaterial->TransparencyFactor.Set(transparency); - _fbxMaterial->GetAmbientColor().Set(fbxDouble3( + _fbxMaterial->Ambient.Set(fbxDouble3( ambient.x(), ambient.y(), ambient.z())); - _fbxMaterial->GetEmissiveColor().Set(fbxDouble3( + _fbxMaterial->Emissive.Set(fbxDouble3( emission.x(), emission.y(), emission.z())); - _fbxMaterial->GetSpecularColor().Set(fbxDouble3( + _fbxMaterial->Specular.Set(fbxDouble3( specular.x(), specular.y(), specular.z())); - _fbxMaterial->GetShininess().Set(shininess); + _fbxMaterial->Shininess.Set(shininess); } } if (tex && tex->getImage(0)) @@ -405,7 +405,7 @@ WriterNodeVisitor::Material::Material(WriterNodeVisitor& writerNodeVisitor, imageFilenameSet.insert(destPath); } - _fbxTexture = KFbxTexture::Create(pSdkManager, it->second.c_str()); + _fbxTexture = KFbxFileTexture::Create(pSdkManager, it->second.c_str()); _fbxTexture->SetFileName(it->second.c_str()); } } @@ -468,15 +468,14 @@ WriterNodeVisitor::setLayerTextureAndMaterial(KFbxMesh* mesh) lMaterialLayer->SetReferenceMode(KFbxLayerElement::eINDEX_TO_DIRECT); lTextureDiffuseLayer->GetDirectArray().SetCount(_lastMaterialIndex); - lMaterialLayer->GetDirectArray().SetCount(_lastMaterialIndex); for (MaterialMap::iterator it = _materialMap.begin(); it != _materialMap.end(); ++it) { if (it->second.getIndex() != -1) { KFbxSurfaceMaterial* lMaterial = it->second.getFbxMaterial(); - KFbxTexture* lTexture = it->second.getFbxTexture(); + KFbxFileTexture* lTexture = it->second.getFbxTexture(); lTextureDiffuseLayer->GetDirectArray().SetAt(it->second.getIndex(), lTexture); - lMaterialLayer->GetDirectArray().SetAt(it->second.getIndex(), lMaterial); + _curFbxNode->AddMaterial(lMaterial); } } mesh->GetLayer(0)->SetMaterials(lMaterialLayer); diff --git a/src/osgPlugins/fbx/WriterNodeVisitor.h b/src/osgPlugins/fbx/WriterNodeVisitor.h index 42d664095..79ef627f5 100644 --- a/src/osgPlugins/fbx/WriterNodeVisitor.h +++ b/src/osgPlugins/fbx/WriterNodeVisitor.h @@ -27,6 +27,7 @@ #if defined(_MSC_VER) #pragma warning( disable : 4505 ) +#pragma warning( default : 4996 ) #endif #include @@ -152,7 +153,7 @@ class WriterNodeVisitor: public osg::NodeVisitor const osgDB::ReaderWriter::Options * options, int index = -1); - KFbxTexture* getFbxTexture() const + KFbxFileTexture* getFbxTexture() const { return _fbxTexture; } @@ -179,7 +180,7 @@ class WriterNodeVisitor: public osg::NodeVisitor private: KFbxSurfacePhong* _fbxMaterial; - KFbxTexture* _fbxTexture; + KFbxFileTexture* _fbxTexture; int _index;///< Index in the Map const osg::Image* _osgImage; const std::string& _directory; diff --git a/src/osgPlugins/fbx/fbxMaterialToOsgStateSet.cpp b/src/osgPlugins/fbx/fbxMaterialToOsgStateSet.cpp index 8a4af3605..d250e8323 100644 --- a/src/osgPlugins/fbx/fbxMaterialToOsgStateSet.cpp +++ b/src/osgPlugins/fbx/fbxMaterialToOsgStateSet.cpp @@ -5,9 +5,9 @@ #include -static osg::Texture::WrapMode convertWrap(KFbxTexture::EWrapMode wrap) +static osg::Texture::WrapMode convertWrap(KFbxFileTexture::EWrapMode wrap) { - return wrap == KFbxTexture::eREPEAT ? + return wrap == KFbxFileTexture::eREPEAT ? osg::Texture2D::REPEAT : osg::Texture2D::CLAMP_TO_EDGE; } @@ -25,18 +25,18 @@ FbxMaterialToOsgStateSet::convert(const KFbxSurfaceMaterial* pFbxMat) result.material = pOsgMat; - fbxString shadingModel = pFbxMat->GetShadingModel().Get(); + fbxString shadingModel = pFbxMat->ShadingModel.Get(); - const KFbxSurfaceLambert* pFbxLambert = dynamic_cast(pFbxMat); + const KFbxSurfaceLambert* pFbxLambert = KFbxCast(pFbxMat); // diffuse map... const KFbxProperty lProperty = pFbxMat->FindProperty(KFbxSurfaceMaterial::sDiffuse); if (lProperty.IsValid()) { - int lNbTex = lProperty.GetSrcObjectCount(KFbxTexture::ClassId); + int lNbTex = lProperty.GetSrcObjectCount(KFbxFileTexture::ClassId); for (int lTextureIndex = 0; lTextureIndex < lNbTex; lTextureIndex++) { - KFbxTexture* lTexture = KFbxCast(lProperty.GetSrcObject(KFbxTexture::ClassId, lTextureIndex)); + KFbxFileTexture* lTexture = KFbxCast(lProperty.GetSrcObject(KFbxFileTexture::ClassId, lTextureIndex)); if (lTexture) { result.diffuseTexture = fbxTextureToOsgTexture(lTexture); @@ -54,10 +54,10 @@ FbxMaterialToOsgStateSet::convert(const KFbxSurfaceMaterial* pFbxMat) const KFbxProperty lOpacityProperty = pFbxMat->FindProperty(KFbxSurfaceMaterial::sTransparentColor); if (lOpacityProperty.IsValid()) { - int lNbTex = lOpacityProperty.GetSrcObjectCount(KFbxTexture::ClassId); + int lNbTex = lOpacityProperty.GetSrcObjectCount(KFbxFileTexture::ClassId); for (int lTextureIndex = 0; lTextureIndex < lNbTex; lTextureIndex++) { - KFbxTexture* lTexture = KFbxCast(lOpacityProperty.GetSrcObject(KFbxTexture::ClassId, lTextureIndex)); + KFbxFileTexture* lTexture = KFbxCast(lOpacityProperty.GetSrcObject(KFbxFileTexture::ClassId, lTextureIndex)); if (lTexture) { // TODO: if texture image does NOT have an alpha channel, should it be added? @@ -77,14 +77,14 @@ FbxMaterialToOsgStateSet::convert(const KFbxSurfaceMaterial* pFbxMat) const KFbxProperty lReflectionProperty = pFbxMat->FindProperty(KFbxSurfaceMaterial::sReflection); if (lReflectionProperty.IsValid()) { - int lNbTex = lReflectionProperty.GetSrcObjectCount(KFbxTexture::ClassId); + int lNbTex = lReflectionProperty.GetSrcObjectCount(KFbxFileTexture::ClassId); for (int lTextureIndex = 0; lTextureIndex < lNbTex; lTextureIndex++) { - KFbxTexture* lTexture = KFbxCast(lReflectionProperty.GetSrcObject(KFbxTexture::ClassId, lTextureIndex)); + KFbxFileTexture* lTexture = KFbxCast(lReflectionProperty.GetSrcObject(KFbxFileTexture::ClassId, lTextureIndex)); if (lTexture) { // support only spherical reflection maps... - if (KFbxTexture::eUMT_ENVIRONMENT == lTexture->GetMappingType()) + if (KFbxFileTexture::eUMT_ENVIRONMENT == lTexture->GetMappingType()) { result.reflectionTexture = fbxTextureToOsgTexture(lTexture); result.reflectionChannel = lTexture->UVSet.Get(); @@ -100,10 +100,10 @@ FbxMaterialToOsgStateSet::convert(const KFbxSurfaceMaterial* pFbxMat) const KFbxProperty lEmissiveProperty = pFbxMat->FindProperty(KFbxSurfaceMaterial::sEmissive); if (lEmissiveProperty.IsValid()) { - int lNbTex = lEmissiveProperty.GetSrcObjectCount(KFbxTexture::ClassId); + int lNbTex = lEmissiveProperty.GetSrcObjectCount(KFbxFileTexture::ClassId); for (int lTextureIndex = 0; lTextureIndex < lNbTex; lTextureIndex++) { - KFbxTexture* lTexture = KFbxCast(lEmissiveProperty.GetSrcObject(KFbxTexture::ClassId, lTextureIndex)); + KFbxFileTexture* lTexture = KFbxCast(lEmissiveProperty.GetSrcObject(KFbxFileTexture::ClassId, lTextureIndex)); if (lTexture) { result.emissiveTexture = fbxTextureToOsgTexture(lTexture); @@ -119,24 +119,24 @@ FbxMaterialToOsgStateSet::convert(const KFbxSurfaceMaterial* pFbxMat) if (pFbxLambert) { - fbxDouble3 color = pFbxLambert->GetDiffuseColor().Get(); - double factor = pFbxLambert->GetDiffuseFactor().Get(); + fbxDouble3 color = pFbxLambert->Diffuse.Get(); + double factor = pFbxLambert->DiffuseFactor.Get(); pOsgMat->setDiffuse(osg::Material::FRONT_AND_BACK, osg::Vec4( static_cast(color[0] * factor), static_cast(color[1] * factor), static_cast(color[2] * factor), - static_cast(1.0 - pFbxLambert->GetTransparencyFactor().Get()))); + static_cast(1.0 - pFbxLambert->TransparencyFactor.Get()))); - color = pFbxLambert->GetAmbientColor().Get(); - factor = pFbxLambert->GetAmbientFactor().Get(); + color = pFbxLambert->Ambient.Get(); + factor = pFbxLambert->AmbientFactor.Get(); pOsgMat->setAmbient(osg::Material::FRONT_AND_BACK, osg::Vec4( static_cast(color[0] * factor), static_cast(color[1] * factor), static_cast(color[2] * factor), 1.0f)); - color = pFbxLambert->GetEmissiveColor().Get(); - factor = pFbxLambert->GetEmissiveFactor().Get(); + color = pFbxLambert->Emissive.Get(); + factor = pFbxLambert->EmissiveFactor.Get(); pOsgMat->setEmission(osg::Material::FRONT_AND_BACK, osg::Vec4( static_cast(color[0] * factor), static_cast(color[1] * factor), @@ -144,12 +144,12 @@ FbxMaterialToOsgStateSet::convert(const KFbxSurfaceMaterial* pFbxMat) 1.0f)); // get maps factors... - result.diffuseFactor = pFbxLambert->GetDiffuseFactor().Get(); + result.diffuseFactor = pFbxLambert->DiffuseFactor.Get(); - if (const KFbxSurfacePhong* pFbxPhong = dynamic_cast(pFbxLambert)) + if (const KFbxSurfacePhong* pFbxPhong = KFbxCast(pFbxLambert)) { - color = pFbxPhong->GetSpecularColor().Get(); - factor = pFbxPhong->GetSpecularFactor().Get(); + color = pFbxPhong->Specular.Get(); + factor = pFbxPhong->SpecularFactor.Get(); pOsgMat->setSpecular(osg::Material::FRONT_AND_BACK, osg::Vec4( static_cast(color[0] * factor), static_cast(color[1] * factor), @@ -157,10 +157,10 @@ FbxMaterialToOsgStateSet::convert(const KFbxSurfaceMaterial* pFbxMat) 1.0f)); pOsgMat->setShininess(osg::Material::FRONT_AND_BACK, - static_cast(pFbxPhong->GetShininess().Get())); + static_cast(pFbxPhong->Shininess.Get())); // get maps factors... - result.reflectionFactor = pFbxPhong->GetReflectionFactor().Get(); + result.reflectionFactor = pFbxPhong->ReflectionFactor.Get(); // get more factors here... } } @@ -182,7 +182,7 @@ FbxMaterialToOsgStateSet::convert(const KFbxSurfaceMaterial* pFbxMat) } osg::ref_ptr -FbxMaterialToOsgStateSet::fbxTextureToOsgTexture(const KFbxTexture* fbx) +FbxMaterialToOsgStateSet::fbxTextureToOsgTexture(const KFbxFileTexture* fbx) { ImageMap::iterator it = _imageMap.find(fbx->GetFileName()); if (it != _imageMap.end()) diff --git a/src/osgPlugins/fbx/fbxMaterialToOsgStateSet.h b/src/osgPlugins/fbx/fbxMaterialToOsgStateSet.h index 8f5aac824..25868ee01 100644 --- a/src/osgPlugins/fbx/fbxMaterialToOsgStateSet.h +++ b/src/osgPlugins/fbx/fbxMaterialToOsgStateSet.h @@ -10,6 +10,7 @@ #if defined(_MSC_VER) #pragma warning( disable : 4505 ) +#pragma warning( default : 4996 ) #endif #include @@ -87,7 +88,7 @@ public: private: //Convert a texture fbx to an osg texture. osg::ref_ptr - fbxTextureToOsgTexture(const KFbxTexture* pOsgTex); + fbxTextureToOsgTexture(const KFbxFileTexture* pOsgTex); FbxMaterialMap _fbxMaterialMap; ImageMap _imageMap; const osgDB::Options* _options; diff --git a/src/osgPlugins/fbx/fbxRAnimation.cpp b/src/osgPlugins/fbx/fbxRAnimation.cpp index 44a1d17e9..72202bbdf 100644 --- a/src/osgPlugins/fbx/fbxRAnimation.cpp +++ b/src/osgPlugins/fbx/fbxRAnimation.cpp @@ -7,6 +7,7 @@ #if defined(_MSC_VER) #pragma warning( disable : 4505 ) + #pragma warning( default : 4996 ) #endif #include #include diff --git a/src/osgPlugins/fbx/fbxRCamera.cpp b/src/osgPlugins/fbx/fbxRCamera.cpp index a9814d905..7e66a7749 100644 --- a/src/osgPlugins/fbx/fbxRCamera.cpp +++ b/src/osgPlugins/fbx/fbxRCamera.cpp @@ -5,6 +5,7 @@ #if defined(_MSC_VER) #pragma warning( disable : 4505 ) +#pragma warning( default : 4996 ) #endif #include @@ -12,7 +13,7 @@ osgDB::ReaderWriter::ReadResult OsgFbxReader::readFbxCamera(KFbxNode* pNode) { - const KFbxCamera* fbxCamera = dynamic_cast(pNode->GetNodeAttribute()); + const KFbxCamera* fbxCamera = KFbxCast(pNode->GetNodeAttribute()); if (!fbxCamera) { diff --git a/src/osgPlugins/fbx/fbxRLight.cpp b/src/osgPlugins/fbx/fbxRLight.cpp index 6f06f112b..063becb91 100644 --- a/src/osgPlugins/fbx/fbxRLight.cpp +++ b/src/osgPlugins/fbx/fbxRLight.cpp @@ -4,6 +4,7 @@ #if defined(_MSC_VER) #pragma warning( disable : 4505 ) +#pragma warning( default : 4996 ) #endif #include @@ -11,7 +12,7 @@ osgDB::ReaderWriter::ReadResult OsgFbxReader::readFbxLight(KFbxNode* pNode, int& nLightCount) { - const KFbxLight* fbxLight = dynamic_cast(pNode->GetNodeAttribute()); + const KFbxLight* fbxLight = KFbxCast(pNode->GetNodeAttribute()); if (!fbxLight) { diff --git a/src/osgPlugins/fbx/fbxRMesh.cpp b/src/osgPlugins/fbx/fbxRMesh.cpp index df771ffda..6ad6c2f30 100644 --- a/src/osgPlugins/fbx/fbxRMesh.cpp +++ b/src/osgPlugins/fbx/fbxRMesh.cpp @@ -20,6 +20,7 @@ #if defined(_MSC_VER) #pragma warning( disable : 4505 ) +#pragma warning( default : 4996 ) #endif #include @@ -356,7 +357,7 @@ void addChannel( void readAnimation(KFbxNode* pNode, KFbxScene& fbxScene, const std::string& targetName, osg::ref_ptr& pAnimationManager, - KFbxMesh* pMesh, int nShape) + KFbxMesh* pMesh, int nBlendShape, int nBlendShapeChannel, int nShape) { for (int i = 0; i < fbxScene.GetSrcObjectCount(FBX_TYPE(KFbxAnimStack)); ++i) { @@ -373,7 +374,8 @@ void readAnimation(KFbxNode* pNode, KFbxScene& fbxScene, const std::string& targ { KFbxAnimLayer* pAnimLayer = pAnimStack->GetMember(FBX_TYPE(KFbxAnimLayer), j); - KFbxAnimCurve* pCurve = pMesh->GetShapeChannel(nShape, pAnimLayer); + KFbxAnimCurve* pCurve = pMesh->GetShapeChannel(nBlendShape, nBlendShapeChannel, pAnimLayer, false); + if (!pCurve) { continue; @@ -403,9 +405,6 @@ void readAnimation(KFbxNode* pNode, KFbxScene& fbxScene, const std::string& targ addChannel(pChannel, pAnimationManager, pTakeName); } } - - { - } } void addBindMatrix( @@ -710,7 +709,7 @@ osgDB::ReaderWriter::ReadResult OsgFbxReader::readMesh( int nPolys = fbxMesh->GetPolygonCount(); int nDeformerCount = fbxMesh->GetDeformerCount(KFbxDeformer::eSKIN); - int nMorphShapeCount = 0; + int nDeformerBlendShapeCount = fbxMesh->GetDeformerCount(KFbxDeformer::eBLENDSHAPE); GeometryType geomType = GEOMETRY_STATIC; @@ -719,7 +718,7 @@ osgDB::ReaderWriter::ReadResult OsgFbxReader::readMesh( { geomType = GEOMETRY_RIG; } - else if ((nMorphShapeCount = fbxMesh->GetShapeCount())) + else if (nDeformerBlendShapeCount) { geomType = GEOMETRY_MORPH; } @@ -802,9 +801,9 @@ osgDB::ReaderWriter::ReadResult OsgFbxReader::readMesh( // Polygons - Store to add after triangles polygonRefList.push_back(PolygonRef(pGeometry, i, nVertex)); nVertex += lPolygonSize; - } - else - { + } + else + { int nVertex0 = nVertex; nVertex += (std::min)(2, lPolygonSize); @@ -991,9 +990,63 @@ osgDB::ReaderWriter::ReadResult OsgFbxReader::readMesh( pGeode->addUpdateCallback(new osgAnimation::UpdateMorph(morph.getName())); //read morph geometry - for (int j = 0; j < nMorphShapeCount; ++j) + for (int nBlendShape = 0; nBlendShape < nDeformerBlendShapeCount; ++nBlendShape) { - const KFbxGeometryBase* pMorphShape = fbxMesh->GetShape(i); + KFbxBlendShape* pBlendShape = KFbxCast(fbxMesh->GetDeformer(nBlendShape, KFbxDeformer::eBLENDSHAPE)); + const int nBlendShapeChannelCount = pBlendShape->GetBlendShapeChannelCount(); + + for (int nBlendShapeChannel = 0; nBlendShapeChannel < nBlendShapeChannelCount; ++nBlendShapeChannel) + { + KFbxBlendShapeChannel* pBlendShapeChannel = pBlendShape->GetBlendShapeChannel(nBlendShapeChannel); + if (!pBlendShapeChannel->GetTargetShapeCount()) continue; + + //Assume one shape + if (pBlendShapeChannel->GetTargetShapeCount() > 1) + { + OSG_WARN << "Multiple FBX Target Shapes, only the first will be used" << std::endl; + } + const KFbxGeometryBase* pMorphShape = pBlendShapeChannel->GetTargetShape(0); + + const KFbxLayerElementNormal* pFbxShapeNormals = 0; + if (const KFbxLayer* pFbxShapeLayer = pMorphShape->GetLayer(0)) + { + pFbxShapeNormals = pFbxShapeLayer->GetNormals(); + if (!layerElementValid(pFbxShapeNormals)) pFbxShapeNormals = 0; + } + + osg::Geometry* pMorphTarget = new osg::Geometry(morph); + pMorphTarget->setVertexArray(static_cast( + pMorphTarget->getVertexArray()->clone(osg::CopyOp::DEEP_COPY_ARRAYS))); + if (pFbxShapeNormals) + { + if (osg::Array* pNormals = pMorphTarget->getNormalArray()) + { + pMorphTarget->setNormalArray(static_cast( + pNormals->clone(osg::CopyOp::DEEP_COPY_ARRAYS))); + } + } + pMorphTarget->setName(pMorphShape->GetName()); + morph.addMorphTarget(pMorphTarget, 0.0f); + + readAnimation(pNode, fbxScene, morph.getName(), pAnimationManager, fbxMesh, + nBlendShape, nBlendShapeChannel, (int)morph.getMorphTargetList().size() - 1); + } + } + } + + int nMorphTarget = 0; + for (int nBlendShape = 0; nBlendShape < nDeformerBlendShapeCount; ++nBlendShape) + { + KFbxBlendShape* pBlendShape = KFbxCast(fbxMesh->GetDeformer(nBlendShape, KFbxDeformer::eBLENDSHAPE)); + const int nBlendShapeChannelCount = pBlendShape->GetBlendShapeChannelCount(); + + for (int nBlendShapeChannel = 0; nBlendShapeChannel < nBlendShapeChannelCount; ++nBlendShapeChannel) + { + KFbxBlendShapeChannel* pBlendShapeChannel = pBlendShape->GetBlendShapeChannel(nBlendShapeChannel); + if (!pBlendShapeChannel->GetTargetShapeCount()) continue; + + //Assume one shape again + const KFbxGeometryBase* pMorphShape = pBlendShapeChannel->GetTargetShape(0); const KFbxLayerElementNormal* pFbxShapeNormals = 0; if (const KFbxLayer* pFbxShapeLayer = pMorphShape->GetLayer(0)) @@ -1002,77 +1055,52 @@ osgDB::ReaderWriter::ReadResult OsgFbxReader::readMesh( if (!layerElementValid(pFbxShapeNormals)) pFbxShapeNormals = 0; } - osg::Geometry* pMorphTarget = new osg::Geometry(morph); - pMorphTarget->setVertexArray(static_cast( - pMorphTarget->getVertexArray()->clone(osg::CopyOp::DEEP_COPY_ARRAYS))); - if (pFbxShapeNormals) + const KFbxVector4* pControlPoints = pMorphShape->GetControlPoints(); + int nControlPoints = pMorphShape->GetControlPointsCount(); + for (int fbxIndex = 0; fbxIndex < nControlPoints; ++fbxIndex) { - if (osg::Array* pNormals = pMorphTarget->getNormalArray()) + osg::Vec3d vPos = convertVec3(pControlPoints[fbxIndex]); + for (FbxToOsgVertexMap::const_iterator it = + fbxToOsgVertMap.find(fbxIndex); + it != fbxToOsgVertMap.end() && + it->first == fbxIndex; ++it) { - pMorphTarget->setNormalArray(static_cast( - pNormals->clone(osg::CopyOp::DEEP_COPY_ARRAYS))); - } - } - pMorphTarget->setName(fbxMesh->GetShapeName(j)); - morph.addMorphTarget(pMorphTarget, 0.0f); + GIPair gi = it->second; + osgAnimation::MorphGeometry& morphGeom = + dynamic_cast(*gi.first); + osg::Geometry* pGeometry = morphGeom.getMorphTarget(nMorphTarget).getGeometry(); - readAnimation(pNode, fbxScene, morph.getName(), pAnimationManager, fbxMesh, j); - } - } - - for (int i = 0; i < nMorphShapeCount; ++i) - { - const KFbxGeometryBase* pMorphShape = fbxMesh->GetShape(i); - - const KFbxLayerElementNormal* pFbxShapeNormals = 0; - if (const KFbxLayer* pFbxShapeLayer = pMorphShape->GetLayer(0)) - { - pFbxShapeNormals = pFbxShapeLayer->GetNormals(); - if (!layerElementValid(pFbxShapeNormals)) pFbxShapeNormals = 0; - } - - const KFbxVector4* pControlPoints = pMorphShape->GetControlPoints(); - int nControlPoints = pMorphShape->GetControlPointsCount(); - for (int fbxIndex = 0; fbxIndex < nControlPoints; ++fbxIndex) - { - osg::Vec3d vPos = convertVec3(pControlPoints[fbxIndex]); - for (FbxToOsgVertexMap::const_iterator it = - fbxToOsgVertMap.find(fbxIndex); - it != fbxToOsgVertMap.end() && - it->first == fbxIndex; ++it) - { - GIPair gi = it->second; - osgAnimation::MorphGeometry& morphGeom = - dynamic_cast(*gi.first); - osg::Geometry* pGeometry = morphGeom.getMorphTarget(i).getGeometry(); - - if (pGeometry->getVertexArray()->getType() == osg::Array::Vec3dArrayType) - { - osg::Vec3dArray* pVertices = static_cast(pGeometry->getVertexArray()); - (*pVertices)[gi.second] = vPos; - } - else - { - osg::Vec3Array* pVertices = static_cast(pGeometry->getVertexArray()); - (*pVertices)[gi.second] = vPos; - } - - if (pFbxShapeNormals && pGeometry->getNormalArray()) - { - if (pGeometry->getNormalArray()->getType() == osg::Array::Vec3dArrayType) + if (pGeometry->getVertexArray()->getType() == osg::Array::Vec3dArrayType) { - osg::Vec3dArray* pNormals = static_cast(pGeometry->getNormalArray()); - (*pNormals)[gi.second] = convertVec3( - pFbxShapeNormals->GetDirectArray().GetAt(osgToFbxNormMap[gi])); + osg::Vec3dArray* pVertices = static_cast(pGeometry->getVertexArray()); + (*pVertices)[gi.second] = vPos; } else { - osg::Vec3Array* pNormals = static_cast(pGeometry->getNormalArray()); - (*pNormals)[gi.second] = convertVec3( - pFbxShapeNormals->GetDirectArray().GetAt(osgToFbxNormMap[gi])); + osg::Vec3Array* pVertices = static_cast(pGeometry->getVertexArray()); + (*pVertices)[gi.second] = vPos; + } + + if (pFbxShapeNormals && pGeometry->getNormalArray()) + { + if (pGeometry->getNormalArray()->getType() == osg::Array::Vec3dArrayType) + { + osg::Vec3dArray* pNormals = static_cast(pGeometry->getNormalArray()); + (*pNormals)[gi.second] = convertVec3( + pFbxShapeNormals->GetDirectArray().GetAt(osgToFbxNormMap[gi])); + } + else + { + osg::Vec3Array* pNormals = static_cast(pGeometry->getNormalArray()); + (*pNormals)[gi.second] = convertVec3( + pFbxShapeNormals->GetDirectArray().GetAt(osgToFbxNormMap[gi])); + } } } } + + //don't put this in the for loop as we don't want to do it if the loop continues early + ++nMorphTarget; } } } @@ -1125,7 +1153,7 @@ osgDB::ReaderWriter::ReadResult OsgFbxReader::readMesh( osgDB::ReaderWriter::ReadResult OsgFbxReader::readFbxMesh(KFbxNode* pNode, std::vector& stateSetList) { - KFbxMesh* lMesh = dynamic_cast(pNode->GetNodeAttribute()); + KFbxMesh* lMesh = KFbxCast(pNode->GetNodeAttribute()); if (!lMesh) { diff --git a/src/osgPlugins/fbx/fbxRNode.cpp b/src/osgPlugins/fbx/fbxRNode.cpp index baa82ab0e..9640ce8dd 100644 --- a/src/osgPlugins/fbx/fbxRNode.cpp +++ b/src/osgPlugins/fbx/fbxRNode.cpp @@ -23,11 +23,50 @@ #if defined(_MSC_VER) #pragma warning( disable : 4505 ) + #pragma warning( default : 4996 ) #endif #include #include "fbxReader.h" +bool isAnimated(KFbxProperty& prop, KFbxScene& fbxScene) +{ + for (int i = 0; i < fbxScene.GetSrcObjectCount(FBX_TYPE(KFbxAnimStack)); ++i) + { + KFbxAnimStack* pAnimStack = KFbxCast(fbxScene.GetSrcObject(FBX_TYPE(KFbxAnimStack), i)); + + const int nbAnimLayers = pAnimStack->GetMemberCount(FBX_TYPE(KFbxAnimLayer)); + for (int j = 0; j < nbAnimLayers; j++) + { + KFbxAnimLayer* pAnimLayer = pAnimStack->GetMember(FBX_TYPE(KFbxAnimLayer), j); + if (prop.GetCurveNode(pAnimLayer, false)) + { + return true; + } + } + } + return false; +} + +bool isAnimated(KFbxProperty& prop, const char* channel, KFbxScene& fbxScene) +{ + for (int i = 0; i < fbxScene.GetSrcObjectCount(FBX_TYPE(KFbxAnimStack)); ++i) + { + KFbxAnimStack* pAnimStack = KFbxCast(fbxScene.GetSrcObject(FBX_TYPE(KFbxAnimStack), i)); + + const int nbAnimLayers = pAnimStack->GetMemberCount(FBX_TYPE(KFbxAnimLayer)); + for (int j = 0; j < nbAnimLayers; j++) + { + KFbxAnimLayer* pAnimLayer = pAnimStack->GetMember(FBX_TYPE(KFbxAnimLayer), j); + if (prop.GetCurve(pAnimLayer, channel, false)) + { + return true; + } + } + } + return false; +} + osg::Quat makeQuat(const fbxDouble3& degrees, ERotationOrder fbxRotOrder) { double radiansX = osg::DegreesToRadians(degrees[0]); @@ -144,7 +183,8 @@ void makeLocalMatrix(const KFbxNode* pNode, osg::Matrix& m) void readTranslationElement(KFbxTypedProperty& prop, osgAnimation::UpdateMatrixTransform* pUpdate, - osg::Matrix& staticTransform) + osg::Matrix& staticTransform, + KFbxScene& fbxScene) { fbxDouble3 fbxPropValue = prop.Get(); osg::Vec3d val( @@ -152,9 +192,7 @@ void readTranslationElement(KFbxTypedProperty& prop, fbxPropValue[1], fbxPropValue[2]); - if (prop.GetKFCurve(KFCURVENODE_T_X) || - prop.GetKFCurve(KFCURVENODE_T_Y) || - prop.GetKFCurve(KFCURVENODE_T_Z)) + if (isAnimated(prop, fbxScene)) { if (!staticTransform.isIdentity()) { @@ -197,11 +235,10 @@ void readRotationElement(KFbxTypedProperty& prop, ERotationOrder fbxRotOrder, bool quatInterpolate, osgAnimation::UpdateMatrixTransform* pUpdate, - osg::Matrix& staticTransform) + osg::Matrix& staticTransform, + KFbxScene& fbxScene) { - if (prop.GetKFCurve(KFCURVENODE_R_X) || - prop.GetKFCurve(KFCURVENODE_R_Y) || - prop.GetKFCurve(KFCURVENODE_R_Z)) + if (isAnimated(prop, fbxScene)) { if (quatInterpolate) { @@ -230,7 +267,7 @@ void readRotationElement(KFbxTypedProperty& prop, for (int i = 0; i < 3; ++i) { int j = order[2-i]; - if (prop.GetKFCurve(curveNames[j])) + if (isAnimated(prop, curveNames[j], fbxScene)) { if (!staticTransform.isIdentity()) { @@ -256,7 +293,8 @@ void readRotationElement(KFbxTypedProperty& prop, void readScaleElement(KFbxTypedProperty& prop, osgAnimation::UpdateMatrixTransform* pUpdate, - osg::Matrix& staticTransform) + osg::Matrix& staticTransform, + KFbxScene& fbxScene) { fbxDouble3 fbxPropValue = prop.Get(); osg::Vec3d val( @@ -264,9 +302,7 @@ void readScaleElement(KFbxTypedProperty& prop, fbxPropValue[1], fbxPropValue[2]); - if (prop.GetKFCurve(KFCURVENODE_S_X) || - prop.GetKFCurve(KFCURVENODE_S_Y) || - prop.GetKFCurve(KFCURVENODE_S_Z)) + if (isAnimated(prop, fbxScene)) { if (!staticTransform.isIdentity()) { @@ -281,11 +317,11 @@ void readScaleElement(KFbxTypedProperty& prop, } } -void readUpdateMatrixTransform(osgAnimation::UpdateMatrixTransform* pUpdate, KFbxNode* pNode) +void readUpdateMatrixTransform(osgAnimation::UpdateMatrixTransform* pUpdate, KFbxNode* pNode, KFbxScene& fbxScene) { osg::Matrix staticTransform; - readTranslationElement(pNode->LclTranslation, pUpdate, staticTransform); + readTranslationElement(pNode->LclTranslation, pUpdate, staticTransform, fbxScene); fbxDouble3 fbxRotOffset = pNode->RotationOffset.Get(); fbxDouble3 fbxRotPiv = pNode->RotationPivot.Get(); @@ -308,7 +344,7 @@ void readUpdateMatrixTransform(osgAnimation::UpdateMatrixTransform* pUpdate, KFb readRotationElement(pNode->LclRotation, fbxRotOrder, pNode->QuaternionInterpolate.IsValid() && pNode->QuaternionInterpolate.Get(), - pUpdate, staticTransform); + pUpdate, staticTransform, fbxScene); if (rotationActive) { @@ -322,7 +358,7 @@ void readUpdateMatrixTransform(osgAnimation::UpdateMatrixTransform* pUpdate, KFb fbxSclOffset[1] + fbxSclPiv[1] - fbxRotPiv[1], fbxSclOffset[2] + fbxSclPiv[2] - fbxRotPiv[2])); - readScaleElement(pNode->LclScaling, pUpdate, staticTransform); + readScaleElement(pNode->LclScaling, pUpdate, staticTransform, fbxScene); staticTransform.preMultTranslate(osg::Vec3d( -fbxSclPiv[0], @@ -337,7 +373,7 @@ void readUpdateMatrixTransform(osgAnimation::UpdateMatrixTransform* pUpdate, KFb osg::Group* createGroupNode(KFbxSdkManager& pSdkManager, KFbxNode* pNode, const std::string& animName, const osg::Matrix& localMatrix, bool bNeedSkeleton, - std::map& nodeMap) + std::map& nodeMap, KFbxScene& fbxScene) { if (bNeedSkeleton) { @@ -345,7 +381,7 @@ osg::Group* createGroupNode(KFbxSdkManager& pSdkManager, KFbxNode* pNode, osgBone->setDataVariance(osg::Object::DYNAMIC); osgBone->setName(pNode->GetName()); osgAnimation::UpdateBone* pUpdate = new osgAnimation::UpdateBone(animName); - readUpdateMatrixTransform(pUpdate, pNode); + readUpdateMatrixTransform(pUpdate, pNode, fbxScene); osgBone->setUpdateCallback(pUpdate); nodeMap.insert(std::pair(pNode, osgBone)); @@ -368,7 +404,7 @@ osg::Group* createGroupNode(KFbxSdkManager& pSdkManager, KFbxNode* pNode, if (bAnimated) { osgAnimation::UpdateMatrixTransform* pUpdate = new osgAnimation::UpdateMatrixTransform(animName); - readUpdateMatrixTransform(pUpdate, pNode); + readUpdateMatrixTransform(pUpdate, pNode, fbxScene); pTransform->setUpdateCallback(pUpdate); } @@ -539,7 +575,7 @@ osgDB::ReaderWriter::ReadResult OsgFbxReader::readFbxNode( osgDB::ReaderWriter::ReadResult(0); } - if (!osgGroup) osgGroup = createGroupNode(pSdkManager, pNode, animName, localMatrix, bIsBone, nodeMap); + if (!osgGroup) osgGroup = createGroupNode(pSdkManager, pNode, animName, localMatrix, bIsBone, nodeMap, fbxScene); osg::Group* pAddChildrenTo = osgGroup.get(); if (bCreateSkeleton) diff --git a/src/osgPlugins/fbx/fbxReader.h b/src/osgPlugins/fbx/fbxReader.h index 982682661..35e0fb2c0 100644 --- a/src/osgPlugins/fbx/fbxReader.h +++ b/src/osgPlugins/fbx/fbxReader.h @@ -44,14 +44,14 @@ public: const osgDB::Options& options1, AuthoringTool authoringTool1, bool lightmapTextures1, - bool tessellatePolygons1) + bool tessellatePolygons1) : pSdkManager(pSdkManager1), fbxScene(fbxScene1), fbxMaterialToOsgStateSet(fbxMaterialToOsgStateSet1), fbxSkeletons(fbxSkeletons1), options(options1), - lightmapTextures(lightmapTextures1), - tessellatePolygons(tessellatePolygons1), + lightmapTextures(lightmapTextures1), + tessellatePolygons(tessellatePolygons1), authoringTool(authoringTool1) {}