什麼是視頻關鍵幀?流媒體服務器如何提取視頻的關鍵幀?

我上一篇文章寫了關於視頻直播點播服務器中調整關鍵幀間隔的方法,同時也發現也是有一部分的開發者是有這個需求的。我記得之前我粗略寫過I幀的判斷:H264編碼NALU結構介紹與I幀判斷方法,但也是粗略的寫了一下,本篇文章我決定就關鍵幀來做個詳細點的說明,最基本的就是——什麼是關鍵幀。

關鍵幀,就是說這一幀是連接兩段不同的內容,這一幀後面的視頻內容會有新的變化或過渡;在時間軸上這一幀帶有小黑點標誌;空白關鍵幀,跟關鍵幀作用相同,但是這一幀沒有內容,在時間軸上,這一幀沒有小黑點標誌;在這一幀填充內容後,就變成關鍵幀了;普通幀是用來計量播放時間或過渡時間用的,不能手動設置普通幀的內容,它是播放過程中由前後關鍵幀以及過渡類型自動填充的,手動插入或刪除普通幀,會改變前後兩個關鍵幀之間的過渡時間。

視頻關鍵幀分爲I幀,P幀,B幀,這裏介紹下區別,也是我搜索得到的,僅供參考。I幀纔是關鍵幀,P,B算不上關鍵幀。

I幀是幀內壓縮編碼得到的,通常是每個GOP組的第一幀/基礎幀,在一組中只有一個I幀,I幀所佔信息量大,解碼時僅有I幀即可完整重構圖像,所以才叫關鍵幀。

P幀與B幀是幀間壓縮,P幀沒有完整圖像數據,只有與前一幀的差別信息,因此也叫預測幀,B幀則是考慮前後幀的差別(故而也叫雙向預測幀),因此B幀解碼時間最長,壓縮比最大。

那怎麼提取視頻的關鍵幀呢?其實提取關鍵幀比提取視頻幀快很多倍,下面我就基於Android系統來講一下提取視頻幀的方法:

第一個參數
是傳入截取時間,只能是us(微秒)

第二個參數

OPTION_CLOSEST
在給定的時間,檢索最近一個幀,這個幀不一定是關鍵幀。

OPTION_CLOSEST_SYNC
在給定的時間,檢索最近一個同步與數據源相關聯的的幀(關鍵幀)。

OPTION_NEXT_SYNC
在給定時間之後檢索一個同步與數據源相關聯的關鍵幀。

OPTION_PREVIOUS_SYNC
在給定時間之前檢索一個同步與數據源相關的關鍵幀

這裏爲了提取我們想要的幀,不使用關鍵幀,所以用 OPTION_CLOSEST

public Bitmap getFrameAtTime() 

//如果不加參數的話,提取第一個關鍵幀
public Bitmap getFrameAtTime() {
        return getFrameAtTime(-1, OPTION_CLOSEST_SYNC);
    }

   /**
     * 獲取視頻文件截圖
     *
     * @param path 視頻文件的路徑
     * @return Bitmap 返回獲取的Bitmap
     */
    public Bitmap getVideoThumb(String path) {
        MediaMetadataRetriever media = new MediaMetadataRetriever();
        media.setDataSource(path);
        Bitmap frameAtTime = media.getFrameAtTime(1 * 1000 * 1000, MediaMetadataRetriever.OPTION_CLOSEST);
        if (frameAtTime == null) {
            frameAtTime = media.getFrameAtTime(3 * 1000 * 1000, MediaMetadataRetriever.OPTION_CLOSEST);
        }
        return frameAtTime;
    }
發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章