bool animateVector2(MKey * keys, unsigned int keysNumber, float t, MVector2 * vector2) { M_PROFILE_SCOPE(animateVector2); // no keys if (keysNumber == 0) return false; // one key if (keysNumber == 1) { (*vector2) = *((MVector2 *)keys->getData()); return true; } // out of range MKey * keyMin = keys; MKey * keyMax = keys + (keysNumber - 1); int tMin = keyMin->getT(); int tMax = keyMax->getT(); if (t <= tMin) { (*vector2) = *((MVector2 *)keyMin->getData()); return true; } if (t >= tMax) { (*vector2) = *((MVector2 *)keyMax->getData()); return true; } // interpolation for (unsigned int i = 1; i < keysNumber; i++) { MKey * key0 = keys; MKey * key1 = keys+1; int t0 = key0->getT(); int t1 = key1->getT(); if ((t >= t0) && (t <= t1)) { float factor = (t - t0) / (float)(t1 - t0); MVector2 * data0 = (MVector2 *)key0->getData(); MVector2 * data1 = (MVector2 *)key1->getData(); (*vector2) = (*data0) + ((*data1) - (*data0))*factor; return true; } keys++; } return false; }
bool animateQuaternion(MKey * keys, unsigned int keysNumber, float t, MQuaternion * quaternion) { // no keys if (keysNumber == 0) return false; // one key if (keysNumber == 1) { (*quaternion) = *((MQuaternion *)keys->getData()); return true; } // out of range MKey * keyMin = keys; MKey * keyMax = keys + (keysNumber - 1); int tMin = keyMin->getT(); int tMax = keyMax->getT(); if (t <= tMin) { (*quaternion) = *((MQuaternion *)keyMin->getData()); return true; } if (t >= tMax) { (*quaternion) = *((MQuaternion *)keyMax->getData()); return true; } // interpolation for (unsigned int i = 1; i < keysNumber; i++) { MKey * key0 = keys; MKey * key1 = keys+1; int t0 = key0->getT(); int t1 = key1->getT(); if (t == t0) { (*quaternion) = *(MQuaternion *)key0->getData(); return true; } if (t == t1) { (*quaternion) = *(MQuaternion *)key1->getData(); return true; } if ((t > t0) && (t < t1)) { float factor = (t - t0) / (float)(t1 - t0); MQuaternion * data0 = (MQuaternion *)key0->getData(); MQuaternion * data1 = (MQuaternion *)key1->getData(); (*quaternion) = MQuaternion(*data0, *data1, factor); return true; } keys++; } return false; }
bool xmlArmatureAnimLoad(const char * filename, void * data) { TiXmlDocument doc(filename); if(! doc.LoadFile()) return false; TiXmlHandle hDoc(&doc); TiXmlElement * pRootNode; TiXmlHandle hRoot(0); // Maratis pRootNode = hDoc.FirstChildElement().Element(); if(! pRootNode) return false; if(strcmp(pRootNode->Value(), "Maratis") != 0) return false; hRoot = TiXmlHandle(pRootNode); // BonesAnim TiXmlElement * armatureAnimNode = pRootNode->FirstChildElement("ArmatureAnim"); if(! armatureAnimNode) return false; unsigned int bonesAnimNumber = 0; armatureAnimNode->QueryUIntAttribute("num", &bonesAnimNumber); if(bonesAnimNumber == 0) return false; // create armature anim MArmatureAnim * armatureAnim = (MArmatureAnim *)data; MObject3dAnim * objAnims = armatureAnim->allocBonesAnim(bonesAnimNumber); // Bone TiXmlElement * boneNode = armatureAnimNode->FirstChildElement("Bone"); for(boneNode; boneNode; boneNode=boneNode->NextSiblingElement("Bone")) { // position TiXmlElement * positionNode = boneNode->FirstChildElement("position"); if(positionNode) { unsigned int kSize = 0; positionNode->QueryUIntAttribute("num", &kSize); MKey * keys = objAnims->allocPositionKeys(kSize); readVector3Keys(positionNode, keys); } // rotation TiXmlElement * rotationNode = boneNode->FirstChildElement("rotation"); if(rotationNode) { unsigned int kSize = 0; rotationNode->QueryUIntAttribute("num", &kSize); MKey * keys = objAnims->allocRotationKeys(kSize); // k TiXmlElement * kNode = rotationNode->FirstChildElement("k"); for(kNode; kNode; kNode=kNode->NextSiblingElement("k")) { int t = 0; MVector3 euler; MQuaternion * rotation = keys->createQuaternionData(); kNode->QueryIntAttribute("t", &t); kNode->QueryFloatAttribute("x", &euler.x); kNode->QueryFloatAttribute("y", &euler.y); kNode->QueryFloatAttribute("z", &euler.z); rotation->setFromAngles(euler.x, euler.y, euler.z); keys->setT(t); keys++; } } // scale TiXmlElement * scaleNode = boneNode->FirstChildElement("scale"); if(scaleNode) { unsigned int kSize = 0; scaleNode->QueryUIntAttribute("num", &kSize); MKey * keys = objAnims->allocScaleKeys(kSize); readVector3Keys(scaleNode, keys); } objAnims++; } return true; }