零基础Opencv学习(四)

一、查找并绘制轮廓

    /// 载入原始图,必须以二值图模式载入
    cv::Mat image = cv::imread("E:/OpencvStudyTest/4.png", cv::ImreadModes::IMREAD_GRAYSCALE);
    cv::imshow("image", image);
    /// 初始化结果图
    cv::Mat dstImage = cv::Mat::zeros(image.rows, image.cols, CV_8UC3);
    /// 取大于阈值119的部分
    image = image > 119;
    cv::imshow("srcimage", image);

    /// 定义轮廓与层次结构
    std::vector<std::vector<cv::Point>> contouts;
    std::vector<cv::Vec4i> hierarchy;

    /// 查找轮廓
    cv::findContours(image, contouts, hierarchy, cv::RETR_CCOMP, cv::CHAIN_APPROX_SIMPLE);
    /// 遍历所有顶层的轮廓,以随机颜色绘制
    for(int index = 0; index >= 0; index = hierarchy[index][0])
    {
        cv::Scalar color(rand() & 255, rand() & 255, rand() & 255);
        cv::drawContours(dstImage, contouts, index, color, cv::FILLED, 8, hierarchy);
    }

    cv::imshow("dstImage", dstImage);

二、寻找物体凸包 convexHull

    /// 加载源图像
    cv::Mat dstImage;
    cv::Mat image = cv::imread("E:/OpencvStudyTest/6.png", cv::ImreadModes::IMREAD_COLOR);
    cv::imshow("image", image);
    /// 转换成灰度图并模糊降噪
    cv::cvtColor(image, dstImage, cv::COLOR_BGR2GRAY);
    cv::blur(dstImage, dstImage, cv::Size(3, 3));
    cv::imshow("dstImage", dstImage);

    cv::threshold(dstImage, dstImage, 100, 255, cv::THRESH_BINARY);

    /// 定义轮廓与层次结构
    std::vector<std::vector<cv::Point>> contouts;
    std::vector<cv::Vec4i> hierarchy;
    /// 查找轮廓
    cv::findContours(dstImage, contouts, hierarchy, cv::RETR_CCOMP, cv::CHAIN_APPROX_SIMPLE, cv::Point(0, 0));
    /// 遍历每个轮廓,寻找其凸包
    std::vector<std::vector<cv::Point>> hull(contouts.size());
    for(int i = 0; i < contouts.size(); i++)
    {
        cv::convexHull(cv::Mat(contouts[i]), hull[i], false);
    }
    /// 绘制出轮廓机器凸包
    cv::RNG rng(12345);
    cv::Mat drawing = cv::Mat::zeros(dstImage.size(), CV_8UC3);
    for(int i = 0; i < contouts.size(); i++)
    {
        cv::Scalar color = cv::Scalar(rng.uniform(0, 255), rng.uniform(0, 255), rng.uniform(0, 255));
        cv::drawContours(drawing, contouts, i, color, 1, 8, std::vector<cv::Vec4i>(), 0, cv::Point());
        cv::drawContours(drawing, hull, i, color, 1, 8, std::vector<cv::Vec4i>(), 0, cv::Point());
    }
    cv::imshow("drawing", drawing);

三、图像修复

    cv::Mat imageSource = cv::imread("E:/OpencvStudyTest/6.png");
    if (!imageSource.data)
    {
        return -1;
    }
    cv::imshow("原图", imageSource);
    cv::Mat imageGray;
    //转换为灰度图
    cv::cvtColor(imageSource, imageGray, CV_RGB2GRAY, 0);
    cv::Mat imageMask = cv::Mat(imageSource.size(), CV_8UC1, cv::Scalar::all(0));

    //通过阈值处理生成Mask
    cv::threshold(imageGray, imageMask, 240, 255, CV_THRESH_BINARY);
    cv::Mat Kernel = cv::getStructuringElement(cv::MORPH_RECT, cv::Size(3, 3));
    //对Mask膨胀处理,增加Mask面积
    cv::dilate(imageMask, imageMask, Kernel);

    //图像修复
    cv::inpaint(imageSource, imageMask, imageSource, 5, cv::INPAINT_TELEA);
    cv::imshow("imageMask", imageMask);
    cv::imshow("imageSource", imageSource);

四、模板匹配 matchTemplate

	cv::Mat m_srcImage = cv::imread("E:/OpencvStudyTest/6.png", cv::ImreadModes::IMREAD_COLOR);
	cv::Mat m_tempImage = cv::imread("E:/OpencvStudyTest/61.png", cv::ImreadModes::IMREAD_COLOR);

	cv::Mat m_resultImage;
	int m_nMatchMethod = cv::TM_SQDIFF;
	int m_nMaxTrackbarNum = 2;

	cv::Mat srcImage;
	m_srcImage.copyTo(srcImage);

	/// 初始化用于结果输出的矩阵
	int resultImage_rows = m_srcImage.rows - m_tempImage.rows + 1;
	int resultImage_cols = m_srcImage.cols - m_tempImage.cols + 1;
	m_resultImage.create(resultImage_rows, resultImage_cols, CV_32FC1);

	/// 进行匹配和标准化
	cv::matchTemplate(m_srcImage, m_tempImage, m_resultImage, m_nMatchMethod);
	cv::normalize(m_resultImage, m_resultImage, 0, 1, cv::NORM_MINMAX, -1, cv::Mat());

	/// minMaxLoc定位最匹配位置
	double minValue;
	double maxValue;
	cv::Point minLocation;
	cv::Point maxLocation;
	cv::Point matchLocation;
	minMaxLoc(m_resultImage, &minValue, &maxValue, &minLocation, &maxLocation, cv::Mat());

	///  TM_SQDIFF TM_SQDIFF_NORMED 数值越小,匹配度越高,其他的反之
	if (m_nMatchMethod == cv::TM_SQDIFF || m_nMatchMethod == cv::TM_SQDIFF_NORMED)
	{
		matchLocation = minLocation;
	}
	else
	{
		matchLocation = maxLocation;
	}

	/// 绘制出矩形并显示结果
	cv::rectangle(m_srcImage, matchLocation, cv::Point(matchLocation.x + m_tempImage.cols, matchLocation.y + m_tempImage.rows), cv::Scalar(0, 0, 255), 2, 8, 0);
	cv::rectangle(m_resultImage, matchLocation, cv::Point(matchLocation.x + m_tempImage.cols, matchLocation.y + m_tempImage.rows), cv::Scalar(0, 0, 255), 2, 8, 0);

	cv::imshow("m_srcImage", m_srcImage);
	cv::imshow("m_resultImage", m_resultImage);

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包

打赏作者

随风逐流wrx

你的鼓励将是我创作的最大动力

¥1 ¥2 ¥4 ¥6 ¥10 ¥20
扫码支付:¥1
获取中
扫码支付

您的余额不足,请更换扫码支付或充值

打赏作者

实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值