1 图像混合

1 引入

我们有时候会将两幅图像混合到一起,得到一幅新的图像,不同部分透明度不同,就会产生不一样的美感!


OpenCV中提供了图像混合的API,可以按权重加和,计算原理如下:


【OpenCV教程】10 图像混合_c++


如果应用到图像中,我们令输出图像为dst,两个输入图像分别为img1,img2,权重分别为α,β,我们另外需要一个参数γ调整一下图像的亮度,γ大于0,图像变亮,图像小于0,图像变暗,后面我们还会说明。


【OpenCV教程】10 图像混合_c++_02


2 图像混合API

图像混合的API是 addWeighted ,该API实现的功能是:


计算两个数组(图像)的加权和。


API定义如下:


def addWeighted(src1, alpha, src2, beta, gamma, dst=None, dtype=None)


API参数含义如下:


(1)src1:第一个输入图像(2)alpha:第一个图像的参数(3)src2:第二个输入图像,图像的尺寸、深度必须和前一个输入图像一致(4)beta:第二个图像的参数(5)gamma:每个和相加的附加标量(6)dst:输出图像(7)dtype:输出图像类型,默认为-1,即和两个输入图像一致。


dst可以不写在参数中,当做API的返回值传出,一般情况下,我们也采用第二种方式,当返回值传出。

3 代码示例

举个例子:


# coding=utf-8

import cv.cv2 as cv

img1 = cv.imread('./image/YT_ZM.png')
img2 = cv.imread('./image/YT_ZWJ.png')

gamma = 0
dst = cv.addWeighted(img1, 0.5, img2, 0.5, gamma)

cv.imshow('new image',dst)
cv.waitKey(0)
cv.destroyAllWindows()


执行结果如下:


【OpenCV教程】10 图像混合_c++_03


4 参数调整问题

调用OpenCV的API,其实就是调参的过程,在调整今天讲的API的参数的时候,我们就要来说明两个问题:


权重问题:两个图像的权重和是否必须为1?附加标量问题:附加标量是用来干嘛的,不同的取值,有什么不同?


对于第一个问题,两幅图像所占权重之和不一定为1,如果不是1,也可以:


dst = cv.addWeighted(img1, 0.2, img2, 0.5, gamma)


执行结果如下:



但是一般来说,权重之和越接近1,得到的图像效果越好


对于第二个问题,gamma这个参数用来对混合后的图像明暗程度进行调整,有如下三种情况:


(1)gamma>0:调亮图像,值越大,亮度越大;(2)gamma=0:不改变图像;(3)gamma<0:调按图像,值越小,亮度越小;


举个例子,我们分别让gamma为:-100,0,100,执行结果如下:


gamma = -100


gamma = 0


【OpenCV教程】10 图像混合_c++_04

gamma = 100


2 部分混合

1 代码分析与编写

如果我们想要混合的图像大小不一样,或者想要混合其中的某个部分,应该怎么办呢?


我们可以先选定ROI区域,然后对ROI区域混合。


# coding=utf-8

import cv.cv2 as cv

img3 = cv.imread('./image/sign.png')
img4 = cv.imread('./image/opencv.png')

ROI = img3[50:50 + img4.shape[0], 50:50 + img4.shape[1]] # 获取ROI区域

dst = cv.addWeighted(ROI, 0.5, img4, 0.50# 图像融合

img3[50:50 + img4.shape[0], 50:50 + img4.shape[1]] = dst #附加到原图上


cv.imshow('new image',img3)
cv.waitKey(0)
cv.destroyAllWindows()


2 效果展示

执行结果如下:


【OpenCV教程】10 图像混合_c++_05


3 模拟视频淡入淡出切换

1 效果介绍

做视频的时候,做两个视频或者图片的转换,需要通过淡入淡出转换,或者做PPT的时候,需要使用淡入淡出进行切换


接下来,让我们使用OpenCV实现下这个效果吧!

2 流程分析与代码编写

淡入淡出是一个动态效果,一幅图像的透明度由0逐渐转化为1,即由不透明转化为百分百透明;一幅图像的透明度由1逐渐转化为0,即由百分百透明转化为不透明。


我们每进行一次调整透明度,就把图像输出一下。


# coding=utf-8

import cv.cv2 as cv

img5 = cv.imread('./image/YT_ZM1.png')
img6 = cv.imread('./image/YT_ZWJ1.png')

alpha = 0.0

while alpha <= 1:
    dst = cv.addWeighted(img5, alpha, img6, 1-alpha, 0)
    cv.imshow('new image', dst)
    cv.waitKey(30)
    alpha += 0.01

cv.destroyAllWindows()