diff --git a/Triangle.NET/TestApp/Generators/RingPolygon.cs b/Triangle.NET/TestApp/Generators/RingPolygon.cs
index 86386be..08ded0a 100644
--- a/Triangle.NET/TestApp/Generators/RingPolygon.cs
+++ b/Triangle.NET/TestApp/Generators/RingPolygon.cs
@@ -7,6 +7,7 @@
namespace MeshExplorer.Generators
{
using System;
+ using System.Collections.Generic;
using TriangleNet.Geometry;
///
@@ -54,15 +55,19 @@ namespace MeshExplorer.Generators
double ro, r = 10;
double step = 2 * Math.PI / m;
+ var inner = new List(m);
+
// Inner ring
for (int i = 0; i < m; i++)
{
- input.Add(new Vertex(r * Math.Cos(i * step), r * Math.Sin(i * step)));
- input.Add(new Edge(i, (i + 1) % m, 1));
+ inner.Add(new Vertex(r * Math.Cos(i * step), r * Math.Sin(i * step)));
}
+ input.AddContour(inner, 1);
+
r = 1.5 * r;
+ var outer = new List(n);
step = 2 * Math.PI / n;
double offset = step / 2;
@@ -77,10 +82,11 @@ namespace MeshExplorer.Generators
ro = r + r * Util.Random.NextDouble() * (param1 / 100);
}
- input.Add(new Vertex(ro * Math.Cos(i * step + offset), ro * Math.Sin(i * step + offset)));
- input.Add(new Edge(m + i, m + ((i + 1) % n), 2));
+ outer.Add(new Vertex(ro * Math.Cos(i * step + offset), ro * Math.Sin(i * step + offset)));
}
+ input.AddContour(outer, 2);
+
input.Holes.Add(new Point(0, 0));
return input;
diff --git a/Triangle.NET/TestApp/Generators/StarInBox.cs b/Triangle.NET/TestApp/Generators/StarInBox.cs
index 9bd2e4a..b35c68b 100644
--- a/Triangle.NET/TestApp/Generators/StarInBox.cs
+++ b/Triangle.NET/TestApp/Generators/StarInBox.cs
@@ -29,9 +29,9 @@ namespace MeshExplorer.Generators
{
int numRays = GetParamValueInt(0, param0);
- var input = new Polygon(numRays + 4);
+ var g = new Polygon(numRays + 4);
- input.Add(new Vertex(0, 0)); // Center
+ g.Add(new Vertex(0, 0)); // Center
double x, y, r, e, step = 2 * Math.PI / numRays;
@@ -42,22 +42,22 @@ namespace MeshExplorer.Generators
x = r * Math.Cos(i * step + e);
y = r * Math.Sin(i * step + e);
- input.Add(new Vertex(x, y, 2));
- input.Add(new Edge(0, i + 1, 2));
+ g.Add(new Vertex(x, y, 2));
+ g.Add(new Segment(g.Points[0], g.Points[i + 1], 2));
}
- input.Add(new Vertex(-1, -1, 1)); // Box
- input.Add(new Vertex(1, -1, 1));
- input.Add(new Vertex(1, 1, 1));
- input.Add(new Vertex(-1, 1, 1));
+ g.Add(new Vertex(-1, -1, 1)); // Box
+ g.Add(new Vertex(1, -1, 1));
+ g.Add(new Vertex(1, 1, 1));
+ g.Add(new Vertex(-1, 1, 1));
- numRays = input.Count;
- input.Add(new Edge(numRays - 1, numRays - 2, 1));
- input.Add(new Edge(numRays - 2, numRays - 3, 1));
- input.Add(new Edge(numRays - 3, numRays - 4, 1));
- input.Add(new Edge(numRays - 4, numRays - 1, 1));
+ numRays = g.Count;
+ g.Add(new Segment(g.Points[numRays - 1], g.Points[numRays - 2], 1));
+ g.Add(new Segment(g.Points[numRays - 2], g.Points[numRays - 3], 1));
+ g.Add(new Segment(g.Points[numRays - 3], g.Points[numRays - 4], 1));
+ g.Add(new Segment(g.Points[numRays - 4], g.Points[numRays - 1], 1));
- return input;
+ return g;
}
}
}
diff --git a/Triangle.NET/TestApp/IO/Formats/JsonFile.cs b/Triangle.NET/TestApp/IO/Formats/JsonFile.cs
index 3891e7e..1c11dfe 100644
--- a/Triangle.NET/TestApp/IO/Formats/JsonFile.cs
+++ b/Triangle.NET/TestApp/IO/Formats/JsonFile.cs
@@ -154,7 +154,7 @@ namespace MeshExplorer.IO.Formats
}
}
- public void Write(IMesh mesh, StreamWriter stream)
+ public void Write(IMesh mesh, Stream stream)
{
throw new NotImplementedException();
}
@@ -226,7 +226,7 @@ namespace MeshExplorer.IO.Formats
throw new NotImplementedException();
}
- public void Write(IPolygon polygon, StreamWriter stream)
+ public void Write(IPolygon polygon, Stream stream)
{
throw new NotImplementedException();
}
@@ -315,6 +315,9 @@ namespace MeshExplorer.IO.Formats
int p0, p1;
+ throw new NotImplementedException();
+ // TODO: Fix JSON format
+
for (int i = 0; i < n; i += 2)
{
mark = 0;
@@ -332,7 +335,7 @@ namespace MeshExplorer.IO.Formats
throw new Exception("JSON format error (segment index).");
}
- geometry.Add(new Edge(p0, p1, mark));
+ //geometry.Add(new Edge(p0, p1, mark));
}
}
}
@@ -497,7 +500,7 @@ namespace MeshExplorer.IO.Formats
writer.Write("]");
}
- private void WriteSegments(IEnumerable data, StreamWriter writer, int ns)
+ private void WriteSegments(IEnumerable data, StreamWriter writer, int ns)
{
int i = 0;
diff --git a/Triangle.NET/TestApp/IO/Formats/TriangleFile.cs b/Triangle.NET/TestApp/IO/Formats/TriangleFile.cs
index 5b3c622..ae60afa 100644
--- a/Triangle.NET/TestApp/IO/Formats/TriangleFile.cs
+++ b/Triangle.NET/TestApp/IO/Formats/TriangleFile.cs
@@ -57,7 +57,7 @@ namespace MeshExplorer.IO.Formats
format.Write(polygon, filename);
}
- public void Write(IPolygon polygon, StreamWriter stream)
+ public void Write(IPolygon polygon, Stream stream)
{
format.Write(polygon, stream);
}
@@ -75,7 +75,7 @@ namespace MeshExplorer.IO.Formats
}
}
- public void Write(IMesh mesh, StreamWriter stream)
+ public void Write(IMesh mesh, Stream stream)
{
format.Write(mesh, stream);
}
diff --git a/Triangle.NET/Triangle.Rendering/ColorManager.cs b/Triangle.NET/Triangle.Rendering/ColorManager.cs
index ba37f33..713e9b9 100644
--- a/Triangle.NET/Triangle.Rendering/ColorManager.cs
+++ b/Triangle.NET/Triangle.Rendering/ColorManager.cs
@@ -145,7 +145,7 @@ namespace TriangleNet.Rendering
}
}
- internal void Dispose(Dictionary brushes)
+ internal void Dispose(Dictionary brushes)
{
foreach (var brush in brushes.Values)
{
@@ -153,9 +153,9 @@ namespace TriangleNet.Rendering
}
}
- internal Dictionary GetBrushDictionary()
+ internal Dictionary GetBrushDictionary()
{
- var brushes = new Dictionary();
+ var brushes = new Dictionary();
foreach (var item in ColorDictionary)
{
diff --git a/Triangle.NET/Triangle.Rendering/GDI/MeshRenderer.cs b/Triangle.NET/Triangle.Rendering/GDI/MeshRenderer.cs
index e8d4348..38c3614 100644
--- a/Triangle.NET/Triangle.Rendering/GDI/MeshRenderer.cs
+++ b/Triangle.NET/Triangle.Rendering/GDI/MeshRenderer.cs
@@ -115,7 +115,12 @@ namespace TriangleNet.Rendering.GDI
if (filled)
{
- g.FillPolygon(brushes[partition[i]], tri);
+ var b = brushes[partition[i]];
+
+ if (b.Color.A > 0)
+ {
+ g.FillPolygon(b, tri);
+ }
}
else
{
diff --git a/Triangle.NET/Triangle.Rendering/RenderContext.cs b/Triangle.NET/Triangle.Rendering/RenderContext.cs
index b16bea4..0daa90c 100644
--- a/Triangle.NET/Triangle.Rendering/RenderContext.cs
+++ b/Triangle.NET/Triangle.Rendering/RenderContext.cs
@@ -80,6 +80,14 @@ namespace TriangleNet.Rendering
// Always clear voronoi layer.
RenderLayers[4].Reset(true);
+ int i = 0;
+
+ // Ensure linear numbering of polygon vertices.
+ foreach (var p in data.Points)
+ {
+ p.ID = i++;
+ }
+
this.bounds = RenderLayers[2].SetPoints(data);
this.zoom.Initialize(bounds);
diff --git a/Triangle.NET/Triangle/Geometry/Contour.cs b/Triangle.NET/Triangle/Geometry/Contour.cs
new file mode 100644
index 0000000..7ddb23d
--- /dev/null
+++ b/Triangle.NET/Triangle/Geometry/Contour.cs
@@ -0,0 +1,166 @@
+// -----------------------------------------------------------------------
+//
+// Triangle.NET code by Christian Woltering, http://triangle.codeplex.com/
+//
+// -----------------------------------------------------------------------
+
+namespace TriangleNet.Geometry
+{
+ using System;
+ using System.Collections.Generic;
+
+ public class Contour
+ {
+ int marker;
+
+ public List Points { get; set; }
+
+ ///
+ /// Initializes a new instance of the class.
+ ///
+ public Contour(IEnumerable points, int marker)
+ {
+ this.Points = new List(points);
+
+ int count = Points.Count;
+
+ // Check if first vertex equals last vertex.
+ if (Points[0] == Points[count - 1])
+ {
+ count--;
+ Points.RemoveAt(count);
+ }
+
+ this.marker = marker;
+ }
+
+ public Point FindInteriorPoint(bool convex)
+ {
+ if (convex)
+ {
+ int count = this.Points.Count;
+
+ var centroid = new Point(0.0, 0.0);
+
+ for (int i = 0; i < count; i++)
+ {
+ centroid.x += this.Points[i].x;
+ centroid.y += this.Points[i].y;
+ }
+
+ // If the hole is convex, use its centroid.
+ centroid.x /= count;
+ centroid.y /= count;
+
+ return centroid;
+ }
+
+ return FindPointInPolygon(this.Points);
+ }
+
+ public List GetSegments()
+ {
+ var segments = new List();
+
+ var p = this.Points;
+
+ int count = p.Count - 1;
+
+ for (int i = 0; i < count; i++)
+ {
+ // Add segments to polygon.
+ segments.Add(new Segment(p[i], p[i + 1], marker));
+ }
+
+ // Close the contour.
+ segments.Add(new Segment(p[count], p[0], marker));
+
+ return segments;
+ }
+
+ private static Point FindPointInPolygon(List contour)
+ {
+ var bounds = new Rectangle();
+ bounds.Expand(contour);
+
+ int length = contour.Count;
+ int limit = 8;
+
+ var test = new Point();
+
+ Point a, b; // Current edge.
+ double cx, cy; // Center of current edge.
+ double dx, dy; // Direction perpendicular to edge.
+
+ for (int i = 0; i < length; i++)
+ {
+ a = contour[i];
+ b = contour[(i + 1) % length];
+
+ cx = (a.x + b.x) / 2;
+ cy = (a.y + b.y) / 2;
+
+ dx = (b.y - a.y) / 1.374;
+ dy = (a.x - b.x) / 1.374;
+
+ for (int j = 1; j <= limit; j++)
+ {
+ // Search to the right of the segment.
+ test.x = cx + dx / j;
+ test.y = cy + dy / j;
+
+ if (bounds.Contains(test) && IsPointInPolygon(test, contour))
+ {
+ return test;
+ }
+
+ // Search on the other side of the segment.
+ test.x = cx - dx / j;
+ test.y = cy - dy / j;
+
+ if (bounds.Contains(test) && IsPointInPolygon(test, contour))
+ {
+ return test;
+ }
+ }
+ }
+
+ throw new Exception();
+ }
+
+ ///
+ /// Return true if the given point is inside the polygon, or false if it is not.
+ ///
+ /// The point to check.
+ /// The polygon (list of contour points).
+ ///
+ ///
+ /// WARNING: If the point is exactly on the edge of the polygon, then the function
+ /// may return true or false.
+ ///
+ /// See http://alienryderflex.com/polygon/
+ ///
+ private static bool IsPointInPolygon(Point point, List poly)
+ {
+ bool inside = false;
+
+ double x = point.x;
+ double y = point.y;
+
+ int count = poly.Count;
+
+ for (int i = 0, j = count - 1; i < count; i++)
+ {
+ if (((poly[i].y < y && poly[j].y >= y) || (poly[j].y < y && poly[i].y >= y))
+ && (poly[i].x <= x || poly[j].x <= x))
+ {
+ inside ^= (poly[i].x + (y - poly[i].y) / (poly[j].y - poly[i].y) * (poly[j].x - poly[i].x) < x);
+ }
+
+ j = i;
+ }
+
+ return inside;
+ }
+ }
+}
diff --git a/Triangle.NET/Triangle/Geometry/IEdge.cs b/Triangle.NET/Triangle/Geometry/IEdge.cs
index ab34b9f..ff55d80 100644
--- a/Triangle.NET/Triangle/Geometry/IEdge.cs
+++ b/Triangle.NET/Triangle/Geometry/IEdge.cs
@@ -1,4 +1,9 @@
-
+// -----------------------------------------------------------------------
+//
+// Triangle.NET code by Christian Woltering, http://triangle.codeplex.com/
+//
+// -----------------------------------------------------------------------
+
namespace TriangleNet.Geometry
{
public interface IEdge
diff --git a/Triangle.NET/Triangle/Geometry/IPolygon.cs b/Triangle.NET/Triangle/Geometry/IPolygon.cs
index a99672c..19475db 100644
--- a/Triangle.NET/Triangle/Geometry/IPolygon.cs
+++ b/Triangle.NET/Triangle/Geometry/IPolygon.cs
@@ -1,4 +1,9 @@
-
+// -----------------------------------------------------------------------
+//
+// Triangle.NET code by Christian Woltering, http://triangle.codeplex.com/
+//
+// -----------------------------------------------------------------------
+
namespace TriangleNet.Geometry
{
using System.Collections.Generic;
@@ -17,7 +22,7 @@ namespace TriangleNet.Geometry
///
/// Gets the segments of the polygon.
///
- List Segments { get; }
+ List Segments { get; }
///
/// Gets a list of points defining the holes of the polygon.
@@ -30,12 +35,12 @@ namespace TriangleNet.Geometry
List Regions { get; }
///
- /// Gets or sets value indicating wether the vertices have marks or not.
+ /// Gets or sets a value indicating whether the vertices have marks or not.
///
bool HasPointMarkers { get; set; }
///
- /// Gets or sets value indicating wether the segments have marks or not.
+ /// Gets or sets a value indicating whether the segments have marks or not.
///
bool HasSegmentMarkers { get; set; }
diff --git a/Triangle.NET/Triangle/Geometry/ISegment.cs b/Triangle.NET/Triangle/Geometry/ISegment.cs
index 1af96be..86a7d48 100644
--- a/Triangle.NET/Triangle/Geometry/ISegment.cs
+++ b/Triangle.NET/Triangle/Geometry/ISegment.cs
@@ -1,5 +1,5 @@
// -----------------------------------------------------------------------
-//
+//
// Triangle.NET code by Christian Woltering, http://triangle.codeplex.com/
//
// -----------------------------------------------------------------------
diff --git a/Triangle.NET/Triangle/Geometry/Polygon.cs b/Triangle.NET/Triangle/Geometry/Polygon.cs
index 1b113e7..3c2f955 100644
--- a/Triangle.NET/Triangle/Geometry/Polygon.cs
+++ b/Triangle.NET/Triangle/Geometry/Polygon.cs
@@ -1,4 +1,9 @@
-
+// -----------------------------------------------------------------------
+//
+// Triangle.NET code by Christian Woltering, http://triangle.codeplex.com/
+//
+// -----------------------------------------------------------------------
+
namespace TriangleNet.Geometry
{
using System;
@@ -14,7 +19,7 @@ namespace TriangleNet.Geometry
List holes;
List regions;
- List segments;
+ List segments;
///
public List Points
@@ -35,7 +40,7 @@ namespace TriangleNet.Geometry
}
///
- public List Segments
+ public List Segments
{
get { return segments; }
}
@@ -80,7 +85,7 @@ namespace TriangleNet.Geometry
holes = new List();
regions = new List();
- segments = new List();
+ segments = new List();
HasPointMarkers = markers;
HasSegmentMarkers = markers;
@@ -90,76 +95,27 @@ namespace TriangleNet.Geometry
public void AddContour(IEnumerable points, int marker = 0,
bool hole = false, bool convex = false)
{
- // Copy input to list.
- var contour = new List(points);
+ var c = new Contour(points, marker);
- int offset = this.points.Count;
- int count = contour.Count;
+ this.points.AddRange(c.Points);
- // Check if first vertex equals last vertex.
- if (contour[0] == contour[count - 1])
- {
- count--;
- contour.RemoveAt(count);
- }
-
- // Add points to polygon.
- this.points.AddRange(contour);
-
- var centroid = new Point(0.0, 0.0);
-
- for (int i = 0; i < count; i++)
- {
- centroid.x += contour[i].x;
- centroid.y += contour[i].y;
-
- // Add segments to polygon.
- this.segments.Add(new Edge(offset + i, offset + ((i + 1) % count), marker));
- }
+ this.segments.AddRange(c.GetSegments());
if (hole)
{
- if (convex)
- {
- // If the hole is convex, use its centroid.
- centroid.x /= count;
- centroid.y /= count;
-
- this.holes.Add(centroid);
- }
- else
- {
- this.holes.Add(FindPointInPolygon(contour));
- }
+ this.holes.Add(c.FindInteriorPoint(convex));
}
}
///
public void AddContour(IEnumerable points, int marker, Point hole)
{
- // Copy input to list.
- var contour = new List(points);
+ var c = new Contour(points, marker);
- int offset = this.points.Count;
- int count = contour.Count;
+ this.points.AddRange(c.Points);
- // Check if first vertex equals last vertex.
- if (contour[0] == contour[count - 1])
- {
- count--;
- contour.RemoveAt(count);
- }
+ this.segments.AddRange(c.GetSegments());
- // Add points to polygon.
- this.points.AddRange(contour);
-
- for (int i = 0; i < count; i++)
- {
- // Add segments to polygon.
- this.segments.Add(new Edge(offset + i, offset + ((i + 1) % count), marker));
- }
-
- // TODO: check if hole is actually inside contour?
this.holes.Add(hole);
}
@@ -180,109 +136,12 @@ namespace TriangleNet.Geometry
this.points.Add(vertex);
}
- ///
- /// Add a vertex to the polygon.
- ///
- public void Add(Vertex vertex, double[] attributes)
- {
- // TODO: check attibutes
-
- vertex.attributes = attributes;
-
- this.points.Add(vertex);
- }
-
///
/// Add a segment to the polygon.
///
- public void Add(Edge edge)
+ public void Add(ISegment segment)
{
- this.segments.Add(edge);
- }
-
- private Point FindPointInPolygon(List contour)
- {
- var bounds = new Rectangle();
- bounds.Expand(contour);
-
- int length = contour.Count;
- int limit = 8;
-
- var test = new Point();
-
- Point a, b; // Current edge.
- double cx, cy; // Center of current edge.
- double dx, dy; // Direction perpendicular to edge.
-
- for (int i = 0; i < length; i++)
- {
- a = contour[i];
- b = contour[(i + 1) % length];
-
- cx = (a.x + b.x) / 2;
- cy = (a.y + b.y) / 2;
-
- dx = (b.y - a.y) / 1.374;
- dy = (a.x - b.x) / 1.374;
-
- for (int j = 1; j <= limit; j++)
- {
- // Search to the right of the segment.
- test.x = cx + dx / j;
- test.y = cy + dy / j;
-
- if (bounds.Contains(test) && IsPointInPolygon(test, contour))
- {
- return test;
- }
-
- // Search on the other side of the segment.
- test.x = cx - dx / j;
- test.y = cy - dy / j;
-
- if (bounds.Contains(test) && IsPointInPolygon(test, contour))
- {
- return test;
- }
- }
- }
-
- throw new Exception();
- }
-
- ///
- /// Return true if the given point is inside the polygon, or false if it is not.
- ///
- /// The point to check.
- /// The polygon (list of contour points).
- ///
- ///
- /// WARNING: If the point is exactly on the edge of the polygon, then the function
- /// may return true or false.
- ///
- /// See http://alienryderflex.com/polygon/
- ///
- private bool IsPointInPolygon(Point point, List poly)
- {
- bool inside = false;
-
- double x = point.x;
- double y = point.y;
-
- int count = poly.Count;
-
- for (int i = 0, j = count - 1; i < count; i++)
- {
- if (((poly[i].y < y && poly[j].y >= y) || (poly[j].y < y && poly[i].y >= y))
- && (poly[i].x <= x || poly[j].x <= x))
- {
- inside ^= (poly[i].x + (y - poly[i].y) / (poly[j].y - poly[i].y) * (poly[j].x - poly[i].x) < x);
- }
-
- j = i;
- }
-
- return inside;
+ this.segments.Add(segment);
}
}
}
diff --git a/Triangle.NET/Triangle/Geometry/Segment.cs b/Triangle.NET/Triangle/Geometry/Segment.cs
new file mode 100644
index 0000000..0066b85
--- /dev/null
+++ b/Triangle.NET/Triangle/Geometry/Segment.cs
@@ -0,0 +1,93 @@
+// -----------------------------------------------------------------------
+//
+// Triangle.NET code by Christian Woltering, http://triangle.codeplex.com/
+//
+// -----------------------------------------------------------------------
+
+namespace TriangleNet.Geometry
+{
+ using System;
+
+ ///
+ /// Represents a straight line segment in 2D space.
+ ///
+ public class Segment : ISegment
+ {
+ Vertex v0;
+ Vertex v1;
+
+ int boundary;
+
+ ///
+ /// Initializes a new instance of the class.
+ ///
+ public Segment(Vertex v0, Vertex v1)
+ : this (v0, v1, 0)
+ {
+ }
+
+ ///
+ /// Initializes a new instance of the class.
+ ///
+ public Segment(Vertex v0, Vertex v1, int boundary)
+ {
+ this.v0 = v0;
+ this.v1 = v1;
+
+ this.boundary = boundary;
+ }
+
+ ///
+ /// Gets the specified segment endpoint.
+ ///
+ /// The endpoint index (0 or 1).
+ ///
+ public Vertex GetVertex(int index)
+ {
+ if (index == 0)
+ {
+ return v0;
+ }
+
+ if (index == 1)
+ {
+ return v1;
+ }
+
+ throw new IndexOutOfRangeException();
+ }
+
+ ///
+ /// WARNING: not implemented.
+ ///
+ public ITriangle GetTriangle(int index)
+ {
+ throw new NotImplementedException();
+ }
+
+ ///
+ /// Gets the first endpoints index.
+ ///
+ public int P0
+ {
+ get { return v0.id; }
+ }
+
+ ///
+ /// Gets the second endpoints index.
+ ///
+ public int P1
+ {
+ get { return v1.id; }
+ }
+
+ ///
+ /// Gets or sets the segments boundary mark.
+ ///
+ public int Boundary
+ {
+ get { return boundary; }
+ set { boundary = value; }
+ }
+ }
+}
diff --git a/Triangle.NET/Triangle/IO/IMeshFormat.cs b/Triangle.NET/Triangle/IO/IMeshFormat.cs
index ec91624..99a2a13 100644
--- a/Triangle.NET/Triangle/IO/IMeshFormat.cs
+++ b/Triangle.NET/Triangle/IO/IMeshFormat.cs
@@ -29,10 +29,10 @@ namespace TriangleNet.IO
void Write(IMesh mesh, string filename);
///
- /// Save a mesh to a .
+ /// Save a mesh to a .
///
/// An instance of the interface.
/// The stream to save to.
- void Write(IMesh mesh, StreamWriter stream);
+ void Write(IMesh mesh, Stream stream);
}
}
diff --git a/Triangle.NET/Triangle/IO/IPolygonFormat.cs b/Triangle.NET/Triangle/IO/IPolygonFormat.cs
index 9889230..7394243 100644
--- a/Triangle.NET/Triangle/IO/IPolygonFormat.cs
+++ b/Triangle.NET/Triangle/IO/IPolygonFormat.cs
@@ -29,10 +29,10 @@ namespace TriangleNet.IO
void Write(IPolygon polygon, string filename);
///
- /// Save a polygon geometry to a .
+ /// Save a polygon geometry to a .
///
/// An instance of the class.
/// The stream to save to.
- void Write(IPolygon polygon, StreamWriter stream);
+ void Write(IPolygon polygon, Stream stream);
}
}
diff --git a/Triangle.NET/Triangle/IO/TriangleFormat.cs b/Triangle.NET/Triangle/IO/TriangleFormat.cs
index b1bda4a..58f18d3 100644
--- a/Triangle.NET/Triangle/IO/TriangleFormat.cs
+++ b/Triangle.NET/Triangle/IO/TriangleFormat.cs
@@ -55,7 +55,7 @@ namespace TriangleNet.IO
TriangleWriter.WriteElements((Mesh)mesh, Path.ChangeExtension(filename, ".ele"));
}
- public void Write(IMesh mesh, StreamWriter stream)
+ public void Write(IMesh mesh, Stream stream)
{
throw new NotImplementedException();
}
@@ -83,7 +83,7 @@ namespace TriangleNet.IO
TriangleWriter.WritePoly(polygon, filename);
}
- public void Write(IPolygon polygon, StreamWriter stream)
+ public void Write(IPolygon polygon, Stream stream)
{
throw new NotImplementedException();
}
diff --git a/Triangle.NET/Triangle/IO/TriangleReader.cs b/Triangle.NET/Triangle/IO/TriangleReader.cs
index bd10ba6..80ba993 100644
--- a/Triangle.NET/Triangle/IO/TriangleReader.cs
+++ b/Triangle.NET/Triangle/IO/TriangleReader.cs
@@ -59,29 +59,36 @@ namespace TriangleNet.IO
/// The current line.
/// Number of point attributes
/// Number of point markers (0 or 1)
- static void ReadVertex(Polygon data, int index, string[] line, int attributes, int marks)
+ static void ReadVertex(List data, int index, string[] line, int attributes, int marks)
{
double x = double.Parse(line[1], nfi);
double y = double.Parse(line[2], nfi);
- int mark = 0;
- double[] attribs = attributes == 0 ? null : new double[attributes];
- // Read the vertex attributes.
- for (int j = 0; j < attributes; j++)
- {
- if (line.Length > 3 + j)
- {
- attribs[j] = double.Parse(line[3 + j], nfi);
- }
- }
+ var v = new Vertex(x, y);
// Read a vertex marker.
if (marks > 0 && line.Length > 3 + attributes)
{
- mark = int.Parse(line[3 + attributes]);
+ v.Boundary = int.Parse(line[3 + attributes]);
}
- data.Add(new Vertex(x, y, mark), attribs);
+ if (attributes > 0)
+ {
+ var attribs = new double[attributes];
+
+ // Read the vertex attributes.
+ for (int j = 0; j < attributes; j++)
+ {
+ if (line.Length > 3 + j)
+ {
+ attribs[j] = double.Parse(line[3 + j], nfi);
+ }
+ }
+
+ v.attributes = attribs;
+ }
+
+ data.Add(v);
}
#endregion
@@ -219,7 +226,7 @@ namespace TriangleNet.IO
startIndex = int.Parse(line[0], nfi);
}
- ReadVertex(data, i, line, attributes, nodemarkers);
+ ReadVertex(data.Points, i, line, attributes, nodemarkers);
}
}
}
@@ -326,19 +333,21 @@ namespace TriangleNet.IO
startIndex = int.Parse(line[0], nfi);
}
- ReadVertex(data, i, line, attributes, nodemarkers);
+ ReadVertex(data.Points, i, line, attributes, nodemarkers);
}
}
else
{
// If the .poly file claims there are zero vertices, that means that
// the vertices should be read from a separate .node file.
- string nodefile = Path.ChangeExtension(polyfilename, ".node");
- data = ReadNodeFile(nodefile);
+ data = ReadNodeFile(Path.ChangeExtension(polyfilename, ".node"));
+
invertices = data.Points.Count;
}
- if (data.Points == null)
+ var points = data.Points;
+
+ if (points.Count == 0)
{
throw new Exception("No nodes available.");
}
@@ -401,7 +410,7 @@ namespace TriangleNet.IO
}
else
{
- data.Add(new Edge(end1, end2, mark));
+ data.Add(new Segment(points[end1], points[end2], mark));
}
}
diff --git a/Triangle.NET/Triangle/IO/TriangleWriter.cs b/Triangle.NET/Triangle/IO/TriangleWriter.cs
index acdb2f2..19a95af 100644
--- a/Triangle.NET/Triangle/IO/TriangleWriter.cs
+++ b/Triangle.NET/Triangle/IO/TriangleWriter.cs
@@ -202,17 +202,22 @@ namespace TriangleNet.IO
// Number of segments, number of boundary markers (zero or one).
writer.WriteLine("{0} {1}", polygon.Segments.Count, hasMarkers ? "1" : "0");
+ Vertex p, q;
+
int j = 0;
foreach (var seg in polygon.Segments)
{
+ p = seg.GetVertex(0);
+ q = seg.GetVertex(1);
+
// Segment number, indices of its two endpoints, and possibly a marker.
if (hasMarkers)
{
- writer.WriteLine("{0} {1} {2} {3}", j, seg.P0, seg.P1, seg.Boundary);
+ writer.WriteLine("{0} {1} {2} {3}", j, p.ID, q.ID, seg.Boundary);
}
else
{
- writer.WriteLine("{0} {1} {2}", j, seg.P0, seg.P1);
+ writer.WriteLine("{0} {1} {2}", j, p.ID, q.ID);
}
j++;
diff --git a/Triangle.NET/Triangle/Mesh.cs b/Triangle.NET/Triangle/Mesh.cs
index 585f79c..a3028df 100644
--- a/Triangle.NET/Triangle/Mesh.cs
+++ b/Triangle.NET/Triangle/Mesh.cs
@@ -35,7 +35,7 @@ namespace TriangleNet
// Using hashsets for memory management should quite fast.
internal Dictionary triangles;
- internal Dictionary subsegs;
+ internal Dictionary subsegs;
internal Dictionary vertices;
// Hash seeds (should belong to mesh instance)
@@ -111,7 +111,7 @@ namespace TriangleNet
///
/// Gets the mesh segments.
///
- public ICollection Segments
+ public ICollection Segments
{
get { return this.subsegs.Values; }
}
@@ -183,11 +183,11 @@ namespace TriangleNet
// triangle side or subsegment end that isn't attached to a real
// subsegment.
- internal Segment dummysub;
+ internal SubSegment dummysub;
private void Initialize()
{
- dummysub = new Segment();
+ dummysub = new SubSegment();
dummysub.hash = DUMMY;
// Initialize the two adjoining subsegments to be the omnipresent
@@ -231,7 +231,7 @@ namespace TriangleNet
vertices = new Dictionary();
triangles = new Dictionary();
- subsegs = new Dictionary();
+ subsegs = new Dictionary();
flipstack = new Stack();
@@ -287,13 +287,13 @@ namespace TriangleNet
}
else if (num == NodeNumbering.CuthillMcKee)
{
- CuthillMcKee rcm = new CuthillMcKee();
- int[] perm_inv = rcm.Renumber(this);
+ var rcm = new CuthillMcKee();
+ var iperm = rcm.Renumber(this);
// Permute the node indices.
foreach (var node in this.vertices.Values)
{
- node.id = perm_inv[node.id];
+ node.id = iperm[node.id];
}
}
@@ -689,7 +689,7 @@ namespace TriangleNet
/// Reference to the new subseg.
internal void MakeSegment(ref Osub newsubseg)
{
- Segment seg = new Segment();
+ var seg = new SubSegment();
seg.hash = this.hash_seg++;
@@ -1924,7 +1924,7 @@ namespace TriangleNet
/// Deallocate space for a subsegment, marking it dead.
///
///
- internal void SubsegDealloc(Segment dyingsubseg)
+ internal void SubsegDealloc(SubSegment dyingsubseg)
{
// Mark the subsegment as dead. This makes it possible to detect dead
// subsegments when traversing the list of all subsegments.
diff --git a/Triangle.NET/Triangle/Meshing/ConstraintMesher.cs b/Triangle.NET/Triangle/Meshing/ConstraintMesher.cs
index 49a54aa..7fd3756 100644
--- a/Triangle.NET/Triangle/Meshing/ConstraintMesher.cs
+++ b/Triangle.NET/Triangle/Meshing/ConstraintMesher.cs
@@ -169,9 +169,10 @@ namespace TriangleNet.Meshing
///
public void FormSkeleton(IPolygon input)
{
- Vertex endpoint1, endpoint2;
- int end1, end2;
- int boundmarker;
+ // The segment endpoints.
+ Vertex p, q;
+
+ int label;
mesh.insegments = 0;
@@ -191,51 +192,31 @@ namespace TriangleNet.Meshing
mesh.MakeVertexMap();
}
- boundmarker = 0;
+ label = 0;
// Read and insert the segments.
foreach (var seg in input.Segments)
{
mesh.insegments++;
- end1 = seg.P0;
- end2 = seg.P1;
- boundmarker = seg.Boundary;
+ label = seg.Boundary;
- if ((end1 < 0) || (end1 >= mesh.invertices))
+ // TODO: wrap segment dictionary access in try / catch?
+
+ p = seg.GetVertex(0);
+ q = seg.GetVertex(1);
+
+ if ((p.x == q.x) && (p.y == q.y))
{
if (Log.Verbose)
{
- logger.Warning("Invalid first endpoint of segment.", "Mesh.FormSkeleton().1");
- }
- }
- else if ((end2 < 0) || (end2 >= mesh.invertices))
- {
- if (Log.Verbose)
- {
- logger.Warning("Invalid second endpoint of segment.", "Mesh.FormSkeleton().2");
+ logger.Warning("Endpoints of segment (IDs " + p.id + "/" + q.id + ") are coincident.",
+ "Mesh.FormSkeleton()");
}
}
else
{
- // TODO: Is using the vertex ID reliable???
- // It should be. The ID gets appropriately set in TransferNodes().
-
- // Find the vertices numbered 'end1' and 'end2'.
- endpoint1 = mesh.vertices[end1];
- endpoint2 = mesh.vertices[end2];
- if ((endpoint1.x == endpoint2.x) && (endpoint1.y == endpoint2.y))
- {
- if (Log.Verbose)
- {
- logger.Warning("Endpoints of segment (IDs " + end1 + "/" + end2 + ") are coincident.",
- "Mesh.FormSkeleton()");
- }
- }
- else
- {
- InsertSegment(endpoint1, endpoint2, boundmarker);
- }
+ InsertSegment(p, q, label);
}
}
}
diff --git a/Triangle.NET/Triangle/Meshing/Converter.cs b/Triangle.NET/Triangle/Meshing/Converter.cs
index 34b9370..be6d9b9 100644
--- a/Triangle.NET/Triangle/Meshing/Converter.cs
+++ b/Triangle.NET/Triangle/Meshing/Converter.cs
@@ -213,10 +213,12 @@ namespace TriangleNet.Meshing
Otri checkneighbor = default(Otri);
Osub subseg = default(Osub);
Otri prevlink; // Triangle
- TVertex shorg;
- TVertex segmentorg, segmentdest;
- int[] end = new int[2];
+
+ TVertex tmp;
+ TVertex sorg, sdest;
+
bool notfound;
+
//bool segmentmarkers = false;
int boundmarker;
int aroundvertex;
@@ -234,40 +236,38 @@ namespace TriangleNet.Meshing
{
subseg.seg = item;
- end[0] = polygon.Segments[i].P0;
- end[1] = polygon.Segments[i].P1;
+ sorg = polygon.Segments[i].GetVertex(0);
+ sdest = polygon.Segments[i].GetVertex(1);
+
boundmarker = polygon.Segments[i].Boundary;
- for (int j = 0; j < 2; j++)
+ if ((sorg.id < 0 || sorg.id >= mesh.invertices) || (sdest.id < 0 || sdest.id >= mesh.invertices))
{
- if ((end[j] < 0) || (end[j] >= mesh.invertices))
- {
- Log.Instance.Error("Segment has an invalid vertex index.", "MeshReader.Reconstruct()");
- throw new Exception("Segment has an invalid vertex index.");
- }
+ Log.Instance.Error("Segment has an invalid vertex index.", "MeshReader.Reconstruct()");
+ throw new Exception("Segment has an invalid vertex index.");
}
// set the subsegment's vertices.
subseg.orient = 0;
- segmentorg = mesh.vertices[end[0]];
- segmentdest = mesh.vertices[end[1]];
- subseg.SetOrg(segmentorg);
- subseg.SetDest(segmentdest);
- subseg.SetSegOrg(segmentorg);
- subseg.SetSegDest(segmentdest);
+ subseg.SetOrg(sorg);
+ subseg.SetDest(sdest);
+ subseg.SetSegOrg(sorg);
+ subseg.SetSegDest(sdest);
subseg.seg.boundary = boundmarker;
// Try linking the subsegment to triangles that share these vertices.
for (subseg.orient = 0; subseg.orient < 2; subseg.orient++)
{
// Take the number for the destination of subsegloop.
- aroundvertex = end[1 - subseg.orient];
+ aroundvertex = subseg.orient == 1 ? sorg.id : sdest.id;
+
int index = vertexarray[aroundvertex].Count - 1;
+
// Look for triangles having this vertex.
prevlink = vertexarray[aroundvertex][index];
nexttri = vertexarray[aroundvertex][index];
checktri = nexttri;
- shorg = subseg.Org();
+ tmp = subseg.Org();
notfound = true;
// Look for triangles having this edge. Note that I'm only
// comparing each triangle's destination with the subsegment;
@@ -280,7 +280,7 @@ namespace TriangleNet.Meshing
{
checkdest = checktri.Dest();
- if (shorg == checkdest)
+ if (tmp == checkdest)
{
// We have a match. Remove this triangle from the list.
//prevlink = vertexarray[aroundvertex][index];
diff --git a/Triangle.NET/Triangle/Meshing/GenericMesher.cs b/Triangle.NET/Triangle/Meshing/GenericMesher.cs
index d0eca4d..4aeaf50 100644
--- a/Triangle.NET/Triangle/Meshing/GenericMesher.cs
+++ b/Triangle.NET/Triangle/Meshing/GenericMesher.cs
@@ -100,10 +100,10 @@ namespace TriangleNet.Meshing
left = bounds.Left;
bottom = bounds.Bottom;
- int i, j, k, l, n;
+ int i, j, k, l, n = 0;
// Add vertices.
- var points = polygon.Points;
+ var points = new Vertex[(nx + 1) * (ny + 1)];
for (i = 0; i <= nx; i++)
{
@@ -113,10 +113,12 @@ namespace TriangleNet.Meshing
{
y = bottom + j * dy;
- points.Add(new Vertex(x, y));
+ points[n++] = new Vertex(x, y);
}
}
+ polygon.Points.AddRange(points);
+
n = 0;
// Set vertex hash and id.
@@ -130,22 +132,44 @@ namespace TriangleNet.Meshing
segments.Capacity = 2 * (nx + ny);
+ Vertex a, b;
+
for (j = 0; j < ny; j++)
{
// Left
- segments.Add(new Edge(j, j + 1));
+ a = points[j];
+ b = points[j + 1];
+
+ segments.Add(new Segment(a, b, 1));
+
+ a.Boundary = b.Boundary = 1;
// Right
- segments.Add(new Edge(nx * (ny + 1) + j, nx * (ny + 1) + (j + 1)));
+ a = points[nx * (ny + 1) + j];
+ b = points[nx * (ny + 1) + (j + 1)];
+
+ segments.Add(new Segment(a, b, 1));
+
+ a.Boundary = b.Boundary = 1;
}
for (i = 0; i < nx; i++)
{
// Bottom
- segments.Add(new Edge(i * (ny + 1), (i + 1) * (ny + 1)));
+ a = points[i * (ny + 1)];
+ b = points[(i + 1) * (ny + 1)];
+
+ segments.Add(new Segment(a, b, 1));
+
+ a.Boundary = b.Boundary = 1;
// Top
- segments.Add(new Edge(i * (ny + 1) + nx, (i + 1) * (ny + 1) + nx));
+ a = points[i * (ny + 1) + nx];
+ b = points[(i + 1) * (ny + 1) + nx];
+
+ segments.Add(new Segment(a, b, 1));
+
+ a.Boundary = b.Boundary = 1;
}
// Add triangles.
diff --git a/Triangle.NET/Triangle/Meshing/IMesh.cs b/Triangle.NET/Triangle/Meshing/IMesh.cs
index 1e6a1be..7a769dd 100644
--- a/Triangle.NET/Triangle/Meshing/IMesh.cs
+++ b/Triangle.NET/Triangle/Meshing/IMesh.cs
@@ -23,7 +23,7 @@ namespace TriangleNet.Meshing
///
/// Gets the segments (constraint edges) of the mesh.
///
- ICollection Segments { get; }
+ ICollection Segments { get; }
///
/// Gets the triangles of the mesh.
diff --git a/Triangle.NET/Triangle/Tools/PolygonValidator.cs b/Triangle.NET/Triangle/Tools/PolygonValidator.cs
index da1da08..7c99140 100644
--- a/Triangle.NET/Triangle/Tools/PolygonValidator.cs
+++ b/Triangle.NET/Triangle/Tools/PolygonValidator.cs
@@ -7,6 +7,7 @@
namespace TriangleNet.Tools
{
using System;
+ using System.Collections.Generic;
using TriangleNet.Geometry;
public static class PolygonValidator
@@ -18,23 +19,37 @@ namespace TriangleNet.Tools
{
var logger = Log.Instance;
+ var points = poly.Points;
+
int horrors = 0;
int i = 0;
- int count = poly.Points.Count;
+ int count = points.Count;
- foreach (var p in poly.Points)
+ if (count < 3)
+ {
+ logger.Warning("Polygon must have at least 3 vertices.", "PolygonValidator.IsConsistent()");
+ return false;
+ }
+
+ foreach (var p in points)
{
if (p == null)
{
horrors++;
logger.Warning(String.Format("Point {0} is null.", i), "PolygonValidator.IsConsistent()");
}
- else if (double.IsNaN(p.x + p.y) || double.IsInfinity(p.x + p.y))
+ else if (double.IsNaN(p.x) || double.IsNaN(p.y))
{
horrors++;
logger.Warning(String.Format("Point {0} has invalid coordinates.", i), "PolygonValidator.IsConsistent()");
}
+ else if (double.IsInfinity(p.x) || double.IsInfinity(p.y))
+ {
+ horrors++;
+ logger.Warning(String.Format("Point {0} has invalid coordinates.", i), "PolygonValidator.IsConsistent()");
+ }
+
i++;
}
@@ -46,27 +61,33 @@ namespace TriangleNet.Tools
{
horrors++;
logger.Warning(String.Format("Segment {0} is null.", i), "PolygonValidator.IsConsistent()");
- }
- else
- {
- if (seg.P0 < 0 || seg.P0 >= count)
- {
- horrors++;
- logger.Warning(String.Format("Segment {0} has invalid startpoint.", i),
- "PolygonValidator.IsConsistent()");
- }
- if (seg.P1 < 0 || seg.P1 >= count)
- {
- horrors++;
- logger.Warning(String.Format("Segment {0} has invalid endpoint.", i),
- "PolygonValidator.IsConsistent()");
- }
+ // Always abort if a NULL-segment is found.
+ return false;
+ }
+
+ var p = seg.GetVertex(0);
+ var q = seg.GetVertex(1);
+
+ if ((p.x == q.x) && (p.y == q.y))
+ {
+ horrors++;
+ logger.Warning(String.Format("Endpoints of segment {0} are coincident (IDs {1} / {2}).", i, p.id, q.id),
+ "PolygonValidator.IsConsistent()");
}
i++;
}
+ if (points[0].ID == points[1].ID)
+ {
+ horrors += CheckVertexIDs(poly, count);
+ }
+ else
+ {
+ horrors += CheckDuplicateIDs(poly);
+ }
+
return horrors == 0;
}
@@ -116,8 +137,8 @@ namespace TriangleNet.Tools
q0 = p0;
q1 = p1;
- p0 = (seg.P0 >= 0 && seg.P0 < count) ? poly.Points[seg.P0] : null;
- p1 = (seg.P1 >= 0 && seg.P1 < count) ? poly.Points[seg.P1] : null;
+ p0 = seg.GetVertex(0);
+ p1 = seg.GetVertex(1);
if (q0 != null && q1 != null)
{
@@ -160,5 +181,57 @@ namespace TriangleNet.Tools
// Calculate the Z coordinate of the cross product.
return (a.X - b.X) * (c.Y - b.Y) - (a.Y - b.Y) * (c.X - b.X);
}
+
+ private static int CheckVertexIDs(IPolygon poly, int count)
+ {
+ var logger = Log.Instance;
+
+ int horrors = 0;
+
+ int i = 0;
+
+ Vertex p, q;
+
+ foreach (var seg in poly.Segments)
+ {
+ p = seg.GetVertex(0);
+ q = seg.GetVertex(1);
+
+ if (p.ID < 0 || p.ID >= count)
+ {
+ horrors++;
+ logger.Warning(String.Format("Segment {0} has invalid startpoint.", i),
+ "PolygonValidator.IsConsistent()");
+ }
+
+ if (q.ID < 0 || q.ID >= count)
+ {
+ horrors++;
+ logger.Warning(String.Format("Segment {0} has invalid endpoint.", i),
+ "PolygonValidator.IsConsistent()");
+ }
+
+ i++;
+ }
+
+ return horrors;
+ }
+
+ private static int CheckDuplicateIDs(IPolygon poly)
+ {
+ var ids = new HashSet();
+
+ // Check for duplicate ids.
+ foreach (var p in poly.Points)
+ {
+ if (!ids.Add(p.ID))
+ {
+ Log.Instance.Warning("Found duplicate vertex ids.", "PolygonValidator.IsConsistent()");
+ return 1;
+ }
+ }
+
+ return 0;
+ }
}
}
diff --git a/Triangle.NET/Triangle/Topology/Osub.cs b/Triangle.NET/Triangle/Topology/Osub.cs
index 3a82522..f60281b 100644
--- a/Triangle.NET/Triangle/Topology/Osub.cs
+++ b/Triangle.NET/Triangle/Topology/Osub.cs
@@ -20,10 +20,10 @@ namespace TriangleNet.Topology
///
public struct Osub
{
- internal Segment seg;
+ internal SubSegment seg;
internal int orient; // Ranges from 0 to 1.
- public Segment Segment
+ public SubSegment Segment
{
get { return seg; }
}
@@ -213,7 +213,7 @@ namespace TriangleNet.Topology
///
/// Note that the other subsegment will still think it's
/// connected to this subsegment.
- internal void Dissolve(Segment dummy)
+ internal void Dissolve(SubSegment dummy)
{
seg.subsegs[orient].seg = dummy;
}
@@ -237,7 +237,7 @@ namespace TriangleNet.Topology
///
/// Check a subsegment's deallocation.
///
- internal static bool IsDead(Segment sub)
+ internal static bool IsDead(SubSegment sub)
{
return sub.subsegs[0].seg == null;
}
@@ -245,7 +245,7 @@ namespace TriangleNet.Topology
///
/// Set a subsegment's deallocation.
///
- internal static void Kill(Segment sub)
+ internal static void Kill(SubSegment sub)
{
sub.subsegs[0].seg = null;
sub.subsegs[1].seg = null;
diff --git a/Triangle.NET/Triangle/Topology/Otri.cs b/Triangle.NET/Triangle/Topology/Otri.cs
index cc8da35..ba9efee 100644
--- a/Triangle.NET/Triangle/Topology/Otri.cs
+++ b/Triangle.NET/Triangle/Topology/Otri.cs
@@ -454,7 +454,7 @@ namespace TriangleNet.Topology
///
/// Dissolve a bond (from the triangle side).
///
- internal void SegDissolve(Segment dummy)
+ internal void SegDissolve(SubSegment dummy)
{
tri.subsegs[orient].seg = dummy;
}
diff --git a/Triangle.NET/Triangle/Topology/Segment.cs b/Triangle.NET/Triangle/Topology/SubSegment.cs
similarity index 93%
rename from Triangle.NET/Triangle/Topology/Segment.cs
rename to Triangle.NET/Triangle/Topology/SubSegment.cs
index 3cbb21b..dcbc78f 100644
--- a/Triangle.NET/Triangle/Topology/Segment.cs
+++ b/Triangle.NET/Triangle/Topology/SubSegment.cs
@@ -13,7 +13,7 @@ namespace TriangleNet.Topology
///
/// The subsegment data structure.
///
- public class Segment : ISegment
+ public class SubSegment : ISegment
{
// Hash for dictionary. Will be set by mesh instance.
internal int hash;
@@ -23,7 +23,7 @@ namespace TriangleNet.Topology
internal Otri[] triangles;
internal int boundary;
- public Segment()
+ public SubSegment()
{
// Four NULL vertices.
vertices = new Vertex[4];
diff --git a/Triangle.NET/Triangle/Triangle.csproj b/Triangle.NET/Triangle/Triangle.csproj
index 7dd5d81..be22a09 100644
--- a/Triangle.NET/Triangle/Triangle.csproj
+++ b/Triangle.NET/Triangle/Triangle.csproj
@@ -38,15 +38,31 @@
-
+
+
+
-
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
@@ -54,69 +70,54 @@
-
-
-
+
+
+
+
+
+
+
+
+
+
+
-
+
+
+
-
+
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
diff --git a/Triangle.NET/Triangle/Voronoi/Legacy/BoundedVoronoiLegacy.cs b/Triangle.NET/Triangle/Voronoi/Legacy/BoundedVoronoiLegacy.cs
index c9993a3..ace56aa 100644
--- a/Triangle.NET/Triangle/Voronoi/Legacy/BoundedVoronoiLegacy.cs
+++ b/Triangle.NET/Triangle/Voronoi/Legacy/BoundedVoronoiLegacy.cs
@@ -30,7 +30,7 @@ namespace TriangleNet.Voronoi.Legacy
List segPoints;
int segIndex;
- Dictionary subsegMap;
+ Dictionary subsegMap;
bool includeBoundary = true;
@@ -151,7 +151,7 @@ namespace TriangleNet.Voronoi.Legacy
int blinded = 0;
Stack triangles;
- subsegMap = new Dictionary();
+ subsegMap = new Dictionary();
Otri f = default(Otri);
Otri f0 = default(Otri);