private void CopyBodyVertices(Bone Bne)
        {
            BoneBinding boneBinding = BodyMesh.BoneBindings.FirstOrDefault(x => BodyMesh.Bones[(int)x.BoneIndex] == Bne.Name);

            if (boneBinding != null)
            {
                for (int i = 0; i < (boneBinding.RealVertexCount - 2); i += 3)
                {
                    int vertexIndex = (int)boneBinding.FirstRealVertexIndex + i;

                    BodyMesh.TransformedVertices[vertexIndex].BoneBinding = boneBinding.BoneIndex;
                    BodyMesh.TransformedVertices[vertexIndex].Position    = BodyMesh.RealVertices[vertexIndex].Position;

                    BodyMesh.TransformedVertices[vertexIndex + 1].BoneBinding = boneBinding.BoneIndex;
                    BodyMesh.TransformedVertices[vertexIndex + 1].Position    = BodyMesh.RealVertices[vertexIndex + 1].Position;

                    BodyMesh.TransformedVertices[vertexIndex + 2].BoneBinding = boneBinding.BoneIndex;
                    BodyMesh.TransformedVertices[vertexIndex + 2].Position    = BodyMesh.RealVertices[vertexIndex + 2].Position;

                    BodyMesh.TransformedVertices[vertexIndex].TextureCoordinate     = BodyMesh.RealVertices[vertexIndex].TextureCoordinate;
                    BodyMesh.TransformedVertices[vertexIndex + 1].TextureCoordinate = BodyMesh.RealVertices[vertexIndex + 1].TextureCoordinate;
                    BodyMesh.TransformedVertices[vertexIndex + 2].TextureCoordinate = BodyMesh.RealVertices[vertexIndex + 2].TextureCoordinate;

                    BodyMesh.TransformedVertices[vertexIndex].Normal     = BodyMesh.RealVertices[vertexIndex].Normal;
                    BodyMesh.TransformedVertices[vertexIndex + 1].Normal = BodyMesh.RealVertices[vertexIndex + 1].Normal;
                    BodyMesh.TransformedVertices[vertexIndex + 2].Normal = BodyMesh.RealVertices[vertexIndex + 2].Normal;
                }
            }

            foreach (Bone Child in Bne.Children)
            {
                CopyBodyVertices(Child);
            }
        }
        public void Merge(BoneBinding other)
        {
            if (Position == null)
            {
                Position = other.Position;
            }
            else if (other.Position != null)
            {
                Position.Merge(other.Position);
            }

            if (Rotation == null)
            {
                Rotation = other.Rotation;
            }
            else if (other.Rotation != null)
            {
                Rotation.Merge(other.Rotation);
            }
        }
Exemplo n.º 3
0
        /// <summary>
        /// Transforms all vertices in a given mesh to their correct positions.
        /// </summary>
        /// <param name="Msh">The mesh to transform.</param>
        /// <param name="bone">The bone to transform to.</param>
        private void TransformVertices(Mesh Msh, Bone bone, MeshType MshType)
        {
            switch (MshType)
            {
            case MeshType.Head:
                for (int i = 0; i < Msh.TotalVertexCount; i++)
                {
                    //Transform the head vertices' position by the absolute transform
                    //for the headbone (which is always bone 17) to render the head in place.
                    Msh.TransformedVertices[i].Position = Vector3.Transform(Msh.RealVertices[i].Position,
                                                                            Skel.Bones[Skel.FindBone("HEAD")].AbsoluteMatrix);

                    Msh.TransformedVertices[i].TextureCoordinate = Msh.RealVertices[i].TextureCoordinate;

                    //Transform the head normals' position by the absolute transform
                    //for the headbone (which is always bone 17) to render the head in place.
                    Msh.TransformedVertices[i].Normal = Vector3.Transform(Msh.RealVertices[i].Normal,
                                                                          Skel.Bones[Skel.FindBone("HEAD")].AbsoluteMatrix);
                }

                return;

            case MeshType.Body:
                BoneBinding boneBinding = Msh.BoneBindings.FirstOrDefault(x => Msh.Bones[(int)x.BoneIndex] == bone.Name);

                if (boneBinding != null)
                {
                    for (int i = 0; i < boneBinding.RealVertexCount; i++)
                    {
                        int vertexIndex = (int)boneBinding.FirstRealVertexIndex + i;
                        VertexPositionNormalTexture relativeVertex = Msh.RealVertices[vertexIndex];

                        Matrix translatedMatrix = Matrix.CreateTranslation(new Vector3(relativeVertex.Position.X, relativeVertex.Position.Y, relativeVertex.Position.Z)) * bone.AbsoluteMatrix;
                        Msh.TransformedVertices[vertexIndex].Position = Vector3.Transform(Vector3.Zero, translatedMatrix);

                        Msh.TransformedVertices[vertexIndex].TextureCoordinate = relativeVertex.TextureCoordinate;

                        //Normals...
                        translatedMatrix = Matrix.CreateTranslation(new Vector3(relativeVertex.Normal.X, relativeVertex.Normal.Y, relativeVertex.Normal.Z)) * bone.AbsoluteMatrix;
                        Msh.TransformedVertices[vertexIndex].Normal = Vector3.Transform(Vector3.Zero, translatedMatrix);
                    }
                }

                foreach (var child in bone.Children)
                {
                    TransformVertices(Msh, child, MshType);
                }

                break;

            case MeshType.LHand:
                for (int i = 0; i < Msh.TotalVertexCount; i++)
                {
                    //Transform the left hand vertices' position by the absolute transform
                    //for the left handbone (which is always bone 10) to render the left hand in place.
                    Msh.TransformedVertices[i].Position = Vector3.Transform(Msh.RealVertices[i].Position,
                                                                            Skel.Bones[Skel.FindBone("L_HAND")].AbsoluteMatrix);

                    //Transform the left hand normals' position by the absolute transform
                    //for the left handbone (which is always bone 10) to render the left hand in place.
                    Msh.TransformedVertices[i].Normal = Vector3.Transform(Msh.RealVertices[i].Normal,
                                                                          Skel.Bones[Skel.FindBone("L_HAND")].AbsoluteMatrix);
                }

                return;

            case MeshType.RHand:
                for (int i = 0; i < Msh.TotalVertexCount; i++)
                {
                    //Transform the right hand vertices' position by the absolute transform
                    //for the right handbone (which is always bone 15) to render the right hand in place.
                    Msh.TransformedVertices[i].Position = Vector3.Transform(Msh.RealVertices[i].Position,
                                                                            Skel.Bones[Skel.FindBone("R_HAND")].AbsoluteMatrix);

                    //Transform the right hand normals' position by the absolute transform
                    //for the right handbone (which is always bone 15) to render the right hand in place.
                    Msh.TransformedVertices[i].Normal = Vector3.Transform(Msh.RealVertices[i].Normal,
                                                                          Skel.Bones[Skel.FindBone("R_HAND")].AbsoluteMatrix);
                }

                return;
            }
        }
Exemplo n.º 4
0
        private void ConformMeshBoneBindings(Mesh mesh, Mesh conformToMesh)
        {
            foreach (var conformBone in conformToMesh.BoneBindings)
            {
                BoneBinding inputBone = null;
                foreach (var bone in mesh.BoneBindings)
                {
                    if (bone.BoneName == conformBone.BoneName)
                    {
                        inputBone = bone;
                        break;
                    }
                }

                if (inputBone == null)
                {
                    // Create a new "dummy" binding if it does not exist in the new mesh
                    inputBone = new BoneBinding();
                    inputBone.BoneName = conformBone.BoneName;
                    mesh.BoneBindings.Add(inputBone);
                }

                // The bones match, copy relevant parameters from the conforming binding to the input.
                inputBone.OBBMin = conformBone.OBBMin;
                inputBone.OBBMax = conformBone.OBBMax;
            }
        }
Exemplo n.º 5
0
        private void GenerateDummySkeleton(Root root)
        {
            foreach (var model in root.Models)
            {
                if (model.Skeleton == null)
                {
                    Utils.Info(String.Format("Generating dummy skeleton for model '{0}'", model.Name));
                    var skeleton = new Skeleton();
                    skeleton.Name = model.Name;
                    skeleton.LODType = 0;
                    skeleton.IsDummy = true;
                    root.Skeletons.Add(skeleton);

                    var bone = new Bone();
                    bone.Name = model.Name;
                    bone.ParentIndex = -1;
                    skeleton.Bones = new List<Bone> { bone };
                    bone.Transform = new Transform();

                    // TODO: Transform / IWT is not always identity on dummy bones!
                    skeleton.UpdateInverseWorldTransforms();
                    model.Skeleton = skeleton;

                    foreach (var mesh in model.MeshBindings)
                    {
                        if (mesh.Mesh.BoneBindings != null && mesh.Mesh.BoneBindings.Count > 0)
                        {
                            throw new ParsingException("Failed to generate dummy skeleton: Mesh already has bone bindings.");
                        }

                        var binding = new BoneBinding();
                        binding.BoneName = bone.Name;
                        // TODO: Calculate bounding box!
                        binding.OBBMin = new float[] { -10, -10, -10 };
                        binding.OBBMax = new float[] { 10, 10, 10 };
                        mesh.Mesh.BoneBindings = new List<BoneBinding> { binding };
                    }
                }
            }
        }