天天看點

Kinect for Windows SDK開發初體驗(二)操作Camera

Kinect SDK出來之後,不到24小時,很多Geek們已經将自己的示例釋出到網上去了。可見,好東西肯定會被大家認可的,不好的東西投入再多的宣傳也沒用。

這一篇我們就要正式進入Kinect的程式設計世界了,介紹我們如何從Camera擷取圖像資訊。先來介紹一下Kinect的整體結構,省得大家在後邊的介紹中被某些名詞弄暈。

<a href="http://images.cnblogs.com/cnblogs_com/aawolf/201106/201106181530519386.png"></a>

Kinect一共有三個Camera,其中中間的一個是RGB Camera,用來擷取640x480的彩色圖像,每秒鐘最多擷取30幀圖像;兩側是兩個景深(3D Depth)傳感器,用來檢測玩家的相對位置,原理和人眼立體成像是一樣的,不過這兩個傳感器使用的是紅外線,是以說奧巴馬玩不了Kinect的人一定是居心叵測。Kinect兩側是麥克風,下邊還有一個可移動底座,用來調整Kinect的仰角。

今天我們主要是操作RGB Camera和Depth Sensor,首先,我們要完成Kinect開發環境的配置:

第一步,建立WPF工程

打開Visual Studio 2010,建立一個WPF工程,名叫KinectWpfDemo:

<a href="http://images.cnblogs.com/cnblogs_com/aawolf/201106/201106181534381788.png"></a>

當然,由于Kinect SDK中包含基于.NET的程式集,除了WPF外,我們使用.NET WinForm或XNA架構都可以,目前還沒有人在Silverlight平台上實驗成功。

第二步,添加Kinect程式集的引用

在Solution Explorer中,右鍵單擊KinectWpfDemo,在右鍵菜單中選擇“Add Reference…”。在彈出的對話框中,我們在.NET标簽頁裡,選擇“Microsoft.Research.Kinect”程式集。如下圖所示:

<a href="http://images.cnblogs.com/cnblogs_com/aawolf/201106/201106181904196523.png"></a>

第三步,添加Coding4Fun Kinect Toolkit

這是一個可選項,不過為了之後的程式設計友善,建議大家添加一個。Coding4Fun Kinect Toolkit的下載下傳位址:

<a href="http://c4fkinect.codeplex.com/">http://c4fkinect.codeplex.com/</a>

解壓縮後,一共有五個檔案,針對WinForm、WPF平台,還有一個Microsoft.Expression.Drawing.dll。我們通過Add Reference,将Coding4Fun.Kinect.Wpf.dll添加進來。

<a href="http://images.cnblogs.com/cnblogs_com/aawolf/201106/201106181904215850.png"></a>

第四步,添加控件

輕按兩下打開MainWindow.xaml,在設計器中添加兩個Image控件,一個用于顯示RGB圖像,另一個用于顯示Depth資訊。

第五步,引用命名空間

打開MainWindow.xaml.cs檔案,在檔案頭部添加對于Kinect對象的引用:

回到MainWindow.xaml的設計器中,在屬性視窗中選擇Event,找到Loaded和Closed兩個方法,分别輕按兩下,添加兩個事件的處理函數:

<a href="http://images.cnblogs.com/cnblogs_com/aawolf/201106/201106181904234063.png"></a>

在MainWindow.xaml.cs檔案的MainWindow類中,聲明Runtime的變量:

Runtime nui;

然後,在Loaded事件的處理函數中添加Runtime初始化的代碼:

接下來是Closed事件中關閉Runtime的代碼:

Runtime對象是Kinect SDK中最主要的一個類,所有針對Kinect的操作都由Runtime類進行了封裝。Runtime的構造函數沒有接受任何參數,但有一個顯式的初始化函數Initialize,接受RuntimeOptions參數,指定調用Kinect的哪些功能。其中RuntimeOptions.UseColor表示使用RGB Camera,而RuntimeOptions.UseDepth則表示使用Depth傳感器。

初始化工作完成之後,我們要通過RGB Camera來擷取實時的圖像資料了。我們首先要聲明一個事件處理方法,來接收視訊資料的資訊:

然後是事件處理函數:

提示:Getting Started上提供的Sample Code有誤,需要将最後一個參數中的data.Width改為imageData.Width才可以正常運作。

VideoFrameReady事件會傳遞一個ImageFrameReadyEventArgs參數給事件處理函數,其中的ImageFrame會包含關于圖檔的各種資訊,比如Type變量指定了圖像是來自RGB還是Depth,Resolution變量指定了分辨率,而Image中以byte[]數組的方式儲存了圖像的真實資料。

然後的工作就是根據PlanarImage中包括的資料來建立一個Bitmap對象,然後将其傳遞給Image控件,顯示到WPF程式的界面上。

最後,我們還要在構造函數裡打開視訊流,來擷取視訊資料:

第一個參數是ImageStreamType,用來指定打開的裝置流類型;第二個參數是PoolSize,指定緩沖區的數量,至少為2,保證一個Buffer進行繪制,另一個Buffer進行資料填充;第三個參數指定Camera的分辨率;第四個參數則是擷取的圖檔類型。

顯示效果如下圖所示:

<a href="http://images.cnblogs.com/cnblogs_com/aawolf/201106/201106181904253704.png"></a>

上面的示例代碼,沒有使用Coding4Fun的Helper類,如果使用的話,則代碼如下:

Helper類使用了C#的Extension Methods,為ImageFrame增加了一些轉換方法。我們還可以将圖像儲存為檔案,考慮到檔案系統存儲的效率檔案,建議大家不用每張都存。

接下來我們要擷取Depth資訊了,過程與RGB Camera類似。首先要確定Runtime對象被初始化時,已經添加了RuntimeOptions.UseDepth的屬性,否則裝置無法正常打開。

然後,添加擷取Depth資料的事件處理,并打開Depth的資料流,這次的分辨率是320x240:

下面是事件處理函數,在另外一個Image函數裡,顯示Depth圖像:

偷懶,是以使用了Coding4Fun的Helper類。程式運作的效果如下:

<a href="http://images.cnblogs.com/cnblogs_com/aawolf/201106/201106181904289608.png"></a>

這一篇中,我們完成了Kinect開發環境的配置、添加了Coding4Fun Kinect Toolkit、從RGB Camera和Depth Sensor中擷取了圖像資訊。

接下來,我們就要進入Kinect動作捕捉部分了。

本文轉自馬甯部落格園部落格,原文連結:http://www.cnblogs.com/aawolf/archive/2011/06/18/2084352.html,如需轉載請自行聯系原作者

繼續閱讀