void Start() { points = new Vector2f[100]; FillWithRandom(points); convex = ConvexHull2.FindHull(points); convex.BuildIndices(); }
public void AlgorithmHullFaces() { var triangles = mConvexHull3.Triangles; var dataCloud = mConvexHull3.DataCloud; var points = mConvexHull3.Vertices; if (triangles.Count < 4) { Debugger.Get.Log("Insufficient points to form a tetrahedron.", DebugOption.SBB3); return; } mVolume = float.MaxValue; foreach (Triangle triangle in triangles) { List <Vector3> localPoints = new List <Vector3>(triangles.Count * 3); float farthestDistance = -float.MaxValue; foreach (int point in points) { Vector3 dataCloudPoint = dataCloud[point]; float distance = Mathf.Abs(triangle.CalculateDistance(dataCloudPoint)); farthestDistance = Mathf.Max(farthestDistance, distance); localPoints.Add(triangle.ToLocal(dataCloudPoint)); } ConvexHull2 ch2 = new ConvexHull2(localPoints); ch2.AlgorithmQuickhull(); OBB2 obb2 = new OBB2(ch2); obb2.AlgorithmRotatingCalipers(); float newVolume = obb2.Area * farthestDistance; if (newVolume < mVolume) { mVolume = newVolume; var worldRect = new { BottomLeftCorner = triangle.ToWorld(obb2.Rectangle.Corner), BottomRightCorner = triangle.ToWorld(obb2.Rectangle.Corner + obb2.Rectangle.X * obb2.Rectangle.Extents.x), TopLeftCorner = triangle.ToWorld(obb2.Rectangle.Corner + obb2.Rectangle.Y * obb2.Rectangle.Extents.y) }; mBox.Extents = new Vector3(obb2.Rectangle.Extents.x, obb2.Rectangle.Extents.y, farthestDistance); mBox.Corner = worldRect.BottomLeftCorner; mBox.X = (worldRect.BottomRightCorner - mBox.Corner).normalized; mBox.Y = (worldRect.TopLeftCorner - mBox.Corner).normalized; mBox.Z = -triangle.N; // Triangle normal always points outside convex hull. } } }
public static void test_convex_hull_2() { Random r = new Random(31337); //LocalProfiler p = new LocalProfiler(); //p.Start("Hulls"); QueryNumberType[] modes = new QueryNumberType[] { QueryNumberType.QT_DOUBLE, QueryNumberType.QT_INT64 }; foreach (var queryMode in modes) { for (int k = 0; k < 1000; ++k) { int N = 2500; double scale = (r.NextDouble() + 0.1) * 1024.0; Vector2d[] pts = TestUtil.RandomPoints2(N, r, Vector2d.Zero, scale); double eps = MathUtil.Epsilonf; ConvexHull2 hull = new ConvexHull2(pts, eps, queryMode); Polygon2d hullPoly = hull.GetHullPolygon(); foreach (Vector2d v in pts) { if (hullPoly.Contains(v)) { continue; } double d = hullPoly.DistanceSquared(v); if (d < eps) { continue; } System.Console.WriteLine("test_convex_hull: Point {0} not contained!", v); } } } //p.StopAll(); //System.Console.WriteLine(p.AllTimes()); //SVGWriter writer = new SVGWriter(); //foreach (Vector2d v in pts) { // writer.AddCircle(new Circle2d(v, 3.0), SVGWriter.Style.Outline("black", 1.0f)); //} //writer.AddPolygon(hullPoly, SVGWriter.Style.Outline("red", 2.0f)); //writer.Write(TestUtil.GetTestOutputPath("test.svg")); }
private static ConvexHull2 GetConvexHull(IReadOnlyCollection <Contour> contours) { List <Vector2d> points = new List <Vector2d>(); foreach (Contour contour in contours) { foreach (var point in contour.Points) { points.Add(new Vector2d(point.x, point.y)); } } ConvexHull2 convexHull2 = new ConvexHull2(points, EquityTolerance, QueryNumberType.QT_DOUBLE); return(convexHull2); }
private void Start() { lineMaterial = new Material(Shader.Find("Hidden/Internal-Colored")); vertices = new List <Vertex2>(); Random.InitState(seed); for (int i = 0; i < NumberOfVertices; i++) { float x = size * Random.Range(-1.0f, 1.0f); float y = size * Random.Range(-1.0f, 1.0f); vertices.Add(new Vertex2(x, y)); } hull = new ConvexHull2(); hull.Generate(vertices); }
public void FindHull() { Vector2f[] points = new Vector2f[] { new Vector2f(0, 0), new Vector2f(10, 0), new Vector2f(10, 10), new Vector2f(6, 5), new Vector2f(4, 1) }; Polygon2f convex = ConvexHull2.FindHull(points); Assert.AreEqual(3, convex.VerticesCount); Assert.AreEqual(points[0], convex.Positions[0]); Assert.AreEqual(points[1], convex.Positions[1]); Assert.AreEqual(points[2], convex.Positions[2]); Assert.IsTrue(ConvexHull2.IsStronglyConvex(convex.Positions, convex.IsCCW)); }
void LoadIfNecessary() { if (meshFilter == null) { meshFilter = GetComponent <MeshFilter>(); } if (ch2 == null) { ch2 = new ConvexHull2(new List <Vector3>()); } if (obb2 == null) { obb2 = new OBB2(ch2); } if (ch3 == null) { ch3 = new ConvexHull3(new List <Vector3>()); } if (obb3 == null) { obb3 = new OBB3(ch3); } }
// exports svg w/ different containments of point set (created by slicing mesh) public static void containment_demo_svg() { DMesh3 mesh = TestUtil.LoadTestInputMesh("bunny_solid.obj"); MeshTransforms.Scale(mesh, 4); AxisAlignedBox3d meshBounds = mesh.CachedBounds; Vector3d origin = meshBounds.Center; origin -= 0.2 * meshBounds.Height * Vector3d.AxisY; Frame3f plane = new Frame3f(origin, new Vector3d(1, 3, 0).Normalized); MeshPlaneCut cut = new MeshPlaneCut(mesh, plane.Origin, plane.Z); cut.Cut(); AxisAlignedBox2d polyBounds = AxisAlignedBox2d.Empty; List <Polygon2d> polys = new List <Polygon2d>(); foreach (EdgeLoop loop in cut.CutLoops) { Polygon2d poly = new Polygon2d(); foreach (int vid in loop.Vertices) { poly.AppendVertex(mesh.GetVertex(vid).xz); } poly.Rotate(new Matrix2d(90, true), Vector2d.Zero); polys.Add(poly); polyBounds.Contain(poly.Bounds); } SVGWriter svg = new SVGWriter(); var polyStyle = SVGWriter.Style.Outline("red", 1.0f); var contStyle = SVGWriter.Style.Outline("black", 1.0f); for (int k = 0; k < 3; ++k) { double shift = (k == 2) ? 1.4f : 1.1f; Vector2d tx = (k - 1) * (polyBounds.Width * shift) * Vector2d.AxisX; List <Vector2d> pts = new List <Vector2d>(); foreach (Polygon2d poly in polys) { var p2 = new Polygon2d(poly).Translate(tx); pts.AddRange(p2.Vertices); svg.AddPolygon(p2, polyStyle); } if (k == 0) { ConvexHull2 hull = new ConvexHull2(pts, 0.001, QueryNumberType.QT_DOUBLE); svg.AddPolygon(hull.GetHullPolygon(), contStyle); } else if (k == 1) { ContMinBox2 contbox = new ContMinBox2(pts, 0.001, QueryNumberType.QT_DOUBLE, false); svg.AddPolygon(new Polygon2d(contbox.MinBox.ComputeVertices()), contStyle); } else if (k == 2) { ContMinCircle2 contcirc = new ContMinCircle2(pts); svg.AddCircle(contcirc.Result, contStyle); } } svg.Write(TestUtil.GetTestOutputPath("contain_demos.svg")); }
/// <summary> /// 获取点集合的凸包polygon2d /// </summary> /// <param name="vector2ds"></param> /// <returns></returns> public static Polygon2d ConvexHullPolygon2d(this IEnumerable <Vector2d> vector2ds) { ConvexHull2 convexHull2 = new ConvexHull2(vector2ds.ToList(), Precision_.Precison, QueryNumberType.QT_DOUBLE); return(convexHull2.GetHullPolygon()); }
public OBB2(ConvexHull2 convexHull2Data) { mConvexHull2 = convexHull2Data; mRectangle = new Rectangle(); }