4
votes

In OpenCV python, say we read an image with cv2.imread and get a BGR numpy array. We next generate a mask with the cv2.inRange command. The mask has the same width/height and each mask pixel is either black or white.

I want to copy a region from the mask (taken as an image of black and white pixels) onto a region of the color image.

How do I do that? This does not work

img[10:20,10:20] = mask[10:20,10:20]

Must I convert the mask to BGR image first? If so how?

Edit: I do not want to apply the whole mask to the image as in apply mask to color image. Another way to say what I want: see the mask as a black and white image. I want to copy a region of that image (as a set of black or white pixels) onto another image. The resulting image will be a color image except for one smaller rectangular region that contains only black or white pixels. The result will be similar to if I in photoshop copy a rectangular area of a black/white image and past that rectangle onto an area of a color image.

(I'm new to OpenCV)

1
What do you mean by "copy a region from the mask"? Can you show it using an image?Håken Lid
The mask is binary. I want to copy each black or white pixel in the mask region (coordinates) onto (replacing) the same pixel region in the image. Similar to if I in photoshop select and copy a rectangular region on one image and paste it onto another image.cv2asker
Possible duplicate of apply mask to color imageHåken Lid
If I understand the linked "apply mask to color image" page correctly it applies the whole mask to the image. I do not want that. Another way to say what I want: see the mask as a black and white image. I want to copy a region of that image (as a set of black or white pixels) onto another image. The resulting image will be a color image except for one smaller rectangular region that contains only black or white pixels (in the same pattern as in the mask image).cv2asker
Ok. In that case you have to treat the mask as a image, and convert it to the same colorspace as img before merging them. Have you tried that?Håken Lid

1 Answers

0
votes

If you try to do it with a single channel (grayscale) mask directly, the shapes of the array slices will not be the same, and the operation will fail.

>>> img[10:20,10:20] = mask[10:20,10:20]

ValueError: could not broadcast input array from shape (10,10) into shape (10,10,3)

You have to convert the mask to BGR, which will make it 3 channels, like the original image.

>>> bgr_mask = cv2.cvtColor(mask, cv2.COLOR_GRAY2BGR)
>>> img[10:20,10:20] = bgr_mask[10:20,10:20]