SciPy Create 2D Polygon Mask SciPy Create 2D Polygon Mask python python

SciPy Create 2D Polygon Mask


The answer turns out to be quite simple:

import numpyfrom PIL import Image, ImageDraw# polygon = [(x1,y1),(x2,y2),...] or [x1,y1,x2,y2,...]# width = ?# height = ?img = Image.new('L', (width, height), 0)ImageDraw.Draw(img).polygon(polygon, outline=1, fill=1)mask = numpy.array(img)


As a slightly more direct alternative to @Anil's answer, matplotlib has matplotlib.nxutils.points_inside_poly that can be used to quickly rasterize an arbitrary polygon. E.g.

import numpy as npfrom matplotlib.nxutils import points_inside_polynx, ny = 10, 10poly_verts = [(1,1), (5,1), (5,9),(3,2),(1,1)]# Create vertex coordinates for each grid cell...# (<0,0> is at the top left of the grid in this system)x, y = np.meshgrid(np.arange(nx), np.arange(ny))x, y = x.flatten(), y.flatten()points = np.vstack((x,y)).Tgrid = points_inside_poly(points, poly_verts)grid = grid.reshape((ny,nx))print grid

Which yields (a boolean numpy array):

[[False False False False False False False False False False] [False  True  True  True  True False False False False False] [False False False  True  True False False False False False] [False False False False  True False False False False False] [False False False False  True False False False False False] [False False False False  True False False False False False] [False False False False False False False False False False] [False False False False False False False False False False] [False False False False False False False False False False] [False False False False False False False False False False]]

You should be able to pass grid to any of the scipy.ndimage.morphology functions quite nicely.


An update on Joe's comment.Matplotlib API has changed since the comment was posted, and now you need to use a method provided by a submodule matplotlib.path.

Working code is below.

import numpy as npfrom matplotlib.path import Pathnx, ny = 10, 10poly_verts = [(1,1), (5,1), (5,9),(3,2),(1,1)]# Create vertex coordinates for each grid cell...# (<0,0> is at the top left of the grid in this system)x, y = np.meshgrid(np.arange(nx), np.arange(ny))x, y = x.flatten(), y.flatten()points = np.vstack((x,y)).Tpath = Path(poly_verts)grid = path.contains_points(points)grid = grid.reshape((ny,nx))print grid