Пример #1
0
 public DCELHalfEdge2D(DCELVertex2D origin, DCELFace2D face, DCELHalfEdge2D twin, DCELHalfEdge2D next)
 {
     Origin = origin;
     Face   = face;
     Twin   = twin;
     Next   = next;
 }
Пример #2
0
        /// <summary>
        /// Verifica se la faccia è convessa. Un poligono semplice è strettamente convesso se ogni
        /// angolo interno è strettamente inferiore a 180 gradi.
        /// </summary>
        /// <returns>True se la faccia è convessa, false altrimenti.</returns>

        public bool IsConvex()
        {
            DCELHalfEdge2D he    = this.Edge;
            DCELHalfEdge2D prev  = he.Previous();
            DCELVertex2D   first = he.Origin;

            do
            {
                Vector v1 = new Vector(
                    prev.Origin.Coordinates.X - he.Origin.Coordinates.X,
                    prev.Origin.Coordinates.Y - he.Origin.Coordinates.Y);

                Vector v2 = new Vector(
                    he.Next.Origin.Coordinates.X - he.Origin.Coordinates.X,
                    he.Next.Origin.Coordinates.Y - he.Origin.Coordinates.Y);

                double dotProduct = (v1.X * v2.X + v1.Y * v2.Y);
                double norm1      = Math.Sqrt(Math.Pow(v1.X, 2) + Math.Pow(v1.Y, 2));
                double norm2      = Math.Sqrt(Math.Pow(v2.X, 2) + Math.Pow(v2.Y, 2));
                double angle      = (Math.Acos(dotProduct / (norm1 * norm2)) * 180) / Math.PI;

                if (angle > 180)
                {
                    return(false);
                }

                prev = he;
                he   = he.Next;
            }while (he.Origin != first);

            //returns true if every internal angle is less than or equal to 180 degrees
            return(true);
        }
Пример #3
0
        public bool AddVertex(DCELVertex2D vertex)
        {
            vertexList.Add(vertex);
            vertexCount++;

            return(true);
        }
Пример #4
0
 public bool RemoveVertex(DCELVertex2D vertex)
 {
     if (vertexList.Remove(vertex))
     {
         vertexCount--;
         return(true);
     }
     return(false);
 }
Пример #5
0
        /// <summary>
        /// Restituisce i lati della faccia.
        /// </summary>
        /// <returns>DCELHalfEdge collection.</returns>
        public IEnumerable <DCELHalfEdge2D> Sides()
        {
            DCELHalfEdge2D he    = this.Edge;
            DCELVertex2D   first = he.Origin;

            do
            {
                yield return(he);

                he = he.Next;
            }while (he.Origin != first);
        }
Пример #6
0
        public static IEnumerable <DCELHalfEdge2D> LeavingEdges(DCELMesh2D mesh, DCELVertex2D vertex, QueryExecutionMode executionMode)
        {
            var query = mesh.HalfEdgeList.AsEnumerable();

            switch (executionMode)
            {
            case QueryExecutionMode.Default:
                query = query.Where(x => x.Origin == vertex);
                break;

            case QueryExecutionMode.AsParallel:
                query = query.AsParallel().Where(x => x.Origin == vertex);
                break;

            case QueryExecutionMode.ForEachLoop:
                foreach (var leavingEdge in mesh.HalfEdgeList)
                {
                    if (leavingEdge.Origin == vertex)
                    {
                        yield return(leavingEdge);
                    }
                }
                yield break;

            case QueryExecutionMode.ForLoop:
                for (int i = 0; i < mesh.HalfEdgeCount; i++)
                {
                    if (mesh.HalfEdgeList[i].Origin == vertex)
                    {
                        yield return(mesh.HalfEdgeList[i]);
                    }
                }
                yield break;

            case QueryExecutionMode.ForWithAssignment:
                int n = mesh.HalfEdgeCount;
                for (int i = 0; i < n; i++)
                {
                    if (mesh.HalfEdgeList[i].Origin == vertex)
                    {
                        yield return(mesh.HalfEdgeList[i]);
                    }
                }
                yield break;
            }

            foreach (var leavingEdge in query)
            {
                yield return(leavingEdge);
            }
        }
Пример #7
0
        public bool TriangulateFace(DCELFace2D face)
        {
            //lista di appoggio
            List <DCELHalfEdge2D> edges = face.Sides().ToList();
            //sides è il numero di lati della faccia
            int sides = edges.Count;
            //first è il vertice a partire dal quale viene suddiviso il poligono
            DCELVertex2D first = edges[0].Origin;

            //se la faccia non esiste o se esiste ma ha meno di 4 lati o non è convessa restituisco false
            //if (sides <= 3 || !this.Contains(face) || !face.IsConvex())
            //    return false;

            for (int i = 0; i < sides; i++)
            {
                if (i == 0)
                {
                    this.AddFace(new DCELFace2D(edges[i]));
                    edges[i].Face = faceList[FaceCount - 1];
                    i++;
                    edges[i].Face = faceList[FaceCount - 1];
                    this.AddHalfEdge(new DCELHalfEdge2D(edges[i].Next.Origin, faceList[FaceCount - 1], null, edges[0]));
                    edges[i].Next = edgeList[HalfEdgeCount - 1];
                }
                else if (i == sides - 2)
                {
                    this.AddFace(new DCELFace2D(null));
                    this.AddHalfEdge(new DCELHalfEdge2D(first, faceList[FaceCount - 1], edgeList[HalfEdgeCount - 1], edges[i]));
                    edges[i].Face = faceList[FaceCount - 1];
                    i++;
                    edges[i].Face = faceList[FaceCount - 1];
                    edgeList[HalfEdgeCount - 2].Twin = edgeList[HalfEdgeCount - 1];
                    faceList[FaceCount - 1].Edge     = edgeList[HalfEdgeCount - 1];
                    edges[i].Next = edgeList[HalfEdgeCount - 1];
                }
                else
                {
                    this.AddFace(new DCELFace2D(null));
                    this.AddHalfEdge(new DCELHalfEdge2D(first, faceList[FaceCount - 1], edgeList[HalfEdgeCount - 1], edges[i]));
                    faceList[FaceCount - 1].Edge = edgeList[HalfEdgeCount - 1];
                    edges[i].Face = faceList[FaceCount - 1];
                    edgeList[HalfEdgeCount - 2].Twin = edgeList[HalfEdgeCount - 1];
                    this.AddHalfEdge(new DCELHalfEdge2D(edges[i].Next.Origin, faceList[faceCount - 1], null, edgeList[HalfEdgeCount - 1]));
                    edges[i].Next = edgeList[HalfEdgeCount - 1];
                }
            }
            //ora è possibile rimuovere la faccia dalla lista
            return(RemoveFace(face));
        }
Пример #8
0
        /// <summary>
        /// Restituisce tutte le facce confinanti.
        /// </summary>
        /// <returns>DCELFace collection.</returns>
        public IEnumerable <DCELFace2D> Neighbours()
        {
            DCELHalfEdge2D he    = this.Edge;
            DCELVertex2D   first = he.Origin;

            do
            {
                if (he.Twin != null)
                {
                    if (!he.Twin.Face.IsInfinite())
                    {
                        yield return(he.Twin.Face);
                    }
                }
                he = he.Next;
            }while (he.Origin != first);
        }
Пример #9
0
 public bool Contains(DCELVertex2D vertex)
 {
     return(vertexList.Contains(vertex));
 }