Search code examples
pythonnumpyopencvimage-processinggrayscale

OpenCV - I need to insert color image into black and white image and


I insert black and white image into color image with this code and it is ok:

face_grey = cv.cvtColor(face, cv.COLOR_RGB2GRAY)
for row in range(0, face_grey.shape[0]):
  for column in range(face_grey.shape[1]):
    img_color[row + 275][column + 340] = face_grey[row][column]
plt.imshow(img_color)

but, when i try to insert color image into black and white image with this code, i get error:

img_gray = cv.cvtColor(img, cv.COLOR_RGB2GRAY)
for row in range(0, face.shape[0]):
  for column in range(face.shape[1]):
    img_gray[row + 275][column + 340] = face[row][column]
plt.imshow(img_gray)
TypeError: only size-1 arrays can be converted to Python scalars
ValueError: setting an array element with a sequence.

Solution

  • A colour image needs 3 channels to represent red, green and blue components.

    A greyscale image has only a single channel - grey.

    You cannot put a 3-channel image in a 1-channel image any more than you can put a 3-pin plug in a single hole socket.

    You need to promote your grey image to 3 identical channels first:

    background = cv2.cvtColor(background, cv2.COLOR_GRAY2BGR)
    

    Example:

    # Make grey background, i.e. 1 channel
    background = np.full((200,300), 127, dtype=np.uint8)
    
    # Make small colour overlay, i.e. 3 channels
    color = np.random.randint(0, 256, (100,100,3), dtype=np.uint8)
    
    # Upgrade background from grey to BGR, i.e. 1 channel to 3 channels
    background = cv2.cvtColor(background, cv2.COLOR_GRAY2BGR)
    
    # Check its new shape
    print(background.shape)       # prints (200, 300, 3)
    
    # Paste in small coloured image
    background[10:110, 180:280] = color
    

    enter image description here