本文长度为1865字,预计阅读5分钟
导读
上一篇文章《学习|OpenCV图片修复函数inpaint》我们试验了OpenCV的图像修复函数,这篇我们结合鼠标事件使用修复做到想修复哪就修复哪的效果。
视频效果演示
核心方法
图像修复和鼠标事件
图像修复
上图中可以看到图像修复的函数我们加入了一个输入参数就是矩形的选中框,通过输入的选中框设定新模版中的对应区域,再进行修复,比上一个例子中要简化了很多,看起来也方便。
鼠标事件
鼠标事件中,我们按按下鼠标时设置矩形框的起点坐标,在按住并移动时在源图像上画矩形显示出来,最后在鼠标抬起时完成矩形框的生成,并将生成的矩形框做为参数调用图像修复的参数。
完整代码
本Demo本身代码量就不大,所以不再上传Demo了
#include <iostream>
#include <opencv2/opencv.hpp>
using namespace cv;
using namespace std;
Mat src;
Mat srccopy; //用于拷贝出的源图像
string showsrc = "源图";
//鼠标控制
Rect rect; //鼠标选取的矩形
bool firstleftbutton = false;
bool leftButtonDownFlag = false; //左键单击后视频暂停播放的标志位
Point rectstartPoint; //矩形框起点
Point rectstopPoint; //矩形框终点
void onMouse(int event, int x, int y, int flags, void* ustc); //鼠标回调函数
//图像修复
void oninpaint(Rect rect);
int main(int argc,char** argv)
{
src = imread("E:/DCIM/Test3.jpg");
//窗体
namedWindow(showsrc);
//设置鼠标响影事件
setMouseCallback(showsrc, onMouse);
//显示图像
imshow(showsrc, src);
waitKey(0);
return 0;
}
//鼠标回调函数
void onMouse(int event, int x, int y, int flags, void * ustc)
{
//鼠标左键按下
if (event == CV_EVENT_LBUTTONDOWN)
{
leftButtonDownFlag = true; //更新按下标志位
rectstartPoint = cv::Point(x, y); //设置矩形的开始点
rectstopPoint = rectstartPoint; //刚按下时结束点和开始点一样
}
//当鼠标按下并且开始移动时
else if (event == CV_EVENT_MOUSEMOVE && leftButtonDownFlag)
{
srccopy = src.clone(); //复制源图像
rectstopPoint = cv::Point(x, y); //设置矩形的结束点
if (rectstartPoint != rectstopPoint)
{
//当矩形的开始点和结束点不同后在复制的图像上绘制矩形
cv::rectangle(srccopy, rectstartPoint, rectstopPoint,
cv::Scalar(0, 0, 255));
}
imshow(showsrc, srccopy);
}
//当鼠标抬起时
else if (event == CV_EVENT_LBUTTONUP)
{
leftButtonDownFlag = false;//按下鼠标标志位复位
rect = Rect(rectstartPoint, rectstopPoint);//设置选中后的矩形
oninpaint(rect);
}
}
//图像修复
void oninpaint(Rect rect)
{
//创建是个模版画上要修复的区域
Mat tmp = Mat::zeros(src.size(), CV_8UC1);
rectangle(tmp, rect, Scalar::all(255), -1);
//进行图像修复
Mat result;
inpaint(src, tmp, result, 5, INPAINT_TELEA);
imshow(showsrc, result);
}
修复效果截图
源图与修复后的图对比
源图
src
修复后图
result
完