예제 #1
0
 public static void SetUpVertexNormal(TriMesh mesh, EnumNormal type)
 {
     Vector3D[] normal = TriMeshUtil.ComputeNormalVertex(mesh, type);
     for (int i = 0; i < mesh.Vertices.Count; i++)
     {
         mesh.Vertices[i].Traits.Normal = normal[i];
     }
 }
예제 #2
0
 public void MappingGauss(TriMesh mesh)
 {
     for (int i = 0; i < mesh.Vertices.Count; i++)
     {
         Vector3D[] normals = TriMeshUtil.ComputeNormalVertex(mesh, EnumNormal.SphereInscribed);
         mesh.Vertices[i].Traits.Position = normals[i];
     }
     TriMeshUtil.SetUpNormalVertex(mesh);
 }
예제 #3
0
        public static PrincipalCurvature[] ComputePrincipleCurvatures(TriMesh mesh, double[] CornerArea, double[] PointArea)
        {
            Vector3D[] vertexNormal = TriMeshUtil.ComputeNormalVertex(mesh);

            // Add dynamic trait for principle curvature computation
            double[]             curv = new double[mesh.Vertices.Count];
            PrincipalCurvature[] pc   = new PrincipalCurvature[mesh.Vertices.Count];

            // Initialize a coordinate system for each vertex
            foreach (TriMesh.Vertex v in mesh.Vertices)
            {
                pc[v.Index] = new PrincipalCurvature();
                // Vector that points from this vertex to an adjacent one
                pc[v.Index].maxDir = (v.HalfEdge.ToVertex.Traits.Position - v.Traits.Position).Cross(vertexNormal[v.Index]).Normalize();
                // Get a vector orthogonal to this vector and the vertex normal
                pc[v.Index].minDir = vertexNormal[v.Index].Cross(pc[v.Index].maxDir);
            }

            TriMesh.HalfEdge[] fh = new TriMesh.HalfEdge[3];
            TriMesh.Vertex[]   fv = new TriMesh.Vertex[3];
            Vector3D[]         e = new Vector3D[3];
            Vector3D           t, b, dn, faceNormal;

            // Compute curvature for each face
            foreach (TriMesh.Face f in mesh.Faces)
            {
                // Get halfedges for this face
                fh[0] = f.HalfEdge;
                fh[1] = fh[0].Next;
                fh[2] = fh[1].Next;

                // Get vertices for this face
                fv[0] = fh[0].ToVertex;
                fv[1] = fh[1].ToVertex;
                fv[2] = fh[2].ToVertex;

                // Edge vectors
                e[0] = fv[2].Traits.Position - fv[1].Traits.Position;
                e[1] = fv[0].Traits.Position - fv[2].Traits.Position;
                e[2] = fv[1].Traits.Position - fv[0].Traits.Position;

                t = e[0];
                t.Normalize();

                faceNormal = e[0].Cross(e[1]);
                faceNormal.Normalize();

                b = faceNormal.Cross(t);
                b.Normalize();

                // Estimate curvature by variation of normals along edges
                double[] m = new double[3];
                double[,] w = new double[3, 3];

                for (int i = 0; i < 3; ++i)
                {
                    double u = e[i].Dot(t);
                    double v = e[i].Dot(b);

                    w[0, 0] += u * u;
                    w[0, 1] += u * v;
                    w[2, 2] += v * v;

                    dn = vertexNormal[fv[(i + 2) % 3].Index] - vertexNormal[fv[(i + 1) % 3].Index];

                    double dnu = dn.Dot(t);
                    double dnv = dn.Dot(b);

                    m[0] += dnu * u;
                    m[1] += dnu * v + dnv * u;
                    m[2] += dnv * v;
                }

                w[1, 1] = w[0, 0] + w[2, 2];
                w[1, 2] = w[0, 1];

                // Least squares solution
                double[] diag = new double[3];
                if (Transform.LdlTransposeDecomp(w, diag))
                {
                    Transform.LdlTransposeSolveInPlace(w, diag, m);

                    // Adjust curvature for vertices of this face
                    for (int i = 0; i < 3; ++i)
                    {
                        UV tb = new UV {
                            U = t, V = b
                        };
                        KUV mk = new KUV {
                            U = m[0], UV = m[1], V = m[2]
                        };
                        UV dst = new UV {
                            U = pc[fv[i].Index].maxDir, V = pc[fv[i].Index].minDir
                        };
                        KUV c = Transform.ProjectCurvature(tb, mk, dst);

                        double weight = CornerArea[fh[i].Index] / PointArea[fv[i].Index];
                        pc[fv[i].Index].max += weight * c.U;
                        curv[fv[i].Index]   += weight * c.UV;
                        pc[fv[i].Index].min += weight * c.V;
                    }
                }
            }

            // Compute curvature for each vertex
            foreach (TriMesh.Vertex v in mesh.Vertices)
            {
                UV src = new UV {
                    U = pc[v.Index].maxDir, V = pc[v.Index].minDir
                };
                KUV srcK = new KUV {
                    U = pc[v.Index].max, UV = curv[v.Index], V = pc[v.Index].min
                };
                pc[v.Index] = Transform.DiagonalizeCurvature(src, srcK, vertexNormal[v.Index]);
            }

            return(pc);
        }