예제 #1
0
        /// <summary>
        /// Tests whether the rectangle is within a given distance of the polyline,
        /// where the distance is given by the metric lat^2 + long^2 in WGS84
        /// coordinates (so it doesn't correspond to real distance).
        /// </summary>
        /// <returns><c>true</c>, if rect is within distance, <c>false</c> otherwise.</returns>
        /// <param name="geoRect">A valid geo rectangle.</param>
        /// <param name="distance">Distance in units of sqrt(lat^2 + long^2).</param>
        public bool RectWithinDistance(Rect geoRect, double distance)
        {
            if (!GeoRectUtils.IsValidGeoRect(geoRect))
            {
                throw new ArgumentException("Rectangle must be valid geo rectangle.");
            }

            // Try fast heuristics for longer polylines.
            if (Points.Count >= 10)
            {
                Rect fattenedBounds = BoundingRect();
                fattenedBounds.xMin -= distance;
                fattenedBounds.yMin -= distance;
                fattenedBounds.xMax += distance;
                fattenedBounds.yMax += distance;

                // Ensure rectangle is within geo bounds.
                fattenedBounds.yMin = Math.Max(-90, fattenedBounds.yMin);
                fattenedBounds.yMax = Math.Min(90, fattenedBounds.yMax);

                // Quick test to rule out certain cases (good for long polylines)
                if (!GeoRectUtils.Intersect(geoRect, fattenedBounds))
                {
                    return(false);
                }

                GeoPolyline firstHalf  = new GeoPolyline(this, 0, Points.Count / 2);
                GeoPolyline secondHalf = new GeoPolyline(this, Points.Count / 2, Points.Count);

                return(firstHalf.RectWithinDistance(geoRect, distance) ||
                       secondHalf.RectWithinDistance(geoRect, distance));
            }

            if (Points.Count >= 2)
            {
                return(Segments.Any(segment => GeoRectUtils.RectNearSegment(segment, geoRect, distance)));
            }

            if (Points.Count == 1)
            {
                // Perform a capsule test on a single point (this amounts to
                // a circle test).
                return(GeoRectUtils.RectNearSegment(new GeoSegment(Points[0], Points[0]), geoRect, distance));
            }

            return(true);
        }
예제 #2
0
 public bool Contains(GeoCoordinates coordinates)
 {
     return(GeoRectUtils.GeoContains(Bounds, coordinates));
 }
예제 #3
0
 /// <summary>
 /// Checks whether this quad covers some of the area containing <paramref name="geoRect"/>.
 /// </summary>
 /// <returns>True if this intersects the given rectangle, false otherwise.</returns>
 /// <param name="geoRect">The rectangle for which to test for intersection.</param>
 public bool Intersects(Rect geoRect)
 {
     return(GeoRectUtils.Intersect(Bounds, geoRect));
 }