From: Wim Taymans Date: Tue, 5 Feb 2013 09:46:50 +0000 (+0100) Subject: videoscale: scale each field in interlace mode X-Git-Tag: 1.1.1~367 X-Git-Url: http://review.tizen.org/git/?a=commitdiff_plain;h=0085a77919875cc34efe990fc0a0d6dfa3157689;p=platform%2Fupstream%2Fgst-plugins-base.git videoscale: scale each field in interlace mode When we are dealing with interlaced content, scale each field intependently so that we don't destroy the interlacing. See https://bugzilla.gnome.org/show_bug.cgi?id=588535 --- diff --git a/gst/videoscale/gstvideoscale.c b/gst/videoscale/gstvideoscale.c index 5771371..2c8e9a1 100644 --- a/gst/videoscale/gstvideoscale.c +++ b/gst/videoscale/gstvideoscale.c @@ -203,6 +203,9 @@ static void gst_video_scale_set_property (GObject * object, guint prop_id, static void gst_video_scale_get_property (GObject * object, guint prop_id, GValue * value, GParamSpec * pspec); +static GstFlowReturn do_scale (GstVideoFilter * filter, VSImage dest[4], + VSImage src[4]); + #define gst_video_scale_parent_class parent_class G_DEFINE_TYPE (GstVideoScale, gst_video_scale, GST_TYPE_VIDEO_FILTER); @@ -1002,7 +1005,7 @@ done: static void gst_video_scale_setup_vs_image (VSImage * image, GstVideoFrame * frame, - gint component, gint b_w, gint b_h) + gint component, gint b_w, gint b_h, gboolean interlaced, gint field) { GstVideoFormat format; gint width, height; @@ -1018,6 +1021,11 @@ gst_video_scale_setup_vs_image (VSImage * image, GstVideoFrame * frame, image->height = GST_VIDEO_FORMAT_INFO_SCALE_HEIGHT (frame->info.finfo, component, MAX (1, height - b_h)); + if (interlaced) { + image->real_height /= 2; + image->height /= 2; + } + image->border_top = (image->real_height - image->height) / 2; image->border_bottom = image->real_height - image->height - image->border_top; @@ -1035,12 +1043,19 @@ gst_video_scale_setup_vs_image (VSImage * image, GstVideoFrame * frame, image->border_right = image->real_width - image->width - image->border_left; } - image->real_pixels = frame->data[component]; - image->stride = frame->info.stride[component]; + image->real_pixels = GST_VIDEO_FRAME_PLANE_DATA (frame, component); + image->stride = GST_VIDEO_FRAME_PLANE_STRIDE (frame, component); + + if (interlaced) { + if (field == 1) + image->real_pixels += image->stride; + image->stride *= 2; + } image->pixels = image->real_pixels + image->border_top * image->stride + image->border_left * GST_VIDEO_FRAME_COMP_PSTRIDE (frame, component); + } static const guint8 * @@ -1111,11 +1126,39 @@ gst_video_scale_transform_frame (GstVideoFilter * filter, GstFlowReturn ret = GST_FLOW_OK; VSImage dest[4] = { {NULL,}, }; VSImage src[4] = { {NULL,}, }; + gint i; + gboolean interlaced; + + interlaced = GST_VIDEO_FRAME_IS_INTERLACED (in_frame); + + for (i = 0; i < GST_VIDEO_FRAME_N_PLANES (in_frame); i++) { + gst_video_scale_setup_vs_image (&src[i], in_frame, i, 0, 0, interlaced, 0); + gst_video_scale_setup_vs_image (&dest[i], out_frame, i, + videoscale->borders_w, videoscale->borders_h, interlaced, 0); + } + ret = do_scale (filter, dest, src); + + if (interlaced) { + for (i = 0; i < GST_VIDEO_FRAME_N_PLANES (in_frame); i++) { + gst_video_scale_setup_vs_image (&src[i], in_frame, i, 0, 0, interlaced, + 1); + gst_video_scale_setup_vs_image (&dest[i], out_frame, i, + videoscale->borders_w, videoscale->borders_h, interlaced, 1); + } + ret = do_scale (filter, dest, src); + } + return ret; +} + +static GstFlowReturn +do_scale (GstVideoFilter * filter, VSImage dest[4], VSImage src[4]) +{ + GstVideoScale *videoscale = GST_VIDEO_SCALE (filter); + GstFlowReturn ret = GST_FLOW_OK; gint method; const guint8 *black; - gboolean add_borders; GstVideoFormat format; - gint i; + gboolean add_borders; GST_OBJECT_LOCK (videoscale); method = videoscale->method; @@ -1133,12 +1176,6 @@ gst_video_scale_transform_frame (GstVideoFilter * filter, method = GST_VIDEO_SCALE_BILINEAR; } - for (i = 0; i < GST_VIDEO_FRAME_N_PLANES (in_frame); i++) { - gst_video_scale_setup_vs_image (&src[i], in_frame, i, 0, 0); - gst_video_scale_setup_vs_image (&dest[i], out_frame, i, - videoscale->borders_w, videoscale->borders_h); - } - GST_CAT_DEBUG_OBJECT (GST_CAT_PERFORMANCE, filter, "doing videoscale format %s", GST_VIDEO_INFO_NAME (&filter->in_info));