From 8667e55c831968fa0a12619511ea17b2f94f40e7 Mon Sep 17 00:00:00 2001 From: Michael Smith Date: Tue, 22 Nov 2005 23:58:14 +0000 Subject: [PATCH] ext/jpeg/: JPEG fractiony goodness. Original commit message from CVS: * ext/jpeg/gstjpegdec.c: (gst_jpeg_dec_setcaps), (gst_jpeg_dec_chain), (gst_jpeg_dec_change_state): * ext/jpeg/gstjpegdec.h: * ext/jpeg/gstjpegenc.c: (gst_jpegenc_setcaps): * ext/jpeg/gstjpegenc.h: * ext/jpeg/gstsmokeenc.c: (gst_smokeenc_setcaps), (gst_smokeenc_resync): * ext/jpeg/gstsmokeenc.h: JPEG fractiony goodness. --- ChangeLog | 12 ++++++++++++ ext/jpeg/gstjpegdec.c | 46 ++++++++++++++++++++++++++++++++-------------- ext/jpeg/gstjpegdec.h | 7 +++++-- ext/jpeg/gstjpegenc.c | 21 +++++++++++++++------ ext/jpeg/gstjpegenc.h | 1 - ext/jpeg/gstsmokeenc.c | 27 +++++++++++++-------------- ext/jpeg/gstsmokeenc.h | 1 - 7 files changed, 77 insertions(+), 38 deletions(-) diff --git a/ChangeLog b/ChangeLog index ab87fdd..9fd5495 100644 --- a/ChangeLog +++ b/ChangeLog @@ -1,3 +1,15 @@ +2005-11-23 Michael Smith + + * ext/jpeg/gstjpegdec.c: (gst_jpeg_dec_setcaps), + (gst_jpeg_dec_chain), (gst_jpeg_dec_change_state): + * ext/jpeg/gstjpegdec.h: + * ext/jpeg/gstjpegenc.c: (gst_jpegenc_setcaps): + * ext/jpeg/gstjpegenc.h: + * ext/jpeg/gstsmokeenc.c: (gst_smokeenc_setcaps), + (gst_smokeenc_resync): + * ext/jpeg/gstsmokeenc.h: + JPEG fractiony goodness. + 2005-11-22 Michael Smith * gst/goom/filters.c: diff --git a/ext/jpeg/gstjpegdec.c b/ext/jpeg/gstjpegdec.c index ab54772..8b26c3d 100644 --- a/ext/jpeg/gstjpegdec.c +++ b/ext/jpeg/gstjpegdec.c @@ -54,7 +54,7 @@ GST_STATIC_PAD_TEMPLATE ("sink", GST_STATIC_CAPS ("image/jpeg, " "width = (int) [ " G_STRINGIFY (MIN_WIDTH) ", " G_STRINGIFY (MAX_WIDTH) " ], " "height = (int) [ " G_STRINGIFY (MIN_HEIGHT) ", " - G_STRINGIFY (MAX_HEIGHT) " ], " "framerate = (double) [ 0, MAX ]") + G_STRINGIFY (MAX_HEIGHT) " ], " "framerate = (fraction) [ 0/1, MAX ]") ); GST_DEBUG_CATEGORY (jpeg_dec_debug); @@ -588,15 +588,17 @@ gst_jpeg_dec_setcaps (GstPad * pad, GstCaps * caps) { GstStructure *s; GstJpegDec *dec; - gdouble fps; + const GValue *framerate; dec = GST_JPEG_DEC (GST_OBJECT_PARENT (pad)); s = gst_caps_get_structure (caps, 0); - if (gst_structure_get_double (s, "framerate", &fps)) { - dec->fps = fps; + if ((framerate = gst_structure_get_value (s, "framerate")) != NULL) { + dec->framerate_numerator = gst_value_get_fraction_numerator (framerate); + dec->framerate_denominator = gst_value_get_fraction_denominator (framerate); dec->packetized = TRUE; - GST_DEBUG ("got framerate of %f fps => packetized mode", fps); + GST_DEBUG ("got framerate of %d/%d fps => packetized mode", + dec->framerate_numerator, dec->framerate_denominator); } /* do not extract width/height here. we do that in the chain @@ -783,15 +785,22 @@ gst_jpeg_dec_chain (GstPad * pad, GstBuffer * buf) goto wrong_size; if (width != dec->caps_width || height != dec->caps_height || - dec->fps != dec->caps_fps) { + dec->framerate_numerator != dec->caps_framerate_numerator || + dec->framerate_denominator != dec->caps_framerate_denominator) { GstCaps *caps; - /* framerate == 0.0 is a still frame */ + /* framerate == 0/1 is a still frame */ + if (dec->framerate_denominator == 0) { + dec->framerate_numerator = 0; + dec->framerate_denominator = 1; + } + caps = gst_caps_new_simple ("video/x-raw-yuv", "format", GST_TYPE_FOURCC, GST_MAKE_FOURCC ('I', '4', '2', '0'), "width", G_TYPE_INT, width, "height", G_TYPE_INT, height, - "framerate", G_TYPE_DOUBLE, (double) dec->fps, NULL); + "framerate", GST_TYPE_FRACTION, dec->framerate_numerator, + dec->framerate_denominator, NULL); GST_DEBUG_OBJECT (dec, "setting caps %" GST_PTR_FORMAT, caps); GST_DEBUG_OBJECT (dec, "max_v_samp_factor=%d", @@ -802,7 +811,8 @@ gst_jpeg_dec_chain (GstPad * pad, GstBuffer * buf) dec->caps_width = width; dec->caps_height = height; - dec->caps_fps = dec->fps; + dec->caps_framerate_numerator = dec->framerate_numerator; + dec->caps_framerate_denominator = dec->framerate_denominator; } ret = gst_pad_alloc_buffer (dec->srcpad, GST_BUFFER_OFFSET_NONE, @@ -813,9 +823,15 @@ gst_jpeg_dec_chain (GstPad * pad, GstBuffer * buf) outdata = GST_BUFFER_DATA (outbuf); GST_BUFFER_TIMESTAMP (outbuf) = dec->next_ts; - if (dec->packetized) { - duration = GST_SECOND / dec->fps; - dec->next_ts += duration; + if (dec->packetized && dec->framerate_numerator != 0) { + GstClockTime next_ts; + + dec->frames_decoded++; + next_ts = dec->frames_decoded * GST_SECOND * + dec->framerate_denominator / dec->framerate_numerator; + + duration = next_ts - dec->next_ts; + dec->next_ts = next_ts; } else { duration = GST_CLOCK_TIME_NONE; dec->next_ts = GST_CLOCK_TIME_NONE; @@ -922,8 +938,10 @@ gst_jpeg_dec_change_state (GstElement * element, GstStateChange transition) switch (transition) { case GST_STATE_CHANGE_READY_TO_PAUSED: - dec->fps = 0.0; - dec->caps_fps = 0.0; + dec->framerate_numerator = 0; + dec->framerate_denominator = 1; + dec->caps_framerate_numerator = dec->caps_framerate_denominator = 0; + dec->frames_decoded = 0; dec->caps_width = -1; dec->caps_height = -1; dec->packetized = FALSE; diff --git a/ext/jpeg/gstjpegdec.h b/ext/jpeg/gstjpegdec.h index 4d8f42c..de034fa 100644 --- a/ext/jpeg/gstjpegdec.h +++ b/ext/jpeg/gstjpegdec.h @@ -76,10 +76,13 @@ struct _GstJpegDec { guint64 next_ts; /* video state */ - gdouble fps; + gint framerate_numerator; + gint framerate_denominator; + gint frames_decoded; /* negotiated state */ - gdouble caps_fps; + gint caps_framerate_numerator; + gint caps_framerate_denominator; gint caps_width; gint caps_height; diff --git a/ext/jpeg/gstjpegenc.c b/ext/jpeg/gstjpegenc.c index 9605349..0aee1eb 100644 --- a/ext/jpeg/gstjpegenc.c +++ b/ext/jpeg/gstjpegenc.c @@ -131,7 +131,7 @@ GST_STATIC_PAD_TEMPLATE ("src", GST_PAD_ALWAYS, GST_STATIC_CAPS ("image/jpeg, " "width = (int) [ 16, 4096 ], " - "height = (int) [ 16, 4096 ], " "framerate = (double) [ 1, MAX ]") + "height = (int) [ 16, 4096 ], " "framerate = (fraction) [ 0/1, MAX ]") ); static void @@ -295,19 +295,28 @@ gst_jpegenc_setcaps (GstPad * pad, GstCaps * caps) GstCaps *othercaps; GstPad *otherpad; gboolean ret; + const GValue *framerate; otherpad = (pad == jpegenc->srcpad) ? jpegenc->sinkpad : jpegenc->srcpad; structure = gst_caps_get_structure (caps, 0); - gst_structure_get_double (structure, "framerate", &jpegenc->fps); + framerate = gst_structure_get_value (structure, "framerate"); gst_structure_get_int (structure, "width", &jpegenc->width); gst_structure_get_int (structure, "height", &jpegenc->height); othercaps = gst_caps_copy (gst_pad_get_pad_template_caps (otherpad)); - gst_caps_set_simple (othercaps, - "width", G_TYPE_INT, jpegenc->width, - "height", G_TYPE_INT, jpegenc->height, - "framerate", G_TYPE_DOUBLE, jpegenc->fps, NULL); + if (framerate) { + gst_caps_set_simple (othercaps, + "width", G_TYPE_INT, jpegenc->width, + "height", G_TYPE_INT, jpegenc->height, + "framerate", GST_TYPE_FRACTION, + gst_value_get_fraction_numerator (framerate), + gst_value_get_fraction_denominator (framerate), NULL); + } else { + gst_caps_set_simple (othercaps, + "width", G_TYPE_INT, jpegenc->width, + "height", G_TYPE_INT, jpegenc->height, NULL); + } ret = gst_pad_set_caps (jpegenc->srcpad, othercaps); gst_caps_unref (othercaps); diff --git a/ext/jpeg/gstjpegenc.h b/ext/jpeg/gstjpegenc.h index b68b485..d2f9401 100644 --- a/ext/jpeg/gstjpegenc.h +++ b/ext/jpeg/gstjpegenc.h @@ -58,7 +58,6 @@ struct _GstJpegEnc { gint format; gint width; gint height; - gdouble fps; /* the video buffer */ gint bufsize; GstBuffer *buffer; diff --git a/ext/jpeg/gstsmokeenc.c b/ext/jpeg/gstsmokeenc.c index 06c02a8..2923380 100644 --- a/ext/jpeg/gstsmokeenc.c +++ b/ext/jpeg/gstsmokeenc.c @@ -116,7 +116,7 @@ GST_STATIC_PAD_TEMPLATE ("src", GST_PAD_ALWAYS, GST_STATIC_CAPS ("video/x-smoke, " "width = (int) [ 16, 4096 ], " - "height = (int) [ 16, 4096 ], " "framerate = (double) [ 1, MAX ]") + "height = (int) [ 16, 4096 ], " "framerate = (fraction) [ 0/1, MAX ]") ); static void @@ -239,11 +239,20 @@ gst_smokeenc_setcaps (GstPad * pad, GstCaps * caps) gboolean ret = TRUE; GstCaps *othercaps; GstPad *otherpad; + const GValue *framerate; otherpad = (pad == smokeenc->srcpad) ? smokeenc->sinkpad : smokeenc->srcpad; structure = gst_caps_get_structure (caps, 0); - gst_structure_get_double (structure, "framerate", &smokeenc->fps); + framerate = gst_structure_get_value (structure, "framerate"); + if (framerate) { + smokeenc->fps_num = gst_value_get_fraction_numerator (framerate); + smokeenc->fps_denom = gst_value_get_fraction_denominator (framerate); + } else { + smokeenc->fps_num = 0; + smokeenc->fps_denom = 1; + } + gst_structure_get_int (structure, "width", &smokeenc->width); gst_structure_get_int (structure, "height", &smokeenc->height); @@ -251,7 +260,8 @@ gst_smokeenc_setcaps (GstPad * pad, GstCaps * caps) gst_caps_set_simple (othercaps, "width", G_TYPE_INT, smokeenc->width, "height", G_TYPE_INT, smokeenc->height, - "framerate", G_TYPE_DOUBLE, smokeenc->fps, NULL); + "framerate", GST_TYPE_FRACTION, smokeenc->fps_num, smokeenc->fps_denom, + NULL); ret = gst_pad_set_caps (smokeenc->srcpad, othercaps); gst_caps_unref (othercaps); @@ -266,19 +276,8 @@ gst_smokeenc_setcaps (GstPad * pad, GstCaps * caps) static void gst_smokeenc_resync (GstSmokeEnc * smokeenc) { - GValue fps = { 0 }; - GValue framerate = { 0 }; - GST_DEBUG ("gst_smokeenc_resync: resync"); - g_value_init (&fps, G_TYPE_DOUBLE); - g_value_init (&framerate, GST_TYPE_FRACTION); - g_value_set_double (&fps, smokeenc->fps); - g_value_transform (&fps, &framerate); - - smokeenc->fps_num = gst_value_get_fraction_numerator (&framerate); - smokeenc->fps_denom = gst_value_get_fraction_denominator (&framerate); - smokecodec_encode_new (&smokeenc->info, smokeenc->width, smokeenc->height, smokeenc->fps_num, smokeenc->fps_denom); smokecodec_set_quality (smokeenc->info, smokeenc->min_quality, diff --git a/ext/jpeg/gstsmokeenc.h b/ext/jpeg/gstsmokeenc.h index cc1bbea..9c9f643 100644 --- a/ext/jpeg/gstsmokeenc.h +++ b/ext/jpeg/gstsmokeenc.h @@ -56,7 +56,6 @@ struct _GstSmokeEnc { gint height; gint frame; gint keyframe; - gdouble fps; gint fps_num, fps_denom; SmokeCodecInfo *info; -- 2.7.4