摘要:Delphi被稱為第四代編程語言,它具有簡單、高效、功能強大的特點。和VC、VC++等編程語言相比,Delphi更簡單、更易于掌握,而在功能上卻絲毫不遜色,集成了多種語言的特點,可以開發出靈活強大的程序。在各種聊天程序、聊天室中,常常用到網絡視頻技術,開發網絡視頻程序的工具有很多,Delphi是很多程序員喜愛的一種。本文就筆者開發的基于Delphi的網絡視頻編程進行分析闡述,并給出部分Delphi的相關代碼。
關鍵詞:Delphi;網絡視頻;編程
中圖分類號:TP311文獻標識碼:A文章編號:1009-3044(2009)14-3619-02
1 引言
在各種聊天程序、聊天室中,常常用到網絡視頻技術。Delphi具有強大的功能,也可以用Delphi來開發網絡視頻。本文就筆者開發的基于Delphi的網絡視頻編程進行分析闡述,并給出部分Delphi的相關代碼。
2 視頻捕獲
視頻捕獲,可以使用微軟提供的專門用于視頻捕獲的VFW(Video for Windows)SDK。VFW SDK為在Windows系統中實現視頻捕獲提供了標準的接口,從而大大方便了程序員的設計開發。
VFW是微軟公司推出的關于數字視頻的一個軟件包,它能使應用程序通過數字化設備從傳統的模擬視頻源得到數字化的視頻剪輯。VFW的一個關鍵思想是播放時不需要專用硬件,為了解決數字視頻數據量大的問題,需要對數據進行壓縮。VFW使程序員能通過發送消息或設置屬性來捕獲、播放和編輯視頻剪輯。
VFW主要由以下6個模塊組成:① AVICAP.DLL:包含了執行視頻捕獲的函數,它給AVI文件I/O和視頻、音頻設備驅動程序提供一個高級接口;② MSVIDEO.DLL:包含一套特殊的DrawDib函數,用來處理屏幕上的視頻操作;③ MCIAVI.DRV:包括對VFW 的MCI命令解釋器的驅動程序;④AVIFILE.DLL:包含由標準多媒體I/O(MMIO)函數提供的更高的命令,用來訪問.AVI文件;⑤壓縮管理器(ICM):用于管理的視頻壓縮/解壓縮的編譯碼器(CodeC);⑥ 音頻壓縮管理器ACM:提供與ICM相似的服務,適用于波形音頻。
AVICAP為應用程序提供了一個簡單的、基于消息的接口,使之能訪問視頻和波形音頻硬件,并能在將視頻流捕獲到硬盤上的過程中進行控制。AVICAP支持實時的視頻流捕獲和圖像捕獲并提供對視頻源的控制。AVICAP在捕獲視頻方面具有一定的優勢,它能直接訪問視頻緩沖區,不需要生成中間文件,實時性很強,效率很高。同時,它也可將數字視頻捕獲到文件。
利用AVICAP進行視頻捕獲的開發步驟有:① 創建“捕獲窗”;② 關聯捕獲窗和驅動程序;③ 設置視頻設備的屬性;④ 打開預覽。
通過以上4步就可以建立一個基本的視頻捕獲程序。下面介紹實現基于Delphi的視頻捕獲。
使用微軟的AVICAP32.DLL實現對視頻攝像頭控制:
1) 打開Delphi,新建一個工程,并新建一個窗口。先定義一個函數和部分常量(定義成全局類型)。
const WM_AP_START=WM_USER;
const DRIVER_CONNECT=WM_CAP_START+10
const SET_PREVIEW=WM_CAP_START+50
const SET_CALLBACK_VIDE05TREAM=WM_CAP_START+6;
const SET_SCALE=WM_ CAP_TART+53;
const SET_PREVIEWRATE=WM_CAP_START+52
const DRIVER_DISCONNECT=WM_CAP_START+11;
function capCreateCaptureWindowA(1pszWindowName:PCHAR;
dwStyleaongint;x:integer;y:integer;nWidth:integer;
nHeight:integer;ParentWin:HWND;nId:integer):HWND;
STDCALL EXTERNAL 'AVICAP32.DLL'
2) 在窗口上放置一個Panel,添加2個按鈕,Caption設置為“開始”和“停止”,并定義一個全局變量,var CWin2:THandle;//定義捕捉窗句柄。
“開始”按鈕代碼如下:
CWin2: =capCreateCapture WindowA('My CAPWin', WS_CHILD or WS_VISIBLE,
Panell.Left, Panell.Top, Panell.Width, Panell.Height,Form 1. Handle, 0 )
//上面代碼創建“捕獲窗”
if CWin2<>0 then
begin
SendMessage ( CWin2 , SET_CALLBACK_VIDEOSTREAM,0, 0);
SendMessage (CWin2,DRIVER_CONNECT,O,0);
//上面代碼關聯捕獲窗和驅動程序
SendMessage(CWin2,SET SCALE,1,0)
SendMessage (CWin2,SET_PREVIEWRATE,66,0);
//上面代碼Scale , Rate設置預覽的比例與速度
SendMessage(CWin2,SET_PREVIEW,1,0);
//上面代碼打開預覽
end;
運行Delphi,這時就可以在屏幕上看到來自攝像頭的圖像了。
“停止”按鈕代碼如下:
if Cwin2<>0 then begin
SendMessage(CWin2, DRIVER_DISCONNECT,0,0);
CWin2:= 0;
end;
3 對捕獲的視頻進行壓縮與解壓
通過AVICap窗口捕獲的每一幀的數據是以BMP (RAW)文件格式存放的,若直接進行傳輸,數據量非常大,對網絡的帶寬要求非常高,因此在傳輸之前必須對每一幀的數據進行壓
縮處理后再進行傳輸。具體步驟:
第一步,安裝視頻壓縮引擎。媒體播放器軟件都帶有壓縮引擎,也可以從網上下載單獨的解壓縮引擎,比如MPEG4或DIVX等。
第二步,初始化壓縮引擎。選擇壓縮引擎,獲得壓縮引擎的支持,確定輸人、輸出格式,設置壓縮器。
第三步,壓縮幀數據。通過指定的壓縮引擎,對獲取的每一幀數據進行壓縮。
解壓的過程與壓縮的過程類似,通過選擇相對應的解壓引擎,將壓縮的數據解壓,以便于回放。
4 視頻數據傳輸
4.1 基本概念
計算機在傳輸數據時有兩種方式:分別是TCP(Transmission Control Protocol,傳輸控制協議)及UDP(User Datagram Protocol,用戶數據報協議),兩者分別因數據傳輸的不同請求而提供不同的數據傳輸方式。
1) TCP協議
TCP是一個基于連接的通信協議,主要目的是提供大量數據傳輸并確保其傳輸無誤,因此提供錯誤檢查、數據復原及數據重傳等機制。TCP在傳輸數據之前,會先在主機間(例如主控端與被控端)創建連接。根據此連接,數據可在計算機間相互傳輸,即所謂的雙向傳輸模式。
2) UDP協議
UDP是一個非連接式的通信協議,主要目的在于傳輸少量的數據。與TCP不同的是,TCP在傳輸之前必須創建連接,而UDP不需要,只要設置計算機間的IP及使用相同的端口,就可以相互傳輸數據。因此UDP只提供單向的數據傳輸,即所謂的單向無連接傳輸模式。
由于UDP不需要先創建連接,節省了TCP創建連接所需的時間,所以適合在主機間進行單向的數據傳輸。由于視頻數據的傳輸對于實時性要求很高,即使傳輸過程中有個別幀的數據有錯,也不會影響整個視頻的效果,故本文將會詳細介紹如何通過UDP實現視頻數據的傳輸。
4.2 控件及相關內容介紹
在Delphi中對于UDP及TCP都提供了很好的支持,而且將它們封裝起來。開發人員無須知道協議的具體實現細節,而只要使用Delphi提供的TIdUDPServer元件(在Indy Servers頁)即可完成相應的功能。下面我們一起來認識一下這個元件。
1) 相關屬性
DefaultPort該屬性是用來指定作為客戶端時要打開的端口號,也就是通過該端口來接收數據。
Active該屬性是用來打開指定的端口號,設置為True表示打開端口,False表示關閉端口。
BroadcastEnabled該屬性是用來設置是否用來實現廣播,設置為True表示可以廣播,False表示不能廣播。
2) 相關事件
OnUDPRead當客戶端收到服務器端發來數據時觸發該事件,通過該事件我們可以取得服務器端發的每一幀的數據,以便在客戶端回放。
除了以上提到的一些屬性及事件外,TIdUDPServer還有一個重要的方法需要了解,那就是SendBuffer,通過該方法可以在服務器端向指定客戶端的指定端口發送數據。
5 結束語
目前,Delphi已經被很多的程序開發者作為開發網絡視頻程序工具。本文介紹的網絡視頻編程,應該是目前比較常用的方法之一。本文所有程序在Win XP/Delpphi 7.0下實現通過,所用視頻攝像頭為市場上普通銷售的產品。
參考文獻:
[1] 白先平. 應用Delphi開發視頻語音聊天軟件[J]. 科技資訊,2006,29:113.
[2] 李國芳. 在VC++ 6.0中實現視頻捕獲編程[J]. 井岡山醫專學報,2003(4):76-78.
[3] 劉德華. 在Delphi下實現對數據庫中圖像的操作[J]. 電腦編程技巧與維護,2007(7):60-62.
[4] 何鵬飛. Delphi7程序設計教程[M]. 北京:清華大學出版社,2003.