inpaint-图像修补算法

图像的修补技术由inpaint函数实现,它可以用来从扫描的照片中清除灰尘和划痕,或者从静态图像或视屏中去除不需要的物体。
函数原型C++:

void inpaint( InputArray src, InputArray inpaintMask, OutputArray dst,
    double inpaintRadius, int flags )

1)InputArray类型的src,输入图像,填Mat类的对象即可,且需要8位单通道或者三通道图像;
2)InputArray类型的inpaintMask,修复掩膜,为8位的单通道图像。其中的非零像素表示需要修补的区域;
3)OutputArray类型的dst,函数调用后的运算结果存在这里,和源图片有一样的尺寸和类型;
4)double类型的inpaintRadius,需要修补的每个点的圆形领域,为修复算法的参考半径。
5)int类型的flags,修补方法的标识符,可以是:

INPAINT_NS: 基于Navier-Stokes方程的方法
INPATNT_TELEA: Alexandru Telea方法

#include 
#include 
#include 
#include 
using namespace cv;
using namespace std;

#define WINDOW_NAME1 "原始图"
#define WINDOW_NAME2 "修补后的效果图"

Mat srcImage1, inpaintMask;
Point previousPoint(-1, -1);

static void on_Mouse(int event, int x, int y, int flags, void*)
{
	/*鼠标左键弹起消息*/
	if (event == EVENT_LBUTTONUP || !(flags & EVENT_FLAG_LBUTTON))
		previousPoint = Point(-1, -1);
	/*鼠标左键按下消息*/
	else if (event == EVENT_LBUTTONDOWN)
		previousPoint = Point(x, y);
	/*鼠标按下并移动,进行绘制*/
	else if (event == EVENT_MOUSEMOVE && (flags & EVENT_FLAG_LBUTTON))
	{
		Point pt(x, y);
		if (previousPoint.x < 0)
			previousPoint = pt;
		line(inpaintMask, previousPoint, pt, Scalar::all(255), 5, 8, 0);//画白线
		line(srcImage1, previousPoint, pt, Scalar::all(255), 5, 8, 0);//画白线
		previousPoint = pt;
		imshow(WINDOW_NAME1, srcImage1);
	}
}

int main()
{
	Mat srcImage = imread("me.jpg", -1);
	srcImage1 = srcImage.clone();
	inpaintMask = Mat::zeros(srcImage1.size(), CV_8U);

	imshow(WINDOW_NAME1, srcImage1);

	/*设置鼠标回调消息*/
	setMouseCallback( WINDOW_NAME1, on_Mouse, 0 );

	while (1)
	{
		char c = (char)waitKey();
		if (c == 27)
			break;
		/*恢复成原始图像*/
		if (c == '2')
		{
			inpaintMask = Scalar::all(0); //0就是不需要修补的部分
			srcImage.copyTo(srcImage1);
			imshow(WINDOW_NAME1, srcImage1);
		}
		if (c == '1')
		{
			Mat inpaintedImage;
			inpaint(srcImage1, inpaintMask, inpaintedImage, 3, INPAINT_TELEA);
			imshow(WINDOW_NAME2, inpaintedImage);
		}
	}

	return 0;
}

运行结果:
inpaint-图像修补算法_第1张图片
inpaint-图像修补算法_第2张图片

你可能感兴趣的:(机器视觉,【OpenCV】整理记录)