Get vertices of each edge on mesh and separate by groups like vector3

Hi all

For some time I’m trying to achieve to get all the vertices of a mesh edge and separate by groups, but I’m not good with scripting, my knowledge is out of working with classes and static members.

I manage not to run this script, I need help to achieve this:

using UnityEngine;
using System.Collections;

public class GetEdges1 : MonoBehaviour {
   
   
    /// Builds an array of edges that connect to only one triangle.
    /// In other words, the outline of the mesh    
    public static Edge[] BuildManifoldEdges(Mesh mesh)
    {
        // Build a edge list for all unique edges in the mesh
        Edge[] edges = BuildEdges(mesh.vertexCount, mesh.triangles);
       
        // We only want edges that connect to a single triangle
        ArrayList culledEdges = new ArrayList();
        foreach (Edge edge in edges)
        {
            if (edge.faceIndex[0] == edge.faceIndex[1])
            {
                culledEdges.Add(edge);
            }
        }
       
        return culledEdges.ToArray(typeof(Edge)) as Edge[];
    }
   
    /// Builds an array of unique edges
    /// This requires that your mesh has all vertices welded. However on import, Unity has to split
    /// vertices at uv seams and normal seams. Thus for a mesh with seams in your mesh you
    /// will get two edges adjoining one triangle.
    /// Often this is not a problem but you can fix it by welding vertices 
    /// and passing in the triangle array of the welded vertices.
    public static Edge[] BuildEdges(int vertexCount, int[] triangleArray)
    {
        int maxEdgeCount = triangleArray.Length;
        int[] firstEdge = new int[vertexCount + maxEdgeCount];
        int nextEdge = vertexCount;
        int triangleCount = triangleArray.Length / 3;
       
        for (int a = 0; a < vertexCount; a++)
            firstEdge[a] = -1;
       
        // First pass over all triangles. This finds all the edges satisfying the
        // condition that the first vertex index is less than the second vertex index
        // when the direction from the first vertex to the second vertex represents
        // a counterclockwise winding around the triangle to which the edge belongs.
        // For each edge found, the edge index is stored in a linked list of edges
        // belonging to the lower-numbered vertex index i. This allows us to quickly
        // find an edge in the second pass whose higher-numbered vertex index is i.
        Edge[] edgeArray = new Edge[maxEdgeCount];
       
        int edgeCount = 0;
        for (int a = 0; a < triangleCount; a++)
        {
            int i1 = triangleArray[a * 3 + 2];
            for (int b = 0; b < 3; b++)
            {
                int i2 = triangleArray[a * 3 + b];
                if (i1 < i2)
                {
                    Edge newEdge = new Edge();
                    newEdge.vertexIndex[0] = i1;
                    newEdge.vertexIndex[1] = i2;
                    newEdge.faceIndex[0] = a;
                    newEdge.faceIndex[1] = a;
                    edgeArray[edgeCount] = newEdge;
                   
                    int edgeIndex = firstEdge[i1];
                    if (edgeIndex == -1)
                    {
                        firstEdge[i1] = edgeCount;
                    }
                    else
                    {
                        while (true)
                        {
                            int index = firstEdge[nextEdge + edgeIndex];
                            if (index == -1)
                            {
                                firstEdge[nextEdge + edgeIndex] = edgeCount;
                                break;
                            }
                           
                            edgeIndex = index;
                        }
                    }
                   
                    firstEdge[nextEdge + edgeCount] = -1;
                    edgeCount++;
                }
               
                i1 = i2;
            }
        }
       
        // Second pass over all triangles. This finds all the edges satisfying the
        // condition that the first vertex index is greater than the second vertex index
        // when the direction from the first vertex to the second vertex represents
        // a counterclockwise winding around the triangle to which the edge belongs.
        // For each of these edges, the same edge should have already been found in
        // the first pass for a different triangle. Of course we might have edges with only one triangle
        // in that case we just add the edge here
        // So we search the list of edges
        // for the higher-numbered vertex index for the matching edge and fill in the
        // second triangle index. The maximum number of comparisons in this search for
        // any vertex is the number of edges having that vertex as an endpoint.
       
        for (int a = 0; a < triangleCount; a++)
        {
            int i1 = triangleArray[a * 3 + 2];
            for (int b = 0; b < 3; b++)
            {
                int i2 = triangleArray[a * 3 + b];
                if (i1 > i2)
                {
                    bool foundEdge = false;
                    for (int edgeIndex = firstEdge[i2]; edgeIndex != -1; edgeIndex = firstEdge[nextEdge + edgeIndex])
                    {
                        Edge edge = edgeArray[edgeIndex];
                        if ((edge.vertexIndex[1] == i1) && (edge.faceIndex[0] == edge.faceIndex[1]))
                        {
                            edgeArray[edgeIndex].faceIndex[1] = a;
                            foundEdge = true;
                            break;
                        }
                    }
                   
                    if (!foundEdge)
                    {
                        Edge newEdge = new Edge();
                        newEdge.vertexIndex[0] = i1;
                        newEdge.vertexIndex[1] = i2;
                        newEdge.faceIndex[0] = a;
                        newEdge.faceIndex[1] = a;
                        edgeArray[edgeCount] = newEdge;
                        edgeCount++;
                    }
                }
               
                i1 = i2;
            }
        }
       
        Edge[] compactedEdges = new Edge[edgeCount];
        for (int e = 0; e < edgeCount; e++)
            compactedEdges[e] = edgeArray[e];
       
        /*for (int i = 0; i < compactedEdges.Length; i++)
        {
            //print(i + ": " + edges[i].v1 + ", " + edges[i].v2);
            Debug.DrawLine(compactedEdges[i].vertexIndex, compactedEdges[i].faceIndex[i], Color.yellow);
        }*/
       
        return compactedEdges;
    }
   
   
    public class Edge
    {
        // The indiex to each vertex
        public int[] vertexIndex = new int[2];
        // The index into the face.
        // (faceindex[0] == faceindex[1] means the edge connects to only one triangle)
        public int[] faceIndex = new int[2];
    }

}

Here a detail of the process I think it can be

1 - get all the triangles that have near normal Vector3.Up, it may be something like this

if (Vector3.Angle(Vector3.up, mesh.normals[i]) > 20){
   // Not included in the list of triangles
}

2 - determine all edges of the mesh and separate groups without selecting the internal vertices, In the image selected triangles are blue.

other case

3 - save each group of vertices as vectors in an array, but ordered, no matter where Begin or in which direction. Maybe ArrayList of groups of vertices.

People, I need help, i tried but I failed.

I started getting the coordinates of the vertices forming the edge of the boundary, instantiating a cube at each vertex and this is what I get.

1727119--108925--Sin título.jpg

Assumes that hubs should be created along the red line, but it is not.

that’s what I’m doing wrong?
this is what I’m using

using UnityEngine;
using System.Collections;

public class PointsCreator : MonoBehaviour {

    //compactedEdges.vertexIndex[1] == i1) && (edge.faceIndex[0]
    private Mesh mesh;
    private GetEdges1.Edge[] edgesz;
    public Transform prefab;
    private Vector3[]groupA;

    void Start() {
            Debug.Log("Start");
            mesh = this.GetComponent<MeshFilter>().mesh;
            edgesz = GetEdges1.BuildManifoldEdges(mesh);
            groupA = new Vector3[edgesz.Length];
   
        print("edgesz: " + edgesz.Length);
        for (int i = 0; i < edgesz.Length; i++) {
                Vector3 punto = mesh.vertices[mesh.triangles[edgesz[i].faceIndex[0]]];
                //Debug.Log(punto);
                groupA[i] = punto;
            }

        int f = 0;
        while (f < groupA.Length) {
            Transform clone = Instantiate(prefab, groupA[f], Quaternion.identity) as Transform;
            f++;
        }
        Debug.Log("Finish");
    }
}