コード例 #1
0
        private static Location LocateInPolygonRing(Coordinate p, LinearRing ring)
        {
            // bounding-box check
            if (!ring.EnvelopeInternal.Intersects(p))
            {
                return(Location.Exterior);
            }

            return(PointLocation.LocateInRing(p, ring.CoordinateSequence));
        }
コード例 #2
0
        /// <summary>
        /// Uses a heuristic to reduce the number of points scanned to compute the hull.
        /// The heuristic is to find a polygon guaranteed to
        /// be in (or on) the hull, and eliminate all points inside it.
        /// A quadrilateral defined by the extremal points
        /// in the four orthogonal directions
        /// can be used, but even more inclusive is
        /// to use an octilateral defined by the points in the 8 cardinal directions.
        /// Note that even if the method used to determine the polygon vertices
        /// is not 100% robust, this does not affect the robustness of the convex hull.
        /// <para>
        /// To satisfy the requirements of the Graham Scan algorithm,
        /// the returned array has at least 3 entries.
        /// </para>
        /// </summary>
        /// <param name="pts">The coordinates to reduce</param>
        /// <returns>The reduced array of coordinates</returns>
        private static Coordinate[] Reduce(Coordinate[] pts)
        {
            var polyPts = ComputeOctRing(pts /*_inputPts*/);

            // unable to compute interior polygon for some reason
            if (polyPts == null)
            {
                return(pts);
            }

            // add points defining polygon
            var reducedSet = new HashSet <Coordinate>();

            for (int i = 0; i < polyPts.Length; i++)
            {
                reducedSet.Add(polyPts[i]);
            }

            /*
             * Add all unique points not in the interior poly.
             * PointLocation.IsInRing is not defined for points actually on the ring,
             * but this doesn't matter since the points of the interior polygon
             * are forced to be in the reduced set.
             */
            for (int i = 0; i < pts.Length; i++)
            {
                if (!PointLocation.IsInRing(pts[i], polyPts))
                {
                    reducedSet.Add(pts[i]);
                }
            }

            var reducedPts = CoordinateArrays.ToCoordinateArray(reducedSet);// new Coordinate[reducedSet.Count];

            Array.Sort(reducedPts);

            // ensure that computed array has at least 3 points (not necessarily unique)
            if (reducedPts.Length < 3)
            {
                return(PadArray3(reducedPts));
            }

            return(reducedPts);
        }
コード例 #3
0
        private static Location LocateOnLineString(Coordinate p, LineString l)
        {
            // bounding-box check
            if (!l.EnvelopeInternal.Intersects(p))
            {
                return(Location.Exterior);
            }

            var pt = l.Coordinates;

            if (!l.IsClosed)
            {
                if (p.Equals(pt[0]) || p.Equals(pt[pt.Length - 1]))
                {
                    return(Location.Boundary);
                }
            }
            if (PointLocation.IsOnLine(p, pt))
            {
                return(Location.Interior);
            }
            return(Location.Exterior);
        }