summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorWim Taymans <wim.taymans@collabora.co.uk>2009-05-15 15:25:06 +0200
committerWim Taymans <wim@metal.(none)>2009-06-01 13:37:28 +0200
commit183978237964b8cc0d8394e694d45a138c84ce1a (patch)
tree574057bd4ad4121eb5c265a3b7d52e041dc713c0
parent2f6439dfde4eb3fc7c59af27f77bb058fb5fd1e6 (diff)
basesink: add framestepping in time
-rw-r--r--libs/gst/base/gstbasesink.c50
1 files changed, 36 insertions, 14 deletions
diff --git a/libs/gst/base/gstbasesink.c b/libs/gst/base/gstbasesink.c
index a7e187d77..588224aae 100644
--- a/libs/gst/base/gstbasesink.c
+++ b/libs/gst/base/gstbasesink.c
@@ -158,7 +158,7 @@ typedef struct
guint32 seqnum; /* the seqnum of the STEP event */
GstFormat format; /* the format of the amount */
guint64 amount; /* the total amount of data to skip */
- guint64 remaining; /* the remaining amount of data to skip */
+ guint64 position; /* the position in the stepped data */
guint64 duration; /* the duration in time of the skipped data */
guint64 start; /* running_time of the start */
gdouble rate; /* rate of skipping */
@@ -1512,8 +1512,9 @@ stop_stepping (GstBaseSink * sink, GstSegment * segment,
GST_DEBUG_OBJECT (sink, "step complete");
- GST_DEBUG_OBJECT (sink, "step stop at running_time %" GST_TIME_FORMAT,
- GST_TIME_ARGS (*rstart));
+ GST_DEBUG_OBJECT (sink,
+ "step stop at running_time %" GST_TIME_FORMAT ", timestamp %"
+ GST_TIME_FORMAT, GST_TIME_ARGS (*rstart), GST_TIME_ARGS (cstart));
/* configure the duration of the elapsed segment */
current->duration = *rstart - current->start;
@@ -1523,8 +1524,14 @@ stop_stepping (GstBaseSink * sink, GstSegment * segment,
/* update the segment, discarding what was consumed, running time goes
* backwards with the duration of the data we skipped. FIXME, this only works
* in PAUSED. */
+ segment->time = gst_segment_to_stream_time (segment, segment->format, cstart);
segment->start = cstart;
- *rstart -= current->duration;
+ segment->accum = current->start;
+
+ /* the clip segment is used for position report in paused... */
+ memcpy (sink->abidata.ABI.clip_segment, segment, sizeof (GstSegment));
+
+ *rstart = current->start;
*rstop -= current->duration;
message =
@@ -1542,7 +1549,8 @@ stop_stepping (GstBaseSink * sink, GstSegment * segment,
static gboolean
handle_stepping (GstBaseSink * sink, GstSegment * segment,
- GstStepInfo * current)
+ GstStepInfo * current, gint64 * cstart, gint64 * cstop, gint64 * rstart,
+ gint64 * rstop)
{
GstBaseSinkPrivate *priv;
gboolean step_end = FALSE;
@@ -1552,17 +1560,31 @@ handle_stepping (GstBaseSink * sink, GstSegment * segment,
/* see if we need to skip this buffer because of stepping */
switch (current->format) {
case GST_FORMAT_TIME:
+ {
+ guint64 end;
+
+ end = current->start + current->amount;
+
+ current->position = *rstart - current->start;
+
GST_DEBUG_OBJECT (sink,
"got time step %" GST_TIME_FORMAT "/%" GST_TIME_FORMAT,
- GST_TIME_ARGS (current->remaining), GST_TIME_ARGS (current->amount));
+ GST_TIME_ARGS (current->position), GST_TIME_ARGS (current->amount));
+
+ if (current->position >= current->amount || *rstop >= end) {
+ step_end = TRUE;
+ *cstart += end - *rstart;
+ *rstart = end;
+ }
break;
+ }
case GST_FORMAT_BUFFERS:
GST_DEBUG_OBJECT (sink,
"got default step %" G_GUINT64_FORMAT "/%" G_GUINT64_FORMAT,
- current->remaining, current->amount);
+ current->position, current->amount);
- if (current->remaining > 0) {
- current->remaining--;
+ if (current->position < current->amount) {
+ current->position++;
} else {
step_end = TRUE;
}
@@ -1571,7 +1593,7 @@ handle_stepping (GstBaseSink * sink, GstSegment * segment,
default:
GST_DEBUG_OBJECT (sink,
"got unknown step %" G_GUINT64_FORMAT "/%" G_GUINT64_FORMAT,
- current->remaining, current->amount);
+ current->position, current->amount);
break;
}
return step_end;
@@ -1711,15 +1733,15 @@ do_times:
rstop = gst_segment_to_running_time (segment, format, cstop);
if (G_UNLIKELY (step->valid)) {
- if (!(step_end = handle_stepping (basesink, segment, step)))
+ if (!(step_end = handle_stepping (basesink, segment, step, &cstart, &cstop,
+ &rstart, &rstop)))
*stepped = TRUE;
}
eos_done:
/* done label only called when doing EOS, we also stop stepping then */
if (step_end)
- stop_stepping (basesink, segment, &priv->current_step, cstart, cstop,
- &rstart, &rstop);
+ stop_stepping (basesink, segment, step, cstart, cstop, &rstart, &rstop);
/* save times */
*rsstart = sstart;
@@ -3368,7 +3390,7 @@ gst_base_sink_perform_step (GstBaseSink * sink, GstPad * pad, GstEvent * event)
priv->pending_step.seqnum = seqnum;
priv->pending_step.format = format;
priv->pending_step.amount = amount;
- priv->pending_step.remaining = amount;
+ priv->pending_step.position = 0;
priv->pending_step.rate = rate;
priv->pending_step.intermediate = intermediate;
priv->pending_step.valid = TRUE;