OpenCv,图像的线性叠加,以及滑动条的添加

注:本文部分文字参考自OpenCV中文网,仅供个人学习记录之用!如果无意中侵犯了您的版权请联系本人:[email protected],.本人会及时编辑掉


一,概述

1,原理说明

  1. 既然我们要执行

    我们需要两幅输入图像 ( 和 )。相应地,我们使用常用的方法加载图像

    src1 = imread("LinuxLogo.jpg");
    src2 = imread("WindowsLogo.jpg");
    

    Warning

     

    因为我们对 src1 和 src2 求  ,它们必须要有相同的尺寸(宽度和高度)和类型。

  2. 现在我们生成图像 g(x) .为此目的,使用函数 addWeighted 可以很方便地实现:

    beta = ( 1.0 - alpha );
    addWeighted( src1, alpha, src2, beta, 0.0, dst);
    

    这是因为 addWeighted 进行如下计算

    这里  对应于上面代码中被设为  的参数。

  3. 创建显示窗口,显示图像并等待用户结束程序。

2,程序中的关键函数

AddWeighted
计算两数组的加磅值的和 
void cvAddWeighted( const CvArr* src1, double alpha, const CvArr* src2, double beta, double gamma, CvArr* dst );
src1  第一个原数组. 
alpha  第一个数组元素的磅值 
src2  第二个原数组 
beta  第二个数组元素的磅值 
dst  输出数组 
gamma  作和合添加的数量。 

函数 cvAddWeighted 计算两数组的加磅值的和: dst(I)=src1(I)*alpha+src2(I)*beta+gamma 
所有的数组必须的相同的类型相同的大小(或 ROI 大小)


createTrackbar

Creates a trackbar and attaches it to the specified window.

第一个参数,const string&类型的trackbarname,表示轨迹条的名字,用来代表我们创建的轨迹条。
第二个参数,const string&类型的winname,填窗口的名字,表示这个轨迹条会依附到哪个窗口上,即对应namedWindow()创建窗口时填的某一个窗口名。
第三个参数,int* 类型的value,一个指向整型的指针,表示滑块的位置。并且在创建时,滑块的初始位置就是是由该变量当前的值。
第四个参数,int类型的count,表示滑块可以达到的最大位置的值。PS:滑块最小的位置的值始终为0。
第五个参数,TrackbarCallback类型的onChange,首先注意他有默认值0。这是一个指向回调函数的指针,每次滑块位置改变时,这个函数都会进行回调。并且这个函数的原型必须为void XXXX(int,void*);其中第一个参数是轨迹条的位置,第二个参数是用户数据(看下面的第六个参数)。如果回调是NULL指针,表示没有回调函数的调用,仅第三个参数value有变化。
第六个参数,void*类型的userdata,他也有默认值0。这个参数是用户传给回调函数的数据,用来处理轨迹条事件。如果使用的第三个参数value实参是全局变量的话,完全可以不去管这个userdata参数。下面的例子中用到的调用为


二,实验

1,线性融合图像

// ConsoleAppOpenCvAddImages.cpp : 定义控制台应用程序的入口点。
//

#include "stdafx.h"
#include "opencv2/highgui/highgui.hpp"
#include <iostream>

using namespace cv;

int _tmain(int argc, _TCHAR* argv[])
{
   double alpha = 0.5;
   double beta=0.0; 
   double input=0.0;
   int count=0;
   Mat src1, src2, dst;

   while (true)
   {
	   /// Ask the user enter alpha
	   std::cout<<" Simple Linear Blender "<<std::endl;
	   std::cout<<"-----------------------"<<std::endl;
	   std::cout<<"* Enter alpha [0-1]: ";
	   std::cin>>input;

	   // We use the alpha provided by the user iff it is between 0 and 1
	   if( alpha >= 0 && alpha <= 1 )
			 alpha = input; 

	   /// Read image ( same size, same type )
	   src1 = imread("LinuxLogo.jpg");
	   src2 = imread("WindowsLogo.jpg");

	   if( !src1.data )
	   { 
		   std::cout<< "Error loading src1"<<std::endl; 
		   return -1; 
	   }
	   if( !src2.data ) 
	   {
		   std::cout<< "Error loading src2"<<std::endl;
		   return -1;
	   }
	   /// Create Windows
	   namedWindow("Linear Blend", 1);
	   beta = ( 1.0 - alpha );
	   addWeighted( src1, alpha, src2, beta, 0.0, dst);
	   imshow( "Linear Blend", dst );
	   count++;
	   if (count>10)
	   {
		   break;
	   }
	    waitKey(0);
   }
   return 0;
}

OpenCv,图像的线性叠加,以及滑动条的添加_第1张图片OpenCv,图像的线性叠加,以及滑动条的添加_第2张图片OpenCv,图像的线性叠加,以及滑动条的添加_第3张图片

2,实验二,添加滑动条

// ConsoleAppMatTest.cpp : Defines the entry point for the console application.
//

#include "stdafx.h"
#include < opencv2/highgui/highgui.hpp >
#include "iostream"
using namespace std;
using namespace cv;

/** Global Variables */
const int alpha_slider_max = 100;//滑动条最大值
int alpha_slider_init;//滑动条初始值
double alpha;
double beta;

/** Matrices to store images */
Mat src1;//第一附图
Mat src2;//第二幅图
Mat dst;//存储融合后的图像

static void on_trackbar( int, void* )
{

	//判断两幅图片是否相同以及是否成功读入  
	CV_Assert(src1.depth() == CV_8U);  
	CV_Assert(src1.depth() == src2.depth());  
	CV_Assert(src1.size() == src2.size()); 
	if( !src1.data ) 
		cout<<"Error loading src1"<<endl; 
	if( !src2.data ) 
		cout<<"Error loading src2"<<endl; 
	/******************融合开始********************/
   alpha = (double) alpha_slider_init/alpha_slider_max ;
   beta = ( 1.0 - alpha );
   addWeighted( src1, alpha, src2, beta, 0.0, dst);//线性融合
   imshow( "Linear Blend", dst );
}


int main( void )
{
   /// Read image ( same size, same type )
   src1 = imread("LinuxLogo.jpg");
   src2 = imread("WindowsLogo.jpg");
   /// Initialize values
   alpha_slider_init = 10;
   /// Create Windows
   namedWindow("Linear Blend", 1);

   /// 创建滑动条
   char TrackbarName[50];//滑动条名字
   sprintf_s( TrackbarName, "Alpha x %d", alpha_slider_max );
   createTrackbar( TrackbarName, "Linear Blend", &alpha_slider_init, alpha_slider_max, on_trackbar );

   /// Show some stuff
   on_trackbar( alpha_slider_init, 0 );

   /// Wait until user press some key
   waitKey(0);
   return EXIT_SUCCESS;
}

OpenCv,图像的线性叠加,以及滑动条的添加_第4张图片


三,OpenCV+MFC简单实现

未完待续...........

你可能感兴趣的:(opencv,图像处理)