這個項目是關于如何從網絡攝像頭或者視訊檔案(*.AVI)中捕獲視訊的,這個項目是用C#和OPENCV編寫的。
這将有助于那些喜歡C#和OpenCV環境的人。這個程式完全基于Visual Studio 2010 version C#.NET環境。這個程式展示了怎樣用C#.NET環境的Visual Studio 2010 IDE編寫OpenCV,這個程式是一個怎樣用Visual Studio 2010,C#.NET建立程式的例子。
在這篇文章中,我解釋了怎樣配置Visual Studio 2010,一種配置計算機環境變量EmguCV2.4.9以便運作OpenCV程式的步驟。
![](https://img.laitimes.com/img/_0nNw4CM6IyYiwiM6ICdiwiIn5GcuADMyQTYzITMyATZ0UmNkJ2NiZWO2UGZ3YmNyUDN1AjYfdWbp9CXt92Yu4GZjlGbh5SZslmZxl3Lc9CX6MHc0RHaiojIsJye.png)
EmguCV:讓我們開始工作吧。。。
EmguCV 是一個跨平台的運作OpenCV圖形庫的殼。它允許從.NET語言例如C#,VB,VC++中調用OpenCV函數,這個殼可以用Mono編譯,在Windows,Linux,Mac OS X,iPhone,iPad 和Android 裝置中運作。
EmguCV是用C#編寫的。可以在Mono中編譯,是以它可以在任何Mono支援的平台上運作,包括 Linux, Mac and Android。
<a target="_blank" href="http://my.oschina.net/pou">pou</a>
翻譯于 2年前
2人頂
第 1 步: 安裝 EmguCV 2.4.9
下載下傳 EmguCV 2.4.9 版本. 将它安裝在 c:\ 磁盤 位置, 不要改變路徑, 使用預設的路徑“C:\Emgu\emgucv-windows-universal-gpu2.4.9.1847”.
安裝路徑 – “C:\Emgu\emgucv-windows-universal-gpu2.4.9.1847”.
所有的框框都選上,全包安裝.
第 2 步: 設定環境變量:
在使用者和系統變量中設定如下的三個路徑.
C:\Emgu\emgucv-windows-universal-gpu 2.4.9.1847\bin;
C:\Emgu\emgucv-windows-universal-gpu 2.4.9.1847\bin\x64;
C:\Emgu\emgucv-windows-universal-gpu 2.4.9.1847\bin\x86;
第 3 步: 配置 Visual Studio 2010:
建立一個新的 Windows Application 項目,命名為‘Two Layer’.
選擇引用, 右鍵點選添加引用.
選擇 Browse 頁籤, 找到“C:\Emgu\emgucv-windows-universal-gpu2.4.9.1847\bin”, 選擇“Emgu.CV.dll”,”Emgu.CV.UI.dll”,”Emgu.Util.dll” 三個檔案, 并點選ok.
引用就會在Solution Explorer中出現.
<a target="_blank" href="http://my.oschina.net/xuleo">leoxu</a>
0人頂
捕獲視訊功能,捕獲視訊有兩種方式,一種是從錄影機捕獲,第二種是從視訊檔案捕獲。接下來的部分,代碼會向你展示如果從錄影機捕獲視屏.
在這一節中, 捕獲, FRAME PER SECOND 設定為 30 FPS, 視訊檔案捕獲的高和寬分别設定為 240, 320 . 然後video_seek
被初始化為零 '0', 這個視訊搜尋控制會在視訊限制的低位和高位之間搜尋視訊.
下面的語句在應用程式中最有用. 它有點像多線程. 當應用程式進入到空閑狀态,"ProcessFrame" 就會一直調用直到視訊幀結束或者直到幀不為 'null'.
1
<code>Application.Idle += ProcessFrame;</code>
在從視訊檔案捕獲的代碼中,我們需要總幀數來設定視訊搜尋控制的上限. FOURCC 被用來找到多媒體的編碼解碼器名稱.
<code>#region cameracapture</code>
<code> </code><code>if</code> <code>(comboBox1.Text == </code><code>"Capture From Camera"</code><code>)</code>
<code> </code><code>{</code>
<code> </code><code>try</code>
<code> </code><code>{</code>
<code> </code><code>_capture = </code><code>null</code><code>;</code>
<code> </code><code>_capture = </code><code>new</code> <code>Capture(0);</code>
<code> </code><code>_capture.SetCaptureProperty(Emgu.CV.CvEnum.CAP_PROP.CV_CAP_PROP_FPS, 30);</code>
<code> </code><code>_capture.SetCaptureProperty(Emgu.CV.CvEnum.CAP_PROP.CV_CAP_PROP_FRAME_HEIGHT, 240);</code>
<code> </code><code>_capture.SetCaptureProperty(Emgu.CV.CvEnum.CAP_PROP.CV_CAP_PROP_FRAME_WIDTH, 320);</code>
<code> </code><code>Time_Label.Text = </code><code>"Time: "</code><code>;</code>
<code> </code><code>Codec_lbl.Text = </code><code>"Codec: "</code><code>;</code>
<code> </code><code>Frame_lbl.Text = </code><code>"Frame: "</code><code>;</code>
<code> </code><code>webcam_frm_cnt = 0;</code>
<code> </code><code>cam = 1;</code>
<code> </code><code>Video_seek.Value = 0;</code>
<code> </code><code>Application.Idle += ProcessFrame;</code>
<code> </code><code>button1.Text = </code><code>"Stop"</code><code>;</code>
<code> </code><code>comboBox1.Enabled = </code><code>false</code><code>;</code>
<code> </code><code>}</code>
<code> </code><code>catch</code> <code>(NullReferenceException excpt)</code>
<code> </code><code>MessageBox.Show(excpt.Message);</code>
<code> </code><code>}</code>
<code>#endregion cameracapture</code>
<code>#region filecapture</code>
<code> </code><code>if</code> <code>(comboBox1.Text == </code><code>"Capture From File"</code><code>)</code>
<code> </code><code>openFileDialog1.Filter = </code><code>"MP4|*.mp4"</code><code>;</code>
<code> </code><code>openFileDialog1.FileName = </code><code>""</code><code>;</code>
<code> </code><code>if</code> <code>(openFileDialog1.ShowDialog() == DialogResult.OK)</code>
<code> </code><code>try</code>
<code> </code><code>{</code>
<code> </code><code>_capture = </code><code>null</code><code>;</code>
<code> </code><code>_capture = </code><code>new</code> <code>Capture(openFileDialog1.FileName);</code>
<code> </code><code>_capture.SetCaptureProperty(Emgu.CV.CvEnum.CAP_PROP.CV_CAP_PROP_FRAME_HEIGHT, 240);</code>
<code> </code><code>_capture.SetCaptureProperty(Emgu.CV.CvEnum.CAP_PROP.CV_CAP_PROP_FRAME_WIDTH, 320);</code>
<code> </code><code>FrameRate = _capture.GetCaptureProperty(Emgu.CV.CvEnum.CAP_PROP.CV_CAP_PROP_FPS);</code>
<code> </code><code>TotalFrames = _capture.GetCaptureProperty(Emgu.CV.CvEnum.CAP_PROP.CV_CAP_PROP_FRAME_COUNT);</code>
<code> </code><code>codec_double = _capture.GetCaptureProperty(Emgu.CV.CvEnum.CAP_PROP.CV_CAP_PROP_FOURCC);</code>
<code> </code><code>string</code> <code>s = </code><code>new</code> <code>string</code><code>(System.Text.Encoding.UTF8.GetString</code>
<code> </code><code>(BitConverter.GetBytes(Convert.ToUInt32(codec_double))).ToCharArray());</code>
<code> </code><code>Codec_lbl.Text = </code><code>"Codec: "</code> <code>+ s;</code>
<code> </code><code>cam = 0;</code>
<code> </code><code>Video_seek.Minimum = 0;</code>
<code> </code><code>Video_seek.Maximum = (</code><code>int</code><code>)TotalFrames - 1;</code>
<code> </code><code>Application.Idle += ProcessFrame;</code>
<code> </code><code>button1.Text = </code><code>"Stop"</code><code>;</code>
<code> </code><code>comboBox1.Enabled = </code><code>false</code><code>;</code>
<code> </code><code>}</code>
<code> </code><code>catch</code> <code>(NullReferenceException excpt)</code>
<code> </code><code>MessageBox.Show(excpt.Message);</code>
<code> </code><code>}</code>
<code> </code><code>}</code>
<code>#endregion filecapture</code>
下面的函數用來處理幀. 幀處理可以提取出一些詳細資訊,如幀的編号,時間軸,總的幀數等. 這個函數展示了圖檔盒子中的圖像序列. 幀可以被轉換成位元組數組. 這個位元組資料可以被轉換成每一幀的16進制值. 然後那些十六進制值被存到數組中做進一步的處理. 從裝置或者視訊檔案捕獲的視訊中提取目前幀.
<code>frame = _capture.QueryFrame();</code>
幀被轉換成 bitmap 并被指派給圖檔盒子用于展示 .
<code>pictureBox1.Image = frame.ToBitmap();</code>
函數在按幀率劃分的特定時間休眠.
<a target="_blank" href="http://www.oschina.net/translate/video-capture-using-opencv-with-csharp#">?</a>
<code>Thread.Sleep((</code><code>int</code><code>)(1000.0 / FrameRate));</code>
幀被轉換成位元組數組.
這個位元組資料被轉換成每一幀的16進制值. 然後那些十六進制值被存到數組中做進一步的處理.
<code>private</code> <code>void</code> <code>ProcessFrame(</code><code>object</code> <code>sender, EventArgs arg)</code>
<code>{</code>
<code> </code><code>try</code>
<code> </code><code>{</code>
<code> </code><code>Framesno = _capture.GetCaptureProperty(Emgu.CV.CvEnum.CAP_PROP.CV_CAP_PROP_POS_FRAMES);</code>
<code> </code><code>frame = _capture.QueryFrame();</code>
<code> </code><code>if</code> <code>(frame != </code><code>null</code><code>)</code>
<code> </code><code>{</code>
<code> </code><code>pictureBox1.Image = frame.ToBitmap();</code>
<code> </code><code>if</code> <code>(cam == 0)</code>
<code> </code><code>{</code>
<code> </code><code>Video_seek.Value = (</code><code>int</code><code>)(Framesno);</code>
<code> </code><code>double</code> <code>time_index = _capture.GetCaptureProperty(Emgu.CV.CvEnum.CAP_PROP.CV_CAP_PROP_POS_MSEC);</code>
<code> </code><code>Time_Label.Text = </code><code>"Time: "</code> <code>+ TimeSpan.FromMilliseconds(time_index).ToString().Substring(0, 8);</code>
<code> </code><code>double</code> <code>framenumber = _capture.GetCaptureProperty(Emgu.CV.CvEnum.CAP_PROP.CV_CAP_PROP_POS_FRAMES);</code>
<code> </code><code>Frame_lbl.Text = </code><code>"Frame: "</code> <code>+ framenumber.ToString();</code>
<code> </code><code>Thread.Sleep((</code><code>int</code><code>)(1000.0 / FrameRate));</code>
<code> </code><code>}</code>
<code> </code><code>if</code> <code>(cam == 1)</code>
<code> </code><code>Frame_lbl.Text = </code><code>"Frame: "</code> <code>+ (webcam_frm_cnt++).ToString();</code>
<code> </code><code>catch</code> <code>(Exception ex)</code>
<code> </code><code>MessageBox.Show(ex.Message.ToString());</code>
<code>}</code>
這個方法用來釋放資料. 它同時也釋放了捕獲變量所需要的一些資源.
<code>private</code> <code>void</code> <code>ReleaseData()</code>
<code> </code><code>if</code> <code>(_capture != </code><code>null</code><code>)</code>
<code> </code><code>_capture.Dispose();</code>