CBaseMesh::MorphKeyFrame CMaxMesh::frameForChannel( int i, float timeIn ) { TimeValue time = SecToTicks(timeIn); #if defined(USEMORPHLIB) MaxMorphModifier maxMorphModifier = MaxMorphModifier(FindMorpherModifier(m_pINode)); MaxMorphChannel mmc = maxMorphModifier.GetMorphChannel(i); CBaseMesh::MorphKeyFrame frame; std::tstring cmdname(mmc.GetName()); frame.name = std::string(cmdname.begin(), cmdname.end()); frame.time = timeIn; Interval valid=FOREVER; frame.weight = mmc.GetMorphWeight(time); frame.totalWeight = mmc.GetProgressiveMorphWeight(0); #else MorphR3 * morpherModifier = (MorphR3*)FindMorpherModifier(m_pINode); morphChannel const & chanI = morpherModifier->chanBank[i]; CBaseMesh::MorphKeyFrame frame; std::tstring cmdname(chanI.mName.data()); frame.name = std::string(cmdname.begin(), cmdname.end()); frame.time = timeIn; Interval valid=FOREVER; chanI.cblock->GetValue(0, time, frame.weight, valid); frame.totalWeight = chanI.mTargetPercent; #endif return frame; }
CBaseMesh::MorphKeyFrame CMaxMesh::frameForChannel( int i, float timeIn ) { TimeValue time = SecToTicks(timeIn); MorphR3 * morpherModifier = (MorphR3*)FindMorpherModifier(m_pINode); morphChannel const & chanI = morpherModifier->chanBank[i]; CBaseMesh::MorphKeyFrame frame; frame.name = chanI.mName.data(); frame.time = timeIn; Interval valid=FOREVER; chanI.cblock->GetValue(0, time, frame.weight, valid); frame.totalWeight = chanI.mTargetPercent; return frame; }
bool CMaxMesh::Create(INode *pINode, Mesh *pIMesh, bool bDelete) { // check for valid mesh if(pIMesh == 0) { theExporter.SetLastError("Invalid handle.", __FILE__, __LINE__); return false; } m_pINode = pINode; m_pIMesh = pIMesh; m_bDelete = bDelete; // recursively create materials if(!CreateMaterial(m_pINode->GetMtl())) return false; // build all normals if necessary m_pIMesh->checkNormals(TRUE); // precalculate the object transformation matrix m_tm = m_pINode->GetObjectTM(SecToTicks(theExporter.GetInterface()->GetCurrentTime())); // try to get the physique modifier m_pModifier = FindPhysiqueModifier(pINode); if(m_pModifier == 0) { // try to get the skin modifier m_pModifier = FindSkinModifier(pINode); if(m_pModifier == 0) { m_pModifier = FindMorpherModifier(pINode); if( m_pModifier == 0 ) { m_modifierType = MODIFIER_NONE; } m_modifierType = MODIFIER_MORPHER; } else { m_modifierType = MODIFIER_SKIN; } } else { m_modifierType = MODIFIER_PHYSIQUE; } return true; }
Matrix3 SGP_MaxInterface::GetNodeTM(INode *pNode, float time) { // initialize matrix with the identity Matrix3 tm; tm.IdentityMatrix(); // only do this for valid nodes if(pNode != NULL) { // get the node transformation tm = pNode->GetNodeTM(SecToTicks(time)); // make the transformation uniform tm.NoScale(); } return tm; }
int CMaxAnimationImport::DoImport( const TCHAR* name, ImpInterface* ii, Interface* i, BOOL suppressPrompts) { AFX_MANAGE_STATE(AfxGetStaticModuleState()); HWND window = i->GetMAXHWnd(); CFileDialog fileDialog(TRUE, "xsf", 0, OFN_HIDEREADONLY | OFN_OVERWRITEPROMPT, 0, CWnd::FromHandle(window)); if (fileDialog.DoModal() != IDOK) { return IMPEXP_CANCEL; } CString skeleton = fileDialog.GetPathName(); cal3d::RefPtr<CalCoreSkeleton> skel = CalLoader::loadCoreSkeleton(std::string(skeleton)); if (!skel) { MessageBox( window, "Loading skeleton file failed", "Import Cal3D Animation", MB_OK | MB_ICONERROR); return IMPEXP_FAIL; } cal3d::RefPtr<CalCoreAnimation> anim = CalLoader::loadCoreAnimation(name); if (!anim) { MessageBox( window, "Loading animation file failed", "Import Cal3D Animation", MB_OK | MB_ICONERROR); return IMPEXP_FAIL; } typedef std::list<CalCoreTrack*> CoreTrackList; CoreTrackList& trackList = anim->getListCoreTrack(); for (CoreTrackList::iterator itr = trackList.begin(); itr != trackList.end(); ++itr) { CalCoreTrack* track = *itr; int boneId = track->getCoreBoneId(); CalCoreBone* bone = skel->getCoreBone(boneId); if (!bone) continue; INode* node = i->GetINodeByName(bone->getName().c_str()); if (!node) continue; unsigned kfCount = track->getCoreKeyframeCount(); SuspendAnimate(); AnimateOn(); for (unsigned i = 0; i < kfCount; ++i) { CalCoreKeyframe* kf = track->getCoreKeyframe(i); CalQuaternion kf_q = kf->getRotation(); CalVector kf_v = kf->getTranslation(); TimeValue time = SecToTicks(kf->getTime()); Matrix3 tm; tm.IdentityMatrix(); Quat(kf_q.x, kf_q.y, kf_q.z, kf_q.w).MakeMatrix(tm); tm.SetTrans(Point3(kf_v.x, kf_v.y, kf_v.z)); INode* parent = node->GetParentNode(); if (parent) { tm *= parent->GetNodeTM(time); } node->SetNodeTM(time, tm); } ResumeAnimate(); /* typedef std::map<float, CalCoreKeyframe*> KeyMap; KeyMap& keys = track->getMapCoreKeyframe(); int mapsize = sizeof(keys); int size = keys.size(); int idx = 0; for (KeyMap::iterator mi = keys.begin(); mi != keys.end(); ++mi) { Point3 p; CalCoreKeyframe* kf = mi->second; p.x = kf->getTranslation().x; p.y = kf->getTranslation().y; p.z = kf->getTranslation().z; pos->SetValue(SecToTicks(mi->first), &p); } */ /* IKeyControl* kc = GetKeyControlInterface(pos); if (!kc) continue; typedef std::map<float, CalCoreKeyframe*> KeyMap; KeyMap& keys = track->getMapCoreKeyframe(); kc->SetNumKeys(keys.size()); int idx = 0; for (KeyMap::iterator mi = keys.begin(); mi != keys.end(); ++mi) { ITCBPoint3Key key; key.time = SecToTicks(mi->first); key.tens = 0; key.cont = 0; key.bias = 0; key.easeIn = 25.0; key.easeOut = 25.0; key.val.x = mi->second->getTranslation().x; key.val.y = mi->second->getTranslation().y; key.val.z = mi->second->getTranslation().z; kc->SetKey(idx++, &key); } kc->SortKeys(); */ } return IMPEXP_SUCCESS; }
int CMaxAnimationImport::DoImport( const TCHAR* name, ImpInterface* ii, Interface* i, BOOL suppressPrompts) { AFX_MANAGE_STATE(AfxGetStaticModuleState()); HWND window = i->GetMAXHWnd(); CFileDialog fileDialog(TRUE, "xsf", 0, OFN_HIDEREADONLY | OFN_OVERWRITEPROMPT, 0, CWnd::FromHandle(window)); if (fileDialog.DoModal() != IDOK) { return IMPEXP_CANCEL; } CString skeleton = fileDialog.GetPathName(); CalCoreSkeletonPtr skel = CalLoader::loadCoreSkeleton(std::string(skeleton)); if (!skel) { MessageBox( window, "Loading skeleton file failed", "Import Cal3D Animation", MB_OK | MB_ICONERROR); return IMPEXP_FAIL; } CalCoreAnimationPtr anim = CalLoader::loadCoreAnimation(name); if (!anim) { MessageBox( window, "Loading animation file failed", "Import Cal3D Animation", MB_OK | MB_ICONERROR); return IMPEXP_FAIL; } // Get the pose information in the animation const std::vector<CalTransform>& poses = anim->getPoses(); unsigned int num_poses = poses.size() / anim->getTrackCount(); // Calculate the time_per_frame incorrectly since the duration for animations // is stored incorrectly. float time_per_frame = anim->getDuration() / num_poses; // Import each track for (unsigned track_id = 0; track_id < anim->getTrackCount(); ++track_id) { // Get the core bone mapped to the animation int bone_id = anim->getBoneAssignment(track_id); CalCoreBone* bone = skel->getCoreBone(bone_id); if (!bone) continue; // Get the max node for the bone INode* node = i->GetINodeByName(bone->getName().c_str()); if (!node) continue; SuspendAnimate(); AnimateOn(); // Add each pose keyframe in the track float keyframe_time = 0.0f; for (unsigned keyframe_index = 0; keyframe_index < num_poses; ++keyframe_index) { // Get the keyframe data const CalTransform& pose_coord_sys = poses[(keyframe_index * anim->getTrackCount()) + track_id]; const CalVector &kf_v = pose_coord_sys.getTranslation(); const CalQuaternion &kf_q = pose_coord_sys.getRotation(); TimeValue time = SecToTicks(keyframe_time); // Convert to Max math Matrix3 tm; tm.IdentityMatrix(); Quat(kf_q.x, kf_q.y, kf_q.z, kf_q.w).MakeMatrix(tm); tm.SetTrans(Point3(kf_v.x, kf_v.y, kf_v.z)); // Convert the transform to world space INode* parent = node->GetParentNode(); if (parent) { tm *= parent->GetNodeTM(time); } // Set the new transform on the node node->SetNodeTM(time, tm); keyframe_time += time_per_frame; } ResumeAnimate(); /* typedef std::map<float, CalCoreKeyframe*> KeyMap; KeyMap& keys = track->getMapCoreKeyframe(); int mapsize = sizeof(keys); int size = keys.size(); int idx = 0; for (KeyMap::iterator mi = keys.begin(); mi != keys.end(); ++mi) { Point3 p; CalCoreKeyframe* kf = mi->second; p.x = kf->getTranslation().x; p.y = kf->getTranslation().y; p.z = kf->getTranslation().z; pos->SetValue(SecToTicks(mi->first), &p); } */ /* IKeyControl* kc = GetKeyControlInterface(pos); if (!kc) continue; typedef std::map<float, CalCoreKeyframe*> KeyMap; KeyMap& keys = track->getMapCoreKeyframe(); kc->SetNumKeys(keys.size()); int idx = 0; for (KeyMap::iterator mi = keys.begin(); mi != keys.end(); ++mi) { ITCBPoint3Key key; key.time = SecToTicks(mi->first); key.tens = 0; key.cont = 0; key.bias = 0; key.easeIn = 25.0; key.easeOut = 25.0; key.val.x = mi->second->getTranslation().x; key.val.y = mi->second->getTranslation().y; key.val.z = mi->second->getTranslation().z; kc->SetKey(idx++, &key); } kc->SortKeys(); */ } return IMPEXP_SUCCESS; }