diff options
author | Ronald S. Bultje <rbultje@ronald.bitfreak.net> | 2004-02-29 05:14:24 +0000 |
---|---|---|
committer | Ronald S. Bultje <rbultje@ronald.bitfreak.net> | 2004-02-29 05:14:24 +0000 |
commit | 1451d85dab42c5a8ba6270f0f9a043a44041892f (patch) | |
tree | d7c505d8c5a283760688a9fbbb2359ca3c2d0069 /gst/videodrop | |
parent | 603eae54ad357c7304acaea71a2e54a123fa7162 (diff) | |
download | gst-plugins-bad-1451d85dab42c5a8ba6270f0f9a043a44041892f.tar.gz gst-plugins-bad-1451d85dab42c5a8ba6270f0f9a043a44041892f.tar.bz2 gst-plugins-bad-1451d85dab42c5a8ba6270f0f9a043a44041892f.zip |
gst/videodrop/gstvideodrop.*: Work based on timestamp of input data, not based on the expected framerate from the inp...
Original commit message from CVS:
* gst/videodrop/gstvideodrop.c: (gst_videodrop_init),
(gst_videodrop_chain), (gst_videodrop_change_state):
* gst/videodrop/gstvideodrop.h:
Work based on timestamp of input data, not based on the expected
framerate from the input. The consequence is that this element now
not only scales framerates, but also functions as a framerate
corrector or framerate stabilizer/constantizer.
Diffstat (limited to 'gst/videodrop')
-rw-r--r-- | gst/videodrop/gstvideodrop.c | 46 | ||||
-rw-r--r-- | gst/videodrop/gstvideodrop.h | 2 |
2 files changed, 36 insertions, 12 deletions
diff --git a/gst/videodrop/gstvideodrop.c b/gst/videodrop/gstvideodrop.c index b72e4252..546873f0 100644 --- a/gst/videodrop/gstvideodrop.c +++ b/gst/videodrop/gstvideodrop.c @@ -141,11 +141,6 @@ gst_videodrop_class_init (GstVideodropClass *klass) element_class->change_state = gst_videodrop_change_state; } -#define gst_caps_get_float_range(caps, name, min, max) \ - gst_props_entry_get_float_range(gst_props_get_entry((caps)->properties, \ - name), \ - min, max) - static GstCaps * gst_videodrop_getcaps (GstPad *pad) { @@ -219,6 +214,8 @@ gst_videodrop_link (GstPad *pad, const GstCaps *caps) static void gst_videodrop_init (GstVideodrop *videodrop) { + GST_FLAG_SET (videodrop, GST_ELEMENT_EVENT_AWARE); + GST_DEBUG ("gst_videodrop_init"); videodrop->sinkpad = gst_pad_new_from_template ( gst_static_pad_template_get (&gst_videodrop_sink_template), "sink"); @@ -236,6 +233,7 @@ gst_videodrop_init (GstVideodrop *videodrop) videodrop->inited = FALSE; videodrop->total = videodrop->pass = 0; videodrop->speed = 1.; + videodrop->time_adjust = 0; } static void @@ -245,19 +243,44 @@ gst_videodrop_chain (GstPad *pad, GstData *data) GstBuffer *buf; if (GST_IS_EVENT (data)) { - gst_pad_event_default (videodrop->srcpad, GST_EVENT (data)); + GstEvent *event = GST_EVENT (data); + + if (GST_EVENT_TYPE (event) == GST_EVENT_DISCONTINUOUS) { + /* since we rely on timestamps of the source, we need to handle + * changes in time carefully. */ + gint64 time; + if (gst_event_discont_get_value (event, GST_FORMAT_TIME, &time)) { + videodrop->time_adjust = time; + videodrop->total = videodrop->pass = 0; + } else { + GST_ELEMENT_ERROR (videodrop, STREAM, TOO_LAZY, (NULL), + ("Received discont, but no time information")); + gst_event_unref (event); + return; + } + } + + gst_pad_event_default (pad, event); return; } buf = GST_BUFFER (data); videodrop->total++; - while (videodrop->to_fps / (videodrop->from_fps * videodrop->speed) > - (gfloat) videodrop->pass / videodrop->total) { + while (((GST_BUFFER_TIMESTAMP (buf) - videodrop->time_adjust) * + videodrop->to_fps * videodrop->speed / GST_SECOND) >= videodrop->pass) { + /* since we write to the struct (time/duration), we need a new struct, + * but we don't want to copy around data - a subbuffer is the easiest + * way to accomplish that... */ + GstBuffer *copy = gst_buffer_create_sub (buf, 0, GST_BUFFER_SIZE (buf)); + + /* adjust timestamp/duration and push forward */ + GST_BUFFER_TIMESTAMP (copy) = videodrop->time_adjust / videodrop->speed + + GST_SECOND * videodrop->pass / videodrop->to_fps; + GST_BUFFER_DURATION (copy) = GST_SECOND / videodrop->to_fps; + gst_pad_push (videodrop->srcpad, GST_DATA (copy)); + videodrop->pass++; - gst_buffer_ref (buf); - GST_BUFFER_TIMESTAMP (buf) /= videodrop->speed; - gst_pad_push (videodrop->srcpad, GST_DATA (buf)); } gst_buffer_unref (buf); @@ -307,6 +330,7 @@ gst_videodrop_change_state (GstElement *element) switch (GST_STATE_TRANSITION (element)) { case GST_STATE_PAUSED_TO_READY: videodrop->inited = FALSE; + videodrop->time_adjust = 0; videodrop->total = videodrop->pass = 0; break; default: diff --git a/gst/videodrop/gstvideodrop.h b/gst/videodrop/gstvideodrop.h index 429be2c4..20f954a4 100644 --- a/gst/videodrop/gstvideodrop.h +++ b/gst/videodrop/gstvideodrop.h @@ -48,7 +48,7 @@ struct _GstVideodrop { gfloat from_fps, to_fps; gfloat speed; - guint64 pass, total; + guint64 pass, total, time_adjust; }; struct _GstVideodropClass { |