Minor perf fix in SimpleAudio: Lazily create resampling contexts once instead of every audio frame

This commit is contained in:
Henrik Rydgard 2014-06-22 17:50:47 +02:00
parent 4a2aa3cbe6
commit dc66e18c00

View File

@ -137,6 +137,8 @@ bool SimpleAudio::ResetCodecCtx(int channels, int samplerate){
SimpleAudio::~SimpleAudio() { SimpleAudio::~SimpleAudio() {
#ifdef USE_FFMPEG #ifdef USE_FFMPEG
if (swrCtx_)
swr_free(&swrCtx_);
if (frame_) if (frame_)
av_frame_free(&frame_); av_frame_free(&frame_);
if (codecCtx_) if (codecCtx_)
@ -191,30 +193,32 @@ bool SimpleAudio::Decode(void* inbuf, int inbytes, uint8_t *outbuf, int *outbyte
int64_t wanted_channel_layout = AV_CH_LAYOUT_STEREO; // we want stereo output layout int64_t wanted_channel_layout = AV_CH_LAYOUT_STEREO; // we want stereo output layout
int64_t dec_channel_layout = frame_->channel_layout; // decoded channel layout int64_t dec_channel_layout = frame_->channel_layout; // decoded channel layout
swrCtx_ = swr_alloc_set_opts( if (!swrCtx_) {
swrCtx_, swrCtx_ = swr_alloc_set_opts(
wanted_channel_layout, swrCtx_,
AV_SAMPLE_FMT_S16, wanted_channel_layout,
wanted_resample_freq, AV_SAMPLE_FMT_S16,
dec_channel_layout, wanted_resample_freq,
codecCtx_->sample_fmt, dec_channel_layout,
codecCtx_->sample_rate, codecCtx_->sample_fmt,
0, codecCtx_->sample_rate,
NULL); 0,
NULL);
if (!swrCtx_ || swr_init(swrCtx_) < 0) { if (!swrCtx_ || swr_init(swrCtx_) < 0) {
ERROR_LOG(ME, "swr_init: Failed to initialize the resampling context"); ERROR_LOG(ME, "swr_init: Failed to initialize the resampling context");
avcodec_close(codecCtx_); avcodec_close(codecCtx_);
codec_ = 0; codec_ = 0;
return false; return false;
}
} }
// convert audio to AV_SAMPLE_FMT_S16 // convert audio to AV_SAMPLE_FMT_S16
int swrRet = swr_convert(swrCtx_, &outbuf, frame_->nb_samples, (const u8 **)frame_->extended_data, frame_->nb_samples); int swrRet = swr_convert(swrCtx_, &outbuf, frame_->nb_samples, (const u8 **)frame_->extended_data, frame_->nb_samples);
if (swrRet < 0) { if (swrRet < 0) {
ERROR_LOG(ME, "swr_convert: Error while converting %d", swrRet); ERROR_LOG(ME, "swr_convert: Error while converting %d", swrRet);
return false; return false;
} }
swr_free(&swrCtx_);
// output samples per frame, we should *2 since we have two channels // output samples per frame, we should *2 since we have two channels
outSamples = swrRet * 2; outSamples = swrRet * 2;