您的位置:首页 > 运维架构

OpenCV学习笔记之鼠标响应回调函数setMouseCallback

2016-12-29 15:51 549 查看
        openCv中的鼠标回调函数是为了处理鼠标操作消息的响应事件,函数原型为:

                     C++:   void   SetMouseCallback(const string & winname,MouseCallback onMouse,void* userdata=0)

第一个参数:const string & 类型的winname ,窗口的名字;

第二个参数: MouseCallback 类型的onMouse,指定窗口里每次鼠标事件发生时的时候被调用的函数指针。

这个函数的原型的大概形势为:void Foo(int event ,int x ,int y ,int flags  ,void  * param)。event 是鼠标响应类型,CV_EVENT_*变量之一:

EVENT_MOUSEMOVE
滑动 EVENT_LBUTTONDOWN 左击
EVENT_RBUTTONDOWN 右击

EVENT_MBUTTONDOWN
中键点击 EVENT_LBUTTONUP 左键放开
EVENT_RBUTTONUP 右键放开

EVENT_LBUTTONDBLCLK
左键双击 EVENT_RBUTTONDBLCLK 右键双击
EVENT_MBUTTONDBLCLK 中键双击

x和y是鼠标指针在图像坐标系的坐标(不是窗口坐标系)。

                                              flags是CV_EVENT_FLAG的组合,flag的状态有:

EVENT_FLAG_LBUTTON 左键拖拽
EVENT_FLAG_RBUTTON 右键拖拽
EVENT_FLAG_MBUTTON 中键拖拽
EVENT_FLAG_CTRLKEY 按住Ctrl不放
EVENT_FLAG_SHIFTKEY 按住Shift不放
EVENT_FLAG_ALTKEY 按住Alt不放
param是用户定义的传递到setMouseCallback函数调用的参数。

第三个参数:void *userdata   传给回调函数的参数(onMouse)。

示例代码如下:

//--------------------------------【鼠标响应函数声明部分】----------------
// 描述:
//------------------------------------------------------------------------
void onMouseHandle(int event,int x,int y,int flags,void *param);
void onMouseHandle1(int event,int x,int y);
void DrawRectangle(Mat &img,Rect box);

Rect g_rectangle;
bool g_bDrawingBox=false; //是否进行绘制
RNG g_rng(12345);

void Main2()
{
g_rectangle=Rect(-1,-1,0,0);
Mat srcImage(600,800,CV_8UC3),tempImage;
srcImage.copyTo(tempImage);
srcImage=Scalar::all(0);

//设置鼠标操作回调函数
namedWindow(windowName);
setMouseCallback(windowName,onMouseHandle,(void*)&srcImage);

//程序主循环
while (1)
{
srcImage.copyTo(tempImage);
if(g_bDrawingBox)
DrawRectangle(tempImage,g_rectangle);
imshow(windowName,tempImage);
if(waitKey(10)==27)
break;
}

}
//鼠标回调函数
void onMouseHandle(int event,int x,int y,int flags,void *param)
{

Mat &image=*(Mat *) param;
switch(event)
{
//鼠标移动消息
case EVENT_MOUSEMOVE:
{
if(g_bDrawingBox) //是否进行绘制
{
g_rectangle.width=x-g_rectangle.x;
g_rectangle.height=x-g_rectangle.y;
}
}
break;
case EVENT_LBUTTONDOWN:
g_bDrawingBox=true;
g_rectangle=Rect(x,y,0,0); //记录起始点
break;
//左键抬起消息
case EVENT_LBUTTONUP:
g_bDrawingBox=false;
if(g_rectangle.width<0)
{
g_rectangle.x+=g_rectangle.width;
g_rectangle.width*=-1;
}
if(g_rectangle.height<0)
{
g_rectangle.y+=g_rectangle.height;
g_rectangle.height*=-1;

}
//调用函数进行绘制
DrawRectangle(image,g_rectangle);
break;
}

}
//矩形绘制函数
void DrawRectangle(Mat &img,Rect box)
{
rectangle(img,box.tl(),box.br(),Scalar(g_rng.uniform(0,255),g_rng.uniform(0,255),g_rng.uniform(0,255)));//随机颜色
}效果图:





二、滑动条的创建

        创建滑动条的函数是createTrackbar,函数原型如下:

C++ :int    createTrackbar(const string & trackbarname,   const string & winname  ,int * value  ,int  count   ,TrackbarCallback onChange=0  ,  void * userdata =0 );

        第一个参数:const string & 类型的trackbarname  。滑动条名称。

        第二个参数:const string & 类型的 winname ,窗口的名称。

        第三个参数:int * 类型的value 。整型的指针,表示滑块创建时初始位置。

        第四个参数:int 类型的count ,表示滑块可达到的最大位置。

        第五个参数:TrackbarCallback 类型的onChange。回调函数,滑块移动时会调用onChange函数。

        第六个参数:void *类型的userdata参数。这个参数是用户用来传递给回调函数的参数。

利用滑块调整图像透明度的函数代码:

//创建滑动条
const char windowName[]="【线性混合示例】";

//---------------------【全局变量】-----------------------

const int g_nMAxAlphaValue=100;
int g_nAlphaValueSlider; //滑动条对应的变量
double g_dAlphaValue;
double g_dBetaValue;

//声明存储图像的变量
cv::Mat g_srcImage1;
cv::Mat g_srcImage2;
cv::Mat g_srcImage;

//--------------------------【onTrackBar()函数】----------------------
// 描述:响应滑动条的回调函数
//
//--------------------------------------------------------------------
void onTrackBar(int ,void *)
{
//求当前alpha值相对于最大值得比例
g_dAlphaValue=(double)g_nAlphaValueSlider/(double)g_nMAxAlphaValue;
//则beta值为1减去alpha值
g_dBetaValue=1-g_dAlphaValue;

//根据alpha和beta值进行线性混合
addWeighted(g_srcImage1,g_dAlphaValue,g_srcImage2,g_dBetaValue,0.0,g_srcImage);

//显示效果图
imshow(windowName,g_srcImage);

}
void Main1()
{
//加载图像(两图像尺寸需相同)
g_srcImage1=imread("1-s.jpg");
g_srcImage2=imread("1-s.jpg");
if(!g_srcImage1.data)
{
printf("读取第一幅图片错误!!!");
return ;
}
if(!g_srcImage2.data)
{
printf("读取第二幅图片错误!!!");
return ;
}

//设置滑动条初始位置为70
g_nAlphaValueSlider=70;

//创建窗体
namedWindow(windowName,1);

//在创建的窗体中创建一个滑动条控件
char TrackbarName[50];
sprintf(TrackbarName,"透明值 %d",g_nMAxAlphaValue);

createTrackbar(TrackbarName,windowName,&g_nAlphaValueSlider,g_nMAxAlphaValue,onTrackBar);

//结果在回调函数中显示
onTrackBar(g_nAlphaValueSlider,0);

waitKey(0);

}
内容来自用户分享和网络整理,不保证内容的准确性,如有侵权内容,可联系管理员处理 点击这里给我发消息
标签: