+2005-10-19 Wim Taymans <wim@fluendo.com>
+
+ * gst/base/gstbasesink.c: (gst_base_sink_commit_state),
+ (gst_base_sink_handle_object), (gst_base_sink_query), (do_playing):
+ * gst/base/gstbasesrc.c: (gst_base_src_query):
+ * gst/elements/gstfilesink.c: (gst_file_sink_query):
+ * gst/elements/gsttypefindelement.c:
+ (gst_type_find_handle_src_query), (find_element_get_length),
+ (gst_type_find_element_activate):
+ API change fix.
+
+ * gst/gstquery.c: (gst_query_new_position),
+ (gst_query_set_position), (gst_query_parse_position),
+ (gst_query_new_duration), (gst_query_set_duration),
+ (gst_query_parse_duration), (gst_query_set_segment),
+ (gst_query_parse_segment):
+ * gst/gstquery.h:
+ Bundling query position/duration is not a good idea since duration
+ does not change much and we don't want to recalculate it for every
+ position query, so they are separated again..
+ Base value in segment query is not needed.
+
+ * gst/gstqueue.c: (gst_queue_handle_src_query):
+ * gst/gstutils.c: (gst_element_query_position),
+ (gst_element_query_duration), (gst_pad_query_position),
+ (gst_pad_query_duration):
+ * gst/gstutils.h:
+ Updates for query API change.
+ Added some docs here and there.
+
2005-10-19 Thomas Vander Stichele <thomas at apestaart dot org>
* check/gst/gstbin.c: (GST_START_TEST):
break;
case GST_QUERY_SEGMENT:
{
+ /* FIXME, bring start/stop to stream time */
gst_query_set_segment (query, basesink->segment_rate,
- GST_FORMAT_TIME, basesink->segment_start, basesink->segment_stop,
- basesink->segment_time);
+ GST_FORMAT_TIME, basesink->segment_start, basesink->segment_stop);
break;
}
case GST_QUERY_CONVERT:
{
GstFormat format;
- gst_query_parse_position (query, &format, NULL, NULL);
+ gst_query_parse_position (query, &format, NULL);
switch (format) {
case GST_FORMAT_DEFAULT:
case GST_FORMAT_BYTES:
- b = gst_base_src_get_size (src, &ui64);
- /* better to make get_size take an int64 */
- i64 = b ? (gint64) ui64 : -1;
- gst_query_set_position (query, GST_FORMAT_BYTES, src->offset, i64);
+ gst_query_set_position (query, GST_FORMAT_BYTES, src->offset);
return TRUE;
case GST_FORMAT_PERCENT:
b = gst_base_src_get_size (src, &ui64);
if (b)
i64 *= gst_guint64_to_gdouble (src->offset)
/ gst_guint64_to_gdouble (ui64);
- gst_query_set_position (query, GST_FORMAT_PERCENT,
- i64, GST_FORMAT_PERCENT_MAX);
+ gst_query_set_position (query, GST_FORMAT_PERCENT, i64);
+ return TRUE;
+ default:
+ return FALSE;
+ }
+ }
+ case GST_QUERY_DURATION:
+ {
+ GstFormat format;
+
+ gst_query_parse_duration (query, &format, NULL);
+ switch (format) {
+ case GST_FORMAT_DEFAULT:
+ case GST_FORMAT_BYTES:
+ b = gst_base_src_get_size (src, &ui64);
+ /* better to make get_size take an int64 */
+ i64 = b ? (gint64) ui64 : -1;
+ gst_query_set_duration (query, GST_FORMAT_BYTES, i64);
+ return TRUE;
+ case GST_FORMAT_PERCENT:
+ gst_query_set_duration (query, GST_FORMAT_PERCENT,
+ GST_FORMAT_PERCENT_MAX);
return TRUE;
default:
return FALSE;
switch (GST_QUERY_TYPE (query)) {
case GST_QUERY_POSITION:
- gst_query_parse_position (query, &format, NULL, NULL);
+ gst_query_parse_position (query, &format, NULL);
switch (format) {
case GST_FORMAT_DEFAULT:
case GST_FORMAT_BYTES:
- gst_query_set_position (query, GST_FORMAT_BYTES,
- self->data_written, self->data_written);
+ gst_query_set_position (query, GST_FORMAT_BYTES, self->data_written);
return TRUE;
default:
return FALSE;
switch (GST_QUERY_TYPE (query)) {
case GST_QUERY_POSITION:
{
- gint64 peer_pos, peer_total;
+ gint64 peer_pos;
GstFormat format;
if (typefind->store == NULL)
return TRUE;
- gst_query_parse_position (query, &format, &peer_pos, &peer_total);
+ gst_query_parse_position (query, &format, &peer_pos);
/* FIXME: this code assumes that there's no discont in the queue */
switch (format) {
/* FIXME */
break;
}
- gst_query_set_position (query, format, peer_pos, peer_total);
+ gst_query_set_position (query, format, peer_pos);
break;
}
default:
return 0;
}
if (entry->self->stream_length == 0) {
- if (!gst_pad_query_position (GST_PAD_PEER (entry->self->sink), &format,
- NULL, (gint64 *) & entry->self->stream_length))
+ if (!gst_pad_query_duration (GST_PAD_PEER (entry->self->sink), &format,
+ (gint64 *) & entry->self->stream_length))
goto no_length;
if (format != GST_FORMAT_BYTES) {
gint64 size;
GstFormat format = GST_FORMAT_BYTES;
- gst_pad_query_position (peer, &format, NULL, &size);
+ gst_pad_query_duration (peer, &format, &size);
found_caps = gst_type_find_helper (peer, (guint64) size);
gst_object_unref (peer);
}
static guint32 _n_values = 1; /* we start from 1 because 0 reserved for NONE */
static GstQueryTypeDefinition standard_definitions[] = {
- {GST_QUERY_POSITION, "position", "Current position and total duration"},
+ {GST_QUERY_POSITION, "position", "Current position"},
+ {GST_QUERY_DURATION, "duration", "Total duration"},
{GST_QUERY_LATENCY, "latency", "Latency"},
{GST_QUERY_JITTER, "jitter", "Jitter"},
{GST_QUERY_RATE, "rate", "Configured rate 1000000 = 1"},
structure = gst_structure_new ("GstQueryPosition",
"format", GST_TYPE_FORMAT, format,
- "cur", G_TYPE_INT64, (gint64) - 1,
- "end", G_TYPE_INT64, (gint64) - 1, NULL);
+ "cur", G_TYPE_INT64, (gint64) - 1, NULL);
query = gst_query_new (GST_QUERY_POSITION, structure);
return query;
* @query: the query to fill in
* @format: the requested #GstFormat
* @cur: the current position
- * @end: the end position
*
* Answer a position query by setting the requested values.
*/
void
-gst_query_set_position (GstQuery * query, GstFormat format,
- gint64 cur, gint64 end)
+gst_query_set_position (GstQuery * query, GstFormat format, gint64 cur)
{
GstStructure *structure;
structure = gst_query_get_structure (query);
gst_structure_set (structure,
- "format", GST_TYPE_FORMAT, format,
- "cur", G_TYPE_INT64, cur, "end", G_TYPE_INT64, end, NULL);
+ "format", GST_TYPE_FORMAT, format, "cur", G_TYPE_INT64, cur, NULL);
}
/**
* @query: the query to parse
* @format: the storage for the #GstFormat of the position values
* @cur: the storage for the current position
- * @end: the storage for the end position
*
* Parse a position query answer.
*/
void
-gst_query_parse_position (GstQuery * query, GstFormat * format,
- gint64 * cur, gint64 * end)
+gst_query_parse_position (GstQuery * query, GstFormat * format, gint64 * cur)
{
GstStructure *structure;
*format = g_value_get_enum (gst_structure_get_value (structure, "format"));
if (cur)
*cur = g_value_get_int64 (gst_structure_get_value (structure, "cur"));
- if (end)
- *end = g_value_get_int64 (gst_structure_get_value (structure, "end"));
+}
+
+
+/**
+ * gst_query_new_duration:
+ * @format: the default #GstFormat for the new query
+ *
+ * Constructs a new stream duration query object. Use gst_query_unref()
+ * when done with it.
+ *
+ * Returns: A new #GstQuery
+ */
+GstQuery *
+gst_query_new_duration (GstFormat format)
+{
+ GstQuery *query;
+ GstStructure *structure;
+
+ structure = gst_structure_new ("GstQueryDuration",
+ "format", GST_TYPE_FORMAT, format,
+ "duration", G_TYPE_INT64, (gint64) - 1, NULL);
+ query = gst_query_new (GST_QUERY_DURATION, structure);
+
+ return query;
+}
+
+/**
+ * gst_query_set_duration:
+ * @query: the query to fill in
+ * @format: the requested #GstFormat
+ * @duration: the total duration
+ *
+ * Answer a duration query by setting the requested values.
+ */
+void
+gst_query_set_duration (GstQuery * query, GstFormat format, gint64 duration)
+{
+ GstStructure *structure;
+
+ g_return_if_fail (GST_QUERY_TYPE (query) == GST_QUERY_DURATION);
+
+ structure = gst_query_get_structure (query);
+ gst_structure_set (structure,
+ "format", GST_TYPE_FORMAT, format,
+ "duration", G_TYPE_INT64, duration, NULL);
+}
+
+/**
+ * gst_query_parse_duration:
+ * @query: the query to parse
+ * @format: the storage for the #GstFormat of the duration value
+ * @duration: the storage for the total duration
+ *
+ * Parse a duration query answer.
+ */
+void
+gst_query_parse_duration (GstQuery * query, GstFormat * format,
+ gint64 * duration)
+{
+ GstStructure *structure;
+
+ g_return_if_fail (GST_QUERY_TYPE (query) == GST_QUERY_DURATION);
+
+ structure = gst_query_get_structure (query);
+ if (format)
+ *format = g_value_get_enum (gst_structure_get_value (structure, "format"));
+ if (duration)
+ *duration =
+ g_value_get_int64 (gst_structure_get_value (structure, "duration"));
}
/**
* @format: the #GstFormat of the segment values
* @start_value: the start value
* @stop_value: the stop value
- * @base: the base value
*
* Answer a segment query by setting the requested values.
*/
void
gst_query_set_segment (GstQuery * query, gdouble rate, GstFormat format,
- gint64 start_value, gint64 stop_value, gint64 base)
+ gint64 start_value, gint64 stop_value)
{
GstStructure *structure;
"rate", G_TYPE_DOUBLE, rate,
"format", GST_TYPE_FORMAT, format,
"start_value", G_TYPE_INT64, start_value,
- "stop_value", G_TYPE_INT64, stop_value, "base", G_TYPE_INT64, base, NULL);
+ "stop_value", G_TYPE_INT64, stop_value, NULL);
}
/**
* @format: the storage for the #GstFormat of the values
* @start_value: the storage for the start value
* @stop_value: the storage for the stop value
- * @base: the storage for the base value
*
* Parse a segment query answer.
*/
void
gst_query_parse_segment (GstQuery * query, gdouble * rate, GstFormat * format,
- gint64 * start_value, gint64 * stop_value, gint64 * base)
+ gint64 * start_value, gint64 * stop_value)
{
GstStructure *structure;
if (stop_value)
*stop_value =
g_value_get_int64 (gst_structure_get_value (structure, "stop_value"));
- if (base)
- *base = g_value_get_int64 (gst_structure_get_value (structure, "base"));
}
/**
/**
* GstQueryType:
* @GST_QUERY_NONE: invalid query type
- * @GST_QUERY_POSITION: current/end position in stream
+ * @GST_QUERY_POSITION: current position in stream
+ * @GST_QUERY_DURATION: total duration of the stream
* @GST_QUERY_LATENCY: latency of stream
* @GST_QUERY_JITTER: current jitter of stream
* @GST_QUERY_RATE: current rate of the stream
typedef enum {
GST_QUERY_NONE = 0,
GST_QUERY_POSITION,
+ GST_QUERY_DURATION,
GST_QUERY_LATENCY,
GST_QUERY_JITTER, /* not in draft-query, necessary? */
GST_QUERY_RATE,
/* position query */
GstQuery* gst_query_new_position (GstFormat format);
-void gst_query_set_position (GstQuery *query, GstFormat format,
- gint64 cur, gint64 end);
-void gst_query_parse_position (GstQuery *query, GstFormat *format,
- gint64 *cur, gint64 *end);
+void gst_query_set_position (GstQuery *query, GstFormat format, gint64 cur);
+void gst_query_parse_position (GstQuery *query, GstFormat *format, gint64 *cur);
+
+/* duration query */
+GstQuery* gst_query_new_duration (GstFormat format);
+void gst_query_set_duration (GstQuery *query, GstFormat format, gint64 duration);
+void gst_query_parse_duration (GstQuery *query, GstFormat *format, gint64 *duration);
+
/* convert query */
GstQuery* gst_query_new_convert (GstFormat src_fmt, gint64 value, GstFormat dest_fmt);
void gst_query_set_convert (GstQuery *query, GstFormat src_format, gint64 src_value,
/* segment query */
GstQuery* gst_query_new_segment (GstFormat format);
void gst_query_set_segment (GstQuery *query, gdouble rate, GstFormat format,
- gint64 start_value, gint64 stop_value, gint64 base);
+ gint64 start_value, gint64 stop_value);
void gst_query_parse_segment (GstQuery *query, gdouble *rate, GstFormat *format,
- gint64 *start_value, gint64 *stop_value, gint64 *base);
+ gint64 *start_value, gint64 *stop_value);
/* application specific query */
switch (GST_QUERY_TYPE (query)) {
case GST_QUERY_POSITION:
{
- gint64 peer_pos, peer_total;
+ gint64 peer_pos;
GstFormat format;
/* get peer position */
- gst_query_parse_position (query, &format, &peer_pos, &peer_total);
+ gst_query_parse_position (query, &format, &peer_pos);
/* FIXME: this code assumes that there's no discont in the queue */
switch (format) {
peer_pos -= queue->cur_level.time;
break;
default:
- /* FIXME */
- break;
+ return FALSE;
}
- /* set updated positions */
- gst_query_set_position (query, format, peer_pos, peer_total);
+ /* set updated position */
+ gst_query_set_position (query, format, peer_pos);
break;
}
default:
+ /* peer handled other queries */
break;
}
}
}
+/**
+ * gst_element_query_position:
+ * @element: a #GstElement to invoke the position query on.
+ * @format: a pointer to the #GstFormat asked for.
+ * On return contains the #GstFormat used.
+ * @cur: A location in which to store the current position, or NULL.
+ *
+ * Queries an element for the stream position.
+ *
+ * Returns: TRUE if the query could be performed.
+ */
gboolean
gst_element_query_position (GstElement * element, GstFormat * format,
- gint64 * cur, gint64 * end)
+ gint64 * cur)
{
GstQuery *query;
gboolean ret;
ret = gst_element_query (element, query);
if (ret)
- gst_query_parse_position (query, format, cur, end);
+ gst_query_parse_position (query, format, cur);
gst_query_unref (query);
return ret;
}
+/**
+ * gst_element_query_duration:
+ * @element: a #GstElement to invoke the duration query on.
+ * @format: a pointer to the #GstFormat asked for.
+ * On return contains the #GstFormat used.
+ * @cur: A location in which to store the total duration, or NULL.
+ *
+ * Queries an element for the total stream duration.
+ *
+ * Returns: TRUE if the query could be performed.
+ */
+gboolean
+gst_element_query_duration (GstElement * element, GstFormat * format,
+ gint64 * duration)
+{
+ GstQuery *query;
+ gboolean ret;
+
+ g_return_val_if_fail (GST_IS_ELEMENT (element), FALSE);
+ g_return_val_if_fail (format != NULL, FALSE);
+
+ query = gst_query_new_duration (*format);
+ ret = gst_element_query (element, query);
+
+ if (ret)
+ gst_query_parse_duration (query, format, duration);
+
+ gst_query_unref (query);
+
+ return ret;
+}
+
+/**
+ * gst_element_query_convert:
+ * @element: a #GstElement to invoke the convert query on.
+ * @src_format: a #GstFormat to convert from.
+ * @src_val: a value to convert.
+ * @dest_format: a pointer to the #GstFormat to convert to.
+ * @dest_val: a pointer to the result.
+ *
+ * Queries an element to convert @src_val in @src_format to @dest_format.
+ *
+ * Returns: TRUE if the query could be performed.
+ */
gboolean
gst_element_query_convert (GstElement * element, GstFormat src_format,
gint64 src_val, GstFormat * dest_fmt, gint64 * dest_val)
return ret;
}
-
/**
* gst_pad_can_link:
* @srcpad: the source #GstPad to link.
* @format: a pointer to the #GstFormat asked for.
* On return contains the #GstFormat used.
* @cur: A location in which to store the current position, or NULL.
- * @end: A location in which to store the end position (length), or NULL.
*
- * Queries a pad for the stream position and length.
+ * Queries a pad for the stream position.
*
* Returns: TRUE if the query could be performed.
*/
gboolean
-gst_pad_query_position (GstPad * pad, GstFormat * format, gint64 * cur,
- gint64 * end)
+gst_pad_query_position (GstPad * pad, GstFormat * format, gint64 * cur)
{
GstQuery *query;
gboolean ret;
ret = gst_pad_query (pad, query);
if (ret)
- gst_query_parse_position (query, format, cur, end);
+ gst_query_parse_position (query, format, cur);
+
+ gst_query_unref (query);
+
+ return ret;
+}
+
+/**
+ * gst_pad_query_duration:
+ * @pad: a #GstPad to invoke the duration query on.
+ * @format: a pointer to the #GstFormat asked for.
+ * On return contains the #GstFormat used.
+ * @cur: A location in which to store the total duration, or NULL.
+ *
+ * Queries a pad for the total stream duration.
+ *
+ * Returns: TRUE if the query could be performed.
+ */
+gboolean
+gst_pad_query_duration (GstPad * pad, GstFormat * format, gint64 * duration)
+{
+ GstQuery *query;
+ gboolean ret;
+
+ g_return_val_if_fail (GST_IS_PAD (pad), FALSE);
+ g_return_val_if_fail (format != NULL, FALSE);
+
+ query = gst_query_new_duration (*format);
+ ret = gst_pad_query (pad, query);
+
+ if (ret)
+ gst_query_parse_duration (query, format, duration);
gst_query_unref (query);
/* util query functions */
gboolean gst_element_query_position (GstElement *element, GstFormat *format,
- gint64 *cur, gint64 *end);
+ gint64 *cur);
+gboolean gst_element_query_duration (GstElement *element, GstFormat *format,
+ gint64 *duration);
gboolean gst_element_query_convert (GstElement *element, GstFormat src_format, gint64 src_val,
GstFormat *dest_fmt, gint64 *dest_val);
/* util query functions */
gboolean gst_pad_query_position (GstPad *pad, GstFormat *format,
- gint64 *cur, gint64 *end);
+ gint64 *cur);
+gboolean gst_pad_query_duration (GstPad *pad, GstFormat *format,
+ gint64 *duration);
gboolean gst_pad_query_convert (GstPad *pad, GstFormat src_format, gint64 src_val,
GstFormat *dest_format, gint64 *dest_val);
break;
case GST_QUERY_SEGMENT:
{
+ /* FIXME, bring start/stop to stream time */
gst_query_set_segment (query, basesink->segment_rate,
- GST_FORMAT_TIME, basesink->segment_start, basesink->segment_stop,
- basesink->segment_time);
+ GST_FORMAT_TIME, basesink->segment_start, basesink->segment_stop);
break;
}
case GST_QUERY_CONVERT:
{
GstFormat format;
- gst_query_parse_position (query, &format, NULL, NULL);
+ gst_query_parse_position (query, &format, NULL);
switch (format) {
case GST_FORMAT_DEFAULT:
case GST_FORMAT_BYTES:
- b = gst_base_src_get_size (src, &ui64);
- /* better to make get_size take an int64 */
- i64 = b ? (gint64) ui64 : -1;
- gst_query_set_position (query, GST_FORMAT_BYTES, src->offset, i64);
+ gst_query_set_position (query, GST_FORMAT_BYTES, src->offset);
return TRUE;
case GST_FORMAT_PERCENT:
b = gst_base_src_get_size (src, &ui64);
if (b)
i64 *= gst_guint64_to_gdouble (src->offset)
/ gst_guint64_to_gdouble (ui64);
- gst_query_set_position (query, GST_FORMAT_PERCENT,
- i64, GST_FORMAT_PERCENT_MAX);
+ gst_query_set_position (query, GST_FORMAT_PERCENT, i64);
+ return TRUE;
+ default:
+ return FALSE;
+ }
+ }
+ case GST_QUERY_DURATION:
+ {
+ GstFormat format;
+
+ gst_query_parse_duration (query, &format, NULL);
+ switch (format) {
+ case GST_FORMAT_DEFAULT:
+ case GST_FORMAT_BYTES:
+ b = gst_base_src_get_size (src, &ui64);
+ /* better to make get_size take an int64 */
+ i64 = b ? (gint64) ui64 : -1;
+ gst_query_set_duration (query, GST_FORMAT_BYTES, i64);
+ return TRUE;
+ case GST_FORMAT_PERCENT:
+ gst_query_set_duration (query, GST_FORMAT_PERCENT,
+ GST_FORMAT_PERCENT_MAX);
return TRUE;
default:
return FALSE;
switch (GST_QUERY_TYPE (query)) {
case GST_QUERY_POSITION:
- gst_query_parse_position (query, &format, NULL, NULL);
+ gst_query_parse_position (query, &format, NULL);
switch (format) {
case GST_FORMAT_DEFAULT:
case GST_FORMAT_BYTES:
- gst_query_set_position (query, GST_FORMAT_BYTES,
- self->data_written, self->data_written);
+ gst_query_set_position (query, GST_FORMAT_BYTES, self->data_written);
return TRUE;
default:
return FALSE;
switch (GST_QUERY_TYPE (query)) {
case GST_QUERY_POSITION:
{
- gint64 peer_pos, peer_total;
+ gint64 peer_pos;
GstFormat format;
/* get peer position */
- gst_query_parse_position (query, &format, &peer_pos, &peer_total);
+ gst_query_parse_position (query, &format, &peer_pos);
/* FIXME: this code assumes that there's no discont in the queue */
switch (format) {
peer_pos -= queue->cur_level.time;
break;
default:
- /* FIXME */
- break;
+ return FALSE;
}
- /* set updated positions */
- gst_query_set_position (query, format, peer_pos, peer_total);
+ /* set updated position */
+ gst_query_set_position (query, format, peer_pos);
break;
}
default:
+ /* peer handled other queries */
break;
}
switch (GST_QUERY_TYPE (query)) {
case GST_QUERY_POSITION:
{
- gint64 peer_pos, peer_total;
+ gint64 peer_pos;
GstFormat format;
if (typefind->store == NULL)
return TRUE;
- gst_query_parse_position (query, &format, &peer_pos, &peer_total);
+ gst_query_parse_position (query, &format, &peer_pos);
/* FIXME: this code assumes that there's no discont in the queue */
switch (format) {
/* FIXME */
break;
}
- gst_query_set_position (query, format, peer_pos, peer_total);
+ gst_query_set_position (query, format, peer_pos);
break;
}
default:
return 0;
}
if (entry->self->stream_length == 0) {
- if (!gst_pad_query_position (GST_PAD_PEER (entry->self->sink), &format,
- NULL, (gint64 *) & entry->self->stream_length))
+ if (!gst_pad_query_duration (GST_PAD_PEER (entry->self->sink), &format,
+ (gint64 *) & entry->self->stream_length))
goto no_length;
if (format != GST_FORMAT_BYTES) {
gint64 size;
GstFormat format = GST_FORMAT_BYTES;
- gst_pad_query_position (peer, &format, NULL, &size);
+ gst_pad_query_duration (peer, &format, &size);
found_caps = gst_type_find_helper (peer, (guint64) size);
gst_object_unref (peer);
}