FFmpeg開發之旅(二)---音頻解碼

【寫在前面】

前面我介紹了視頻解碼的流程,發現基礎講得有點少。

因此這裏附上一些額外的基礎內容:https://blog.csdn.net/u011283226/article/details/101024093

本篇主要內容:

1、FFmpeg音頻解碼基本流程

2、libswresample的基本使用方法


 【正文開始】

實際上音頻解碼和視頻解碼的流程是一樣的,因此就不花篇幅講流程了。

這裏先簡單說一下不同的地方:

    //找到音頻流的索引
    audioIndex = av_find_best_stream(formatContext, AVMEDIA_TYPE_AUDIO, -1, -1, nullptr, 0);

在第二個參數,改爲 AVMEDIA_TYPE_AUDIO 即可。

然後從解複用到解碼出 PCM,和視頻解碼的流程是一樣的。

視頻解碼見:https://blog.csdn.net/u011283226/article/details/100868821

當然,本篇文章就這樣結束也不太好,那麼就簡單講一下關於 libswresample 的使用方法吧。

libswresample 是FFmpeg提供的重採樣( Resample )庫,所謂的重採樣也可以簡單理解爲:樣本轉換,因此 libswresample 提供一組高度優化的樣本轉換函數,不管是採樣類型,聲道格式等等都可以進行轉換。

要想使用 libswresample,首先得分配一個SwrContext ,它有兩種分配方式:

1、使用 swr_alloc() 分配一個 SwrContext 指針,並且必須使用 av_opt_set_*() 來設置參數。

具體的參數在 FFmpeg 源碼下的 libswresample / options.c 中。

如果你下載了Qt的源碼,那麼其中就包含了FFmpeg的源碼( 因爲 Chromium 源碼包含FFmpeg,而Qt包含 Chromium ),它在 qtwebengine 中。

2、使用 swr_alloc_set_opts() 分配的同時設置一些參數。

    SwrContext *swrContext = swr_alloc_set_opts(nullptr, int64_t(codecContext->channel_layout), AV_SAMPLE_FMT_S32, codecContext->sample_rate,
                                                int64_t(codecContext->channel_layout), codecContext->sample_fmt, codecContext->sample_rate,
                                                0, nullptr);
    swr_init(swrContext);

我使用第二種方式分配,因爲這裏不需要那麼多參數。

注意,分配了 SwrContext 後,必須使用 swr_init() 來進行初始化。

然後,當我們使用 avcodec_receive_frame() 獲取到一幀解碼的數據後,就可以進行轉換了:

    int size = av_samples_get_buffer_size(nullptr, frame->channels, frame->nb_samples, AV_SAMPLE_FMT_S32, 0);
    uint8_t *buf = new uint8_t[size];
    swr_convert(swrContext, &buf, frame->nb_samples, const_cast<const uint8_t**>(frame->data), frame->nb_samples);
    delete[] buf;

1、使用 av_samples_get_buffer_size() 來獲取給定音頻參數所需的緩衝大小。

2、new (分配) 一個緩衝區。

3、使用 swr_convert() 來進行轉換,in -> out。

因爲FFmpeg的註釋已經足夠詳細了,所以我從不講參數。

4、轉換完成後的數據存儲在 buf 中了,記住別忘了 delete。 


【結語】

本篇實在是沒什麼好寫的,因爲FFmpeg的抽象,所以解碼視頻和音頻的流程基本差不多。

不過,解碼字幕的時候倒是有些不同,這在後面會進行講解的。

最後,附上項目地址:https://github.com/mengps/FFmpeg-Learn,可以自己嘗試一下。

發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章