private IntersectionResults BuildFinalResults(Polygon2 intersectedPolygon) { Contract.Requires(intersectedPolygon != null); Contract.Ensures(Contract.Result<IntersectionResults>() != null); Contract.Ensures(intersectedPolygon.Count >= Contract.OldValue(intersectedPolygon).Count); if (intersectedPolygon.Count == 0) { var untouchedA = FindUntouchedRingsA(); var untouchedB = FindUntouchedRingsB(); intersectedPolygon.AddRange(QualifyRings(untouchedA, untouchedB, true)); intersectedPolygon.AddRange(QualifyRings(untouchedB, untouchedA, false)); } else { var intersectedResultTree = new RingBoundaryTree(intersectedPolygon); intersectedPolygon.AddRange( FilterQualifiedRingsToBoundaryTree( QualifyRings(FindUntouchedRingsA(), B, true), intersectedResultTree ) ); intersectedPolygon.AddRange( FilterQualifiedRingsToBoundaryTree( QualifyRings(FindUntouchedRingsB(), A, false), intersectedResultTree ) ); } return new IntersectionResults { Polygon = intersectedPolygon }; }
private static List<Ring2> QualifyRings( Polygon2 untouchedRings, Polygon2 polygon, bool qualifyEqual ) { Contract.Requires(untouchedRings != null); Contract.Requires(polygon != null); Contract.Ensures(Contract.Result<List<Ring2>>() != null); Contract.Ensures(Contract.ForAll(Contract.Result<List<Ring2>>(), x => null != x)); var result = new List<Ring2>(); var ringTree = new RingBoundaryTree(polygon); foreach (var ring in untouchedRings) { Contract.Assume(ring != null); // TODO: speed this up through some kind of magic, like RingBoundaryTree or something // TODO: var eq = new SpatialEqualityComparerThing(ringA); var stuff = otherRings.Where(r = > eq.SpatiallyEqual(r)); if (polygon.Any(r => ring.SpatiallyEqual(r))) { if (qualifyEqual) result.Add(ring.Clone()); } else if (ringTree.NonIntersectingContains(ring)) result.Add(ring.Clone()); } Contract.Assume(Contract.ForAll(result, x => null != x)); return result; }
private static IEnumerable<Ring2> FilterQualifiedRingsToBoundaryTree(List<Ring2> rings, RingBoundaryTree boundaryTree) { Contract.Requires(rings != null); Contract.Requires(boundaryTree != null); Contract.Ensures(Contract.Result<IEnumerable<Ring2>>() != null); Contract.Ensures(Contract.ForAll(Contract.Result<IEnumerable<Ring2>>(), x => x != null)); return rings.Where(ring => ring.Hole.GetValueOrDefault() == boundaryTree.NonIntersectingContains(ring)); }