1. 图像的膨胀与腐蚀简介:
    图像的膨胀与腐蚀属于图像的形态学操作,图像的形态学操作是基于形状的一系列图像处理操作的合集,其主要是基于集合论基础上的形态学数学,形态学有四个基本操作:腐蚀、膨胀、开、闭;腐蚀与膨胀是图像处理中最常用的形态学操作手段。
    图像的膨胀:与上次所学习中值滤波相类似,它是最大值滤波。其具体内容为,假设有图像A与结构元素B,结构元素B在A上面移动,其中B定义其中心为锚点,计算B覆盖下A的最大像素值用来替换锚点的像素。
    图像的腐蚀:图像的腐蚀与图像的膨胀所进行的操作则相反,其进行的是最小值滤波。
  2. 图像的膨胀与腐蚀用到的相关函数分析:
    ①getStructuringElement()函数可以用来生成进行形态学操作的核,其返回值即是其所生成的形态学操作的核,可以作为后续调用函数的参数。
CV_EXPORTS_W Mat getStructuringElement(int shape, 
									   Size ksize, 
									   Point anchor = Point(-1,-1));

第一个参数为生成的核的形状MORPH_RECT表示矩形MORPH_CORSS表示交叉形MORPH_ELLIPSE表示椭圆
第二个参数为核的尺寸,即上面简述中所声明的结构元素B的尺寸。
第三个参数为锚点的位置。
②dilate()函数用来对图像进行膨胀操作

CV_EXPORTS_W void dilate( InputArray src, OutputArray dst, InputArray kernel,
                          Point anchor = Point(-1,-1), int iterations = 1);

第三个参数为“核”即结构元素,一般由getStructuringElement()函数生成
第四个参数为结构元素锚点的位置
第五个参数为腐蚀操作被递归执行的次数
③erode()函数用来对图像进行腐蚀操作

CV_EXPORTS_W void erode( InputArray src, OutputArray dst, InputArray kernel,
                         Point anchor = Point(-1,-1), int iterations = 1);
  1. 滑动轨迹条的创建与使用:
    本次还会学习一个重要的工具——滑动轨迹条的创建及使用,我们可以通过滑动轨迹条的创建来改变图像形态学操作的程度。
    首先我们来分析滑动轨迹条创建函数createTrackbar():
CV_EXPORTS int createTrackbar(const String& trackbarname, const String& winname,
                              int* value, int count,
                              TrackbarCallback onChange = 0);

第一个参数是滑动空间的名称,即轨迹条的名称
第二个参数是生成的轨迹条存在于那个窗口上
第三个参数是轨迹条生成的初始值
第四个参数是轨迹条能滑动达到的最大值
第五个参数是回调函数的名字
下面我们来分析回调函数,回调函数的声明原型如下所示,笔者感觉回调函数的作用类似于笔者之前学习的嵌入式开发中的中断函数的作用,每当轨迹条滑动即触发中断,进入回调函数,执行一些语句。
typedef void (CV_CDECL *TrackbarCallback)(int pos, void* userdata);

  1. 实验代码即效果展示:
#include<opencv2/opencv.hpp>
#include<iostream>

using namespace std;
using namespace cv;

Mat src, Erode,Dilate;
int element_initial = 3;
int element_max=20;

void erode_callback(int ,void*);
void dilate_callback(int, void*);

int main()
{
	src = imread("C:/Users/he104/Desktop/timg.jpg");
	if (src.empty())
	{
		cout << "could not load the image" << endl;
		return -1;
	}
	namedWindow("orign_image", CV_WINDOW_AUTOSIZE);
	imshow("orign_image", src);
	namedWindow("Dilate_image", CV_WINDOW_AUTOSIZE);
	namedWindow("Erode_image", CV_WINDOW_AUTOSIZE);
	createTrackbar("dilate_trackbar", "Dilate_image", &element_initial, element_max, dilate_callback);
	createTrackbar("erode_trackbar", "Erode_image", &element_initial, element_max, erode_callback);
	erode_callback(0, 0);
	dilate_callback(0, 0);
	waitKey(0);
	destroyAllWindows();
	return 0;
}

void erode_callback(int, void*)
{
	Mat structure = getStructuringElement(MORPH_RECT, Size(element_initial * 2 + 1, element_initial * 2 + 1), Point(-1, -1));
	erode(src, Erode, structure, Point(-1, -1));
	imshow("Erode_image", Erode);
}
void dilate_callback(int, void*)
{
	Mat structure = getStructuringElement(MORPH_RECT, Size(element_initial * 2 + 1, element_initial * 2 + 1), Point(-1, -1));
	dilate(src, Dilate, structure, Point(-1, -1));
	imshow("Dilate_image", Dilate);
}

opencv压缩bmp_回调函数