Example #1
0
        private void AssignMeshes(Assimp.Node node, GameObject parent)
        {
            if (node.MeshIndices.Count == 0)
            {
                return;
            }

            if (scene.Meshes[node.MeshIndices[0]].HasBones)
            {
                delayedMesh.Add(node, parent);
                return;
            }

            Material[]        mats    = new Material[node.MeshIndices.Count];
            CombineInstance[] combine = new CombineInstance[node.MeshIndices.Count];

            int i = 0;

            foreach (int indice in node.MeshIndices)
            {
                combine[i].mesh      = meshes[indice].mesh;
                combine[i].transform = Matrix4x4.identity;
                mats[i] = materials[meshes[indice].materialIndex];
                i++;
            }
            AddSimpleMesh(node, parent, mats, combine);

            progress += (0.25f * node.MeshIndices.Count) / scene.MeshCount;
        }
Example #2
0
        private void exportToAssimp(object sender, EventArgs e)
        {
            Debug.WriteLine("Exporting to assimp");

            if (RenderState.rootObject != null)
            {
                Assimp.AssimpContext ctx = new Assimp.AssimpContext();

                Dictionary <int, int> meshImportStatus = new Dictionary <int, int>();
                Assimp.Scene          aScene           = new Assimp.Scene();
                Assimp.Node           rootNode         = RenderState.rootObject.assimpExport(ref aScene, ref meshImportStatus);
                aScene.RootNode = rootNode;

                //add a single material for now
                Assimp.Material aMat = new Assimp.Material();
                aMat.Name = "testMaterial";
                aScene.Materials.Add(aMat);

                Assimp.ExportFormatDescription[] supported_formats = ctx.GetSupportedExportFormats();
                //Assimp.Scene blenderScene = ctx.ImportFile("SimpleSkin.gltf");
                //ctx.ExportFile(blenderScene, "SimpleSkin.glb", "glb2");
                try
                {
                    ctx.ExportFile(aScene, "test.glb", "glb2");
                    //ctx.ExportFile(aScene, "test.fbx", "fbx");
                }
                catch (Exception ex)
                {
                    Console.WriteLine(ex.Message);
                }
            }
        }
        private static int FindNodeIndex(Assimp.Node rootNode, string nodeName)
        {
            int targetId = 0;

            bool GetTargetIdForNodeRecursive(Assimp.Node node)
            {
                if (node.Name == nodeName)
                {
                    return(true);
                }

                ++targetId;

                foreach (var child in node.Children)
                {
                    if (GetTargetIdForNodeRecursive(child))
                    {
                        return(true);
                    }
                }

                return(false);
            }

            if (GetTargetIdForNodeRecursive(rootNode))
            {
                return(targetId);
            }
            else
            {
                return(-1);
            }
        }
Example #4
0
        private void AssignMeshes(Assimp.Node node, GameObject parent)
        {
            if (node.MeshIndices.Count == 0)
            {
                return;
            }

            MeshFilter   meshFilter   = parent.AddComponent <MeshFilter>();
            MeshRenderer meshRenderer = parent.AddComponent <MeshRenderer>();

            Material[] mats = new Material[node.MeshIndices.Count];

            CombineInstance[] combine = new CombineInstance[node.MeshIndices.Count];

            int i = 0;

            foreach (int indice in node.MeshIndices)
            {
                combine[i].mesh      = meshes[indice].mesh;
                combine[i].transform = Matrix4x4.identity;
                mats[i] = materials[meshes[indice].materialIndex];
                i++;
            }

            meshFilter.mesh = new Mesh();
            meshFilter.mesh.CombineMeshes(combine, false);
            meshFilter.name              = meshes[node.MeshIndices[0]].name;
            meshFilter.mesh.name         = meshFilter.name;
            meshRenderer.sharedMaterials = mats;
            MeshCollider collider = parent.AddComponent <MeshCollider>();

            progress += (0.25f * node.MeshIndices.Count) / scene.MeshCount;
        }
Example #5
0
        private Bone CreateBoneTree(Assimp.Node node, Bone parent)
        {
            Bone internalNode = new Bone
            {
                Name   = node.Name,
                Parent = parent
            };

            if (internalNode.Name == "")
            {
                internalNode.Name = "foo" + _i++;
            }
            _bonesByName[internalNode.Name] = internalNode;
            Assimp.Matrix4x4 trans = node.Transform;
            // trans.Transpose();

            internalNode.LocalTransform         = ToTK(trans);
            internalNode.OriginalLocalTransform = internalNode.LocalTransform;
            CalculateBoneToWorldTransform(internalNode);

            for (int i = 0; i < node.ChildCount; i++)
            {
                Bone child = CreateBoneTree(node.Children[i], internalNode);
                if (child != null)
                {
                    internalNode.Children.Add(child);
                }
            }
            return(internalNode);
        }
Example #6
0
        private NodeContent ParseNode(ModelContent model, Assimp.Node node, NodeContent parent = null)
        {
            NodeContent n = new NodeContent(parent);

            model.Nodes.Add(n);
            if (settings.TransformMesh)
            {
                Matrix matrix = ConvertMatrix(node.Transform);
                matrix.M41      *= settings.Scale.X;
                matrix.M42      *= settings.Scale.Y;
                matrix.M43      *= settings.Scale.Z;
                n.Transformation = matrix;
            }
            else
            {
                n.Transformation = Matrix.Identity;
            }

            n.Name   = node.Name;
            n.Meshes = new List <int>();
            foreach (var meshIndex in node.MeshIndices)
            {
                n.Meshes.Add(meshIndex);
            }
            n.Children = new List <NodeContent>();
            foreach (var child in node.Children)
            {
                n.Children.Add(ParseNode(model, child, n));
            }
            return(n);
        }
Example #7
0
        public virtual Assimp.Node assimpExport(ref Assimp.Scene scn, ref Dictionary <int, int> meshImportStatus)
        {
            //Default shit
            //Create assimp node
            Assimp.Node node = new Assimp.Node(Name);
            node.Transform = MathUtils.convertMatrix(localMat);

            //Handle animations maybe?
            int animComponentId = hasComponent(typeof(AnimComponent));

            if (animComponentId > -1)
            {
                AnimComponent cmp = (AnimComponent)_components[animComponentId];
                cmp.assimpExport(ref scn);
            }

            foreach (Model child in children)
            {
                Assimp.Node c = child.assimpExport(ref scn, ref meshImportStatus);
                node.Children.Add(c);
            }


            return(node);
        }
Example #8
0
        internal static void CopyNodesWithMeshes(Assimp.Scene pScene, Assimp.Node node, ref List <SceneObject> meshArr)
        {
            // if node has meshes, create a new scene object for it
            if (node.HasMeshes)
            {
                foreach (int i in node.MeshIndices)
                {
                    SceneObject so = new SceneObject();
                    so.nodeName = node.Name;
                    if (node.Parent != null)
                    {
                        so.parentNodeName = node.Parent.Name;
                    }
                    so.pMesh     = pScene.Meshes[i];
                    so.transform = node.Transform;
                    so.transform.Transpose();

                    meshArr.Add(so);
                }
            }

            // continue for all child nodes
            if (node.HasChildren)
            {
                foreach (Assimp.Node childNode in node.Children)
                {
                    CopyNodesWithMeshes(pScene, childNode, ref meshArr);
                }
            }
        }
Example #9
0
        void RekursiveDraw(Assimp.Node node, OpenGlDevice Device)
        {
            if ((node.HasMeshes))
            {
                foreach (var index in node.MeshIndices)
                {
                    D3DMesh mesh = (Meshes[index] as D3DMesh);

                    xyzf b = new xyzf(0, 0, 0);


                    CpuSkinningEvaluator.CachedMeshData MD = SkinninEvaluator.GetEntry(mesh);
                    SkinninEvaluator.GetTransformedVertexPosition(node, mesh, 0, out b);
                    if (mesh.Material.Translucent < 1)
                    {
                        TransparentMeshes.Add(new TransParencyItem(mesh, MD._cachedPositions, MD._cachedNormals));
                        continue;
                    }

                    xyzf[] SavePos     = mesh.Position;
                    xyzf[] SaveNormals = mesh.Normals;
                    mesh.Position = MD._cachedPositions;
                    mesh.Normals  = MD._cachedNormals;
                    mesh.Paint(Device);
                    mesh.Position = SavePos;
                    mesh.Normals  = SaveNormals;
                }
            }
            for (int i = 0; i < node.Children.Count; i++)
            {
                RekursiveDraw(node.Children[i], Device);
            }
        }
Example #10
0
        Box RekursiveGetBox(Assimp.Node node, Box BoxMin)
        {
            Box _Box = BoxMin;

            if ((node.HasMeshes))
            {
                foreach (var index in node.MeshIndices)
                {
                    D3DMesh mesh = (Meshes[index] as D3DMesh);

                    xyzf b = new xyzf(0, 0, 0);


                    CpuSkinningEvaluator.CachedMeshData MD = SkinninEvaluator.GetEntry(mesh);
                    SkinninEvaluator.GetTransformedVertexPosition(node, mesh, 0, out b);

                    xyzf[] P = new xyzf[MD._cachedPositions.Length];
                    for (int i = 0; i < P.Length; i++)
                    {
                        P[i] = mesh.Transformation * MD._cachedPositions[i];
                    }
                    _Box = Box.GetEnvBox(P, _Box);
                }
            }
            for (int i = 0; i < node.Children.Count; i++)
            {
                _Box = RekursiveGetBox(node.Children[i], _Box);
            }
            return(_Box);
        }
Example #11
0
        internal SceneNode(Assimp.Node node, Assimp.Matrix4x4 transform, List <SceneMesh> meshes, Action <Matrix4> setTransform, Func <int, MaterialBinding> materialSelector)
        {
            Name      = node.Name;
            draw      = EmptyAction;
            Transform = MatrixHelper.ToMatrix4(transform * node.Transform);
            if (node.HasMeshes)
            {
                draw += () => setTransform(Transform);
                foreach (var index in node.MeshIndices)
                {
                    var mesh = meshes[index];
                    draw += () =>
                    {
                        var material = materialSelector(mesh.MaterialIndex);
                        if (material != null)
                        {
                            material.Bind();
                            mesh.Draw();
                        }
                    };
                }
            }

            if (node.HasChildren)
            {
                children.AddRange(node.Children.Select(
                                      child => new SceneNode(child, node.Transform, meshes, setTransform, materialSelector)));
            }
        }
Example #12
0
        private static Node ConvertNode(Assimp.Node aiNode, List <Assimp.Mesh> aiMeshes, List <MaterialBuildInfo> materialBuildInfos, ConvertGeometryDelegate convertGeometry)
        {
            Node ConvertHierarchyNodeRecursively(Assimp.Node curAiNode, ref Node previousSibling, Node parent, ref Assimp.Matrix4x4 parentNodeWorldTransform)
            {
                var nodeWorldTransform = curAiNode.Transform * parentNodeWorldTransform;

                curAiNode.Transform.Decompose(out var scale, out var rotation, out var translation);

                // Create node
                //var node = new Node( AssimpHelper.FromAssimp( translation ), AngleVector.FromQuaternion( AssimpHelper.FromAssimp( rotation ) ),
                //                     AssimpHelper.FromAssimp( scale ), parent );
                var node = new Node(Vector3.Zero, AngleVector.Zero, Vector3.One, parent);

                if (curAiNode.HasMeshes)
                {
                    Console.WriteLine(curAiNode.Name);
                    node.Geometry = convertGeometry(curAiNode, nodeWorldTransform, aiMeshes, materialBuildInfos);
                }

                // Set sibling (next) reference of previous
                if (previousSibling != null)
                {
                    previousSibling.Sibling = node;
                }

                previousSibling = node;

                if (curAiNode.HasChildren)
                {
                    Node childPreviousSibling = null;
                    foreach (var aiChildNode in curAiNode.Children)
                    {
                        var childNode = ConvertHierarchyNodeRecursively(aiChildNode, ref childPreviousSibling, node, ref nodeWorldTransform);

                        // Make sure to set the 'first child' reference if we haven't already
                        if (node.Child == null)
                        {
                            node.Child = childNode;
                        }
                    }
                }

                return(node);
            }

            // Dummy!
            Node dummyNode      = null;
            var  identityMatrix = Assimp.Matrix4x4.Identity;
            var  rootNode       = ConvertHierarchyNodeRecursively(aiNode, ref dummyNode, null, ref identityMatrix);

            foreach (var node in rootNode.EnumerateAllNodes())
            {
                node.OptimizeFlags();
            }

            return(rootNode);
        }
Example #13
0
        private static IGeometry ConvertCollisionGeometry(Assimp.Node curAiNode, Assimp.Matrix4x4 nodeWorldTransform,
                                                          List <Assimp.Mesh> aiMeshes,
                                                          List <MaterialBuildInfo> materialBuildInfos)
        {
            var vertices  = new List <Assimp.Vector3D>();
            var triangles = new List <Basic.Triangle>();

            foreach (var aiMeshIndex in curAiNode.MeshIndices)
            {
                var aiMesh = aiMeshes[aiMeshIndex];

                for (var i = 0; i < aiMesh.Faces.Count; i++)
                {
                    var aiFace   = aiMesh.Faces[i];
                    var triangle = new Basic.Triangle();
                    var flip     = false;

                    if (!flip)
                    {
                        triangle.A = ( ushort )vertices.AddUnique(aiMesh.Vertices[aiFace.Indices[0]]);
                        triangle.B = aiFace.IndexCount > 1 ? ( ushort )vertices.AddUnique(aiMesh.Vertices[aiFace.Indices[1]]) : triangle.A;
                        triangle.C = aiFace.IndexCount > 2 ? ( ushort )vertices.AddUnique(aiMesh.Vertices[aiFace.Indices[2]]) : triangle.B;
                    }
                    else
                    {
                        triangle.C = ( ushort )vertices.AddUnique(aiMesh.Vertices[aiFace.Indices[0]]);
                        triangle.B = aiFace.IndexCount > 1 ? ( ushort )vertices.AddUnique(aiMesh.Vertices[aiFace.Indices[1]]) : triangle.A;
                        triangle.A = aiFace.IndexCount > 2 ? ( ushort )vertices.AddUnique(aiMesh.Vertices[aiFace.Indices[2]]) : triangle.B;
                    }

                    triangles.Add(triangle);
                }
            }

            var geometry = new Basic.Geometry
            {
                Meshes = new[]
                {
                    new Basic.Mesh
                    {
                        PrimitiveType = PrimitiveType.Triangles,
                        Primitives    = triangles.Cast <Basic.IPrimitive>().ToArray(),
                    }
                },
                VertexPositions = vertices.Select(x =>
                {
                    Assimp.Unmanaged.AssimpLibrary.Instance.TransformVecByMatrix4(ref x, ref nodeWorldTransform);
                    return(AssimpHelper.FromAssimp(x));
                }
                                                  ).ToArray()
            };

            geometry.Bounds = BoundingSphere.Calculate(geometry.VertexPositions);

            return(geometry);
        }
Example #14
0
        private void ImportAnimation(Assimp.Node node, GameObject go, Quaternion cumulRotation)
        {
            Assimp.Animation animation = scene.Animations[0];
            if ((GlobalState.Animation.fps / (float)animation.TicksPerSecond) * animation.DurationInTicks > GlobalState.Animation.EndFrame)
            {
                GlobalState.Animation.EndFrame = Mathf.CeilToInt(GlobalState.Animation.fps / (float)animation.TicksPerSecond * (float)animation.DurationInTicks) + 1;
            }
            Assimp.NodeAnimationChannel nodeChannel = animation.NodeAnimationChannels.Find(x => x.NodeName == node.Name);
            if (nodeChannel == null)
            {
                nodeChannel = animation.NodeAnimationChannels.Find(x => x.NodeName.Split('_')[0] == node.Name);
            }
            if (null != nodeChannel)
            {
                if (nodeChannel.PositionKeyCount < 2 && nodeChannel.RotationKeyCount < 2)
                {
                    return;
                }
                AnimationSet animationSet = new AnimationSet(go);
                animationSet.ComputeCache();
                if (nodeChannel.PositionKeyCount > 1 || nodeChannel.RotationKeyCount == nodeChannel.PositionKeyCount)
                {
                    foreach (Assimp.VectorKey vectorKey in nodeChannel.PositionKeys)
                    {
                        int frame = Mathf.CeilToInt((float)vectorKey.Time * GlobalState.Animation.fps / (float)animation.TicksPerSecond) + 1;
                        animationSet.curves[AnimatableProperty.PositionX].AddKey(new AnimationKey(frame, vectorKey.Value.X, Interpolation.Bezier));
                        animationSet.curves[AnimatableProperty.PositionY].AddKey(new AnimationKey(frame, vectorKey.Value.Y, Interpolation.Bezier));
                        animationSet.curves[AnimatableProperty.PositionZ].AddKey(new AnimationKey(frame, vectorKey.Value.Z, Interpolation.Bezier));
                    }
                }
                foreach (Assimp.VectorKey vectorKey in nodeChannel.ScalingKeys)
                {
                    int frame = Mathf.CeilToInt((float)vectorKey.Time * GlobalState.Animation.fps / (float)animation.TicksPerSecond) + 1;
                    animationSet.curves[AnimatableProperty.ScaleX].AddKey(new AnimationKey(frame, vectorKey.Value.X, Interpolation.Bezier));
                    animationSet.curves[AnimatableProperty.ScaleY].AddKey(new AnimationKey(frame, vectorKey.Value.Y, Interpolation.Bezier));
                    animationSet.curves[AnimatableProperty.ScaleZ].AddKey(new AnimationKey(frame, vectorKey.Value.Z, Interpolation.Bezier));
                }
                Vector3 previousRotation = Vector3.zero;
                foreach (Assimp.QuaternionKey quaternionKey in nodeChannel.RotationKeys)
                {
                    int        frame       = Mathf.RoundToInt((float)quaternionKey.Time * GlobalState.Animation.fps / (float)animation.TicksPerSecond) + 1;
                    Quaternion uQuaternion = new Quaternion(quaternionKey.Value.X, quaternionKey.Value.Y, quaternionKey.Value.Z, quaternionKey.Value.W);
                    uQuaternion = cumulRotation * uQuaternion * Quaternion.Inverse(cumulRotation);

                    Vector3 eulerValue = uQuaternion.eulerAngles;
                    eulerValue.x = previousRotation.x + Mathf.DeltaAngle(previousRotation.x, eulerValue.x);
                    eulerValue.y = previousRotation.y + Mathf.DeltaAngle(previousRotation.y, eulerValue.y);
                    eulerValue.z = previousRotation.z + Mathf.DeltaAngle(previousRotation.z, eulerValue.z);
                    animationSet.curves[AnimatableProperty.RotationX].AddKey(new AnimationKey(frame, eulerValue.x, Interpolation.Bezier));
                    animationSet.curves[AnimatableProperty.RotationY].AddKey(new AnimationKey(frame, eulerValue.y, Interpolation.Bezier));
                    animationSet.curves[AnimatableProperty.RotationZ].AddKey(new AnimationKey(frame, eulerValue.z, Interpolation.Bezier));
                    previousRotation = eulerValue;
                }
                GlobalState.Animation.SetObjectAnimations(go, animationSet);
            }
        }
Example #15
0
        internal static Mesh3D LoadFromFile(Device device, Assimp.Scene pScene, InputElement[] ieLayout)
        {
            Assimp.Node        root    = pScene.RootNode;
            List <SceneObject> meshArr = new List <SceneObject>();

            CopyNodesWithMeshes(pScene, root, ref meshArr);


            return(LoadFromFileSUB(device, pScene, ieLayout, meshArr));
        }
Example #16
0
        public static XElement BuildAssimpNodeTree(Assimp.Node node)
        {
            XElement element = new XElement("Mesh", node.Name);

            foreach (Assimp.Node child in node.Children)
            {
                element.Add(BuildAssimpNodeTree(child));
            }
            return(element);
        }
Example #17
0
        /// <summary>
        /// Get the world transform for the given Assimp node.
        /// </summary>
        /// <param name="node"></param>
        /// <returns></returns>
        private static Assimp.Matrix4x4 ComputeWorldTransform(Assimp.Node node)
        {
            var matrix = node.Transform;

            if (node.Parent != null)
            {
                matrix *= ComputeWorldTransform(node.Parent);
            }

            return(matrix);
        }
Example #18
0
        private void AddSimpleMesh(Assimp.Node node, GameObject parent, Material[] mats, CombineInstance[] combine)
        {
            MeshFilter   meshFilter   = parent.AddComponent <MeshFilter>();
            MeshRenderer meshRenderer = parent.AddComponent <MeshRenderer>();

            meshFilter.mesh = new Mesh();
            meshFilter.mesh.CombineMeshes(combine, false);
            meshFilter.name              = meshes[node.MeshIndices[0]].name;
            meshFilter.mesh.name         = meshFilter.name;
            meshRenderer.sharedMaterials = mats;
            MeshCollider collider = parent.AddComponent <MeshCollider>();
        }
Example #19
0
        private void ParseNodeTransform(Assimp.Node node, List <mat4> list, mat4 parentTransform)
        {
            mat4 thisTransform = parentTransform * node.Transform.ToMat4();

            list.Add(thisTransform);
            if (node.HasChildren)
            {
                foreach (Assimp.Node child in node.Children)
                {
                    ParseNodeTransform(child, list, thisTransform);
                }
            }
        }
        public static Assimp.Matrix4x4 GetWorldMatrix(Assimp.Node node)
        {
            var mat      = node.Transform;
            var currNode = node;

            while (currNode.Parent != null)
            {
                mat     *= currNode.Parent.Transform;
                currNode = currNode.Parent;
            }

            return(mat);
        }
Example #21
0
        private void ParseNode(Assimp.Node node, List <vec3> list, mat4 parentTransform)
        {
            mat4 thisTransform = parentTransform * node.Transform.ToMat4();
            var  position      = new vec3(thisTransform * new vec4(0, 0, 0, 1));

            list.Add(position);
            if (node.HasChildren)
            {
                foreach (Assimp.Node child in node.Children)
                {
                    ParseNode(child, list, thisTransform);
                }
            }
        }
        public Assimp.Scene ConvertToScene(Model model, Config config)
        {
            // Start building scene
            var aiScene = AssimpHelper.CreateDefaultScene();

            // Convert materials
            for (var i = 0; i < model.Materials.Count; i++)
            {
                var material   = model.Materials[i];
                var aiMaterial = new Assimp.Material {
                    Name = FormatMaterialName(material, i)
                };

                if (material.TextureId != null)
                {
                    aiMaterial.TextureDiffuse = new Assimp.TextureSlot
                    {
                        TextureType = Assimp.TextureType.Diffuse,
                        FilePath    = Path.Combine("textures", FormatTextureName(material.TextureId.Value))
                    };
                }

                aiScene.Materials.Add(aiMaterial);
            }

            // Convert nodes
            var aiNodeLookup = new Dictionary <Node, Assimp.Node>();

            for (var i = 0; i < model.Nodes.Count; i++)
            {
                var node   = model.Nodes[i];
                var aiNode = new Assimp.Node(FormatNodeName(node, i), node.Parent != null ? aiNodeLookup[node.Parent] : aiScene.RootNode);
                aiNodeLookup[node] = aiNode;
                aiNode.Transform   = node.Transform.ToAssimp();

                if (node.Geometry != null)
                {
                    ConvertMeshList(node.Geometry.Meshes, node, i, model.Nodes, aiScene, aiNode);

                    if (node.Geometry.TranslucentMeshes != null)
                    {
                        ConvertMeshList(node.Geometry.TranslucentMeshes, node, i, model.Nodes, aiScene, aiNode);
                    }
                }

                aiNode.Parent.Children.Add(aiNode);
            }

            return(aiScene);
        }
Example #23
0
        public BoneAnimation LoadBoneAnimation(Assimp.Scene aScene, Assimp.Node aNode, BoneAnimation parent)
        {
            var boneAnimation = new BoneAnimation()
            {
                Parent    = parent,
                Children  = new List <BoneAnimation>(),
                Positions = new List <Vector3>(),
                Rotations = new List <Quaternion>(),
                Scales    = new List <Vector3>()
            };

            boneAnimation.Name = aNode.Name;

            var animationChanel = aScene.Animations[0].NodeAnimationChannels.Where(n => n.NodeName == boneAnimation.Name).FirstOrDefault();

            if (animationChanel != null)
            {
                boneAnimation.IsAnimate = true;

                foreach (var aScale in animationChanel.ScalingKeys)
                {
                    var scale = new Vector3(aScale.Value.X, aScale.Value.Y, aScale.Value.Z);
                    boneAnimation.Scales.Add(scale);
                }

                foreach (var aRotation in animationChanel.RotationKeys)
                {
                    var rotation = new Quaternion(aRotation.Value.X, aRotation.Value.Y, aRotation.Value.Z, aRotation.Value.W);
                    boneAnimation.Rotations.Add(rotation);
                }

                foreach (var aTranslate in animationChanel.PositionKeys)
                {
                    var translate = new Vector3(aTranslate.Value.X, aTranslate.Value.Y, aTranslate.Value.Z);
                    boneAnimation.Positions.Add(translate);
                }
            }
            else
            {
                boneAnimation.IsAnimate      = false;
                boneAnimation.Transformation = Matrix.Transpose(AssimpHelper.MatrixAssimpToXna(aNode.Transform));
            }

            foreach (var child in aNode.Children)
            {
                boneAnimation.Children.Add(LoadBoneAnimation(aScene, child, boneAnimation));
            }
            BoneAnimations.Add(boneAnimation);
            return(boneAnimation);
        }
        private static void AddOnePosFrame(AquaMotion.KeyData node, Assimp.Node aiNode, float baseScale)
        {
            AquaMotion.MKEY posKeys = new AquaMotion.MKEY();
            posKeys.keyType  = 1;
            posKeys.dataType = 1;
            posKeys.keyCount = 1;
            var mat4 = GetMat4FromAssimpMat4(aiNode.Transform);

            posKeys.vector4Keys = new List <Vector4>()
            {
                new Vector4(mat4.M14 * baseScale, mat4.M24 * baseScale, mat4.M34 * baseScale, 0)
            };
            node.keyData.Add(posKeys);
        }
        public static void CollectAnimated(Assimp.Node node, Dictionary <int, Assimp.Node> nodes)
        {
            //Be extra sure that this isn't an effect node
            if (IsAnimatedNode(node, out string name, out int num))
            {
                //For now, assume animated node is numbered and we can add it directly
                nodes.Add(num, node);
            }

            foreach (var childNode in node.Children)
            {
                CollectAnimated(childNode, nodes);
            }
        }
Example #26
0
        public void ExportModel()
        {
            using (System.Windows.Forms.SaveFileDialog a = new System.Windows.Forms.SaveFileDialog
            {
                DefaultExt = "dae",
                Filter = "SAModel Files|*.sa1mdl|Collada|*.dae|Wavefront|*.obj"
            })
            {
                if (a.ShowDialog() == System.Windows.Forms.DialogResult.OK)
                {
                    string ftype = "collada";
                    switch (System.IO.Path.GetExtension(a.FileName).ToLowerInvariant())
                    {
                    case ".sa1mdl":
                        ModelFile.CreateFile(a.FileName, COL.Model, null, null, null, null, COL.Model.GetModelFormat());
                        return;

                    case ".fbx":
                        ftype = "fbx";
                        break;

                    case ".obj":
                        ftype = "obj";
                        break;
                    }
                    Assimp.AssimpContext context = new Assimp.AssimpContext();
                    Assimp.Scene         scene   = new Assimp.Scene();
                    scene.Materials.Add(new Assimp.Material());
                    Assimp.Node n = new Assimp.Node();
                    n.Name         = "RootNode";
                    scene.RootNode = n;
                    string        rootPath     = System.IO.Path.GetDirectoryName(a.FileName);
                    List <string> texturePaths = new List <string>();
                    int           numSteps     = 0;
                    if (LevelData.TextureBitmaps != null && LevelData.TextureBitmaps.Count > 0)
                    {
                        numSteps = LevelData.TextureBitmaps[LevelData.leveltexs].Length;
                    }
                    for (int i = 0; i < numSteps; i++)
                    {
                        BMPInfo bmp = LevelData.TextureBitmaps[LevelData.leveltexs][i];
                        texturePaths.Add(System.IO.Path.Combine(rootPath, bmp.Name + ".png"));
                        bmp.Image.Save(System.IO.Path.Combine(rootPath, bmp.Name + ".png"));
                    }
                    SAEditorCommon.Import.AssimpStuff.AssimpExport(COL.Model, scene, Matrix.Identity, texturePaths.Count > 0 ? texturePaths.ToArray() : null, scene.RootNode);
                    context.ExportFile(scene, a.FileName, ftype, Assimp.PostProcessSteps.ValidateDataStructure | Assimp.PostProcessSteps.Triangulate | Assimp.PostProcessSteps.FlipUVs);                    //
                }
            }
        }
        private static void AddOneRotFrame(AquaMotion.KeyData node, Assimp.Node aiNode)
        {
            AquaMotion.MKEY rotKeys = new AquaMotion.MKEY();
            rotKeys.keyType  = 2;
            rotKeys.dataType = 3;
            rotKeys.keyCount = 1;
            Matrix4x4.Invert(GetMat4FromAssimpMat4(aiNode.Transform), out Matrix4x4 mat4);
            var quat = Quaternion.CreateFromRotationMatrix(mat4);

            rotKeys.vector4Keys = new List <Vector4>()
            {
                new Vector4(quat.X, quat.Y, quat.Z, quat.W)
            };
            node.keyData.Add(rotKeys);
        }
Example #28
0
        public static Matrix4x4 CalculateWorldTransform(Assimp.Node node)
        {
            Assimp.Matrix4x4 CalculateWorldTransformInternal(Assimp.Node currentNode)
            {
                var transform = currentNode.Transform;

                if (currentNode.Parent != null)
                {
                    transform *= CalculateWorldTransformInternal(currentNode.Parent);
                }

                return(transform);
            }

            return(FromAssimp(CalculateWorldTransformInternal(node)));
        }
        private static void ConvertMeshList(MeshList meshList, Node node, int nodeIndex, List <Node> nodes, Assimp.Scene aiScene, Assimp.Node aiNode)
        {
            var meshStartIndex = aiScene.Meshes.Count;

            foreach (var mesh in meshList)
            {
                switch (mesh.Type)
                {
                case MeshType.Type1:
                    aiScene.Meshes.AddRange(ConvertMeshType1(( MeshType1 )mesh, node, nodeIndex));
                    break;

                case MeshType.Type2:
                    aiScene.Meshes.AddRange(ConvertMeshType2(( MeshType2 )mesh, nodes));
                    break;

                case MeshType.Type3:
                    break;

                case MeshType.Type4:
                    aiScene.Meshes.Add(ConvertMeshType4(( MeshType4 )mesh, node, nodeIndex));
                    break;

                case MeshType.Type5:
                    aiScene.Meshes.AddRange(ConvertMeshType5(( MeshType5 )mesh, node, nodes, nodeIndex));
                    break;

                case MeshType.Type7:
                    aiScene.Meshes.Add(ConvertMeshType7(( MeshType7 )mesh, nodes));
                    break;

                case MeshType.Type8:
                    aiScene.Meshes.Add(ConvertMeshType8(( MeshType8 )mesh, node, nodeIndex));
                    break;
                }
            }

            var meshEndIndex = aiScene.Meshes.Count;

            for (int i = meshStartIndex; i < meshEndIndex; i++)
            {
                var meshNode = new Assimp.Node($"mesh_{i:D2}", aiScene.RootNode);
                meshNode.MeshIndices.Add(i);
                meshNode.Parent.Children.Add(meshNode);
            }
        }
Example #30
0
        private void ParseNode(Assimp.Node node, List <vec3> lstPosition, List <vec3> lstColor, List <Assimp.Node> lstNode, mat4 parentTransform)
        {
            var parentPosition = new vec3(parentTransform * new vec4(0, 0, 0, 1));

            lstPosition.Add(parentPosition); lstColor.Add(new vec3(1, 0, 0)); lstNode.Add(node.Parent);
            mat4 thisTransform = parentTransform * node.Transform.ToMat4();
            var  position      = new vec3(thisTransform * new vec4(0, 0, 0, 1));

            lstPosition.Add(position); lstColor.Add(new vec3(1, 1, 1)); lstNode.Add(node);
            if (node.HasChildren)
            {
                foreach (Assimp.Node child in node.Children)
                {
                    ParseNode(child, lstPosition, lstColor, lstNode, thisTransform);
                }
            }
        }
Example #31
0
 private static void WalkChildren(RWSceneNode rwNode, Assimp.Node parent)
 {
     foreach (RWSceneNode child in rwNode.Children)
     {
         string name = child.BoneMetadata.BoneNameID.ToString();
         Assimp.Node aiNode = new Assimp.Node(name, parent);
     }
 }
Example #32
0
        public static Assimp.Scene ToAssimpScene(RWScene scene)
        {
            Assimp.Scene aiScene = new Assimp.Scene();

            int drawCallIdx = 0;
            int materialIdx = 0;
            int totalSplitIdx = 0;
            List<int> meshStartIndices = new List<int>();
            foreach (RWDrawCall drawCall in scene.DrawCalls)
            {
                meshStartIndices.Add(totalSplitIdx);
                var mesh = scene.Meshes[drawCall.MeshIndex];
                var node = scene.Nodes[drawCall.NodeIndex];

                int splitIdx = 0;
                foreach (RWMeshMaterialSplit split in mesh.MaterialSplitData.MaterialSplits)
                {
                    Assimp.Mesh aiMesh = new Assimp.Mesh(Assimp.PrimitiveType.Triangle);
                    aiMesh.Name = string.Format("DrawCall{0}_Split{1}", drawCallIdx.ToString("00"), splitIdx.ToString("00"));
                    aiMesh.MaterialIndex = split.MaterialIndex + materialIdx;

                    // get split indices
                    int[] indices = split.Indices;
                    if (mesh.MaterialSplitData.PrimitiveType == RWPrimitiveType.TriangleStrip)
                        indices = MeshUtilities.ToTriangleList(indices, true);

                    // pos & nrm
                    for (int i = 0; i < indices.Length; i++)
                    {
                        if (mesh.HasVertices)
                        {
                            var vert = Vector3.Transform(mesh.Vertices[indices[i]], node.WorldTransform);
                            aiMesh.Vertices.Add(vert.ToAssimpVector3D());
                        }
                        if (mesh.HasNormals)
                        {
                            var nrm = Vector3.TransformNormal(mesh.Normals[indices[i]], node.WorldTransform);
                            aiMesh.Normals.Add(nrm.ToAssimpVector3D());
                        }
                    }

                    // tex coords
                    if (mesh.HasTexCoords)
                    {
                        for (int i = 0; i < mesh.TextureCoordinateChannelCount; i++)
                        {
                            List<Assimp.Vector3D> texCoordChannel = new List<Assimp.Vector3D>();

                            for (int j = 0; j < indices.Length; j++)
                            {
                                texCoordChannel.Add(mesh.TextureCoordinateChannels[i][indices[j]].ToAssimpVector3D(0));
                            }

                            aiMesh.TextureCoordinateChannels[i] = texCoordChannel;
                        }
                    }

                    // colors
                    if (mesh.HasColors)
                    {
                        List<Assimp.Color4D> vertColorChannel = new List<Assimp.Color4D>();

                        for (int i = 0; i < indices.Length; i++)
                        {
                            var color = mesh.Colors[indices[i]];
                            vertColorChannel.Add(new Assimp.Color4D(color.R / 255f, color.G / 255f, color.B / 255f, color.A / 255f));
                        }

                        aiMesh.VertexColorChannels[0] = vertColorChannel;
                    }

                    // generate temporary face indices
                    int[] tempIndices = new int[aiMesh.VertexCount];
                    for (int i = 0; i < aiMesh.VertexCount; i++)
                        tempIndices[i] = i;

                    aiMesh.SetIndices(tempIndices, 3);

                    // add the mesh to the list
                    aiScene.Meshes.Add(aiMesh);

                    splitIdx++;
                }

                totalSplitIdx += splitIdx;

                foreach (RWMaterial mat in mesh.Materials)
                {
                    Assimp.Material aiMaterial = new Assimp.Material();
                    aiMaterial.AddProperty(new Assimp.MaterialProperty(Assimp.Unmanaged.AiMatKeys.NAME, "Material" + (materialIdx++).ToString("00")));

                    if (mat.IsTextured)
                    {
                        aiMaterial.AddProperty(new Assimp.MaterialProperty(Assimp.Unmanaged.AiMatKeys.TEXTURE_BASE, mat.TextureReference.ReferencedTextureName + ".png", Assimp.TextureType.Diffuse, 0));
                    }

                    aiScene.Materials.Add(aiMaterial);
                }

                drawCallIdx++;
            }

            // store node lookup
            Dictionary<RWSceneNode, Assimp.Node> nodeLookup = new Dictionary<RWSceneNode, Assimp.Node>();

            // first create the root node
            var rootNode = new Assimp.Node("SceneRoot");
            rootNode.Transform = scene.Nodes[0].Transform.ToAssimpMatrix4x4();
            nodeLookup.Add(scene.Nodes[0], rootNode);

            for (int i = 1; i < scene.Nodes.Count - 1; i++)
            {
                var node = scene.Nodes[i];
                string name = node.BoneMetadata.BoneNameID.ToString();

                var aiNode = new Assimp.Node(name);
                aiNode.Transform = node.Transform.ToAssimpMatrix4x4();

                // get the associated meshes for this node
                var drawCalls = scene.DrawCalls.FindAll(dc => dc.NodeIndex == i);
                foreach (var drawCall in drawCalls)
                {
                    for (int j = 0; j < scene.Meshes[drawCall.MeshIndex].MaterialCount; j++)
                    {
                        aiNode.MeshIndices.Add(meshStartIndices[scene.DrawCalls.IndexOf(drawCall)] + j);
                    }
                }

                nodeLookup[node.Parent].Children.Add(aiNode);
                nodeLookup.Add(node, aiNode);
            }

            aiScene.RootNode = rootNode;

            return aiScene;
        }