summaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authorTaylor Ralph <tralph@mythtv.org>2012-02-04 04:24:13 (GMT)
committer Taylor Ralph <tralph@mythtv.org>2012-02-04 04:24:13 (GMT)
commit6c22eda37519a3da50558e468ce0a76e770b9399 (patch)
tree8994f777095474eb0cb6d9a4add6d5de5d22cb81
parent3c929e8e36194f6cb3aef3b03ecbc7abc9439f9b (diff)
avformatdecoder: improve fps detection in normalized_fps()
This should fix issues with mov style containers by using the avg_frame_rate which is set by the demuxer. NOTE: Using estimated_fps seems to always be accurate for everything except matroska and mov. It appears that ffmpeg takes into account the codec and container fps when generating estimated_fps. Also, XBMC uses estimated_fps for everything except matroska. We should probably do the same. Fixes #10300.
-rw-r--r--mythtv/libs/libmythtv/avformatdecoder.cpp33
1 files changed, 18 insertions, 15 deletions
diff --git a/mythtv/libs/libmythtv/avformatdecoder.cpp b/mythtv/libs/libmythtv/avformatdecoder.cpp
index 40e2d39..8295d51 100644
--- a/mythtv/libs/libmythtv/avformatdecoder.cpp
+++ b/mythtv/libs/libmythtv/avformatdecoder.cpp
@@ -1112,50 +1112,53 @@ int AvFormatDecoder::OpenFile(RingBuffer *rbuffer, bool novideo,
float AvFormatDecoder::normalized_fps(AVStream *stream, AVCodecContext *enc)
{
- float fps, avg_fps, stream_fps, container_fps, estimated_fps;
- avg_fps = stream_fps = container_fps = estimated_fps = 0.0f;
+ float fps, avg_fps, codec_fps, container_fps, estimated_fps;
+ avg_fps = codec_fps = container_fps = estimated_fps = 0.0f;
if (stream->avg_frame_rate.den && stream->avg_frame_rate.num)
avg_fps = av_q2d(stream->avg_frame_rate); // MKV default_duration
if (enc->time_base.den && enc->time_base.num) // tbc
- stream_fps = 1.0f / av_q2d(enc->time_base) / enc->ticks_per_frame;
+ codec_fps = 1.0f / av_q2d(enc->time_base) / enc->ticks_per_frame;
// Some formats report fps waaay too high. (wrong time_base)
- if (stream_fps > 121.0f && (enc->time_base.den > 10000) &&
+ if (codec_fps > 121.0f && (enc->time_base.den > 10000) &&
(enc->time_base.num == 1))
{
enc->time_base.num = 1001; // seems pretty standard
if (av_q2d(enc->time_base) > 0)
- stream_fps = 1.0f / av_q2d(enc->time_base);
+ codec_fps = 1.0f / av_q2d(enc->time_base);
}
if (stream->time_base.den && stream->time_base.num) // tbn
container_fps = 1.0f / av_q2d(stream->time_base);
if (stream->r_frame_rate.den && stream->r_frame_rate.num) // tbr
estimated_fps = av_q2d(stream->r_frame_rate);
- if (QString(ic->iformat->name).contains("matroska") &&
+ // matroska demuxer sets the default_duration to avg_frame_rate
+ // mov,mp4,m4a,3gp,3g2,mj2 demuxer sets avg_frame_rate
+ if ((QString(ic->iformat->name).contains("matroska") ||
+ QString(ic->iformat->name).contains("mov")) &&
avg_fps < 121.0f && avg_fps > 3.0f)
- fps = avg_fps; // matroska default_duration
+ fps = avg_fps;
else if (QString(ic->iformat->name).contains("avi") &&
container_fps < 121.0f && container_fps > 3.0f)
fps = container_fps; // avi uses container fps for timestamps
- else if (stream_fps < 121.0f && stream_fps > 3.0f)
- fps = stream_fps;
+ else if (codec_fps < 121.0f && codec_fps > 3.0f)
+ fps = codec_fps;
else if (container_fps < 121.0f && container_fps > 3.0f)
fps = container_fps;
- else if (estimated_fps < 70.0f && estimated_fps > 20.0f)
+ else if (estimated_fps < 121.0f && estimated_fps > 3.0f)
fps = estimated_fps;
+ else if (avg_fps < 121.0f && avg_fps > 3.0f)
+ fps = avg_fps;
else
- fps = stream_fps;
+ fps = 30000.0f / 1001.0f; // 29.97 fps
- // If it is still out of range, just assume NTSC...
- fps = (fps > 121.0f) ? (30000.0f / 1001.0f) : fps;
if (fps != m_fps)
{
LOG(VB_PLAYBACK, LOG_INFO, LOC +
- QString("Selected FPS is %1 (avg %2 stream %3 "
+ QString("Selected FPS is %1 (avg %2 codec %3 "
"container %4 estimated %5)").arg(fps).arg(avg_fps)
- .arg(stream_fps).arg(container_fps).arg(estimated_fps));
+ .arg(codec_fps).arg(container_fps).arg(estimated_fps));
m_fps = fps;
}