第一章 初识EmguCV

第一章 初识EmguCV

1.1 EmguCV的基本介绍

1.1.1 计算机视觉、OpenCV和EmguCV

计算机视觉是一门研究如何使机器“看”的科学,更进一步的说,就是是指用摄影机和电脑代替人眼对目标进行识别、跟踪和测量等机器视觉,并进一步做图形处理,使电脑处理成为更适合人眼观察或传送给仪器检测的图像。作为一个科学学科,计算机视觉研究相关的理论和技术,试图建立能够从图像或者多维数据中获取‘信息’的人工智能系统。这里所 指的信息指Shannon定义的,可以用来帮助做一个“决定”的信息。因为感知可以看作是从感官信号中提 取信息,所以计算机视觉也可以看作是研究如何使人工系统从图像或多维数据中“感知”的科学。

OpenCV是一个基于BSD许可(开源)发行的跨平台计算机视觉库,可以运行在Linux、Windows、Android和Mac OS操作系统上。它轻量级而且高效——由一系列 C 函数和少量 C++ 类构成,同时提供了Python、Ruby、MATLAB等语言的接口,实现了图像处理和计算机视觉方面的很多通用算法。

OpenCV用C++语言编写,它的主要接口也是C++语言,但是依然保留了大量的C语言接口。该库也有大量的Python、Java and MATLAB/OCTAVE(版本2.5)的接口。这些语言的API接口函数可以通过在线文档获得。如今也提供对于C#、Ch、Ruby,GO的支持。

然而OpenCV的函数并不能直接由C#语言调用。因此,需要用C#对OpenCV进行一次封装,这就是EmguCV。

1.1.2 OpenCV和EmguCV概述

说起EmguCV那就不得不说OpenCV,可以说EmguCV的本质就是OpenCV。它使得C#、VB、VC++可以调用OpenCV函数。

OpenCV于1999年由Intel建立,如今由Willow Garage提供支持。OpenCV是一个基于BSD许可(开源)发行的跨平台计算机视觉库,可以运行在Linux、Windows和Mac OS操作系统上。它轻量级而且高效——由一系列 C 函数和少量 C++ 类构成,同时提供了Python、Ruby、MATLAB等语言的接口,实现了图像处理和计算机视觉方面的很多通用算法。

相比OpenCV,EmguCV发行的时间晚了很多。直到2008年5月才公开发布了最初的版本。

OpenCV官网地址:https://opencv.org/

EmguCV官网地址:http://www.emgu.com/

1.1.3 EmguCV应用

由于EmguCV的作用和OpenCV完全相同,因此这里也用OpenCV来说明。

OpenCV所有的开放源代码协议允许你使用OpenCV的全部代码或者OpenCV的部分代码生成商业产品。使用了OpenCV后,你不必对公众开放自己的源代码或改善后的算法,虽然我们非常希望你能够开放源代码。许多公司(IBM,Microsoft,Intel,SONY,Siemens和Google等其他公司)和研究单位(例如斯坦福大学、MIT、CMU、剑桥大学和INRIA)中的人都广泛使用OpenCV,其部分原因是OpenCV采用了这个宽松的协议。

自从OpenCV在1999年1月发布alpha版本开始,它就被广泛用在许多应用领域、产品和研究成果中。相关应用包括卫星地图和电子地图的拼接,扫描图像的对齐,医学图像去噪(消噪或滤波),图像中的物体分析,安全和入侵检测系统,自动监视和安全系统,制造业中的产品质量检测系统,摄像机标定,军事应用,无人飞行器,无人汽车和无人水下机器人。将视觉识别技术用在声谱图上,OpenCV可以进行声音和音乐识别。在斯坦福大学的Stanley机器人项目中,OpenCV是其视觉系统的关键部分。Stanley在DARPA机器人沙漠挑战赛中,赢得了二百万美元奖金。

1.2 EmguCV对OpenCV的封装

1.2.1函数映射 Emgu.CV.CvInvoke

CvInvoke类可以使C#直接调用OpenCV的函数,这个类中的函数均对应OpenCV中的同名函数。(但有在OpenCV中有极个别的函数EmguCV中没有)例如:

EmguCV中的 CvInvoke.Imread(“Car.jpg”); 等价于OpenCV中的 Imread(“Car.jpg”);

1.2.2 结构映射 Emgu.CV.Structure.Mxxx

EmguCV结构:Emgu.CV.Structure.MCvMat 等价于 OpenCV结构:CvMat

EmguCV结构:Emgu.CV.Structure.MCvScalar等价于 OpenCV结构:CvScalar

EmguCV结构:Emgu.CV.Structure.Mxxx 等价于 OpenCV结构:xxx

可以看出EmguCV中的结构在Emgu.CV.Structure命名空间下,OpenCV的结构名+M。除此之外,EmguCV还借用了一些.NET的结构对应OpenCV的结构。例如:

System.Drawing.Point等价于OpenCV中的CvPoint

System.Drawing.Size等价于OpenCV中的CvSize

System.Drawing.Rectangle等价于OpenCV中的CvRectangle

1.2.3 EmguCV安装后的文件结构(3.4.3版为例)

![img](file:///C:\Users\yuteng\AppData\Local\Temp\ksohtml28888\wps1.jpg)

选中的两个文件夹是最重要的文件夹,平时主要用到的DLL文件在这两个文件夹内。

![img](file:///C:\Users\yuteng\AppData\Local\Temp\ksohtml28888\wps2.jpg)

Solution文件夹里提供了源码和官方的一些示例程序的解决方案(.sln文件),如人脸识别等。

![img](file:///C:\Users\yuteng\AppData\Local\Temp\ksohtml28888\wps3.jpg)

选中的文件夹内的是EmguCV的源码。

1.3 EmguCV的下载、安装和配置

1.3.1 EmguCV的下载和安装

EmguCV经过了十多年的发展,不同的版本的配置和用法差异较大,因此EmguCV推荐使用3.3以及以上版本。Visual studio 推荐使用2015以及以上版本。

EmguCV下载链接:https://sourceforge.net/projects/emgucv/files/emgucv/

在这个链接内包含各个版本的下载地址,可以根据需要下载对应版本

![img](file:///C:\Users\yuteng\AppData\Local\Temp\ksohtml28888\wps4.jpg)

下载完成后是一个.exe文件(版本不同,名称也不同)

![img](file:///C:\Users\yuteng\AppData\Local\Temp\ksohtml28888\wps5.jpg)

双击这个可执行文件就可以进行安装操作

![img](file:///C:\Users\yuteng\AppData\Local\Temp\ksohtml28888\wps6.jpg)

点击下一步

![img](file:///C:\Users\yuteng\AppData\Local\Temp\ksohtml28888\wps7.jpg)

点击我接受

![img](file:///C:\Users\yuteng\AppData\Local\Temp\ksohtml28888\wps8.jpg)

点击下一步

![img](file:///C:\Users\yuteng\AppData\Local\Temp\ksohtml28888\wps9.jpg)

下一步

![img](file:///C:\Users\yuteng\AppData\Local\Temp\ksohtml28888\wps10.jpg)

点击安装,EmguCV就可以安装在指定路径中

![img](file:///C:\Users\yuteng\AppData\Local\Temp\ksohtml28888\wps11.jpg)

如果没有发生异常,则会出现这个界面,点击完成就可退出。

1.3.2 EmguCV的配置

配置方法:计算机右键-属性-高级系统设置-高级-环境变量,找到系统变量的Path选项。

![img](file:///C:\Users\yuteng\AppData\Local\Temp\ksohtml28888\wps12.jpg)

点击编辑,添加EmguCV安装目录下的bin目录,如果是32位的系统还需添加libs\x86文件夹,如果是64位系统则添加libs\x86和libs\x64两个文件夹。(不要把原来的内容删除)

![img](file:///C:\Users\yuteng\AppData\Local\Temp\ksohtml28888\wps13.jpg)

举例:;C:\Emgu\emgucv-windesktop 3.4.3.3016\bin;C:\Emgu\emgucv-windesktop 3.4.3.3016\libs\x64;C:\Emgu\emgucv-windesktop 3.4.3.3016\libs\x86;

1.3.3 在项目中添加引用

这里使用C#语言和visual studio 开发环境进行说明

新建一个窗体程序,在解决方案的【引用】右键添加引用

![img](file:///C:\Users\yuteng\AppData\Local\Temp\ksohtml28888\wps14.jpg)

![img](file:///C:\Users\yuteng\AppData\Local\Temp\ksohtml28888\wps15.jpg)

点击浏览,找到安装目录下的bin文件夹,引用图中所示的DLL文件,点击确定。

在Main方法里,添加

Image<Bgr, byte> image = new Image<Bgr, byte>(320, 240, new Bgr(0, 0, 255));

CvInvoke.Imshow(“img”, image);

CvInvoke.WaitKey(0);

三行代码,点击运行,如果出现一个红色的窗体。则配置成功。

![img](file:///C:\Users\yuteng\AppData\Local\Temp\ksohtml28888\wps16.jpg)

1.4 EmguCV对图像的基本操作

1.4.1 使用EmguCV对图片进行读取和保存

对于图像的读取,可以用CvInvoke.Imread()方法。将读取的图片用Mat类保存起来,然后CvInvoke.Imshow()出来就能正常显示。对于图像的保存,可以用CvInvoke.Imwrite()方法,将读取的图像保存起来。下面对这两个步骤进行详细操作。

首先用visual studio新建一个控制台应用程序,(需要先引用命名空间,在EmguCV的配置中已经有过说明。这里不再赘述)在程序的根目录放置一张aa.JPG的图片,在Main方法中添加如下代码:

class Program

​ {

​ static void Main(string[] args)

​ {

​ //读取源文件

​ Mat srcImg = CvInvoke.Imread(“aa.JPG”);

​ CvInvoke.Imshow(“img”, srcImg);

​ //将图片保存成一个新文件

​ CvInvoke.Imwrite(“new.jpg”, srcImg);

​ //等待按键

​ CvInvoke.WaitKey(0);

​ }

​ }

这里有一个地方需要注意,就是在程序的最后一句加上CvInvoke.WaitKey(0);这行代码,否则程序会一闪而过。如果程序没有异常,则会得到如下的效果。

![img](file:///C:\Users\yuteng\AppData\Local\Temp\ksohtml28888\wps17.jpg)

1.4.2 图像的腐蚀

腐蚀主要用于形态学中除去图像的某些部分,可以有效滤除噪声,保留图像中原有信息。

新建一个控制台应用程序,添加以下代码:

class Program

​ {

​ static void Main(string[] args)

​ {

​ //读取源文件

​ Mat srcImg = CvInvoke.Imread(“aa.JPG”);

​ CvInvoke.Imshow(“img”, srcImg);

​ Mat grayImg = new Mat();

​ CvInvoke.CvtColor(srcImg, grayImg, ColorConversion.Bgr2Gray);

​ Mat element = CvInvoke.GetStructuringElement(ElementShape.Rectangle, new Size(3, 3), new Point(-1, -1));

​ CvInvoke.Erode(grayImg, grayImg, element, new Point(-1, -1), 1, BorderType.Default, new MCvScalar());

​ CvInvoke.Imshow(“newPhoto”, grayImg);

​ //等待按键

​ CvInvoke.WaitKey(0);

​ }

​ }

如果运行无误,则会得到如下结果:

![img](file:///C:\Users\yuteng\AppData\Local\Temp\ksohtml28888\wps18.jpg)

左边的图像是正常的图片,右边的图片是经过腐蚀以后的图片。

1.4.3 图像的滤波

图像滤波,即在尽量保留图像细节特征的条件下对目标图像的噪声进行抑制,是图像预处理中不可缺少的操作,其处理效果的好坏将直接影响到后续图像处理和分析的有效性和可靠性。

由于成像系统、传输介质和记录设备等的不完善,数字图像在其形成、传输记录过程中往往会受到多种噪声的污染。另外,在图像处理的某些环节当输入的像对象并不如预想时也会在结果图像中引入噪声。这些噪声在图像上常表现为一引起较强视觉效果的孤立象素点或象素块。一般,噪声信号与要研究的对象不相关它以无用的信息形式出现,扰乱图像的可观测信息。对于数字图像信号,噪声表为或大或小的极值,这些极值通过加减作用于图像象素的真实灰度值上,在图像造成亮、暗点干扰,极大降低了图像质量,影响图像复原、分割、特征提取、图识别等后继工作的进行。要构造一种有效抑制噪声的滤波机必须考虑两个基本问题能有效地去除目标和背景中的噪声;同时,能很好地保护图像目标的形状、大小及特定的几何和拓扑结构特征。

接下来用一个简单的控制台应用程序来对图像滤波进行简单实现,新建一个控制台程序,在Main方法中添加一下代码:

class Program

​ {

​ static void Main(string[] args)

​ {

​ Mat srcImg = CvInvoke.Imread(“a.png”);

​ CvInvoke.Imshow(“src”, srcImg);

​ Mat dst = new Mat();

​ CvInvoke.MedianBlur(srcImg, dst, 9);

​ CvInvoke.Imshow(“dst”, dst);

​ CvInvoke.WaitKey(0);

​ }

​ }

运行效果如下:

![img](file:///C:\Users\yuteng\AppData\Local\Temp\ksohtml28888\wps19.jpg)

左图是原图像,右图是经过处理的图像。

1.4.4 图像的边缘检测

边缘检测的用途广泛,算法有很多种,但处理步骤都是一致的。都是读取原图像-转成灰度图-降噪-用算法进行边缘检测。下面用控制台程序对边缘检测进行简单实现。代码如下:

class Program

​ {

​ static void Main(string[] args)

​ {

​ //Canny边缘检测,首先读取原图像

​ Mat srcImg = CvInvoke.Imread(“a.png”);

​ //显示原图像

​ CvInvoke.Imshow(“src”, srcImg);

​ Mat grayImg = new Mat();

​ //转成灰度图

​ CvInvoke.CvtColor(srcImg, grayImg, ColorConversion.Bgr2Gray);

​ //进行降噪

​ CvInvoke.GaussianBlur(grayImg, grayImg, new Size(3, 3), 0, 0);

​ //使用Canny算子进行边缘检测

​ CvInvoke.Canny(grayImg, grayImg, 30, 100);

​ //显示检测后的图像

​ CvInvoke.Imshow(“Canny”, grayImg);

​ CvInvoke.WaitKey(0);

​ }

​ }

运行效果如下:左边的图像是原图像,右边的图像是进行边缘检测后的效果。

![img](file:///C:\Users\yuteng\AppData\Local\Temp\ksohtml28888\wps20.jpg)

1.5 视频操作基础

1.5.1 使用摄像头读取视频并保存

在EmguCV中可以用VideoCapture类来实现视频的读取,用VideoWriter类实现视频的保存,下面用控制台应用程序来实现读取视频并保存的功能,新建一个控制台程序,代码如下:

​ class Program

​ {

​ static void Main(string[] args)

​ {

​ show();

​ }

​ private static void show()

​ {

​ VideoCapture cap = new VideoCapture();

​ VideoWriter writer = new VideoWriter(“save.avi”, 20, new Size(640, 480), true);

​ if (!cap.IsOpened)

​ {

​ Console.WriteLine(“打开失败”);

​ return;

​ }

​ Mat mat = new Mat();

​ while (true)

​ {

​ cap.Read(mat);

​ if (mat.IsEmpty)

​ {

​ Console.WriteLine(“读取完毕”);

​ break;

​ }

​ CvInvoke.Imshow(“video”, mat);

​ writer.Write(mat);

​ CvInvoke.WaitKey(30);

​ }

​ CvInvoke.WaitKey(0);

​ }

​ }

VideoCapture cap = new VideoCapture();进行初始化的时候,如果括号中不写参数,就会调用默认的摄像头读取视频

1.5.2 读取并播放视频文件

读取视频文件与读取摄像头的方法相差无几,仅仅是参数不同而已。代码如下

​ class Program

​ {

​ static void Main(string[] args)

​ {

​ show();

​ }

​ private static void show()

​ {

​ VideoCapture cap = new VideoCapture(“AVSEQ02.avi”);

​ VideoWriter writer = new VideoWriter(“save.avi”, 20, new Size(640, 480), true);

​ if (!cap.IsOpened)

​ {

​ Console.WriteLine(“打开失败”);

​ return;

​ }

​ Mat mat = new Mat();

​ while (true)

​ {

​ cap.Read(mat);

​ if (mat.IsEmpty)

​ {

​ Console.WriteLine(“读取完毕”);

​ break;

​ }

​ CvInvoke.Imshow(“video”, mat);

​ writer.Write(mat);

​ CvInvoke.WaitKey(30);

​ }

​ CvInvoke.WaitKey(0);

​ }

​ }

VideoCapture类在初始化的时候,里面的参数如果是视频的文件的路径(可以是相对路径,也可以是绝对路径,甚至可以是网络地址的文件),那么初始化的时候,就会读取路径中的视频。

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

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

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

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值