private static Skeleton ImportSkeleton(ref SkeletonNodeData nodeData) { var skeleton = new Skeleton(); var rootBone = ImportBones(nodeData.RootNode, nodeData.RootNode.Parent, null, ref nodeData); skeleton.RootBone = rootBone; return(skeleton); }
private static bool FindSkeleton(ref Scene scene, out SkeletonNodeData nodeData) { if (!scene.HasMeshes) { throw new NotSupportedException( "The FBX importer requires meshes; a skeleton can not be imported on its own."); } nodeData = new SkeletonNodeData { Nodes = new List <Node>(), DeformationBones = FindDeformationBones(ref scene) }; if (nodeData.DeformationBones.Count == 0) { return(false); } var rootBones = new HashSet <Node>(); foreach (var boneName in nodeData.DeformationBones.Keys) { rootBones.Add(FindRootBone(ref scene, boneName)); } if (rootBones.Count > 1) { throw new NotSupportedException("Multiple skeletons are not supported."); } nodeData.RootNode = rootBones.First(); GetSubtree(nodeData.RootNode, nodeData.Nodes); return(true); }
private static Bone ImportBones(Node aiNode, Node aiParent, Bone parent, ref SkeletonNodeData nodeData) { Debug.Assert(aiNode != null); Debug.Assert(aiParent != null); Bone bone = null; if (!aiNode.Name.Contains("_$AssimpFbx$")) { const string mangling = "_$AssimpFbxNull$"; if (aiNode.Name.Contains(mangling)) { bone = new Bone { Name = aiNode.Name.Replace(mangling, string.Empty), CFrame = (CFrame)ToSharpDX(GetRelativeTransform(aiNode, aiParent)) }; } else if (nodeData.Nodes.Contains(aiNode)) { bone = new Bone { Name = aiNode.Name }; Matrix offsetMatrix; Matrix parentOffsetMatrix; var isOffsetMatrixValid = nodeData.DeformationBones.TryGetValue(aiNode.Name, out offsetMatrix); var isParentOffsetMatrixValid = nodeData.DeformationBones.TryGetValue(aiParent.Name, out parentOffsetMatrix); if (isOffsetMatrixValid && isParentOffsetMatrixValid) { bone.CFrame = (CFrame)(Matrix.Invert(offsetMatrix) * parentOffsetMatrix); } else if (isOffsetMatrixValid && (aiNode == nodeData.RootNode || aiParent == nodeData.RootNode)) { bone.CFrame = (CFrame)(Matrix.Invert(offsetMatrix)); } else { bone.CFrame = (CFrame)ToSharpDX(GetRelativeTransform(aiNode, aiParent)); } } } if (bone != null) { bone.Parent = parent; aiParent = aiNode; parent = bone; } foreach (var child in aiNode.Children) { ImportBones(child, aiParent, parent, ref nodeData); } return(bone); }