/// <summary> /// Gets the segments from the provided ring that run along the provided alongPath. /// </summary> /// <param name="targetRing"></param> /// <param name="alongPath"></param> /// <returns></returns> private static IGeometry GetRingSubcurveAlong([NotNull] IRing targetRing, [NotNull] IPath alongPath) { IGeometry result = SegmentReplacementUtils.GetSegmentsBetween( alongPath.FromPoint, alongPath.ToPoint, targetRing); IGeometry highLevelResult = GeometryUtils.GetHighLevelGeometry(alongPath, true); IGeometry highLevelTarget = GeometryUtils.GetHighLevelGeometry(result, true); if (!GeometryUtils.InteriorIntersects(highLevelResult, highLevelTarget)) { // try the other side of the ring result = SegmentReplacementUtils.GetSegmentsBetween( alongPath.ToPoint, alongPath.FromPoint, targetRing); } Marshal.ReleaseComObject(highLevelResult); Marshal.ReleaseComObject(highLevelTarget); return(result); }
private IPath GetReplacedSegmentsForOtherGeometry( [NotNull] IGeometry geometryToReshape, [NotNull] IPoint betweenSourceIntersectionPoint, [NotNull] IPoint andTargetIntersectionPoint) { Assert.NotNull(_individualReshapes); foreach ( KeyValuePair <IGeometry, IList <ReshapeInfo> > individualReshape in _individualReshapes) { if (individualReshape.Key == geometryToReshape) { continue; } foreach (ReshapeInfo reshapeInfo in individualReshape.Value) { IPath replacedSegments = reshapeInfo.ReplacedSegments; if (replacedSegments != null) { IGeometry highLevelReplacedSegments = GeometryUtils.GetHighLevelGeometry(replacedSegments, true); if ( GeometryUtils.Intersects(highLevelReplacedSegments, betweenSourceIntersectionPoint) && GeometryUtils.Intersects(highLevelReplacedSegments, andTargetIntersectionPoint)) { return(SegmentReplacementUtils.GetSegmentsBetween( betweenSourceIntersectionPoint, andTargetIntersectionPoint, replacedSegments)); } } } } return(null); }
private IPath CalculateSourceTargetPointsConnectLine(IPoint sourceConnectPoint, IPoint targetConnectPoint) { IPath result; var unionReplacedPolyline = (IPolyline)GeometryUtils.GetHighLevelGeometry(_unionReshapeInfo.ReplacedSegments); if (GeometryUtils.Intersects(targetConnectPoint, unionReplacedPolyline)) { // use the connection along the replaced segments result = SegmentReplacementUtils.GetSegmentsBetween( sourceConnectPoint, targetConnectPoint, _unionReshapeInfo.ReplacedSegments); } else { result = GeometryFactory.CreatePath(sourceConnectPoint, targetConnectPoint); } return(result); }
private static IPolyline GetTargetSegmentsAlong( [NotNull] IPolyline targetPolyline, [NotNull] IPolyline alongPolyline, double originalTolerance) { // NOTE: The targetPolyline must be simplified i.e. the adjacent parts should be merged. var exactDifferences = (IGeometryCollection)GeometryFactory.CreateEmptyGeometry(alongPolyline); foreach (IPath differencePath in GeometryUtils.GetPaths(alongPolyline)) { IPath targetPath = GetUniqueTargetPathRunningAlong( targetPolyline, differencePath, originalTolerance); // NOTE: Sometimes, especially with non-linear segments and non-micro-resolution, this logic does not work because // the difference between non-linear geometries can look extremely weird (i.e. incorrect multiparts) // See CanReshapeAlongNonLinearSegmentsPolygonCircleWithMinimumTolerance() in GeometryReshaperTest if (targetPath == null) { _msg.DebugFormat( "Unable to use exact target geometry, because no unique target path found running along {0}. The standard difference (using minimum tolerance) is used instead.", GeometryUtils.ToString(differencePath)); return(alongPolyline); } Assert.NotNull(targetPath, "No target part found when searching with the difference part"); IGeometry exactDifferencePart; if (targetPath.IsClosed) { if (differencePath.IsClosed) { exactDifferencePart = GeometryFactory.Clone(targetPath); } else { IRing targetRing = GeometryFactory.CreateRing(targetPath); exactDifferencePart = GetRingSubcurveAlong(targetRing, differencePath); } } else { exactDifferencePart = SegmentReplacementUtils.GetSegmentsBetween( differencePath.FromPoint, differencePath.ToPoint, targetPath); } exactDifferences.AddGeometry(exactDifferencePart); } var result = (IPolyline)exactDifferences; GeometryUtils.Simplify(result, true, true); return(result); }