Esempio n. 1
0
        /// <summary>
        /// Stolen from MeshBuilder class, maybe make this static method there public...
        /// </summary>
        /// <param name="positions"></param>
        /// <param name="triangleIndices"></param>
        /// <param name="normals"></param>
        private static void ComputeNormals(Vector3Collection positions, IntCollection triangleIndices, out Vector3Collection normals)
        {
            normals = new Vector3Collection(positions.Count);
            normals.AddRange(Enumerable.Repeat(Vector3.Zero, positions.Count));

            for (int t = 0; t < triangleIndices.Count; t += 3)
            {
                var i1 = triangleIndices[t];
                var i2 = triangleIndices[t + 1];
                var i3 = triangleIndices[t + 2];

                var v1 = positions[i1];
                var v2 = positions[i2];
                var v3 = positions[i3];

                var p1 = v2 - v1;
                var p2 = v3 - v1;
                var n  = Vector3.Cross(p1, p2);
                // angle
                p1.Normalize();
                p2.Normalize();
                var a = (float)Math.Acos(Vector3.Dot(p1, p2));
                n.Normalize();
                normals[i1] += (a * n);
                normals[i2] += (a * n);
                normals[i3] += (a * n);
            }

            for (int i = 0; i < normals.Count; i++)
            {
                var n = normals[i];
                n.Normalize();
                normals[i] = n;
            }
        }
Esempio n. 2
0
        public static MeshGeometry3D Merge(params MeshGeometry3D[] meshes)
        {
            var positions = new Vector3Collection();
            var indices   = new IntCollection();

            var normals      = meshes.All(x => x.Normals != null) ? new Vector3Collection() : null;
            var colors       = meshes.All(x => x.Colors != null) ? new Color4Collection() : null;
            var textureCoods = meshes.All(x => x.TextureCoordinates != null) ? new Vector2Collection() : null;
            var tangents     = meshes.All(x => x.Tangents != null) ? new Vector3Collection() : null;
            var bitangents   = meshes.All(x => x.BiTangents != null) ? new Vector3Collection() : null;

            int index = 0;

            foreach (var part in meshes)
            {
                positions.AddRange(part.Positions);
                indices.AddRange(part.Indices.Select(x => x + index));
                index += part.Positions.Count;
            }

            if (normals != null)
            {
                normals = new Vector3Collection(meshes.SelectMany(x => x.Normals));
            }

            if (colors != null)
            {
                colors = new Color4Collection(meshes.SelectMany(x => x.Colors));
            }

            if (textureCoods != null)
            {
                textureCoods = new Vector2Collection(meshes.SelectMany(x => x.TextureCoordinates));
            }

            if (tangents != null)
            {
                tangents = new Vector3Collection(meshes.SelectMany(x => x.Tangents));
            }

            if (bitangents != null)
            {
                bitangents = new Vector3Collection(meshes.SelectMany(x => x.BiTangents));
            }

            var mesh = new MeshGeometry3D()
            {
                Positions = positions,
                Indices   = indices,
            };

            mesh.Normals            = normals;
            mesh.Colors             = colors;
            mesh.TextureCoordinates = textureCoods;
            mesh.Tangents           = tangents;
            mesh.BiTangents         = bitangents;

            return(mesh);
        }
        public static BoneSkinnedMeshGeometry3D CreateSkeletonMesh(IList <Animations.Bone> bones, float scale = 1f)
        {
            var builder = new MeshBuilder(true, false);

            builder.AddPyramid(new Vector3(0, scale / 2, 0), Vector3.UnitZ, Vector3.UnitY, scale, 0, true);
            var singleBone = builder.ToMesh();
            var boneIds    = new List <BoneIds>();
            var positions  = new Vector3Collection(bones.Count * singleBone.Positions.Count);
            var tris       = new IntCollection(bones.Count * singleBone.Indices.Count);

            int offset = 0;

            for (int i = 0; i < bones.Count; ++i)
            {
                if (bones[i].ParentIndex >= 0)
                {
                    int currPos = positions.Count;
                    tris.AddRange(singleBone.Indices.Select(x => x + offset));
                    int j = 0;
                    for (; j < singleBone.Positions.Count - 6; j += 3)
                    {
                        positions.Add(Vector3.TransformCoordinate(singleBone.Positions[j], bones[bones[i].ParentIndex].BindPose));
                        positions.Add(Vector3.TransformCoordinate(singleBone.Positions[j + 1], bones[bones[i].ParentIndex].BindPose));
                        positions.Add(bones[i].BindPose.TranslationVector);
                        boneIds.Add(new BoneIds()
                        {
                            Bone1 = bones[i].ParentIndex, Weights = new Vector4(1, 0, 0, 0)
                        });
                        boneIds.Add(new BoneIds()
                        {
                            Bone1 = bones[i].ParentIndex, Weights = new Vector4(1, 0, 0, 0)
                        });
                        boneIds.Add(new BoneIds()
                        {
                            Bone1 = i, Weights = new Vector4(1, 0, 0, 0)
                        });
                    }
                    for (; j < singleBone.Positions.Count; ++j)
                    {
                        positions.Add(Vector3.TransformCoordinate(singleBone.Positions[j], bones[bones[i].ParentIndex].BindPose));
                        boneIds.Add(new BoneIds()
                        {
                            Bone1 = bones[i].ParentIndex, Weights = new Vector4(1, 0, 0, 0)
                        });
                    }
                    offset += singleBone.Positions.Count;
                }
            }

            builder = new MeshBuilder(true, false);
            for (int i = 0; i < bones.Count; ++i)
            {
                int currPos = builder.Positions.Count;
                builder.AddSphere(Vector3.Zero, scale / 2, 12, 12);
                for (int j = currPos; j < builder.Positions.Count; ++j)
                {
                    builder.Positions[j] = Vector3.TransformCoordinate(builder.Positions[j], bones[i].BindPose);
                    boneIds.Add(new BoneIds()
                    {
                        Bone1 = i, Weights = new Vector4(1, 0, 0, 0)
                    });
                }
            }
            positions.AddRange(builder.Positions);
            tris.AddRange(builder.TriangleIndices.Select(x => x + offset));
            var mesh = new BoneSkinnedMeshGeometry3D()
            {
                Positions = positions, Indices = tris, VertexBoneIds = boneIds
            };

            mesh.Normals = mesh.CalculateNormals();
            return(mesh);
        }
Esempio n. 4
0
        private static void ComputeNormals(Vector3Collection positions, IntCollection triangleIndices, out Vector3Collection normals)
        {
            normals = new Vector3Collection(positions.Count);
            normals.AddRange(Enumerable.Repeat(Vector3.Zero, positions.Count));

            for (int t = 0; t < triangleIndices.Count; t += 3)
            {
                var i1 = triangleIndices[t];
                var i2 = triangleIndices[t + 1];
                var i3 = triangleIndices[t + 2];

                var v1 = positions[i1];
                var v2 = positions[i2];
                var v3 = positions[i3];

                var p1 = v2 - v1;
                var p2 = v3 - v1;
                var n = Vector3.Cross(p1, p2);
                // angle
                p1.Normalize();
                p2.Normalize();
                var a = (float)Math.Acos(Vector3.Dot(p1, p2));
                n.Normalize();
                normals[i1] += (a * n);
                normals[i2] += (a * n);
                normals[i3] += (a * n);
            }

            for (int i = 0; i < normals.Count; i++)
            {
                normals[i].Normalize();
            }
        }