fbxsdk/fileio/collada/fbxcolladautils.h Source File
 
 
 
fbxsdk/fileio/collada/fbxcolladautils.h
Go to the documentation of this file.
00001 /****************************************************************************************
00002  
00003    Copyright (C) 2013 Autodesk, Inc.
00004    All rights reserved.
00005  
00006    Use of this software is subject to the terms of the Autodesk license agreement
00007    provided at the time of installation or download, or which otherwise accompanies
00008    this software in either electronic or hard copy form.
00009  
00010 ****************************************************************************************/
00011 
00013 #ifndef _FBXSDK_FILEIO_COLLADA_UTILS_H_
00014 #define _FBXSDK_FILEIO_COLLADA_UTILS_H_
00015 
00016 #include <fbxsdk.h>
00017 
00018 #include <fbxsdk/fileio/collada/fbxcolladatokens.h>
00019 #include <fbxsdk/fileio/collada/fbxcolladaiostream.h>
00020 
00021 #include <components/libxml2-2.7.8/include/libxml/globals.h>
00022 
00023 #include <map>
00024 #include <set>
00025 #include <vector>
00026 
00027 #include <fbxsdk/fbxsdk_nsbegin.h>
00028 
00029 #ifndef INT_MAX
00030         #define INT_MAX 0x7FFFFFFF
00031 #endif
00032 
00033 #ifndef CENTIMETERS_TO_INCHES
00034         #define CENTIMETERS_TO_INCHES 2.54f
00035 #endif
00036 
00037 #ifndef RADIANS_TO_DEGREES
00038         #define RADIANS_TO_DEGREES 57.295799f
00039 #endif
00040 
00041 enum DAE_Flow { kCOLLADAFlowIn, kCOLLADAFlowOut, kCOLLADAFlowInOut };
00042 
00043 const int MATRIX_STRIDE = 16;
00044 const int VECTOR_STRIDE = 3;
00045 
00046 #define COLLADA_ID_PROPERTY_NAME "COLLADA_ID"
00047 
00048 class XmlNodeDeletionPolicy
00049 {
00050 public:
00051     static inline void DeleteIt(xmlNode ** ptr)
00052     {
00053         if (*ptr != NULL)
00054         {
00055             xmlFreeNode(*ptr);
00056             *ptr = NULL;
00057         }
00058     }
00059 };
00060 
00061 typedef FbxAutoPtr<xmlNode, XmlNodeDeletionPolicy> XmlNodePtr;
00062 
00063 #if defined(_MSC_VER) && _MSC_VER < 1600
00064         // With VisualStudio 2008 and earlier, we have a crash in the std::map[] beacause the xmlNode* does not have
00065         // a default constructor. The XmlNodeWrapper class is used to overcome this compiler limitation. In order
00066         // to minimize the code changes, the wrapper provides various versions to cast into the xmlNode*
00067         class XmlNodeWrapper
00068         {
00069         public:
00070                 XmlNodeWrapper() : mNode(NULL) {};
00071                 XmlNodeWrapper(xmlNode* pNode) : mNode(pNode) {};
00072                 XmlNodeWrapper(const XmlNodeWrapper& pRhs) { mNode = pRhs.mNode; };
00073                 XmlNodeWrapper& operator=(const XmlNodeWrapper& pRhs) 
00074                 { 
00075                         if (this != &pRhs) {mNode = pRhs.mNode; } 
00076                         return *this; 
00077                 }
00078                 operator const xmlNode*() const { return mNode; }
00079                 operator const xmlNode*()               { return mNode; }
00080                 operator xmlNode*() const               { return mNode; }
00081                 operator xmlNode*()                             { return mNode; }
00082 
00083         private:
00084                 xmlNode* mNode;
00085         };
00086         typedef std::map< FbxString, XmlNodeWrapper > SourceElementMapType;
00087         typedef SourceElementMapType SkinMapType;
00088 #else
00089     typedef std::map< FbxString, xmlNode* > SourceElementMapType;
00090         typedef std::map< FbxString, xmlNode* > SkinMapType;
00091 #endif
00092 
00093 // Some information connecting COLLADA layer string, such as "NORMAL" or "UV", to FBX layer element type.
00094 struct ColladaLayerTraits
00095 {
00096     ColladaLayerTraits() 
00097                 : mLayerType(FbxLayerElement::eUnknown), mLayerElementLength(0) {}
00098                 
00099     ColladaLayerTraits(FbxLayerElement::EType pType, int pLength)
00100         : mLayerType(pType), mLayerElementLength(pLength) {}
00101 
00102     // Type of FBX element layer
00103     FbxLayerElement::EType mLayerType;
00104     // Count of double of each element in FBX element layer
00105     int mLayerElementLength;
00106 
00111     static const ColladaLayerTraits GetLayerTraits(const FbxString & pLabel);
00112 };
00113 
00118 void DAE_AddNotificationError(const FbxManager * pSdkManger, const FbxString & pErrorMessage);
00119 
00124 void DAE_AddNotificationWarning(const FbxManager * pSdkManger, const FbxString & pWarningMessage);
00125 
00126 void DAE_ExportArray(xmlNode* parentXmlNode, const char* id, FbxArray<FbxVector4>& arr);
00127 void DAE_ExportArray(xmlNode* parentXmlNode, const char* id, FbxArray<FbxVector2>& arr);
00128 void DAE_ExportArray(xmlNode* parentXmlNode, const char* id, FbxArray<FbxColor>& arr);
00129 void DAE_ExportArray(xmlNode* parentXmlNode, const char* id, FbxArray<double>& arr);
00130 void DAE_ExportArray(xmlNode* parentXmlNode, const char* id, FbxStringList& arr);
00131 
00132 // Syntax modification - for COLLADA 1.4
00133 xmlNode* DAE_ExportSource14(xmlNode* parentXmlNode, const char* id, FbxStringList& accessorParams, FbxArray<double>& arr, bool isCommonProfile=true); 
00134 xmlNode* DAE_ExportSource14(xmlNode* parentXmlNode, const char* id, FbxArray<FbxVector4>& arr);
00135 xmlNode* DAE_ExportSource14(xmlNode* parentXmlNode, const char* id, FbxArray<FbxVector2>& arr);
00136 xmlNode* DAE_ExportSource14(xmlNode* parentXmlNode, const char* id, FbxArray<FbxColor>& arr);
00137 xmlNode* DAE_ExportSource14(xmlNode* parentXmlNode, const char* id, FbxArray<FbxAMatrix>& arr); 
00138 xmlNode* DAE_ExportSource14(xmlNode* parentXmlNode, const char* id, FbxArray<FbxMatrix>& arr);
00139 xmlNode* DAE_ExportSource14(xmlNode* parentXmlNode, const char* id, FbxStringList& arr, const char* type, bool isCommonProfile=true);
00140 
00141 
00142 void DAE_ExportSourceArray(xmlNode* sourceNode, const char* id, FbxArray<FbxColor>& arr);
00143 void DAE_ExportSourceArray14(xmlNode* sourceNode, const char* id, FbxArray<FbxColor>& arr);
00144 
00145 xmlNode* DAE_ExportAccessor(xmlNode* parentXmlNode, const char* id, const char* arrayRef, int count, int stride, const char* name, const char* type);
00146 xmlNode* DAE_ExportAccessor14(xmlNode* parentXmlNode, const char* id, const char* arrayRef, int count, int stride, const char* name, const char* type);
00147 
00148 void DAE_AddXYZAccessor(xmlNode* parentXmlNode, const char* profile, const char* arrayName, const char* arrayRef, int count);
00149 void DAE_AddSTAccessor(xmlNode* parentXmlNode, const char* profile, const char* arrayName, const char* arrayRef, int count);
00150 void DAE_AddFlow(xmlNode* node, DAE_Flow flow);
00151 void DAE_AddXYZAccessor14(xmlNode* parentXmlNode, const char* profile, const char* arrayName, const char* arrayRef, int count);
00152 void DAE_AddSTAccessor14(xmlNode* parentXmlNode, const char* profile, const char* arrayName, const char* arrayRef, int count);
00153 
00154 // AddParameter functions for COLLADA 1.3.
00155 xmlNode* DAE_AddParameter(xmlNode* parentXmlNode, const char* name, const FbxColor& color, DAE_Flow flow);
00156 xmlNode* DAE_AddParameter(xmlNode* parentXmlNode, const char* name, const FbxVector4& vector, DAE_Flow flow);
00157 xmlNode* DAE_AddParameter(xmlNode* parentXmlNode, const char* name, double value, DAE_Flow flow);
00158 xmlNode* DAE_AddParameter(xmlNode* parentXmlNode, const char* name, bool value, DAE_Flow flow);
00159 xmlNode* DAE_AddParameter(xmlNode* parentXmlNode, const char* name, const char* type, const char* value, DAE_Flow flow);
00160 
00161 // Overload functions without DAE_Flow, for COLLADA 1.4.
00162 xmlNode* DAE_AddParameter(xmlNode* parentXmlNode, const char* name, const FbxDouble3& color);
00163 xmlNode* DAE_AddParameter(xmlNode* parentXmlNode, const char* name, const FbxColor& color);
00164 xmlNode* DAE_AddParameter(xmlNode* parentXmlNode, const char* name, const FbxVector4& vector);
00165 xmlNode* DAE_AddParameter(xmlNode* parentXmlNode, const char* name, double value);
00166 xmlNode* DAE_AddParameter(xmlNode* parentXmlNode, const char* name, bool value);
00167 xmlNode* DAE_AddParameter(xmlNode* parentXmlNode, const char* name, const char* type, const char* value);
00168 xmlNode* DAE_AddTechnique(xmlNode* parentXmlNode, const char* technique);
00169 void DAE_AddInput(xmlNode* parentXmlNode, const char* semantic, const char* source, int idx = -1);
00170 void DAE_AddInput14(xmlNode* parentXmlNode, const char* semantic, const char* source, int offset = -1, int set=-1);
00171 
00172 FbxString matrixToString(const FbxAMatrix& mx);
00173 
00174 typedef FbxArray<xmlNode*> CNodeList;
00175 
00181 void findChildrenByType(xmlNode* pParentElement, const std::set<FbxString>& pTypes, CNodeList& pChildrenElements);
00182 
00188 void findChildrenByType(xmlNode* pParentElement, const char * pType, CNodeList& pChildrenElements);
00189 
00190 xmlNode* getSourceAccessor(xmlNode* sourceNode);
00191 xmlNode* getTechniqueNode(xmlNode* parent, const char * profile);
00192 
00193 // Conversions
00194 inline double inchesToCentimeters(double val) { return floor(val / CENTIMETERS_TO_INCHES * 100000) / 100000; }
00195 inline double centimetersToInches(double val) { return floor(val * CENTIMETERS_TO_INCHES * 100000) / 100000; }
00196 
00197 inline double degreesToRadians(double val) { return floor(val / RADIANS_TO_DEGREES * 100000) / 100000; }
00198 inline double radiansToDegrees(double val) { return floor(val * RADIANS_TO_DEGREES * 100000) / 100000; }
00199 
00207 xmlNode* DAE_FindChildElementByAttribute(xmlNode* pParentElement, const char * pAttributeName,
00208                                         const char * pAttributeValue, const char * pDefaultAttributeValue = "");
00209 
00216 xmlNode* DAE_FindChildElementByTag(xmlNode* pParentElement, const char * pTag, xmlNode* pFindFrom = NULL);
00217 
00223 template <typename TYPE>
00224 void DAE_GetElementContent(xmlNode * pElement, TYPE & pData)
00225 {
00226     if (pElement != NULL)
00227     {
00228         FbxAutoFreePtr<xmlChar> lContent(xmlNodeGetContent(pElement));
00229         FromString(&pData, (const char *)lContent.Get());
00230     }
00231 }
00232 
00237 bool DAE_CheckCompatibility(xmlNode * pNodeElement);
00238 
00243 void DAE_GetElementTag(xmlNode * pElement, FbxString & pTag);
00244 
00250 const FbxString DAE_GetElementAttributeValue(xmlNode * pElement, const char * pAttributeName);
00251 
00258 template <typename TYPE>
00259 bool DAE_GetElementAttributeValue(xmlNode * pElement, const char * pAttributeName, TYPE & pData)
00260 {
00261     if (!pElement || !pAttributeName)
00262         return false;
00263 
00264     FbxAutoFreePtr<xmlChar> lPropertyValue(xmlGetProp(pElement, (const xmlChar *)pAttributeName));
00265     if (lPropertyValue)
00266     {
00267         FromString(&pData, (const char *)lPropertyValue.Get());
00268         return true;
00269     }
00270     return false;
00271 }
00272 
00273 // Special instantiation for string;
00274 // Omit the whitespaces, just return the whole string
00275 template <>
00276 inline bool DAE_GetElementAttributeValue(xmlNode * pElement,
00277                                          const char * pAttributeName,
00278                                          FbxString & pData)
00279 {
00280     if (!pElement || !pAttributeName)
00281         return false;
00282 
00283     FbxAutoFreePtr<xmlChar> lPropertyValue(xmlGetProp(pElement, (const xmlChar *)pAttributeName));
00284     if (lPropertyValue)
00285     {
00286         pData = (const char *)lPropertyValue.Get();
00287         return true;
00288     }
00289     return false;
00290 }
00291 
00298 bool DAE_CompareAttributeValue(xmlNode * pElement,
00299                                       const char * pAttributeName,
00300                                       const char * pValue);
00301 
00306 const FbxString DAE_GetIDFromUrlAttribute(xmlNode * pElement);
00307 
00312 const FbxString DAE_GetIDFromSourceAttribute(xmlNode * pElement);
00313 
00319 const FbxString DAE_GetIDFromTargetAttribute(xmlNode * pElement);
00320 
00326 void DAE_SetName(FbxObject * pObject, const FbxString & pName, const FbxString & pID);
00327 
00336 xmlNode * DAE_GetSourceWithSemantic(xmlNode * pConsumerElement, const char * pSemantic,
00337                                     const SourceElementMapType & pSourceElements);
00338 
00345 template <typename T>
00346 xmlNode * DAE_AddChildElement(xmlNode * pParentElement, const char * pTag,
00347                               const T & pContent)
00348 {
00349     const FbxString lRepr = ToString(pContent);
00350     return xmlNewChild(pParentElement, NULL, (xmlChar *)pTag,
00351         (xmlChar *)lRepr.Buffer());
00352 }
00353 
00354 // Create a child element with empty content.
00355 inline xmlNode * DAE_AddChildElement(xmlNode * pParentElement, const char * pTag)
00356 {
00357     return DAE_AddChildElement(pParentElement, pTag, FbxString());
00358 }
00359 
00360 // Create a new element with empty content.
00361 inline xmlNode * DAE_NewElement(const char * pTag)
00362 {
00363     return xmlNewNode(NULL, reinterpret_cast<xmlChar*>(const_cast<char *>(pTag)));
00364 }
00365 
00372 template <typename T>
00373 xmlAttr * DAE_AddAttribute(xmlNode * pElement, const FbxString & pAttributeName,
00374                            const T & pAttributeValue)
00375 {
00376     const FbxString lRepr = ToString(pAttributeValue);
00377     return xmlNewProp(pElement, (xmlChar *)pAttributeName.Buffer(),
00378         (xmlChar *)lRepr.Buffer());
00379 }
00380 
00385 const FbxSystemUnit DAE_ImportUnit(xmlNode * pUnitElement);
00386 
00391 void IncreaseLclTranslationAnimation(FbxNode * pNode, FbxDouble3 & pOffset);
00392 
00398 void RecursiveSearchElement(xmlNode * pBaseElement, const char * pTag, FbxArray<xmlNode*> & pResult);
00399 
00400 #include <fbxsdk/fbxsdk_nsend.h>
00401 
00402 #endif /* _FBXSDK_FILEIO_COLLADA_UTILS_H_ */