I need to alpha-blend 2 images that are not the same size. I’ve managed to get them to composite by resizing to the same size, so I’ve got part of the logic:
import cv2 as cv def combine_two_color_images_composited(foreground_image, background_image): foreground = cv.resize(foreground_image, (400,400), interpolation=cv.INTER_CUBIC).copy() background = cv.resize(background_image, (400,400), interpolation=cv.INTER_CUBIC).copy() alpha =0.5 # do composite of foreground onto the background cv.addWeighted(foreground, alpha, background, 1 - alpha, 0, background) cv.imshow('composited image', background) cv.waitKey(10000)
I’m wondering if I need to make a mask that is the same size as the larger image and then use that with my first image. If so, I don’t know how to do masking yet in OpenCV…. this is but a tiny portion of my project so it’s not something I’ve been able to spend a ton of time researching to learn how masking works.
I have searched all over but the code I’m finding does things like ‘adds’ the images together (side by side).
Advertisement
Answer
To combine the two images you can make use of numpy slicing to select the portion of the background image where you want to blend the foreground, then insert the newly blended portion in your background again.
import cv def combine_two_color_images(image1, image2): foreground, background = image1.copy(), image2.copy() foreground_height = foreground.shape[0] foreground_width = foreground.shape[1] alpha =0.5 # do composite on the upper-left corner of the background image. blended_portion = cv.addWeighted(foreground, alpha, background[:foreground_height,:foreground_width,:], 1 - alpha, 0, background) background[:foreground_height,:foreground_width,:] = blended_portion cv.imshow('composited image', background) cv.waitKey(10000)
edit: To place the foreground at a specified location you use numpy indexing as before. Numpy indexing is very powerful and you will find it useful on many occasions. I linked the documentation above. Is really worth to take a look at.
def combine_two_color_images_with_anchor(image1, image2, anchor_y, anchor_x): foreground, background = image1.copy(), image2.copy() # Check if the foreground is inbound with the new coordinates and raise an error if out of bounds background_height = background.shape[0] background_width = background.shape[1] foreground_height = foreground.shape[0] foreground_width = foreground.shape[1] if foreground_height+anchor_y > background_height or foreground_width+anchor_x > background_width: raise ValueError("The foreground image exceeds the background boundaries at this location") alpha =0.5 # do composite at specified location start_y = anchor_y start_x = anchor_x end_y = anchor_y+foreground_height end_x = anchor_x+foreground_width blended_portion = cv.addWeighted(foreground, alpha, background[start_y:end_y, start_x:end_x,:], 1 - alpha, 0, background) background[start_y:end_y, start_x:end_x,:] = blended_portion cv.imshow('composited image', background) cv.waitKey(10000)