예제 #1
0
def separate_points_by_polygon(points,
                               polygon,
                               closed=True,
                               check_input=True,
                               use_numpy=True):
    """Determine whether points are inside or outside a polygon.

    Args:
        * points: Tuple of (x, y) coordinates, or list of tuples
        * polygon: list or Nx2 array of polygon vertices
        * closed: (optional) determine whether points on boundary should be
              regarded as belonging to the polygon (closed = True)
              or not (closed = False)
        * check_input: Allows faster execution if set to False
        * use_numpy: Use the fast numpy implementation

    Returns:
        * indices_inside_polygon: array of indices of points
              falling inside the polygon
        * indices_outside_polygon: array of indices of points
              falling outside the polygon

    Raises: A generic Exception is raised for unexpected input.

    Example:

        U = [[0,0], [1,0], [1,1], [0,1]]  # Unit square
        separate_points_by_polygon( [[0.5, 0.5], [1, -0.5], [0.3, 0.2]], U)

        will return the indices [0, 2, 1] and count == 2 as only the first
        and the last point are inside the unit square

    Remarks:
        The vertices may be listed clockwise or counterclockwise and
        the first point may optionally be repeated.
        Polygons do not need to be convex.
        Polygons can have holes in them and points inside a hole is
        regarded as being outside the polygon.

    Algorithm is based on work by Darel Finley,
    http://www.alienryderflex.com/polygon/
    """

    if check_input:
        # Input checks
        msg = 'Keyword argument "closed" must be boolean'
        if not isinstance(closed, bool):
            raise PolygonInputError(msg)

        try:
            points = ensure_numeric(points, numpy.float)
        except Exception, e:
            msg = ('Points could not be converted to numeric array: %s' %
                   str(e))
            raise PolygonInputError(msg)

        try:
            polygon = ensure_numeric(polygon, numpy.float)
        except Exception, e:
            msg = ('Polygon could not be converted to numeric array: %s' %
                   str(e))
            raise PolygonInputError(msg)
예제 #2
0
            points = ensure_numeric(points, numpy.float)
        except Exception, e:
            msg = ('Points could not be converted to numeric array: %s' %
                   str(e))
            raise PolygonInputError(msg)

        try:
            polygon = ensure_numeric(polygon, numpy.float)
        except Exception, e:
            msg = ('Polygon could not be converted to numeric array: %s' %
                   str(e))
            raise PolygonInputError(msg)

        msg = 'Polygon array must be a 2d array of vertices'
        if len(polygon.shape) != 2:
            raise PolygonInputError(msg)

        msg = 'Polygon array must have two columns'
        if polygon.shape[1] != 2:
            raise PolygonInputError(msg)

        msg = ('Points array must be 1 or 2 dimensional. '
               'I got %d dimensions: %s' % (len(points.shape), points))
        if not 0 < len(points.shape) < 3:
            raise PolygonInputError(msg)

        if len(points.shape) == 1:
            # Only one point was passed in. Convert to array of points.
            points = numpy.reshape(points, (1, 2))

        msg = ('Point array must have two columns (x,y), '