Opencv学习———颜色识别

VS + opencv开发环境请看毛大神的文章:https://blog.csdn.net/poem_qianmo/article/details/19809337

彩色模型

数字图像处理中常用的采用模型是RGB(红,绿,蓝)模型和HSV(色调,饱和度,亮度),RGB广泛应用于彩色监视器和彩色视频摄像机,我们平时的图片一般都是RGB模型。而HSV模型更符合人描述和解释颜色的方式,HSV的彩色描述对人来说是自然且非常直观的。

HSV模型

HSV模型中颜色的参数分别是:色调(H:hue),饱和度(S:saturation),亮度(V:value)。由A. R. Smith在1978年创建的一种颜色空间, 也称六角锥体模型(Hexcone Model)。

  • 色调(H:hue):用角度度量,取值范围为0°~360°,从红色开始按逆时针方向计算,红色为0°,绿色为120°,蓝色为240°。它们的补色是:黄色为60°,青色为180°,品红为300°;
  • 饱和度(S:saturation):取值范围为0.0~1.0,值越大,颜色越饱和。
  • 亮度(V:value):取值范围为0(黑色)~255(白色)。


因为RGB通道并不能很好地反映出物体具体的颜色信息 , 而相对于RGB空间,HSV空间能够非常直观的表达色彩的明暗,色调,以及鲜艳程度,方便进行颜色之间的对比。

下面是windows上的代码,具体可以看里面的注释:

#include "stdafx.h"
#include <opencv2/opencv.hpp>
#include <opencv2/core/core.hpp>
#include <opencv2/highgui/highgui.hpp>
#include <vector>
#include <cstdio>
#include <iostream>
#include <SDKDDKVer.h>  
#include <stdio.h>  
#include <tchar.h>  

using namespace cv;
using namespace std;

void copymask(Mat image, Mat binary_image, Mat result)
{
	int num_row = image.rows;
	int num_col = image.cols;
	for (int r = 0; r < num_row; r++) {
		uchar* curr_r_open = binary_image.ptr<uchar>(r);
		Vec3b* curr_r_image = image.ptr<Vec3b>(r);
		Vec3b* curr_r_result = result.ptr<Vec3b>(r);
		for (int c = 0; c < num_col; c++) {
			if (curr_r_open[c] == 255) {
				curr_r_result[c] = curr_r_image[c];
			}

		}
	}
}

void Homography(Mat image, Mat Opened)
{
	Mat element_9(9, 9, CV_8U, Scalar(1));
	morphologyEx(image, Opened, MORPH_OPEN, element_9);
}

void ToHSV(Mat image, Mat result)
{
    Mat hsv_image;        
	int num_row = image.rows;
	int num_col = image.cols;

    cvtColor(image, hsv_image, CV_BGR2HSV);//转HSV

    for (int r = 0; r < num_row; r++) {
		Vec3b *data = hsv_image.ptr<Vec3b>(r);
        uchar* curr_r_result = result.ptr<uchar>(r);
        for (int c = 0; c < num_col; c++) {
            //if (((data[c][0] >= 0 && data[c][0] <= 10) || (data[c][0] >= 156 && data[c][0] <= 180)) && (data[c][1] >= 43)) //找红色
			//if ((data[c][0] <= 124 && data[c][0] >= 100) && (data[c][1]>43) && (data[c][2] > 46)) //找蓝色
			if ((data[c][0] >= 35 && data[c][0] <= 77) && (data[c][1] >= 43) && data[c][2] >= 46) { //找绿色
				curr_r_result[c] = 255;
			} else {
                curr_r_result[c] = 0;
            }

        }
    }
}

void setup_result(Mat image, Mat result)
{
	uchar* pxvec = result.ptr<uchar>(0);

	for (int r = 0; r < image.rows; r++) {
		pxvec = result.ptr<uchar>(r);
		for (int c = 0; c < image.cols * image.channels(); c++) {
			pxvec[c] = 255;//初始化为白色
		}
	}
}

int main()
{
	Mat image = imread("C:/Users/Administrator/Desktop/opencv_logo.jpg");
	Mat hue_image;
	Mat binary_image;
	Mat result(image.rows, image.cols, CV_8UC3);
	
	setup_result(image, result);//根据原图尺寸大小,将result初始化成与原图同样大小的白色图片

	imshow("原图", image);//显示原图
	waitKey(30);

	cvtColor(image, hue_image, CV_BGR2GRAY);//将原图转为灰度图
	threshold(hue_image, binary_image, 140, 255, THRESH_BINARY);// 将灰度图转为二值图

	ToHSV(image, binary_image);//将RGB转为HSV

	Homography(binary_image, binary_image);//形态学开运算

	copymask(image, binary_image, result);//利用二值图(binary_image)上目标颜色的轮廓,将原图(image)上相应坐标位置颜色值赋给result
	imshow("result", result);
	waitKey(30);

	getchar();
    return 0;
}

效果:

  • 0
    点赞
  • 10
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

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

余额充值