Python OpenCV 在同一图像中复制透明形状

Python OpenCV Duplicate a transparent shape in the same image

我有一张圆形的图片,请参考下面的图片。我已经取回了透明圆圈,想把那个圆圈贴回图片上,做一些重叠的圆圈。

下面是我的代码,但它导致了问题 A,它就像图像中的(透明)孔。我需要在正常的白色背景上有圆圈。

height, width, channels = circle.shape
original_image[60:60+height, 40:40+width] = circle

我用了cv2.addWeighted但是遇到了混合问题,我需要清晰的圆圈

circle = cv2.addWeighted(original_image[60:60+height, 40:40+width],0.5,circle,0.5,0)
original_image[60:60+rows, 40:40+cols] = circle

如果您已经有一个透明的黑色圆圈,那么在 Python/OpenCV 中有一种方法可以做到这一点。

 - Read the transparent image unchanged
 - Extract the bgr channels and the alpha channel
 - Create a colored image of the background color and size desired
 - Create similar sized white and black images
 - Initialize a copy of the background color image for the output
 - Define a list offset coordinates in the larger image
 - Loop for over the list of offsets and do the following
 - Insert the bgr image into a copy of the white image as the base image
 - Insert the alpha channel into a copy of the black image for a mask
 - composite the initialized output and base images using the mask image
 - When finished with the loop, save the result

输入(透明):

import cv2
import numpy as np

# load image with transparency
img = cv2.imread('black_circle_transp.png', cv2.IMREAD_UNCHANGED)
height, width = img.shape[:2]
print(img.shape)

# extract the bgr channels and the alpha channel
bgr = img[:,:,0:3]
aa = img[:,:,3]
aa = cv2.merge([aa,aa,aa])

# create whatever color background you want, in this case white
background=np.full((500,500,3), (255,255,255), dtype=np.float64)

# create white image of the size you want
white=np.full((500,500,3), (255,255,255), dtype=np.float64)

# create black image of the size you want
black=np.zeros((500,500,3), dtype=np.float64)

# initialize output
result = background.copy()

# define top left corner x,y locations for circle offsets
xy_offsets = [(100,100), (150,150), (200,200)]

# insert bgr and alpha into white and black images respectively of desired output size and composite
for offset in xy_offsets:
    xoff = offset[0]
    yoff = offset[1]
    base = white.copy()
    base[yoff:height+yoff, xoff:width+xoff] = bgr
    mask = black.copy()
    mask[yoff:height+yoff, xoff:width+xoff] = aa
    result = (result * (255-mask) + base * mask)/255
    result = result.clip(0,255).astype(np.uint8)

# save resulting masked image
cv2.imwrite('black_circle_composite.png', result)

# display result, though it won't show transparency
cv2.imshow("image", img)
cv2.imshow("aa", aa)
cv2.imshow("bgr", bgr)
cv2.imshow("result", result)
cv2.waitKey(0)
cv2.destroyAllWindows()

结果: