Alpha掩蔽非正方形区域python cv2

时间:2017-05-31 16:54:49

标签: python opencv numpy

我有一个2d numpy数组,其中0是一个对象,而1是 一个对象。

matrix.shape = (500, 425)

我想创建一个形状为(500, 425, 3)的numpy数组掩码,以便:

mask = np.zeros((500, 425, 3))
if matrix[x][y] == 0:
    mask[x][y] = np.array([0, 0, 0]) # Black pixel if no object
else:
    mask[x][y] = np.array([0, 255, 0]) # Green pixel if object

因此,对象所在的区域为绿色像素,其他地方为黑色像素。我该如何创建这个面具?这是否正常,如果我对图像和蒙版使用cv2.addWeighted,对象上面会有一个透明的绿色遮罩?

2 个答案:

答案 0 :(得分:2)

您正在描述“过度”或“混合”图像合成操作。您可以使用蒙版图像直接组合图像。以这种方式组合两个图像的通用公式是:

A*alpha + B*(1-alpha)

其中A是放置在图像B顶部的图像.Alpha可以是黑色和白色之间的任何值。灰色alpha值将使A看起来透明。转换为浮动图像通常更容易,因为当值介于0和1之间时,数学运算会更容易。

如果您有图像A(源图像)和图像B(绿色图像)和图像(矩阵)。您可以使用以下方法将图像B叠加在图像A的顶部:

outimg[x][y] = (B[x][y] * matrix[x][y]) + (A[x][y] * (1-matrix[x][y]))

或者如果你想要透明度:

#50% transparency
t = 0.5
outimg[x][y] = (B[x][y] * (matrix[x][y]*t)) + (A[x][y] * (1-(matrix[x][y]*t)))

如果您想将图像A放在图像B的顶部,您可以反转表达式中的术语。

以下是使用蒙版和透明度合成图像B(源图像)顶部的图像A(平坦绿色图像)的示例:

源图片:

lena

掩模图片:

lena_mask

import numpy as np
import cv2

i = cv2.imread('lena.bmp')
#convert to floating point
img = np.array(i, dtype=np.float)
img /= 255.0
cv2.imshow('img',img)
cv2.waitKey(0)

j = cv2.imread('lena_mask.bmp')
#convert to floating point
mask = np.array(j, dtype=np.float)
mask /= 255.0
#set transparency to 25%
transparency = .25
mask*=transparency
cv2.imshow('img',mask)
cv2.waitKey(0)

#make a green overlay
green = np.ones(img.shape, dtype=np.float)*(0,1,0)

#green over original image
out = green*mask + img*(1.0-mask)
cv2.imshow('img',out)
cv2.waitKey(0)

cv2.destroyAllWindows()

输出图片:

output

答案 1 :(得分:1)

matrix扩展为3D并将其简单地乘以绿色三联色,就可以轻松实现broadcasting -

matrix[...,None]*[0,255,0]

示例运行 -

In [35]: matrix
Out[35]: 
array([[1, 0, 0, 0],
       [1, 0, 0, 1],
       [0, 0, 1, 0]])

In [36]: matrix[...,None]*[0,255,0]
Out[36]: 
array([[[  0, 255,   0],
        [  0,   0,   0],
        [  0,   0,   0],
        [  0,   0,   0]],

       [[  0, 255,   0],
        [  0,   0,   0],
        [  0,   0,   0],
        [  0, 255,   0]],

       [[  0,   0,   0],
        [  0,   0,   0],
        [  0, 255,   0],
        [  0,   0,   0]]])

第二列表示绿色。

请注意,这不是alpha遮罩,通常涉及第四个通道,但它是一个简单的RGB遮罩。

另一种基于零initialization的方法,可能在性能上更好 -

m,n = matrix.shape
out = np.zeros((m,n,3),dtype=np.uint8)
out[matrix==1,1] = 255 # green channel accessed with the last index being 1