internal static void ExportPolylineToWkt(int export_flags, com.epl.geometry.Polyline polyline, System.Text.StringBuilder @string) { com.epl.geometry.MultiPathImpl polyline_impl = (com.epl.geometry.MultiPathImpl)polyline._getImpl(); int point_count = polyline_impl.GetPointCount(); int path_count = polyline_impl.GetPathCount(); if (point_count > 0 && path_count == 0) { throw new com.epl.geometry.GeometryException("corrupted geometry"); } int precision = 17 - (7 & (export_flags >> 13)); bool b_export_zs = polyline_impl.HasAttribute(com.epl.geometry.VertexDescription.Semantics.Z) && (export_flags & com.epl.geometry.WktExportFlags.wktExportStripZs) == 0; bool b_export_ms = polyline_impl.HasAttribute(com.epl.geometry.VertexDescription.Semantics.M) && (export_flags & com.epl.geometry.WktExportFlags.wktExportStripMs) == 0; com.epl.geometry.AttributeStreamOfDbl position = null; com.epl.geometry.AttributeStreamOfDbl zs = null; com.epl.geometry.AttributeStreamOfDbl ms = null; com.epl.geometry.AttributeStreamOfInt8 path_flags = null; com.epl.geometry.AttributeStreamOfInt32 paths = null; if (point_count > 0) { position = (com.epl.geometry.AttributeStreamOfDbl)polyline_impl.GetAttributeStreamRef(com.epl.geometry.VertexDescription.Semantics.POSITION); path_flags = polyline_impl.GetPathFlagsStreamRef(); paths = polyline_impl.GetPathStreamRef(); if (b_export_zs) { if (polyline_impl._attributeStreamIsAllocated(com.epl.geometry.VertexDescription.Semantics.Z)) { zs = (com.epl.geometry.AttributeStreamOfDbl)(polyline_impl.GetAttributeStreamRef(com.epl.geometry.VertexDescription.Semantics.Z)); } } if (b_export_ms) { if (polyline_impl._attributeStreamIsAllocated(com.epl.geometry.VertexDescription.Semantics.M)) { ms = (com.epl.geometry.AttributeStreamOfDbl)(polyline_impl.GetAttributeStreamRef(com.epl.geometry.VertexDescription.Semantics.M)); } } } if ((export_flags & com.epl.geometry.WktExportFlags.wktExportLineString) != 0) { if (path_count > 1) { throw new System.ArgumentException("Cannot export a LineString with specified export flags: " + export_flags); } LineStringTaggedText_(precision, b_export_zs, b_export_ms, zs, ms, position, path_flags, paths, @string); } else { MultiLineStringTaggedText_(precision, b_export_zs, b_export_ms, zs, ms, position, path_flags, paths, path_count, @string); } }
internal virtual com.epl.geometry.Geometry TryFastIntersectPolylinePolygon_(com.epl.geometry.Polyline polyline, com.epl.geometry.Polygon polygon) { com.epl.geometry.MultiPathImpl polylineImpl = (com.epl.geometry.MultiPathImpl)polyline._getImpl(); com.epl.geometry.MultiPathImpl polygonImpl = (com.epl.geometry.MultiPathImpl)polygon._getImpl(); double tolerance = com.epl.geometry.InternalUtils.CalculateToleranceFromGeometry(m_spatial_reference, polygon, false); com.epl.geometry.Envelope2D clipEnvelope = new com.epl.geometry.Envelope2D(); { polygonImpl.QueryEnvelope2D(clipEnvelope); com.epl.geometry.Envelope2D env1 = new com.epl.geometry.Envelope2D(); polylineImpl.QueryEnvelope2D(env1); env1.Inflate(2.0 * tolerance, 2.0 * tolerance); clipEnvelope.Intersect(env1); System.Diagnostics.Debug.Assert((!clipEnvelope.IsEmpty())); } clipEnvelope.Inflate(10 * tolerance, 10 * tolerance); if (true) { double tol = 0; com.epl.geometry.Geometry clippedPolyline = com.epl.geometry.Clipper.Clip(polyline, clipEnvelope, tol, 0.0); polyline = (com.epl.geometry.Polyline)clippedPolyline; polylineImpl = (com.epl.geometry.MultiPathImpl)polyline._getImpl(); } com.epl.geometry.AttributeStreamOfInt32 clipResult = new com.epl.geometry.AttributeStreamOfInt32(0); int unresolvedSegments = -1; com.epl.geometry.GeometryAccelerators accel = polygonImpl._getAccelerators(); if (accel != null) { com.epl.geometry.RasterizedGeometry2D rgeom = accel.GetRasterizedGeometry(); if (rgeom != null) { unresolvedSegments = 0; clipResult.Reserve(polylineImpl.GetPointCount() + polylineImpl.GetPathCount()); com.epl.geometry.Envelope2D seg_env = new com.epl.geometry.Envelope2D(); com.epl.geometry.SegmentIteratorImpl iter = polylineImpl.QuerySegmentIterator(); while (iter.NextPath()) { while (iter.HasNextSegment()) { com.epl.geometry.Segment seg = iter.NextSegment(); seg.QueryEnvelope2D(seg_env); com.epl.geometry.RasterizedGeometry2D.HitType hit = rgeom.QueryEnvelopeInGeometry(seg_env); if (hit == com.epl.geometry.RasterizedGeometry2D.HitType.Inside) { clipResult.Add(1); } else { if (hit == com.epl.geometry.RasterizedGeometry2D.HitType.Outside) { clipResult.Add(0); } else { clipResult.Add(-1); unresolvedSegments++; } } } } } } if (polygon.GetPointCount() > 5) { double tol = 0; com.epl.geometry.Geometry clippedPolygon = com.epl.geometry.Clipper.Clip(polygon, clipEnvelope, tol, 0.0); polygon = (com.epl.geometry.Polygon)clippedPolygon; polygonImpl = (com.epl.geometry.MultiPathImpl)polygon._getImpl(); accel = polygonImpl._getAccelerators(); } //update accelerators if (unresolvedSegments < 0) { unresolvedSegments = polylineImpl.GetSegmentCount(); } // Some heuristics to decide if it makes sense to go with fast intersect // vs going with the regular planesweep. double totalPoints = (double)(polylineImpl.GetPointCount() + polygonImpl.GetPointCount()); double thisAlgorithmComplexity = ((double)unresolvedSegments * polygonImpl.GetPointCount()); // assume the worst case. double planesweepComplexity = System.Math.Log(totalPoints) * totalPoints; double empiricConstantFactorPlaneSweep = 4; if (thisAlgorithmComplexity > planesweepComplexity * empiricConstantFactorPlaneSweep) { // Based on the number of input points, we deduced that the // plansweep performance should be better than the brute force // performance. return null; } // resort to planesweep if quadtree does not help com.epl.geometry.QuadTreeImpl polygonQuadTree = null; com.epl.geometry.SegmentIteratorImpl polygonIter = polygonImpl.QuerySegmentIterator(); // Some logic to decide if it makes sense to build a quadtree on the // polygon segments if (accel != null && accel.GetQuadTree() != null) { polygonQuadTree = accel.GetQuadTree(); } if (polygonQuadTree == null && polygonImpl.GetPointCount() > 20) { polygonQuadTree = com.epl.geometry.InternalUtils.BuildQuadTree(polygonImpl); } com.epl.geometry.Polyline result_polyline = (com.epl.geometry.Polyline)polyline.CreateInstance(); com.epl.geometry.MultiPathImpl resultPolylineImpl = (com.epl.geometry.MultiPathImpl)result_polyline._getImpl(); com.epl.geometry.QuadTreeImpl.QuadTreeIteratorImpl qIter = null; com.epl.geometry.SegmentIteratorImpl polylineIter = polylineImpl.QuerySegmentIterator(); double[] @params = new double[9]; com.epl.geometry.AttributeStreamOfDbl intersections = new com.epl.geometry.AttributeStreamOfDbl(0); com.epl.geometry.SegmentBuffer segmentBuffer = new com.epl.geometry.SegmentBuffer(); int start_index = -1; int inCount = 0; int segIndex = 0; bool bOptimized = clipResult.Size() > 0; // The algorithm is like that: // Loop through all the segments of the polyline. // For each polyline segment, intersect it with each of the polygon // segments. // If no intersections found then, // If the polyline segment is completely inside, it is added to the // result polyline. // If it is outside, it is thrown out. // If it intersects, then cut the polyline segment to pieces and test // each part of the intersected result. // The cut pieces will either have one point inside, or one point // outside, or the middle point inside/outside. // int polylinePathIndex = -1; while (polylineIter.NextPath()) { polylinePathIndex = polylineIter.GetPathIndex(); int stateNewPath = 0; int stateAddSegment = 1; int stateManySegments = 2; int stateManySegmentsContinuePath = 2; int stateManySegmentsNewPath = 3; int state = stateNewPath; start_index = -1; inCount = 0; while (polylineIter.HasNextSegment()) { int clipStatus = bOptimized ? (int)clipResult.Get(segIndex) : -1; segIndex++; com.epl.geometry.Segment polylineSeg = polylineIter.NextSegment(); if (clipStatus < 0) { System.Diagnostics.Debug.Assert((clipStatus == -1)); // Analyse polyline segment for intersection with the // polygon. if (polygonQuadTree != null) { if (qIter == null) { qIter = polygonQuadTree.GetIterator(polylineSeg, tolerance); } else { qIter.ResetIterator(polylineSeg, tolerance); } int path_index = -1; for (int ind = qIter.Next(); ind != -1; ind = qIter.Next()) { polygonIter.ResetToVertex(polygonQuadTree.GetElement(ind)); // path_index path_index = polygonIter.GetPathIndex(); com.epl.geometry.Segment polygonSeg = polygonIter.NextSegment(); // intersect polylineSeg and polygonSeg. int count = polylineSeg.Intersect(polygonSeg, null, @params, null, tolerance); for (int i = 0; i < count; i++) { intersections.Add(@params[i]); } } } else { // no quadtree built polygonIter.ResetToFirstPath(); while (polygonIter.NextPath()) { while (polygonIter.HasNextSegment()) { com.epl.geometry.Segment polygonSeg = polygonIter.NextSegment(); // intersect polylineSeg and polygonSeg. int count = polylineSeg.Intersect(polygonSeg, null, @params, null, tolerance); for (int i = 0; i < count; i++) { intersections.Add(@params[i]); } } } } if (intersections.Size() > 0) { // intersections detected. intersections.Sort(0, intersections.Size()); // std::sort(intersections.begin(), // intersections.end()); double t0 = 0; intersections.Add(1.0); int status = -1; for (int i = 0, n = intersections.Size(); i < n; i++) { double t = intersections.Get(i); if (t == t0) { continue; } bool bWholeSegment = false; com.epl.geometry.Segment resSeg; if (t0 != 0 || t != 1.0) { polylineSeg.Cut(t0, t, segmentBuffer); resSeg = segmentBuffer.Get(); } else { resSeg = polylineSeg; bWholeSegment = true; } if (state >= stateManySegments) { resultPolylineImpl.AddSegmentsFromPath(polylineImpl, polylinePathIndex, start_index, inCount, state == stateManySegmentsNewPath); if (AnalyseClipSegment_(polygon, resSeg.GetStartXY(), tolerance) != 1) { if (AnalyseClipSegment_(polygon, resSeg, tolerance) != 1) { return null; } } //someting went wrong we'll falback to slower but robust planesweep code. resultPolylineImpl.AddSegment(resSeg, false); state = stateAddSegment; inCount = 0; } else { status = AnalyseClipSegment_(polygon, resSeg, tolerance); switch (status) { case 1: { if (!bWholeSegment) { resultPolylineImpl.AddSegment(resSeg, state == stateNewPath); state = stateAddSegment; } else { if (state < stateManySegments) { start_index = polylineIter.GetStartPointIndex() - polylineImpl.GetPathStart(polylinePathIndex); inCount = 1; if (state == stateNewPath) { state = stateManySegmentsNewPath; } else { System.Diagnostics.Debug.Assert((state == stateAddSegment)); state = stateManySegmentsContinuePath; } } else { inCount++; } } break; } case 0: { state = stateNewPath; start_index = -1; inCount = 0; break; } default: { return null; } } } // may happen if a segment // coincides with the border. t0 = t; } } else { clipStatus = AnalyseClipSegment_(polygon, polylineSeg.GetStartXY(), tolerance); // simple // case // no // intersection. // Both // points // must // be // inside. if (clipStatus < 0) { System.Diagnostics.Debug.Assert((clipStatus >= 0)); return null; } // something goes wrong, resort to // planesweep System.Diagnostics.Debug.Assert((AnalyseClipSegment_(polygon, polylineSeg.GetEndXY(), tolerance) == clipStatus)); if (clipStatus == 1) { // the whole segment inside if (state < stateManySegments) { System.Diagnostics.Debug.Assert((inCount == 0)); start_index = polylineIter.GetStartPointIndex() - polylineImpl.GetPathStart(polylinePathIndex); if (state == stateNewPath) { state = stateManySegmentsNewPath; } else { System.Diagnostics.Debug.Assert((state == stateAddSegment)); state = stateManySegmentsContinuePath; } } inCount++; } else { System.Diagnostics.Debug.Assert((state < stateManySegments)); start_index = -1; inCount = 0; } } intersections.Clear(false); } else { // clip status is determined by other means if (clipStatus == 0) { // outside System.Diagnostics.Debug.Assert((AnalyseClipSegment_(polygon, polylineSeg, tolerance) == 0)); System.Diagnostics.Debug.Assert((start_index < 0)); System.Diagnostics.Debug.Assert((inCount == 0)); continue; } if (clipStatus == 1) { System.Diagnostics.Debug.Assert((AnalyseClipSegment_(polygon, polylineSeg, tolerance) == 1)); if (state == stateNewPath) { state = stateManySegmentsNewPath; start_index = polylineIter.GetStartPointIndex() - polylineImpl.GetPathStart(polylinePathIndex); } else { if (state == stateAddSegment) { state = stateManySegmentsContinuePath; start_index = polylineIter.GetStartPointIndex() - polylineImpl.GetPathStart(polylinePathIndex); } else { System.Diagnostics.Debug.Assert((state >= stateManySegments)); } } inCount++; continue; } } } if (state >= stateManySegments) { resultPolylineImpl.AddSegmentsFromPath(polylineImpl, polylinePathIndex, start_index, inCount, state == stateManySegmentsNewPath); start_index = -1; } } return result_polyline; }
// Mirrors wkt private static void ExportPolylineToGeoJson_(int export_flags, com.epl.geometry.Polyline polyline, com.epl.geometry.JsonWriter json_writer) { com.epl.geometry.MultiPathImpl polyline_impl = (com.epl.geometry.MultiPathImpl)polyline._getImpl(); int point_count = polyline_impl.GetPointCount(); int path_count = polyline_impl.GetPathCount(); if (point_count > 0 && path_count == 0) { throw new com.epl.geometry.GeometryException("corrupted geometry"); } int precision = 17 - (31 & (export_flags >> 13)); bool bFixedPoint = (com.epl.geometry.GeoJsonExportFlags.geoJsonExportPrecisionFixedPoint & export_flags) != 0; bool b_export_zs = polyline_impl.HasAttribute(com.epl.geometry.VertexDescription.Semantics.Z) && (export_flags & com.epl.geometry.GeoJsonExportFlags.geoJsonExportStripZs) == 0; bool b_export_ms = polyline_impl.HasAttribute(com.epl.geometry.VertexDescription.Semantics.M) && (export_flags & com.epl.geometry.GeoJsonExportFlags.geoJsonExportStripMs) == 0; if (!b_export_zs && b_export_ms) { throw new System.ArgumentException("invalid argument"); } com.epl.geometry.AttributeStreamOfDbl position = null; com.epl.geometry.AttributeStreamOfDbl zs = null; com.epl.geometry.AttributeStreamOfDbl ms = null; com.epl.geometry.AttributeStreamOfInt8 path_flags = null; com.epl.geometry.AttributeStreamOfInt32 paths = null; if (point_count > 0) { position = (com.epl.geometry.AttributeStreamOfDbl)polyline_impl.GetAttributeStreamRef(com.epl.geometry.VertexDescription.Semantics.POSITION); path_flags = polyline_impl.GetPathFlagsStreamRef(); paths = polyline_impl.GetPathStreamRef(); if (b_export_zs) { if (polyline_impl._attributeStreamIsAllocated(com.epl.geometry.VertexDescription.Semantics.Z)) { zs = (com.epl.geometry.AttributeStreamOfDbl)polyline_impl.GetAttributeStreamRef(com.epl.geometry.VertexDescription.Semantics.Z); } } if (b_export_ms) { if (polyline_impl._attributeStreamIsAllocated(com.epl.geometry.VertexDescription.Semantics.M)) { ms = (com.epl.geometry.AttributeStreamOfDbl)polyline_impl.GetAttributeStreamRef(com.epl.geometry.VertexDescription.Semantics.M); } } } if ((export_flags & com.epl.geometry.GeoJsonExportFlags.geoJsonExportPreferMultiGeometry) == 0 && path_count <= 1) { LineStringTaggedText_(precision, bFixedPoint, b_export_zs, b_export_ms, zs, ms, position, path_flags, paths, json_writer); } else { MultiLineStringTaggedText_(precision, bFixedPoint, b_export_zs, b_export_ms, zs, ms, position, path_flags, paths, path_count, json_writer); } }
private static int QuickTest2DPolylinePoint(com.epl.geometry.Polyline geomA, com.epl.geometry.Point2D ptB, double tolerance, int testType) { int mask = com.epl.geometry.OperatorInternalRelationUtils.Relation.Touches | com.epl.geometry.OperatorInternalRelationUtils.Relation.Contains | com.epl.geometry.OperatorInternalRelationUtils.Relation.Within | com.epl.geometry.OperatorInternalRelationUtils.Relation.Disjoint | com.epl.geometry.OperatorInternalRelationUtils.Relation .Intersects; if ((testType & mask) == 0) { return(com.epl.geometry.OperatorInternalRelationUtils.Relation.NoThisRelation); } int res = QuickTest2DMVPointRasterOnly(geomA, ptB, tolerance); if (res > 0) { return(res); } // Go through the segments: double toleranceSqr = tolerance * tolerance; com.epl.geometry.MultiPathImpl mpImpl = (com.epl.geometry.MultiPathImpl)geomA._getImpl(); com.epl.geometry.SegmentIteratorImpl iter = mpImpl.QuerySegmentIterator(); while (iter.NextPath()) { int pathIndex = iter.GetPathIndex(); if (!geomA.IsClosedPath(pathIndex)) { int pathSize = geomA.GetPathSize(pathIndex); int pathStart = geomA.GetPathStart(pathIndex); if (pathSize == 0) { continue; } if (com.epl.geometry.Point2D.SqrDistance(geomA.GetXY(pathStart), ptB) <= toleranceSqr || (pathSize > 1 && com.epl.geometry.Point2D.SqrDistance(geomA.GetXY(pathStart + pathSize - 1), ptB) <= toleranceSqr)) { return((int)com.epl.geometry.OperatorInternalRelationUtils.Relation.Touches); } } if (testType != com.epl.geometry.OperatorInternalRelationUtils.Relation.Touches) { while (iter.HasNextSegment()) { com.epl.geometry.Segment segment = iter.NextSegment(); double t = segment.GetClosestCoordinate(ptB, false); com.epl.geometry.Point2D pt = segment.GetCoord2D(t); if (com.epl.geometry.Point2D.SqrDistance(pt, ptB) <= toleranceSqr) { if ((testType & com.epl.geometry.OperatorInternalRelationUtils.Relation.IntersectsOrDisjoint) != 0) { return(com.epl.geometry.OperatorInternalRelationUtils.Relation.Intersects); } return((int)com.epl.geometry.OperatorInternalRelationUtils.Relation.Contains); } } } } return((testType & com.epl.geometry.OperatorInternalRelationUtils.Relation.IntersectsOrDisjoint) != 0 ? com.epl.geometry.OperatorInternalRelationUtils.Relation.Disjoint : com.epl.geometry.OperatorInternalRelationUtils.Relation.NoThisRelation); }
internal static void TestPointsOnPolyline2D_(com.epl.geometry.Polyline poly, com.epl.geometry.Point2D[] input_points, int count, double tolerance, com.epl.geometry.PolygonUtils.PiPResult[] test_results) { com.epl.geometry.MultiPathImpl mp_impl = (com.epl.geometry.MultiPathImpl)poly._getImpl(); com.epl.geometry.GeometryAccelerators accel = mp_impl._getAccelerators(); com.epl.geometry.RasterizedGeometry2D rgeom = null; if (accel != null) { rgeom = accel.GetRasterizedGeometry(); } int pointsLeft = count; for (int i = 0; i < count; i++) { test_results[i] = com.epl.geometry.PolygonUtils.PiPResult.PiPInside; // set to impossible value if (rgeom != null) { com.epl.geometry.Point2D input_point = input_points[i]; com.epl.geometry.RasterizedGeometry2D.HitType hit = rgeom.QueryPointInGeometry(input_point.x, input_point.y); if (hit == com.epl.geometry.RasterizedGeometry2D.HitType.Outside) { test_results[i] = com.epl.geometry.PolygonUtils.PiPResult.PiPOutside; pointsLeft--; } } } if (pointsLeft != 0) { com.epl.geometry.SegmentIteratorImpl iter = mp_impl.QuerySegmentIterator(); while (iter.NextPath() && pointsLeft != 0) { while (iter.HasNextSegment() && pointsLeft != 0) { com.epl.geometry.Segment segment = iter.NextSegment(); for (int i_1 = 0; i_1 < count && pointsLeft != 0; i_1++) { if (test_results[i_1] == com.epl.geometry.PolygonUtils.PiPResult.PiPInside) { if (segment.IsIntersecting(input_points[i_1], tolerance)) { test_results[i_1] = com.epl.geometry.PolygonUtils.PiPResult.PiPBoundary; pointsLeft--; } } } } } } for (int i_2 = 0; i_2 < count; i_2++) { if (test_results[i_2] == com.epl.geometry.PolygonUtils.PiPResult.PiPInside) { test_results[i_2] = com.epl.geometry.PolygonUtils.PiPResult.PiPOutside; } } }
internal static com.epl.geometry.Geometry LineStringTaggedText(bool b_multi_linestring, int import_flags, com.epl.geometry.WktParser wkt_parser) { com.epl.geometry.MultiPath multi_path; com.epl.geometry.MultiPathImpl multi_path_impl; com.epl.geometry.AttributeStreamOfDbl zs = null; com.epl.geometry.AttributeStreamOfDbl ms = null; com.epl.geometry.AttributeStreamOfDbl position; com.epl.geometry.AttributeStreamOfInt32 paths; com.epl.geometry.AttributeStreamOfInt8 path_flags; position = (com.epl.geometry.AttributeStreamOfDbl)com.epl.geometry.AttributeStreamBase.CreateDoubleStream(0); paths = (com.epl.geometry.AttributeStreamOfInt32)com.epl.geometry.AttributeStreamBase.CreateIndexStream(1, 0); path_flags = (com.epl.geometry.AttributeStreamOfInt8)com.epl.geometry.AttributeStreamBase.CreateByteStream(1, unchecked ((byte)0)); multi_path = new com.epl.geometry.Polyline(); multi_path_impl = (com.epl.geometry.MultiPathImpl)multi_path._getImpl(); int current_token = wkt_parser.NextToken(); if (current_token == com.epl.geometry.WktParser.WktToken.attribute_z) { zs = (com.epl.geometry.AttributeStreamOfDbl)com.epl.geometry.AttributeStreamBase.CreateDoubleStream(0, com.epl.geometry.NumberUtils.TheNaN); multi_path_impl.AddAttribute(com.epl.geometry.VertexDescription.Semantics.Z); wkt_parser.NextToken(); } else { if (current_token == com.epl.geometry.WktParser.WktToken.attribute_m) { ms = (com.epl.geometry.AttributeStreamOfDbl)com.epl.geometry.AttributeStreamBase.CreateDoubleStream(0, com.epl.geometry.NumberUtils.TheNaN); multi_path_impl.AddAttribute(com.epl.geometry.VertexDescription.Semantics.M); wkt_parser.NextToken(); } else { if (current_token == com.epl.geometry.WktParser.WktToken.attribute_zm) { zs = (com.epl.geometry.AttributeStreamOfDbl)com.epl.geometry.AttributeStreamBase.CreateDoubleStream(0, com.epl.geometry.NumberUtils.TheNaN); ms = (com.epl.geometry.AttributeStreamOfDbl)com.epl.geometry.AttributeStreamBase.CreateDoubleStream(0, com.epl.geometry.NumberUtils.TheNaN); multi_path_impl.AddAttribute(com.epl.geometry.VertexDescription.Semantics.Z); multi_path_impl.AddAttribute(com.epl.geometry.VertexDescription.Semantics.M); wkt_parser.NextToken(); } } } int point_count; if (b_multi_linestring) { point_count = MultiLineStringText(zs, ms, position, paths, path_flags, wkt_parser); } else { point_count = LineStringText(false, zs, ms, position, paths, path_flags, wkt_parser); } if (point_count != 0) { System.Diagnostics.Debug.Assert((2 * point_count == position.Size())); multi_path_impl.SetAttributeStreamRef(com.epl.geometry.VertexDescription.Semantics.POSITION, position); multi_path_impl.SetPathStreamRef(paths); multi_path_impl.SetPathFlagsStreamRef(path_flags); if (zs != null) { multi_path_impl.SetAttributeStreamRef(com.epl.geometry.VertexDescription.Semantics.Z, zs); } if (ms != null) { multi_path_impl.SetAttributeStreamRef(com.epl.geometry.VertexDescription.Semantics.M, ms); } multi_path_impl.NotifyModified(com.epl.geometry.MultiVertexGeometryImpl.DirtyFlags.DirtyAll); } return(multi_path); }
internal static com.epl.geometry.Geometry Calculate(com.epl.geometry.Geometry geom, com.epl.geometry.ProgressTracker progress_tracker) { int gt = geom.GetType().Value(); if (gt == com.epl.geometry.Geometry.GeometryType.Polygon) { com.epl.geometry.Polyline dst = new com.epl.geometry.Polyline(geom.GetDescription()); if (!geom.IsEmpty()) { ((com.epl.geometry.MultiPathImpl)geom._getImpl())._copyToUnsafe((com.epl.geometry.MultiPathImpl)dst._getImpl()); } return(dst); } else { if (gt == com.epl.geometry.Geometry.GeometryType.Polyline) { return(CalculatePolylineBoundary_(geom._getImpl(), progress_tracker, false, null)); } else { if (gt == com.epl.geometry.Geometry.GeometryType.Envelope) { com.epl.geometry.Polyline dst = new com.epl.geometry.Polyline(geom.GetDescription()); if (!geom.IsEmpty()) { dst.AddEnvelope((com.epl.geometry.Envelope)geom, false); } return(dst); } else { if (com.epl.geometry.Geometry.IsSegment(gt)) { com.epl.geometry.MultiPoint mp = new com.epl.geometry.MultiPoint(geom.GetDescription()); if (!geom.IsEmpty() && !((com.epl.geometry.Segment)geom).IsClosed()) { com.epl.geometry.Point pt = new com.epl.geometry.Point(); ((com.epl.geometry.Segment)geom).QueryStart(pt); mp.Add(pt); ((com.epl.geometry.Segment)geom).QueryEnd(pt); mp.Add(pt); } return(mp); } else { if (com.epl.geometry.Geometry.IsPoint(gt)) { // returns empty point for points and multipoints. return(null); } } } } } throw new System.ArgumentException(); }
public static void TestEditShape__() { { // Single part polygon com.epl.geometry.Polygon poly = new com.epl.geometry.Polygon(); poly.StartPath(10, 10); poly.LineTo(10, 12); poly.LineTo(14, 15); poly.LineTo(10, 11); com.epl.geometry.EditShape editShape = new com.epl.geometry.EditShape(); int geom = editShape.AddGeometry(poly); com.epl.geometry.Polygon poly2 = (com.epl.geometry.Polygon)editShape.GetGeometry(geom); NUnit.Framework.Assert.IsTrue(poly.Equals(poly2)); } { // Two part poly com.epl.geometry.Polygon poly = new com.epl.geometry.Polygon(); poly.StartPath(10, 10); poly.LineTo(10, 12); poly.LineTo(14, 15); poly.LineTo(10, 11); poly.StartPath(100, 10); poly.LineTo(100, 12); poly.LineTo(14, 150); poly.LineTo(10, 101); poly.LineTo(100, 11); com.epl.geometry.EditShape editShape = new com.epl.geometry.EditShape(); int geom = editShape.AddGeometry(poly); com.epl.geometry.Polygon poly2 = (com.epl.geometry.Polygon)editShape.GetGeometry(geom); NUnit.Framework.Assert.IsTrue(poly.Equals(poly2)); } { // Single part polyline com.epl.geometry.Polyline poly = new com.epl.geometry.Polyline(); poly.StartPath(10, 10); poly.LineTo(10, 12); poly.LineTo(14, 15); poly.LineTo(10, 11); com.epl.geometry.EditShape editShape = new com.epl.geometry.EditShape(); int geom = editShape.AddGeometry(poly); com.epl.geometry.Polyline poly2 = (com.epl.geometry.Polyline)editShape.GetGeometry(geom); NUnit.Framework.Assert.IsTrue(poly.Equals(poly2)); } { // Two part poly com.epl.geometry.Polyline poly = new com.epl.geometry.Polyline(); poly.StartPath(10, 10); poly.LineTo(10, 12); poly.LineTo(14, 15); poly.LineTo(10, 11); poly.StartPath(100, 10); poly.LineTo(100, 12); poly.LineTo(14, 150); poly.LineTo(10, 101); poly.LineTo(100, 11); com.epl.geometry.EditShape editShape = new com.epl.geometry.EditShape(); int geom = editShape.AddGeometry(poly); com.epl.geometry.Polyline poly2 = (com.epl.geometry.Polyline)editShape.GetGeometry(geom); NUnit.Framework.Assert.IsTrue(poly.Equals(poly2)); } { // Five part poly. Close one of parts to test if it works. com.epl.geometry.Polyline poly = new com.epl.geometry.Polyline(); poly.StartPath(10, 10); poly.LineTo(10, 12); poly.LineTo(14, 15); poly.LineTo(10, 11); poly.StartPath(100, 10); poly.LineTo(100, 12); poly.LineTo(14, 150); poly.LineTo(10, 101); poly.LineTo(100, 11); poly.StartPath(1100, 101); poly.LineTo(1300, 132); poly.LineTo(144, 150); poly.LineTo(106, 1051); poly.LineTo(1600, 161); poly.StartPath(100, 190); poly.LineTo(1800, 192); poly.LineTo(184, 8150); poly.LineTo(1080, 181); poly.StartPath(1030, 10); poly.LineTo(1300, 132); poly.LineTo(314, 3150); poly.LineTo(310, 1301); poly.LineTo(3100, 311); com.epl.geometry.EditShape editShape = new com.epl.geometry.EditShape(); int geom = editShape.AddGeometry(poly); editShape.SetClosedPath(editShape.GetNextPath(editShape.GetFirstPath(geom)), true); ((com.epl.geometry.MultiPathImpl)poly._getImpl()).ClosePathWithLine(1); com.epl.geometry.Polyline poly2 = (com.epl.geometry.Polyline)editShape.GetGeometry(geom); NUnit.Framework.Assert.IsTrue(poly.Equals(poly2)); } { // Test erase com.epl.geometry.Polyline poly = new com.epl.geometry.Polyline(); poly.StartPath(10, 10); poly.LineTo(10, 12); poly.LineTo(314, 3150); poly.LineTo(310, 1301); poly.LineTo(3100, 311); com.epl.geometry.EditShape editShape = new com.epl.geometry.EditShape(); int geom = editShape.AddGeometry(poly); int vertex = editShape.GetFirstVertex(editShape.GetFirstPath(geom)); vertex = editShape.RemoveVertex(vertex, true); vertex = editShape.GetNextVertex(vertex); editShape.RemoveVertex(vertex, true); com.epl.geometry.Polyline poly2 = (com.epl.geometry.Polyline)editShape.GetGeometry(geom); poly.SetEmpty(); poly.StartPath(10, 12); poly.LineTo(310, 1301); poly.LineTo(3100, 311); NUnit.Framework.Assert.IsTrue(poly.Equals(poly2)); } { // Test erase com.epl.geometry.Polygon poly = new com.epl.geometry.Polygon(); poly.StartPath(10, 10); poly.LineTo(10, 12); poly.LineTo(314, 3150); poly.LineTo(310, 1301); poly.LineTo(3100, 311); com.epl.geometry.EditShape editShape = new com.epl.geometry.EditShape(); int geom = editShape.AddGeometry(poly); int vertex = editShape.GetFirstVertex(editShape.GetFirstPath(geom)); vertex = editShape.RemoveVertex(vertex, true); vertex = editShape.GetNextVertex(vertex); editShape.RemoveVertex(vertex, true); com.epl.geometry.Polygon poly2 = (com.epl.geometry.Polygon)editShape.GetGeometry(geom); poly.SetEmpty(); poly.StartPath(10, 12); poly.LineTo(310, 1301); poly.LineTo(3100, 311); NUnit.Framework.Assert.IsTrue(poly.Equals(poly2)); } { // Test Filter Close Points com.epl.geometry.Polygon poly = new com.epl.geometry.Polygon(); poly.StartPath(10, 10); poly.LineTo(10, 10.001); poly.LineTo(10.001, 10); com.epl.geometry.EditShape editShape = new com.epl.geometry.EditShape(); int geom = editShape.AddGeometry(poly); editShape.FilterClosePoints(0.002, true, false); com.epl.geometry.Polygon poly2 = (com.epl.geometry.Polygon)editShape.GetGeometry(geom); NUnit.Framework.Assert.IsTrue(poly2.IsEmpty()); } { // Test Filter Close Points com.epl.geometry.Polygon poly = new com.epl.geometry.Polygon(); poly.StartPath(10, 10); poly.LineTo(10, 10.0025); poly.LineTo(11.0, 10); com.epl.geometry.EditShape editShape = new com.epl.geometry.EditShape(); int geom = editShape.AddGeometry(poly); editShape.FilterClosePoints(0.002, true, false); com.epl.geometry.Polygon poly2 = (com.epl.geometry.Polygon)editShape.GetGeometry(geom); NUnit.Framework.Assert.IsTrue(!poly2.IsEmpty()); } { // Test Filter Close Points com.epl.geometry.Polygon poly = new com.epl.geometry.Polygon(); poly.StartPath(10, 10); poly.LineTo(10, 10.001); poly.LineTo(11.0, 10); com.epl.geometry.EditShape editShape = new com.epl.geometry.EditShape(); int geom = editShape.AddGeometry(poly); editShape.FilterClosePoints(0.002, true, false); com.epl.geometry.Polygon poly2 = (com.epl.geometry.Polygon)editShape.GetGeometry(geom); NUnit.Framework.Assert.IsTrue(poly2.IsEmpty()); } { // Test attribute splitting 1 com.epl.geometry.Polyline polyline = new com.epl.geometry.Polyline(); polyline.StartPath(0, 0); polyline.LineTo(1, 1); polyline.LineTo(2, 2); polyline.LineTo(3, 3); polyline.LineTo(4, 4); polyline.StartPath(5, 5); polyline.LineTo(6, 6); polyline.LineTo(7, 7); polyline.LineTo(8, 8); polyline.LineTo(9, 9); polyline.AddAttribute(com.epl.geometry.VertexDescription.Semantics.Z); polyline.SetAttribute(com.epl.geometry.VertexDescription.Semantics.Z, 0, 0, 4); polyline.SetAttribute(com.epl.geometry.VertexDescription.Semantics.Z, 1, 0, 8); polyline.SetAttribute(com.epl.geometry.VertexDescription.Semantics.Z, 2, 0, 12); polyline.SetAttribute(com.epl.geometry.VertexDescription.Semantics.Z, 3, 0, 16); polyline.SetAttribute(com.epl.geometry.VertexDescription.Semantics.Z, 4, 0, 20); polyline.SetAttribute(com.epl.geometry.VertexDescription.Semantics.Z, 5, 0, 22); polyline.SetAttribute(com.epl.geometry.VertexDescription.Semantics.Z, 6, 0, 26); polyline.SetAttribute(com.epl.geometry.VertexDescription.Semantics.Z, 7, 0, 30); polyline.SetAttribute(com.epl.geometry.VertexDescription.Semantics.Z, 8, 0, 34); polyline.SetAttribute(com.epl.geometry.VertexDescription.Semantics.Z, 9, 0, 38); com.epl.geometry.EditShape shape = new com.epl.geometry.EditShape(); int geometry = shape.AddGeometry(polyline); com.epl.geometry.AttributeStreamOfInt32 vertex_handles = new com.epl.geometry.AttributeStreamOfInt32(0); for (int path = shape.GetFirstPath(geometry); path != -1; path = shape.GetNextPath(path)) { for (int vertex = shape.GetFirstVertex(path); vertex != -1; vertex = shape.GetNextVertex(vertex)) { if (vertex != shape.GetLastVertex(path)) { vertex_handles.Add(vertex); } } } double[] t = new double[1]; for (int i = 0; i < vertex_handles.Size(); i++) { int vertex = vertex_handles.Read(i); t[0] = 0.5; shape.SplitSegment(vertex, t, 1); } com.epl.geometry.Polyline chopped_polyline = (com.epl.geometry.Polyline)shape.GetGeometry(geometry); NUnit.Framework.Assert.IsTrue(chopped_polyline.GetPointCount() == 18); double att_ = 4; for (int i_1 = 0; i_1 < 18; i_1++) { double att = chopped_polyline.GetAttributeAsDbl(com.epl.geometry.VertexDescription.Semantics.Z, i_1, 0); NUnit.Framework.Assert.IsTrue(att == att_); att_ += 2; } } { // Test attribute splitting 2 com.epl.geometry.Polyline line1 = new com.epl.geometry.Polyline(); com.epl.geometry.Polyline line2 = new com.epl.geometry.Polyline(); line1.AddAttribute(com.epl.geometry.VertexDescription.Semantics.M); line2.AddAttribute(com.epl.geometry.VertexDescription.Semantics.M); line1.StartPath(0, 0); line1.LineTo(10, 10); line2.StartPath(10, 0); line2.LineTo(0, 10); line1.SetAttribute(com.epl.geometry.VertexDescription.Semantics.M, 0, 0, 7); line1.SetAttribute(com.epl.geometry.VertexDescription.Semantics.M, 1, 0, 17); line2.SetAttribute(com.epl.geometry.VertexDescription.Semantics.M, 0, 0, 5); line2.SetAttribute(com.epl.geometry.VertexDescription.Semantics.M, 1, 0, 15); com.epl.geometry.EditShape shape = new com.epl.geometry.EditShape(); int g1 = shape.AddGeometry(line1); int g2 = shape.AddGeometry(line2); com.epl.geometry.CrackAndCluster.Execute(shape, 0.001, null, true); com.epl.geometry.Polyline chopped_line1 = (com.epl.geometry.Polyline)shape.GetGeometry(g1); com.epl.geometry.Polyline chopped_line2 = (com.epl.geometry.Polyline)shape.GetGeometry(g2); double att1 = chopped_line1.GetAttributeAsDbl(com.epl.geometry.VertexDescription.Semantics.M, 1, 0); double att2 = chopped_line2.GetAttributeAsDbl(com.epl.geometry.VertexDescription.Semantics.M, 1, 0); NUnit.Framework.Assert.IsTrue(att1 == 12); NUnit.Framework.Assert.IsTrue(att2 == 10); } { // Test attribute splitting 3 com.epl.geometry.Polygon polygon = new com.epl.geometry.Polygon(); polygon.AddAttribute(com.epl.geometry.VertexDescription.Semantics.M); polygon.StartPath(0, 0); polygon.LineTo(0, 10); polygon.LineTo(10, 10); polygon.LineTo(10, 0); polygon.SetAttribute(com.epl.geometry.VertexDescription.Semantics.M, 0, 0, 7); polygon.SetAttribute(com.epl.geometry.VertexDescription.Semantics.M, 1, 0, 17); polygon.SetAttribute(com.epl.geometry.VertexDescription.Semantics.M, 2, 0, 23); polygon.SetAttribute(com.epl.geometry.VertexDescription.Semantics.M, 3, 0, 43); com.epl.geometry.EditShape shape = new com.epl.geometry.EditShape(); int geometry = shape.AddGeometry(polygon); com.epl.geometry.AttributeStreamOfInt32 vertex_handles = new com.epl.geometry.AttributeStreamOfInt32(0); int start_v = shape.GetFirstVertex(shape.GetFirstPath(geometry)); int v = start_v; do { vertex_handles.Add(v); v = shape.GetNextVertex(v); }while (v != start_v); double[] t = new double[1]; for (int i = 0; i < vertex_handles.Size(); i++) { int v1 = vertex_handles.Read(i); t[0] = 0.5; shape.SplitSegment(v1, t, 1); } com.epl.geometry.Polygon cut_polygon = (com.epl.geometry.Polygon)shape.GetGeometry(geometry); NUnit.Framework.Assert.IsTrue(cut_polygon.GetPointCount() == 8); com.epl.geometry.Point2D pt0 = cut_polygon.GetXY(0); double a0 = cut_polygon.GetAttributeAsDbl(com.epl.geometry.VertexDescription.Semantics.M, 0, 0); NUnit.Framework.Assert.IsTrue(a0 == 25); com.epl.geometry.Point2D pt1 = cut_polygon.GetXY(1); double a1 = cut_polygon.GetAttributeAsDbl(com.epl.geometry.VertexDescription.Semantics.M, 1, 0); NUnit.Framework.Assert.IsTrue(a1 == 7); com.epl.geometry.Point2D pt2 = cut_polygon.GetXY(2); double a2 = cut_polygon.GetAttributeAsDbl(com.epl.geometry.VertexDescription.Semantics.M, 2, 0); NUnit.Framework.Assert.IsTrue(a2 == 12); com.epl.geometry.Point2D pt3 = cut_polygon.GetXY(3); double a3 = cut_polygon.GetAttributeAsDbl(com.epl.geometry.VertexDescription.Semantics.M, 3, 0); NUnit.Framework.Assert.IsTrue(a3 == 17); com.epl.geometry.Point2D pt4 = cut_polygon.GetXY(4); double a4 = cut_polygon.GetAttributeAsDbl(com.epl.geometry.VertexDescription.Semantics.M, 4, 0); NUnit.Framework.Assert.IsTrue(a4 == 20); com.epl.geometry.Point2D pt5 = cut_polygon.GetXY(5); double a5 = cut_polygon.GetAttributeAsDbl(com.epl.geometry.VertexDescription.Semantics.M, 5, 0); NUnit.Framework.Assert.IsTrue(a5 == 23); com.epl.geometry.Point2D pt6 = cut_polygon.GetXY(6); double a6 = cut_polygon.GetAttributeAsDbl(com.epl.geometry.VertexDescription.Semantics.M, 6, 0); NUnit.Framework.Assert.IsTrue(a6 == 33); com.epl.geometry.Point2D pt7 = cut_polygon.GetXY(7); double a7 = cut_polygon.GetAttributeAsDbl(com.epl.geometry.VertexDescription.Semantics.M, 7, 0); NUnit.Framework.Assert.IsTrue(a7 == 43); } }