ffmpeg转码过程中的dts转换过程

ffmpeg转码过程中的dts转换过程

用ffmpeg api开发转码,在过程:拉流–>avfilter分辨率缩放,重采样–>编码–>写出,avpacket.dts和frame.dts在过程中需要根据不同的timebase进行转换。

一,拉流

在 av_read_frame后得到AVPacket packet


AVPacket packet;

int ret_i = av_read_frame(_format_ctx_p, &packet);

需要把网络数据输入的timebase转换成解码codec的timebase。


if(packet.stream_index == FRAME_TYPE_AUDIO) {
    av_packet_rescale_ts(&packet,
      _format_ctx_p->streams[_audio_index_i]->time_base,//1/1000
      _audio_codec_ctx_p->time_base);//1/48000
      _output_ptr->output_frame((void*)&packet, _audio_codec_ctx_p);
}
if(packet.stream_index == FRAME_TYPE_VIDEO) {
      av_packet_rescale_ts(&packet,
       _format_ctx_p->streams[_video_index_i]->time_base,//1/1000
       _video_codec_ctx_p->time_base);//1/25
       _output_ptr->output_frame((void*)&packet, _video_codec_ctx_p);
}

如果需要解码,也需要转换一下timebase:


new_frame_p->pts = av_rescale_q(new_frame_p->pts, _format_ctx_p->streams[_audio_index_i]->time_base, 
                        _audio_codec_ctx_p->time_base);
......
new_frame_p->pts = av_rescale_q(new_frame_p->pts, _format_ctx_p->streams[_video_index_i]->time_base, 
                        _video_codec_ctx_p->time_base);
注意:_video_codec_ctx_p和_audio_codec_ctx_p是解码的codec:

    _audio_stream_p = _format_ctx_p->streams[_audio_index_i];
    _audio_codec_ctx_p = _audio_stream_p->codec;
    _video_stream_p = _format_ctx_p->streams[_video_index_i];
    _video_codec_ctx_p = _video_stream_p->codec;

二. Avfilter的视频scale和音频重采样

在写入avfilter:av_buffersrc_add_frame_flags,和读取处理后的数据:av_buffersink_get_frame_flags,之后需要处理一下时间戳timebase转换。


AVRational vfilter_tb = _video_filter_ctx.buffersink_ctx->inputs[0]->timebase;
AVRational afilter_tb = _audio_filter_ctx.buffersink_ctx->inputs[0]->timebase;
......
if (视频)
    filtered_frame->pts = av_rescale_q(filtered_frame->pts, vfilter_tb, _vcodec_ctx_p->time_base);
if (音频)
    filtered_frame->pts = av_rescale_q(filtered_frame->pts, afilter_tb, _acodec_ctx_p->time_base);
然后在送去编码。

三. 编码后写数据Muxing

在编码后,把音视频avpacket进行muxing,需要进行timebase的转换:


if(视频)
    av_packet_rescale_ts(pkt_p, _vcodec_ctx_p->time_base, standard_ration);
if(音频)
    av_packet_rescale_ts(pkt_p, _acodec_ctx_p->time_base, standard_ration);
然后送去muxer写数据.
发布了21 篇原创文章 · 获赞 18 · 访问量 5万+

猜你喜欢

转载自blog.csdn.net/sweibd/article/details/90512338
今日推荐