Goal
主要是使用cv::morphologyEx这个函数实现高级的形态学变换。
开运算 闭运算 形态梯度 顶帽 黑帽
Theory
理论来源于《Learning OpenCV》.之前学习了形态学的基本操作腐蚀和膨胀。基于这两个基本操作,这里可以实现更为复杂的高级算法。
Opening
开运算对图像先进行腐蚀,之后进行膨胀。据说可以去除掉小物体(物体为明亮,背景为黑色)Closing
闭运算时对图像先进行膨胀,之后进行腐蚀。据说可以去消除黑洞,与开运算相反。Morphological Gradient
形态学梯度是膨胀和腐蚀的区别。对于查找对象的轮廓很有用。
Top Hat
图像减去开运算的结果。
Black Hat
闭运算减去图像的结果。Code
#include "opencv2/imgproc.hpp"#include "opencv2/imgcodecs.hpp"
#include "opencv2/highgui.hpp"
#include <iostream>
using namespace cv;
// 全局变量
Mat src, dst;
int morph_elem = 0;
int morph_size = 0;
int morph_operator = 0;
int const max_operator = 4;
int const max_elem = 2;
int const max_kernel_size = 21;
const char* window_name = "Morphology Transformations Demo";
/** 头文件 */
void Morphology_Operations( int, void* );
int main( int argc, char** argv )
{
//加载图片
CommandLineParser parser( argc, argv, "{@input | ./lena.jpg | input image}" ); //参数名字,默认,帮助信息
src = imread( parser.get<String>( "@input" ), IMREAD_COLOR );
if (src.empty())
{
std::cout << "Could not open or find the image!\n" << std::endl;
std::cout << "Usage: " << argv[0] << " <Input image>" << std::endl;
return -1;
}
//加载图片
//窗口
namedWindow( window_name, WINDOW_AUTOSIZE ); // 创建
//窗口
//滑动条
createTrackbar("Operator:\n 0: Opening - 1: Closing \n 2: Gradient - 3: Top Hat \n 4: Black Hat", window_name, &morph_operator, max_operator, Morphology_Operations );
//滑动条
//滑动条
//内核类型
createTrackbar( "Element:\n 0: Rect - 1: Cross - 2: Ellipse", window_name,
&morph_elem, max_elem,
Morphology_Operations );
//滑动条
//滑动条
// 内核大小
createTrackbar( "Kernel size:\n 2n +1", window_name,
&morph_size, max_kernel_size,
Morphology_Operations );
//滑动条
// 开始
Morphology_Operations( 0, 0 );
waitKey(0);
return 0;
}
//形态学高级变换函数
void Morphology_Operations( int, void* )
{
// 开,比,形态梯度,顶帽,黑帽。2,3,4,5 and 6
//操作
int operation = morph_operator + 2;
//操作
//结构元素,大小尺寸,锚点
Mat element = getStructuringElement( morph_elem, Size( 2*morph_size + 1, 2*morph_size+1 ), Point( morph_size, morph_size ) );
//应用
morphologyEx( src, dst, operation, element ); //输入,输出,操作,内核
imshow( window_name, dst );
}
//应用
由于补充注释已经很清楚了,这里不再解释。
CMakeLists.txt文件如下
cmake_minimum_required(VERSION 2.8)
project( DisplayImage )
find_package( OpenCV REQUIRED )
include_directories( ${OpenCV_INCLUDE_DIRS} )
add_executable( DisplayImage main.cpp )
target_link_libraries( DisplayImage ${OpenCV_LIBS} )
install(TARGETS DisplayImage RUNTIME DESTINATION bin)
结果如下:
这里只显示了形态梯度,感觉这个很有意思。