基於DirectShow/DES的MPEG-2音視頻編輯軟體的實現方案

來源:互聯網
上載者:User

引言

1994年歐洲制定的數位視訊廣播(DVB)標準和1996年美國聯邦通訊委員會(FCC)的先進電視制式委員會(ATSC)地面廣播電視標準,在視頻部分都採用了MPEG-2 標準。我國的CATV 數字網,也採用DVB 標準。MPEG-2 標準的出現,大大推動了數位視訊業務的發展。越來越多的節目交換是以MPEG-2壓縮方式進行的,使演播室製作涉及大量對MPEG編碼壓縮節目的處理,如非線性編輯涉及的不同節目間的切換、剪下和串編、在畫面上加字幕、台標、實現淡入淡出等。其中節目剪下和串編是實現其他編輯功能的基礎,因此實現節目剪下和串編功能更加重要。

本文針對MPEG-2 音視頻,採用DirectShow(微軟公司提供的在Windows 平台上進行流ApsaraVideo for Media Processing的開發包)的DirectShow編輯業務(DES,DirectShow Editing Services)來實現MPEG-2音視頻節目的剪下和串編。DES作為DirectShow的增強應用,簡化了原本煩瑣的視頻編輯,彌補了非線性編輯應用軟體的空白,可方便地進行音視頻編輯,因此用它來編輯MPEG-2音視頻檔案不失為一個行之有效方法。

DES 簡介

時間軸模型
DES的內部結構模型,是一個基於時間軸(Timeline)的模型,它提出了一個時間軸和軌道的概念,將所有的多媒體編輯組織到一個虛擬時間軸之上,實際上代表了最終的音視訊剪輯作品。而對於程式員來說,這些時間軸和軌道同一般的通訊(COM)介面一樣,都是一個個的純虛類,可以通過繼承、派生和添加必要的函數,來實現編輯操作。圖1給出了DES的時間軸內部模型。

這是一個樹形結構,在這棵樹中,音視頻檔案是葉結點,稱作為媒體源(Source);一個或多個Source組成一個軌道(Track),每個Track都有統一的媒體格式輸出;Track的集合Express匯流排回傳給CPU。CPU或者將資料通過PCI匯流排傳輸給I/O板卡轉換成基帶訊號輸出,或者再回送到軟體轉碼器編碼成DV格式的資料並通過1394匯流排輸出。

相對於基於專門硬體的非編系統,基於CPU+GPU軟體架構的非編系統完全擺脫了對硬體板卡的依賴,突破了專用硬 件結構的局限,利用通用的硬體系統資源實現了高效能的視頻編輯和處理。

在效能方面,目前基於CPU+GPU的主流非編系統已經可以輕鬆實現4~6層三維特技的即時輸出,遠遠超越了目前基 於專用板卡的主流非編系統。

在可擴充性方面,由於系統完全採取軟體架構,一方面通過提高電腦平台的配置來獲得更高的硬體效能,從而直接提高非編系統的效能;另一方面,通過軟體模組的添加和升級,可以支援更多的編輯格式、獲得更多的特技效果。

在穩定性方面,由於拋棄了專用的硬體板卡,改用結構簡單的I/O板卡實現基帶訊號輸出,系統故障率、功耗、發熱量等都大大下降,穩定性則大大提高。通過進一步最佳化系統硬體結構,選用設計更成熟和安全的品牌圖形工作站,同時將I/O板卡作進一步的模組拆分,將類比處理電路從板卡中拆分出來作為一個獨立供電、獨立散熱的介面盒,可使非編系統實現工作站和伺服器級的安全性和穩定性,從而大大降低維護成本,提高裝置利用率。

在成本方面,目前基於CPU+GPU的非編系統,其缺點主要是對電腦系統的配置要求高,電腦平台上的成本投入高昂,但由於沒有專用板卡上的成本投入,總體成本並沒有增加。由於電腦技術快速發展和性價比不斷提高,基於CPU+GPU的非編系統在效能不斷提高的同時總體成本呈下降趨勢。


稱作為集合(Composition),每個Composition可以對其所有的Composition 或Track 進行各種複雜的編輯;頂級的Composition或Track就組成了組(Group);每個Group輸出單一格式的媒體流,所有的Group組成一個時間軸(Timeline),Timeline表示一個視頻編輯的項目,它是這棵樹的根節點。一個Timeline項目必須至少包含一個Group,最典型的情況一般包含兩個Group: 音頻組(Audio Group)和視頻組(VideoGroup)。

圖2所示的是一個典型的基於時間軸的媒體軌道圖,箭頭方向即是時間軸的方向。這個時間軸由兩個組組成,每個組中包含兩個媒體源軌道(SourceTrack)。在視頻組中,軌道是有優先順序的(軌道0具有最低的優先順序,依次類推)。運行時,總是輸出高優先順序的軌道中的媒體源內容。如果此時高優先順序的軌道中沒有媒體源輸出,則讓低優先順序的軌道中的媒體源輸出。1中視頻組的輸出順序為媒體源A→媒體源C→媒體源B。而對於音頻組,它的所有軌道的輸出只是簡單的合成。我們利用時間軸的這一原理,將媒體素材挨個賦予到相應的媒體源上去,隨後將媒體源組織到不同優先順序 別的軌道上,最終在時間軸模型的組織下輸出我們所需要的合成節目。這也就是MPEG-2 音視頻編輯功能的核心模型。

時間概念
DES中大致有3種時間:
(1) 時間軸時間(Timeline Time):相對於整個時間軸項目的時間;
(2) 媒體時間(Media Time):相對於媒體源的時間,比如媒體源是一個檔案,那麼媒體時間實際上是指相對於檔案開頭的位置時間;
(3) 父物件時間(Parent Time):相對於時間軸中已編排的某個對象的時間。

設計方案

設計方案如下:首先要完成播放MPEG-2音視頻檔案的功能,在瀏覽的過程中對需要的音視頻片斷的編入點和編出點作標記。其次要完成可對編輯好的音視頻預覽的功能,如果編輯結果比較滿意,要將其儲存到檔案中。剪下時,僅需對播放中的檔案設定入出點,按儲存按鈕即可邊預覽邊儲存;串編時,依次開啟要編輯的檔案,設定入出點,然後再按預覽或儲存按鈕即可。

實現過程

用DirectShow實現播放功能非常方便。該功能模組主要是由GetCurrentPosition()函數得到編入點和編出點的時間,為後面的編輯提供媒體起始時間。下面主要介紹用DES進行預覽和儲存的實現方法。

時間軸的構建
用DES實現剪輯後的預覽或儲存功能首先必須構建時間軸模型。首先調用了系統提供的一個虛介面(虛介面的含義是:該介面包含許多未被定義的函數方法,它只提供了一個面嚮應用層的介面)。這個虛介面,稱為IAMTimeline。我們要做的事情就是,遵循圖1中時間軸的結構定義自己所需要的屬性和函數,並且建立出我們的時間軸對象。最基本的屬性包括有圖1中所提到的組(Group),集合(Composition),軌道(Track)和媒體源(Source)。

(1) 首先建立一個時間軸對象
IAMTimeline*pTL=NULL;
hr=CoCreatelnstance(CLSID_IAMTimeline,NULL,CLSCTX_INPROC_SERVER,IID IAMTimeline,(void* *)&pTL);
這時,我們面對的是一個空的時間軸架構,接下來所作的是根據自己的需要為我們的“樹形”時間軸結構填上“枝 葉”。

(2) 接下來使用介面方法IAMTimeline::CreateEmptyNode建立各種DES 對象。包括:IAMTimelineGroup(視頻組pVideoGroup,音頻組pAudioGroup)、IAMTimelineComp(視頻pVideoComp,音頻pAuioComp)、IAMTimelineTrack(視頻pVideoTrack,音頻pAuioTrack)、IAMTimelineSrc(視頻pVideoSrc,音頻pAuioSrc)。
以下樣本均為視頻組代碼,音頻組與視頻組類似。
IAMTimelineGroup *pVideoGroup=NULL;
IAMTimelineObj *pVideoGroupObj=NULL;
pTL → CreateEmptyNode(&pVideoGroupObj,TIMELINE_MAJOR_TYPE_GROUP);
pGroupObj→Querylnterface(IID_IAMTimelineGroup,(void **)&pVideoGroup);
調用IAMTimeline::CreateEmptyNode成功後,我們可以得到一個IAMTimelineObj介面指標。也就是說,每個我們創造的DES對象上都實現了IAMTimelineObj介面。

(3) 接著在組中加入軌道
pVideoComp→VTracklnsBefore(pVideoTrackObj, -1);
pVideoTrackObj→Querylnterface(IID_IAMTimelineTrack,(void **)&pVideoTrack)。

(4) 這是最關鍵的一步,設定媒體源的剪下時間和其在時間軸上的時間,然後將其放到相應的軌道上。串編情況下,筆者設計了一個類記錄該媒體源的檔案名稱、片斷長度、編入點和編出點,並用模版類CArray管理該類。
"class CFileInfo
" {
"public:
" CString filename;
" LONGLONG ClipLen;
" LONGLONG Outdot;
" LONGLONG Indot;
" CFileInfo();
" virtual ~CFileInfo();
" } ;
"CArrayFileArray
" for (i=1; i<=FileArray.GetSize();i++)
" {
"FileArray[0].ClipLen = 0;
hr=pVideoSrcObj→SetStartStop(FileArray[i-1].ClipLen,FileArray[i-1].ClipLen+FileArray[i].ClipLen);//設定時間軸時間
hr=pVideoSrcObj→SetMediaTimes(FileArray[i].Indot,FileArray[i].Outdot );//設定媒體源時間
hr=pVideoSrcObj → SetMediaName(T2W(FileArray[i].filename));//設定媒體源檔案名稱
hr=pVideoTrack→SrcAdd(pVideoSrcObj);//將媒體源添加到相應的軌道上
FileArray[i].ClipLen=FileArray[i-1].ClipLen+FileArray[i].ClipLen;//下一個媒體源的時間軸起點時間是前一個媒體源時間軸的終點時間。
" }

預覽功能的實現
建立好時間軸後,建立基本渲染引擎IRenderEngine,它的作用是通過已經建立好的時間軸構建濾波器圖(FilterGraph)供預覽或者輸出檔案。所以,我們需把時間軸的資訊傳遞給它。接下來的過程很簡單了,調用ConnectFrontEnd連線時間線部分所建立的濾波器(F i l t e r ),調用RenderOutputPins。至此,濾波器圖已成功建立,只要調用IMediaControl介面的Run()函數即可進行預覽了。
IRenderEngine *pRenderEngine = NULL;
hr=CoCreatelnstance(CLSID_RenderEngine, NULL,CLSCTX_INPROC_SERVER,IID_IRenderEngine, (void**)&pRenderEngine); //建立基本渲染引擎
hr=pRender→SetTimelineObject(pTL); //確定要渲染的時間軸
hr=pRenderEngine→ConnectFrontEnd( );//構建graph的前端
hr=pRenderEngine→RenderOutputPins( );//將前端出來的引腳根據媒體類型分別串連到音視頻渲染器,完成graph的構建
IGraphBuilder *pGraph=NULL;
IMediaControl *pControl=NULL;
hr=pRender→GetFilterGraph(&pGraph);
hr=pGraph→QueryInterface(IID_IMediaControl, (void **)&pControl);
hr=pControl→Run();//運行Filter Graph。

儲存功能實現
建立好時間軸和前端後,前端輸出的是非壓縮的音頻流和視頻流,而我們要儲存的是壓縮資料,所以必須向濾波器圖中加入MPEG-2音頻編碼器和視頻編碼器以及複用器。

第一步,將視頻編碼器、音頻編碼器和複用器以及檔案寫入程式濾波器加入到濾波器圖中
hr=AddFilterByCLSID(pGraph,LSID_VIDEO_ENCODER,L"mpeg video encoder",&pVideoEncoder);
第二步,得到組的個數及輸出引腳指標,根據引腳的媒體類型將其串連到相應的編碼器上。
long NumGroups;
pTL->GetGroupCount(&NumGroups);
IPin *pPin;
"for (i = 0; i < NumGroups; i++)
" {
" if (pRenderEngine->GetGroupOutputPin(i, &pPin)== S_OK)
" {
" hr=GetMediaType(pPin);
" if (hr==TRUE) // 傳回值為TRUE,則引腳輸出的是視頻流
" ConnectFilters(pGraph,pPin,pVideoEncoder,TRUE);
" else
" ConnectFilters(pGraph,pPin,pAudioEncoder,TRUE);
" }
" }
第三步,將視頻編碼器和音頻編碼器濾波器串連到複用器濾波器上
hr=ConnectFilters(pGraph,pVideoEncoder,pMux,TRUE);
hr=ConnectFilters(pGraph,pAudioEncoder,pMux,TRUE);
第四步,串連複用器和檔案寫入程式濾波器
hr=ConnectFilters(pGraph,pMux,pfilewriter,TRUE);
第五步,建立MPEG輸出檔案IFileSinkFilter *pSin= 0;pfilewriter→QueryInterface(IID_IFileSinkFilter,(void**)&pSink);
pSink→SetFileName(T2W(strSaveFile), NULL);
最後調用IMediaControl介面的Run()函數即可進行儲存了。

測試效果

實現MPEG-2 音視訊剪輯的介面3 所示。列表框顯示了待編輯的檔案清單,雙擊檔案名稱即可顯示該檔案的第一圖3 MPEG-2 音視訊剪輯介面幀,點擊播放按鈕可實現對本地檔案的回放。點擊入點按鈕可設定要剪下檔案的入點,點擊出點按鈕後,將先暫停播放並得到剪下終止點。依次對多個檔案進行出入點設定後點擊預覽按鈕後,回放的畫面流暢,無馬賽克現象,無明顯延時。點擊儲存按鈕可儲存串編結果,儲存後的MPEG-2音視頻流,用暴風影音等軟體對該檔案進行回放,回放的畫面流暢,品質令人滿意。

結束語

音視訊剪輯,無論是對電視台的節目編輯製作,還是對一般的家庭使用者,都具有很大的吸引力。因此,視訊剪輯功能的實用化、普及化具有很強的現實意義。採用DES可使時間軸管理、特技合成更加方便可靠,同時DES採用外掛程式方式,可以有很多支援微軟DirectX的第三方外掛程式使用,使軟體更易於擴充,為使用者提供更多的選擇。DES使得程式的模組化更強,有利於軟體的開發,同時在不斷升級過程中,更可以方便地整合新的功能。當然,這種視頻編輯的方法也存在著它的局限性,即編輯的精度較傳統的硬體實現方法低,不適合應用於精度要求很高的編輯,這也是該軟體實現視頻編輯的一個缺陷。

相關文章

聯繫我們

該頁面正文內容均來源於網絡整理,並不代表阿里雲官方的觀點,該頁面所提到的產品和服務也與阿里云無關,如果該頁面內容對您造成了困擾,歡迎寫郵件給我們,收到郵件我們將在5個工作日內處理。

如果您發現本社區中有涉嫌抄襲的內容,歡迎發送郵件至: info-contact@alibabacloud.com 進行舉報並提供相關證據,工作人員會在 5 個工作天內聯絡您,一經查實,本站將立刻刪除涉嫌侵權內容。

A Free Trial That Lets You Build Big!

Start building with 50+ products and up to 12 months usage for Elastic Compute Service

  • Sales Support

    1 on 1 presale consultation

  • After-Sales Support

    24/7 Technical Support 6 Free Tickets per Quarter Faster Response

  • Alibaba Cloud offers highly flexible support services tailored to meet your exact needs.