omxvideodec: ignore very little variations of the framerate

If less than 1%.

The dynamic format change should not happen when the
resolution does not change and when only the framerate
changes but very slightly, i.e. from 50000/1677=29.81
to 89/3=29.66 so a "percentage change" of less than 1%
(i.e. 100*(29.81-29.66)/29.66 = 0.50 < 1 ). In that case
just ignore it to avoid unnecessary renegotiation.

https://bugzilla.gnome.org/show_bug.cgi?id=759043
This commit is contained in:
Julien Isorce 2017-12-12 17:30:27 +00:00
parent 7048134fa9
commit 6810878193
3 changed files with 20 additions and 1 deletions

View file

@ -28,6 +28,8 @@
#include "gstomxvideo.h"
#include <math.h>
GST_DEBUG_CATEGORY (gst_omx_video_debug_category);
#define GST_CAT_DEFAULT gst_omx_video_debug_category
@ -206,3 +208,17 @@ gst_omx_video_calculate_framerate_q16 (GstVideoInfo * info)
return gst_util_uint64_scale_int (1 << 16, info->fps_n, info->fps_d);
}
gboolean
gst_omx_video_is_equal_framerate_q16 (OMX_U32 q16_a, OMX_U32 q16_b)
{
/* If one of them is 0 use the classic comparison. The value 0 has a special
meaning and is used to indicate the frame rate is unknown, variable, or
is not needed. */
if (!q16_a || !q16_b)
return q16_a == q16_b;
/* If the 'percentage change' is less than 1% then consider it equal to avoid
* an unnecessary re-negotiation. */
return fabs (((gdouble) q16_a) - ((gdouble) q16_b)) / (gdouble) q16_b < 0.01;
}

View file

@ -57,6 +57,8 @@ gst_omx_video_find_nearest_frame (GstOMXBuffer * buf, GList * frames);
OMX_U32 gst_omx_video_calculate_framerate_q16 (GstVideoInfo * info);
gboolean gst_omx_video_is_equal_framerate_q16 (OMX_U32 q16_a, OMX_U32 q16_b);
G_END_DECLS
#endif /* __GST_OMX_VIDEO_H__ */

View file

@ -2342,7 +2342,8 @@ gst_omx_video_dec_set_format (GstVideoDecoder * decoder,
is_format_change |= port_def.format.video.nFrameHeight != info->height;
is_format_change |= (port_def.format.video.xFramerate == 0
&& info->fps_n != 0)
|| (port_def.format.video.xFramerate != framerate_q16);
|| !gst_omx_video_is_equal_framerate_q16 (port_def.format.
video.xFramerate, framerate_q16);
is_format_change |= (self->codec_data != state->codec_data);
if (klass->is_format_change)
is_format_change |=