Python NumPy/OpenCV 2:如何裁剪非矩形区域?

声明:本页面是StackOverFlow热门问题的中英对照翻译,遵循CC BY-SA 4.0协议,如果您需要使用它,必须同样遵循CC BY-SA许可,注明原文地址和作者信息,同时你必须将它归于原作者(不是我):StackOverFlow 原文地址: http://stackoverflow.com/questions/15341538/
Warning: these are provided under cc-by-sa 4.0 license. You are free to use/share it, But you must attribute it to the original authors (not me): StackOverFlow

提示:将鼠标放在中文语句上可以显示对应的英文。显示中英文
时间:2020-08-18 19:51:50  来源:igfitidea点击:

NumPy/OpenCV 2: how do I crop non-rectangular region?

pythonopencvimage-processingnumpy

提问by ffriend

I have a set of points that make a shape(closed polyline). Now I want to copy/crop all pixels from some image inside this shape, leaving the rest black/transparent. How do I do this?

我有一组形成形状的点(闭合折线)。现在我想从这个形状内的某个图像复制/裁剪所有像素,剩下的黑色/透明。我该怎么做呢?

For example, I have this:

例如,我有这个:

enter image description here

在此处输入图片说明

and I want to get this:

我想得到这个:

enter image description here

在此处输入图片说明

采纳答案by KobeJohn

*edit - updated to work with images that have an alpha channel.

*edit - 更新以处理具有 Alpha 通道的图像。

This worked for me:

这对我有用:

  • Make a mask with all black (all masked)
  • Fill a polygon with white in the shape of your ROI
  • combine the mask and your image to get the ROI with black everywhere else
  • 做一个全黑的面具(全部蒙面)
  • 以 ROI 的形状用白色填充多边形
  • 将蒙版和您的图像结合起来,以在其他地方获得黑色的 ROI

You probably just want to keep the image and mask separate for functions that accept masks. However, I believe this does what you specifically asked for:

对于接受掩码的函数,您可能只想将图像和掩码分开。但是,我相信这可以满足您的具体要求:

import cv2
import numpy as np

# original image
# -1 loads as-is so if it will be 3 or 4 channel as the original
image = cv2.imread('image.png', -1)
# mask defaulting to black for 3-channel and transparent for 4-channel
# (of course replace corners with yours)
mask = np.zeros(image.shape, dtype=np.uint8)
roi_corners = np.array([[(10,10), (300,300), (10,300)]], dtype=np.int32)
# fill the ROI so it doesn't get wiped out when the mask is applied
channel_count = image.shape[2]  # i.e. 3 or 4 depending on your image
ignore_mask_color = (255,)*channel_count
cv2.fillPoly(mask, roi_corners, ignore_mask_color)
# from Masterfool: use cv2.fillConvexPoly if you know it's convex

# apply the mask
masked_image = cv2.bitwise_and(image, mask)

# save the result
cv2.imwrite('image_masked.png', masked_image)

回答by Kanish Mathew

The following code would be helpful for cropping the images and get them in a white background.

以下代码将有助于裁剪图像并将它们置于白色背景中。

import cv2
import numpy as np

# load the image
image_path = 'input image path'
image = cv2.imread(image_path)

# create a mask with white pixels
mask = np.ones(image.shape, dtype=np.uint8)
mask.fill(255)

# points to be cropped
roi_corners = np.array([[(0, 300), (1880, 300), (1880, 400), (0, 400)]], dtype=np.int32)
# fill the ROI into the mask
cv2.fillPoly(mask, roi_corners, 0)

# The mask image
cv2.imwrite('image_masked.png', mask)

# applying th mask to original image
masked_image = cv2.bitwise_or(image, mask)

# The resultant image
cv2.imwrite('new_masked_image.png', masked_image)

Input Image: input image

输入图像: 输入图像

Mask Image: mask image

面具图片: 蒙版图像

Resultant output image: enter image description here

结果输出图像: 在此处输入图片说明