使用FFmpeg的libavformat API使用直接流副本创建的文件以3600 fps的速度播放得太快

Chr*_*ger 5 ffmpeg h.264 libavcodec libav libavformat

我正在研究一个libavformat API包装器,它将带有H.264和AAC的MP4文件转换为适合流式传输的MPEG-TS段.我只是在没有重新编码的情况下进行简单的流复制,但我生成的文件以3600 fps而不是24 fps 播放视频.

以下是ffprobe https://gist.github.com/chrisballinger/6733678的一些输出,损坏的文件如下:

r_frame_rate=1/1
avg_frame_rate=0/0
time_base=1/90000
start_pts=0
start_time=0.000000
duration_ts=2999
duration=0.033322
Run Code Online (Sandbox Code Playgroud)

通过ffmpeg手动发送的相同输入文件具有正确的时间戳信息:

r_frame_rate=24/1
avg_frame_rate=0/0
time_base=1/90000
start_pts=126000
start_time=1.400000
duration_ts=449850
duration=4.998333
Run Code Online (Sandbox Code Playgroud)

我认为这个问题存在于我的libavformat设置中:https://github.com/OpenWatch/FFmpegWrapper/blob/master/FFmpegWrapper/FFmpegWrapper.m#L349我在那里重新利用了ffmpeg.c中的一堆代码,这是必需的用于直接流复制.

由于3600看起来像一个"神奇的数字"(60*60),它可能就像我没有正确设置时间尺度一样简单,但我无法弄清楚我的代码与ffmpeg/avconv本身的分歧.

类似的问题在这里,但我认为他们没有达到我的目的:使用libavformat与vcopy/acopy混合使用H.264附件B和AAC流

Chr*_*ger 1

花了一段时间,但这就是答案:https ://stackoverflow.com/a/16903982/805882

packet.pts = av_rescale_q(packet->pts, inStream->time_base, outStream->time_base);
packet.dts = av_rescale_q(packet->dts, inStream->time_base, outStream->time_base);
Run Code Online (Sandbox Code Playgroud)