有些OMCS用戶在他的系統使用了特殊的視頻采集卡作為視頻源(如AV-878采集卡),雖然這些采集卡可以虛擬為一個攝像頭,但有些視頻采集卡需要依賴于自帶了sdk才能正常地完成視頻采集工作。在這種情況下,OMCS是不直接支持這些采集卡的。我們的思路是使OMCS具有自定義擴展的能力:我們讓OMCS提供了擴展接口,讓使用者可以向OMCS框架中注入其自己的視頻采集程序。使用者要達到這種自定義的擴展相當簡單,只需實現兩個接口即可。
1.IVideoCapturer接口
OMCS.Engine.Video.IVideoCapturer定義了視頻采集器的基本功能,其用于采集RGB24格式的圖像,其定義如下:
public interface IVideoCapturer :IDisposable { /// <summary> /// 要采集的視頻大小(分辨率) /// </summary> Size VideoSize { get; } /// <summary> /// 采集的幀頻 /// </summary> int FrameRate { get; } /// <summary> /// 是否正在采集? /// </summary> bool IsCapturing { get; } /// <summary> /// 開始采集 /// </summary> void Start(); /// <summary> /// 停止采集 /// </summary> void Stop(); /// <summary> /// 當采集完一幀時,觸發此事件。事件參數為圖像數據。 /// </summary> event CbGeneric<byte[]> VideoCaptured; /// <summary> /// 當采集發生錯誤時,觸發此事件。 /// </summary> event CbGeneric<Exception> VideoError; /// <summary> /// 當采集的分辨率發生變化時,觸發此事件。 /// </summary> event CbGeneric<Size> VideoSizeChanged; }
(1)在定義實現該接口的類時,可以通過類的構造函數傳入三個參數:設備的Index、采集的分辨率、采集的視頻幀率。
(2)OMCS會在合適的時候調用Start方法啟動注入的采集器,采集器啟動后,當每采集到一幀視頻時,就觸發VideoCaptured事件。OMCS內部預定了該事件,以獲取采集到的圖像數據。
(3)如果在采集的過程中,采集器發生了任何異常,請通過觸發VideoError事件來通知OMCS框架。
(4)如果在采集的過程中,更改了采集器采集的分辨率,請通過觸發VideoSizeChanged事件來通知OMCS。
請特別注意VideoCaptured事件參數的含義:它并不是一個Bitmap的完整數據,而是不包含位圖header的核心數據(OMCS通過設定的采集的分辨率來推斷位圖header的信息)。從Bitmap轉為不包含頭的核心數據的代碼如下所示:
public byte[] GetBitmapCoreData(Bitmap bm) { int buffSize =bm.Width * bm.Height * 24 / 8; byte[] destBuff = new byte[buffSize]; Rectangle bmRect = new Rectangle(new Point(0, 0), new Size(bm.Width, bm.Height)); BitmapData data = bm.LockBits(bmRect, ImageLockMode.ReadOnly, PixelFormat.Format24bppRgb); Marshal.Copy(data.Scan0, destBuff, 0, destBuff.Length); bm.UnlockBits(data); return destBuff; }
當然,如果視頻采集器采集到的本來就是位圖核心數據(通常情況下都是如此),就不需要這層轉換了。
2.IVideoCapturerFactory接口
在實現完IVideoCapturer接口后,我們還需要實現簡單的OMCS.Passive.IVideoCapturerFactory接口。
public interface IVideoCapturerFactory { /// <summary> /// 創建一個新的視頻采集器實例。 /// 如果返回null,則表示使用框架內置的視頻采集器。 /// </summary> /// <param name="deviceIndex">攝像頭索引</param> /// <param name="videoSize">要采集的視頻大小(分辨率)</param> /// <param name="frameRate">采集的幀頻</param> IVideoCapturer CreateVideoCapturer(int deviceIndex, Size videoSize, int frameRate); /// <summary> /// 獲取視頻采集器支持的采集分辨率。 /// 如果返回null,則表示指示框架自己去獲取這些信息。 /// </summary> /// <param name="deviceIndex">攝像頭索引</param> List<CameraCapability> GetCameraCapability(int deviceIndex); }
可以按如下邏輯來實現IVideoCapturerFactory的兩個方法:
(1)實現CreateVideoCapturer方法:判斷deviceIndex所對應的視頻設備是否是特殊的類型,如果是,則new一個我們剛實現的視頻采集類的實例返回;如果不是,則返回null,表示使用框架內置的視頻采集程序。
(2)實現GetCameraCapability方法:判斷deviceIndex所對應的視頻設備是否是特殊的類型,如果是,則把該設備支持的所有分辨率放入列表中返回;如果不是,則返回null,以指示框架自己獲取目標設備的分辨率信息。
3.注入到OMCS
在調用IMultimediaManager的Initialize方法之前,先new一個上面實現的Factory類,然后將其賦值給IMultimediaManager的VideoCapturerFactory屬性。這樣,就完成對OMCS視頻設備的擴展。
文章列表