本示例主要测试了directshow、Emgucv的视频流采集功能,其中Emgucv还实现了人脸的识别。示例源码下载

一、directshow的介绍

实现原理:directshow可以将摄像头的数据流以事件的方式实时传递给程序,程序在此事件中拿到流后可以保存为图片(流可以经过多个filterGraph2对象)。directshow提供将数据绑定到picturebox控件上。以下为打开一个摄像头的步骤:

1. 引入directshow.net控件

此控件可以在网上搜索,即好下载,名称为DirectShowLib-2005,它是directshow的.net版本的封装.

2. 初始化directshow相关的接口

代码如下:

  1. int hr = ;
  2. this.filterGraph2 = (IFilterGraph2)new FilterGraph();
  3. this.captureGraphBuilder2 = (ICaptureGraphBuilder2)new CaptureGraphBuilder2();
  4. this.mediaControl = (IMediaControl)this.filterGraph2;
  5. this.videoWindow = (IVideoWindow)this.filterGraph2;
  6. DsError.ThrowExceptionForHR(hr);

说明:

  1. filterGraph2:流过滤器
  2. captureGraphBuilder2:视频设备处理
  3. mediaControl:视频控制,如:开启或关闭等
  4. videoWidow:视频显示在窗体上的一些信息设置类
  5. filterGraph2会被附加到captureGraphBuilder2对象.

3. 找到摄像头设备

  1. int hr = ;
  2. IEnumMoniker classEnum = null;
  3. IMoniker[] moniker = new IMoniker[];
  4. object source = null;
  5.  
  6. ICreateDevEnum devEnum = (ICreateDevEnum)new CreateDevEnum();
  7. hr = devEnum.CreateClassEnumerator(FilterCategory.VideoInputDevice, out classEnum, );
  8. DsError.ThrowExceptionForHR(hr);
  9.  
  10. Marshal.ReleaseComObject(devEnum);
  11.  
  12. if (classEnum == null)
  13. throw new Exception("classEnum is null");
  14.  
  15. if (classEnum.Next(moniker.Length, moniker, IntPtr.Zero) == )
  16. {
  17. Guid iid = typeof(IBaseFilter).GUID;
  18. moniker[].BindToObject(null, null, ref iid, out source); //moniker绑定以 ibasefilter和object上
  19. }
  20.  
  21. Marshal.ReleaseComObject(moniker[]);
  22. Marshal.ReleaseComObject(classEnum);
  23.  
  24. return (IBaseFilter)source;

找到视频摄像头,将转换为一个IBaseFilter对象。

4. 增加摄像头、视频处理过滤器

将IBaseFilter对象加入到filterGraph2对象上,作为第一层视频的过滤,后面会放到picturebox控件上。然后再加入SampleGrabber对象,用于捕获每一帧的视频数据。

5. 设置摄像头显示参数、预览参数、 设置保存的尺寸信息

此步代码较多,就不在贴代码,后面给出源码下载地址.

6. 绑定以pictruebox控件上,以及运行

  1. int hr = ;
  2. hr = this.videoWindow.put_Owner(this.pictureBox.Handle);
  3. DsError.ThrowExceptionForHR(hr);
  4.  
  5. hr = this.videoWindow.put_WindowStyle(WindowStyle.Child);
  6. DsError.ThrowExceptionForHR(hr);
  7.  
  8. hr = this.videoWindow.put_Visible(OABool.True);
  9. DsError.ThrowExceptionForHR(hr);
  10.  
  11. System.Drawing.Rectangle rc = this.pictureBox.ClientRectangle;
  12. hr = this.videoWindow.SetWindowPosition(, , , );
  13. DsError.ThrowExceptionForHR(hr);

二、emgucv的介绍

emgucv是opencv的.net版本封装,并且opencv获取视频流的方式也是采用的directshow。由于进行了封装,打开和识别人像就极为简单了。

1. 下载emgucv并安装,然后在系统环境变量中添加其安装路径.


至此,还需复制相关的dll到开发项目中:

2. 打开摄像头

  1. private VideoCapture capture;
  2. private Mat mat;
  3. private Common.DetectFace detectFace;
  4. public Form1()
  5. {
  6. InitializeComponent();
  7. CvInvoke.UseOpenCL = false;
  8. detectFace = new Common.DetectFace();
  9. }
  10.  
  11. private void Form1_Load(object sender, EventArgs e)
  12. {
  13. capture = new Emgu.CV.VideoCapture();
  14. capture.ImageGrabbed += Capture_ImageGrabbed;
  15. capture.Start();
  16. }
  17.  
  18. private void Capture_ImageGrabbed(object sender, EventArgs e)
  19. {
  20. if (capture != null && capture.Ptr != IntPtr.Zero)
  21. {
  22. mat = new Mat();
  23. capture.Retrieve(mat, );
  24.  
  25. var ls = detectFace.Detect(mat);
  26. foreach(var face in ls)
  27. {
  28. CvInvoke.Rectangle(mat, face, new Bgr(Color.Red).MCvScalar, );
  29. }
  30.  
  31. imageBox1.Image = mat;
  32. }
  33. }

说明:

  1. Capture_ImageGrabbed捕获到的就是实时的视频流,在此处就可以做相关的处理。
  2. 此处加入了对人脸的识别,并用红框表示出来。

directshow、 Emgucv入门的更多相关文章

  1. DirectShow简单入门程序

    1.首先确认已安装过相关工具及配置环境,然后打开vs2010,新建一对话框应用程序 取名为Player_test1,然后打开菜单->项目->属性-> 添加strmmiids.lib库 ...

  2. DirectShow 最简单的入门 -- 播放一段视频

    #include <dshow.h> #pragma comment(lib,"strmbase.lib") #pragma comment(lib,"qua ...

  3. DirectShow开发快速入门之慨述

    摘要:本篇文档概括性的介绍了DirectShow的主要组成部分,以及一些Directshow的基本概念.熟悉这些基本的知识对于Directshow的应用开发或者过滤器的开发者都会有所帮助. Direc ...

  4. EmguCV C# 安装入门教程

    EmguCv3的安装. EmguCv3下载网址 http://sourceforge.net/projects/emgucv/files/emgucv/3.0.0/ 推荐下载第一个: 点击direct ...

  5. 使用C#+EmguCV处理图像入门(图像读取_显示_保存)二

    上个随笔已经介绍EmguCV的一些常用库和程序安装以及环境变量的配置,这次写的是如何使用这个类库对图像进行操作. EmguCV图像处理系统组成(个人见解): 图像的基本操作: 贴个代码: using ...

  6. 使用C#+EmguCV处理图像入门(一)

    首先我们先了解一下该库的一些相关信息 OpenCV(Open Source Computer Vision Library)是一个(开源免费)发行的跨平台计算机视觉库,可以运行在Linux.Windo ...

  7. 【EmguCV视频教程】VS2017+EmguCV3.4(C# OpenCV)高清入门视频教程

    视频采用VS2017 + EmguCV3.4版本录制,内容类似本人的Python和C++版本,如果需要的朋友可加我咨询,视频共40讲,从按照到读取显示图片,图形预处理,边缘检测,形态学,角点检测,轮廓 ...

  8. 浅入浅出EmguCv(一)OpenCv与EmguCv

    最近接触计算机视觉方面的东西,于是准备下手学习opencv,从官网下载windows的安装版,配置环境,一系列步骤走完后,准备按照惯例弄个HelloWord.也就是按照网上的教程,打开了那个图像处理领 ...

  9. 转:最简单的基于 DirectShow 的视频播放器

    50行代码实现的一个最简单的基于 DirectShow 的视频播放器 本文介绍一个最简单的基于 DirectShow 的视频播放器.该播放器对于初学者来说是十分有用的,它包含了使用 DirectSho ...

随机推荐

  1. java-数组排序--计数排序、桶排序、基数排序

    计数排序引入 不难发现不论是冒泡排序还是插入排序,其排序方法都是通过对每一个数进行两两比较进行排序的,这种方法称为比较排序,实际上对每个数的两两比较严重影响了其效率,理论上比较排序时间复杂度的最低下限 ...

  2. TMS320DM642学习----第六篇(CCS中.dat文件类型详解)

    1.如下为.dat文件中文件头的基本格式: MagicNumber Format StartingAddress PageNum Length [NewFormat] 下面是分别的解释: MagicN ...

  3. C++结构体与Delphi结构体相互传参,结构体中包含结构体的嵌套,数组指针

    //结构体的声明 typedef struct Mwinddirectbaseline { char* p; int s; int i; }Mwinddirectbaseline; typedef s ...

  4. php字符串与数组的特殊情况

    来看一个有趣的实验 实验1 <?php $arr = array('a','b','c'); var_dump(isset($arr[1][0])); var_dump($arr[0][0]); ...

  5. Interpreting NotifyCollectionChangedEventArgs zz

    If you’ve ever consumed INotifyCollectionChanged.CollectionChanged, then you’ve run into some inadeq ...

  6. 变量前缀__device__以及__managed__

    1.__device__ 作为变量前缀时,__device__限定符声明位于设备上的变量.如果此限定符单独使用,则变量具有以下特征: a.位于全局存储器空间中: b.与应用程序具有相同的生命周期: 可 ...

  7. pandas中Dataframe的查询方法([], loc, iloc, at, iat, ix)

    数据介绍 先随机生成一组数据: import pandas as pd import numpy as np state = ['Ohio', 'Ohio', 'Ohio', 'Nevada', 'N ...

  8. java拦截处理System.exit(0)

    在使用TestNG做单元测试时,需要测试的代码中出现System.exit(0),导致单元测试还未结束程序就停止了.解决方法如下: public class TestMain { public sta ...

  9. spark streaming中维护kafka偏移量到外部介质

    spark streaming中维护kafka偏移量到外部介质 以kafka偏移量维护到redis为例. redis存储格式 使用的数据结构为string,其中key为topic:partition, ...

  10. selenium webdriver定位不到元素的五种原因及解决办法

    1.动态id定位不到元素 for example:        //WebElement xiexin_element = driver.findElement(By.id("_mail_ ...