mirror of
https://gitlab.freedesktop.org/gstreamer/gstreamer.git
synced 2025-02-04 13:32:29 +00:00
add new API for framestepping
Add new STEP event and methods for creating/parsing the event Update design docs. Add new STEP_DONE message and method to create/parse. API: GstEvent::gst_event_new_step() API: GstEvent::gst_event_parse_step() API: GstMessage::gst_message_new_step_done() API: GstMessage::gst_message_parse_step_done()
This commit is contained in:
parent
a565dbd1f3
commit
386c516e51
9 changed files with 214 additions and 15 deletions
|
@ -114,15 +114,6 @@ events
|
||||||
rates here, use a seek with a negative rate first to reverse the playback
|
rates here, use a seek with a negative rate first to reverse the playback
|
||||||
direction.
|
direction.
|
||||||
|
|
||||||
"intermediate", G_TYPE_BOOLEAN
|
|
||||||
Signal that this step operation is an intermediate step, part of a series
|
|
||||||
of step operations. It is mostly interesting for stepping in the PAUSED state
|
|
||||||
because the sink will only perform a preroll after a non-intermediate step
|
|
||||||
operation completes. Intermediate steps are usefull to flush out data from
|
|
||||||
other sinks in order to not cause excessive queueing. In the PLAYING state
|
|
||||||
the intermediate flag has no visual effect. In all states, the intermediate
|
|
||||||
flag is passed to the corresponding GST_MESSAGE_STEP_DONE.
|
|
||||||
|
|
||||||
"flush", G_TYPE_BOOLEAN
|
"flush", G_TYPE_BOOLEAN
|
||||||
when flushing is TRUE, the step is performed immediatly:
|
when flushing is TRUE, the step is performed immediatly:
|
||||||
|
|
||||||
|
@ -143,7 +134,16 @@ events
|
||||||
- In the PLAYING state the step operation will be performed after the
|
- In the PLAYING state the step operation will be performed after the
|
||||||
current step operation completes. If there was no previous step
|
current step operation completes. If there was no previous step
|
||||||
operation, the step operation will be performed from the position of the
|
operation, the step operation will be performed from the position of the
|
||||||
last PAUSED state.
|
last PAUSED state.
|
||||||
|
|
||||||
|
"intermediate", G_TYPE_BOOLEAN
|
||||||
|
Signal that this step operation is an intermediate step, part of a series
|
||||||
|
of step operations. It is mostly interesting for stepping in the PAUSED state
|
||||||
|
because the sink will only perform a preroll after a non-intermediate step
|
||||||
|
operation completes. Intermediate steps are usefull to flush out data from
|
||||||
|
other sinks in order to not cause excessive queueing. In the PLAYING state
|
||||||
|
the intermediate flag has no visual effect. In all states, the intermediate
|
||||||
|
flag is passed to the corresponding GST_MESSAGE_STEP_DONE.
|
||||||
|
|
||||||
|
|
||||||
The application will create a STEP event to start or stop the stepping
|
The application will create a STEP event to start or stop the stepping
|
||||||
|
@ -180,12 +180,12 @@ messages
|
||||||
"rate", G_TYPE_DOUBLE
|
"rate", G_TYPE_DOUBLE
|
||||||
The rate and direction at which the frames were stepped.
|
The rate and direction at which the frames were stepped.
|
||||||
|
|
||||||
"intermediate", G_TYPE_BOOLEAN
|
|
||||||
If this is an intermediate step operation that completed.
|
|
||||||
|
|
||||||
"duration", G_TYPE_UINT64
|
"duration", G_TYPE_UINT64
|
||||||
The total duration of the stepped units in GST_FORMAT_TIME.
|
The total duration of the stepped units in GST_FORMAT_TIME.
|
||||||
|
|
||||||
|
"intermediate", G_TYPE_BOOLEAN
|
||||||
|
If this is an intermediate step operation that completed.
|
||||||
|
|
||||||
The message is emited by the element that performs the step operation.
|
The message is emited by the element that performs the step operation.
|
||||||
|
|
||||||
|
|
||||||
|
|
|
@ -743,6 +743,9 @@ gst_event_new_navigation
|
||||||
|
|
||||||
gst_event_new_latency
|
gst_event_new_latency
|
||||||
gst_event_parse_latency
|
gst_event_parse_latency
|
||||||
|
|
||||||
|
gst_event_new_step
|
||||||
|
gst_event_parse_step
|
||||||
<SUBSECTION Standard>
|
<SUBSECTION Standard>
|
||||||
GstEventClass
|
GstEventClass
|
||||||
GST_EVENT
|
GST_EVENT
|
||||||
|
@ -1121,6 +1124,8 @@ gst_message_parse_buffering_stats
|
||||||
gst_message_new_state_changed
|
gst_message_new_state_changed
|
||||||
gst_message_parse_state_changed
|
gst_message_parse_state_changed
|
||||||
gst_message_new_state_dirty
|
gst_message_new_state_dirty
|
||||||
|
gst_message_new_step_done
|
||||||
|
gst_message_parse_step_done
|
||||||
gst_message_new_clock_provide
|
gst_message_new_clock_provide
|
||||||
gst_message_parse_clock_provide
|
gst_message_parse_clock_provide
|
||||||
gst_message_new_clock_lost
|
gst_message_new_clock_lost
|
||||||
|
|
|
@ -1088,3 +1088,90 @@ gst_event_parse_latency (GstEvent * event, GstClockTime * latency)
|
||||||
g_value_get_uint64 (gst_structure_id_get_value (structure,
|
g_value_get_uint64 (gst_structure_id_get_value (structure,
|
||||||
GST_QUARK (LATENCY)));
|
GST_QUARK (LATENCY)));
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* gst_event_new_step:
|
||||||
|
* @format: the format of @amount
|
||||||
|
* @amount: the amount of data to step
|
||||||
|
* @rate: the step rate
|
||||||
|
* @flush: flushing steps
|
||||||
|
* @intermediate: intermediate steps
|
||||||
|
*
|
||||||
|
* Create a new step event. The purpose of the step event is to instruct a sink
|
||||||
|
* to skip @amount (expressed in @format) of media. It can be used to implement
|
||||||
|
* stepping through the video frame by frame or for doing fast trick modes.
|
||||||
|
*
|
||||||
|
* A rate of <= 0.0 is not allowed, pause the pipeline or reverse the playback
|
||||||
|
* direction of the pipeline to get the same effect.
|
||||||
|
*
|
||||||
|
* The @flush flag will clear any pending data in the pipeline before starting
|
||||||
|
* the step operation.
|
||||||
|
*
|
||||||
|
* The @intermediate flag instructs the pipeline that this step operation is
|
||||||
|
* part of a larger step operation.
|
||||||
|
*
|
||||||
|
* Returns: a new #GstEvent
|
||||||
|
*
|
||||||
|
* Since: 0.10.24
|
||||||
|
*/
|
||||||
|
GstEvent *
|
||||||
|
gst_event_new_step (GstFormat format, guint64 amount, gdouble rate,
|
||||||
|
gboolean flush, gboolean intermediate)
|
||||||
|
{
|
||||||
|
GstEvent *event;
|
||||||
|
GstStructure *structure;
|
||||||
|
|
||||||
|
g_return_val_if_fail (rate > 0.0, NULL);
|
||||||
|
|
||||||
|
GST_CAT_INFO (GST_CAT_EVENT, "creating step event");
|
||||||
|
|
||||||
|
structure = gst_structure_id_new (GST_QUARK (EVENT_STEP),
|
||||||
|
GST_QUARK (FORMAT), GST_TYPE_FORMAT, format,
|
||||||
|
GST_QUARK (AMOUNT), G_TYPE_UINT64, amount,
|
||||||
|
GST_QUARK (RATE), G_TYPE_DOUBLE, rate,
|
||||||
|
GST_QUARK (FLUSH), G_TYPE_BOOLEAN, flush,
|
||||||
|
GST_QUARK (INTERMEDIATE), G_TYPE_BOOLEAN, intermediate, NULL);
|
||||||
|
event = gst_event_new_custom (GST_EVENT_STEP, structure);
|
||||||
|
|
||||||
|
return event;
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* gst_event_parse_step:
|
||||||
|
* @event: The event to query
|
||||||
|
* @format: A pointer to store the format in.
|
||||||
|
* @amount: A pointer to store the amount in.
|
||||||
|
* @rate: A pointer to store the rate in.
|
||||||
|
* @flush: A pointer to store the flush boolean in.
|
||||||
|
* @intermediate: A pointer to store the intermediate boolean in.
|
||||||
|
*
|
||||||
|
* Parse the step event.
|
||||||
|
*
|
||||||
|
* Since: 0.10.24
|
||||||
|
*/
|
||||||
|
void
|
||||||
|
gst_event_parse_step (GstEvent * event, GstFormat * format, guint64 * amount,
|
||||||
|
gdouble * rate, gboolean * flush, gboolean * intermediate)
|
||||||
|
{
|
||||||
|
const GstStructure *structure;
|
||||||
|
|
||||||
|
g_return_if_fail (GST_IS_EVENT (event));
|
||||||
|
g_return_if_fail (GST_EVENT_TYPE (event) == GST_EVENT_STEP);
|
||||||
|
|
||||||
|
structure = gst_event_get_structure (event);
|
||||||
|
if (format)
|
||||||
|
*format = g_value_get_enum (gst_structure_id_get_value (structure,
|
||||||
|
GST_QUARK (FORMAT)));
|
||||||
|
if (amount)
|
||||||
|
*amount = g_value_get_uint64 (gst_structure_id_get_value (structure,
|
||||||
|
GST_QUARK (AMOUNT)));
|
||||||
|
if (rate)
|
||||||
|
*rate = g_value_get_double (gst_structure_id_get_value (structure,
|
||||||
|
GST_QUARK (RATE)));
|
||||||
|
if (flush)
|
||||||
|
*flush = g_value_get_boolean (gst_structure_id_get_value (structure,
|
||||||
|
GST_QUARK (FLUSH)));
|
||||||
|
if (intermediate)
|
||||||
|
*intermediate = g_value_get_boolean (gst_structure_id_get_value (structure,
|
||||||
|
GST_QUARK (INTERMEDIATE)));
|
||||||
|
}
|
||||||
|
|
|
@ -92,6 +92,7 @@ typedef enum {
|
||||||
* user requests, such as mouse or keyboard movements,
|
* user requests, such as mouse or keyboard movements,
|
||||||
* to upstream elements.
|
* to upstream elements.
|
||||||
* @GST_EVENT_LATENCY: Notification of new latency adjustment. Since: 0.10.12
|
* @GST_EVENT_LATENCY: Notification of new latency adjustment. Since: 0.10.12
|
||||||
|
* @GST_EVENT_STEP: A request for stepping through the media. Since: 0.10.24
|
||||||
* @GST_EVENT_CUSTOM_UPSTREAM: Upstream custom event
|
* @GST_EVENT_CUSTOM_UPSTREAM: Upstream custom event
|
||||||
* @GST_EVENT_CUSTOM_DOWNSTREAM: Downstream custom event that travels in the
|
* @GST_EVENT_CUSTOM_DOWNSTREAM: Downstream custom event that travels in the
|
||||||
* data flow.
|
* data flow.
|
||||||
|
@ -124,6 +125,7 @@ typedef enum {
|
||||||
GST_EVENT_SEEK = GST_EVENT_MAKE_TYPE (16, FLAG(UPSTREAM)),
|
GST_EVENT_SEEK = GST_EVENT_MAKE_TYPE (16, FLAG(UPSTREAM)),
|
||||||
GST_EVENT_NAVIGATION = GST_EVENT_MAKE_TYPE (17, FLAG(UPSTREAM)),
|
GST_EVENT_NAVIGATION = GST_EVENT_MAKE_TYPE (17, FLAG(UPSTREAM)),
|
||||||
GST_EVENT_LATENCY = GST_EVENT_MAKE_TYPE (18, FLAG(UPSTREAM)),
|
GST_EVENT_LATENCY = GST_EVENT_MAKE_TYPE (18, FLAG(UPSTREAM)),
|
||||||
|
GST_EVENT_STEP = GST_EVENT_MAKE_TYPE (19, FLAG(UPSTREAM)),
|
||||||
|
|
||||||
/* custom events start here */
|
/* custom events start here */
|
||||||
GST_EVENT_CUSTOM_UPSTREAM = GST_EVENT_MAKE_TYPE (32, FLAG(UPSTREAM)),
|
GST_EVENT_CUSTOM_UPSTREAM = GST_EVENT_MAKE_TYPE (32, FLAG(UPSTREAM)),
|
||||||
|
@ -460,6 +462,12 @@ GstEvent* gst_event_new_navigation (GstStructure *structure);
|
||||||
GstEvent* gst_event_new_latency (GstClockTime latency);
|
GstEvent* gst_event_new_latency (GstClockTime latency);
|
||||||
void gst_event_parse_latency (GstEvent *event, GstClockTime *latency);
|
void gst_event_parse_latency (GstEvent *event, GstClockTime *latency);
|
||||||
|
|
||||||
|
/* step event */
|
||||||
|
GstEvent* gst_event_new_step (GstFormat format, guint64 amount, gdouble rate,
|
||||||
|
gboolean flush, gboolean intermediate);
|
||||||
|
void gst_event_parse_step (GstEvent *event, GstFormat *format, guint64 *amount,
|
||||||
|
gdouble *rate, gboolean *flush, gboolean *intermediate);
|
||||||
|
|
||||||
G_END_DECLS
|
G_END_DECLS
|
||||||
|
|
||||||
#endif /* __GST_EVENT_H__ */
|
#endif /* __GST_EVENT_H__ */
|
||||||
|
|
|
@ -1634,3 +1634,85 @@ gst_message_get_stream_status_object (GstMessage * message)
|
||||||
|
|
||||||
return result;
|
return result;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* gst_message_new_step_done:
|
||||||
|
* @src: The object originating the message.
|
||||||
|
* @format: the format of @amount
|
||||||
|
* @amount: the amount of stepped data
|
||||||
|
* @rate: the rate of the stepped amount
|
||||||
|
* @duration: the duration of the data
|
||||||
|
* @intermediate: is this an intermediate step
|
||||||
|
*
|
||||||
|
* This message is posted by elements when they complete a part, when @intermediate set
|
||||||
|
* to TRUE, or a complete step operation.
|
||||||
|
*
|
||||||
|
* @duration will contain the amount of time (in GST_FORMAT_TIME) of the stepped
|
||||||
|
* @amount of media in format @format.
|
||||||
|
*
|
||||||
|
* Returns: The new step_done message.
|
||||||
|
*
|
||||||
|
* MT safe.
|
||||||
|
*
|
||||||
|
* Since: 0.10.24
|
||||||
|
*/
|
||||||
|
GstMessage *
|
||||||
|
gst_message_new_step_done (GstObject * src, GstFormat format, guint64 amount,
|
||||||
|
gdouble rate, guint64 duration, gboolean intermediate)
|
||||||
|
{
|
||||||
|
GstMessage *message;
|
||||||
|
GstStructure *structure;
|
||||||
|
|
||||||
|
structure = gst_structure_id_new (GST_QUARK (MESSAGE_STEP_DONE),
|
||||||
|
GST_QUARK (FORMAT), GST_TYPE_FORMAT, format,
|
||||||
|
GST_QUARK (AMOUNT), G_TYPE_UINT64, amount,
|
||||||
|
GST_QUARK (RATE), G_TYPE_DOUBLE, rate,
|
||||||
|
GST_QUARK (DURATION), G_TYPE_UINT64, duration,
|
||||||
|
GST_QUARK (INTERMEDIATE), G_TYPE_BOOLEAN, intermediate, NULL);
|
||||||
|
message = gst_message_new_custom (GST_MESSAGE_STEP_DONE, src, structure);
|
||||||
|
|
||||||
|
return message;
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* gst_message_parse_step_done:
|
||||||
|
* @message: A valid #GstMessage of type GST_MESSAGE_STEP_DONE.
|
||||||
|
* @format: result location for the format
|
||||||
|
* @amount: result location for the amount
|
||||||
|
* @rate: result location for the rate
|
||||||
|
* @duration: result location for the duration
|
||||||
|
* @intermediate: result location for the intermediate flag
|
||||||
|
*
|
||||||
|
* Extract the requested state from the request_state message.
|
||||||
|
*
|
||||||
|
* MT safe.
|
||||||
|
*
|
||||||
|
* Since: 0.10.24
|
||||||
|
*/
|
||||||
|
void
|
||||||
|
gst_message_parse_step_done (GstMessage * message, GstFormat * format,
|
||||||
|
guint64 * amount, gdouble * rate, guint64 * duration,
|
||||||
|
gboolean * intermediate)
|
||||||
|
{
|
||||||
|
g_return_if_fail (GST_IS_MESSAGE (message));
|
||||||
|
g_return_if_fail (GST_MESSAGE_TYPE (message) == GST_MESSAGE_STEP_DONE);
|
||||||
|
|
||||||
|
if (format)
|
||||||
|
*format = g_value_get_enum (gst_structure_id_get_value (message->structure,
|
||||||
|
GST_QUARK (FORMAT)));
|
||||||
|
if (amount)
|
||||||
|
*amount =
|
||||||
|
g_value_get_uint64 (gst_structure_id_get_value (message->structure,
|
||||||
|
GST_QUARK (AMOUNT)));
|
||||||
|
if (rate)
|
||||||
|
*rate = g_value_get_double (gst_structure_id_get_value (message->structure,
|
||||||
|
GST_QUARK (RATE)));
|
||||||
|
if (duration)
|
||||||
|
*duration =
|
||||||
|
g_value_get_uint64 (gst_structure_id_get_value (message->structure,
|
||||||
|
GST_QUARK (DURATION)));
|
||||||
|
if (intermediate)
|
||||||
|
*intermediate =
|
||||||
|
g_value_get_boolean (gst_structure_id_get_value (message->structure,
|
||||||
|
GST_QUARK (INTERMEDIATE)));
|
||||||
|
}
|
||||||
|
|
|
@ -383,6 +383,12 @@ void gst_message_parse_state_changed (GstMessage *message, GstState *oldstate,
|
||||||
/* STATE_DIRTY */
|
/* STATE_DIRTY */
|
||||||
GstMessage * gst_message_new_state_dirty (GstObject * src);
|
GstMessage * gst_message_new_state_dirty (GstObject * src);
|
||||||
|
|
||||||
|
/* STEP_DONE */
|
||||||
|
GstMessage * gst_message_new_step_done (GstObject * src, GstFormat format, guint64 amount,
|
||||||
|
gdouble rate, guint64 duration, gboolean intermediate);
|
||||||
|
void gst_message_parse_step_done (GstMessage * message, GstFormat *format, guint64 *amount,
|
||||||
|
gdouble *rate, guint64 *duration, gboolean *intermediate);
|
||||||
|
|
||||||
/* CLOCK_PROVIDE */
|
/* CLOCK_PROVIDE */
|
||||||
GstMessage * gst_message_new_clock_provide (GstObject * src, GstClock *clock, gboolean ready);
|
GstMessage * gst_message_new_clock_provide (GstObject * src, GstClock *clock, gboolean ready);
|
||||||
void gst_message_parse_clock_provide (GstMessage *message, GstClock **clock,
|
void gst_message_parse_clock_provide (GstMessage *message, GstClock **clock,
|
||||||
|
|
|
@ -46,7 +46,8 @@ static const gchar *_quark_strings[] = {
|
||||||
"GstMessageAsyncStart", "GstMessageRequestState", "GstMessageStreamStatus",
|
"GstMessageAsyncStart", "GstMessageRequestState", "GstMessageStreamStatus",
|
||||||
"GstQueryPosition", "GstQueryDuration", "GstQueryLatency", "GstQueryConvert",
|
"GstQueryPosition", "GstQueryDuration", "GstQueryLatency", "GstQueryConvert",
|
||||||
"GstQuerySegment", "GstQuerySeeking", "GstQueryFormats", "GstQueryBuffering",
|
"GstQuerySegment", "GstQuerySeeking", "GstQueryFormats", "GstQueryBuffering",
|
||||||
"GstQueryURI"
|
"GstQueryURI", "GstEventStep", "GstMessageStepDone", "amount", "flush",
|
||||||
|
"intermediate"
|
||||||
};
|
};
|
||||||
|
|
||||||
GQuark _priv_gst_quark_table[GST_QUARK_MAX];
|
GQuark _priv_gst_quark_table[GST_QUARK_MAX];
|
||||||
|
|
|
@ -109,7 +109,13 @@ typedef enum _GstQuarkId
|
||||||
GST_QUARK_QUERY_FORMATS = 80,
|
GST_QUARK_QUERY_FORMATS = 80,
|
||||||
GST_QUARK_QUERY_BUFFERING = 81,
|
GST_QUARK_QUERY_BUFFERING = 81,
|
||||||
GST_QUARK_QUERY_URI = 82,
|
GST_QUARK_QUERY_URI = 82,
|
||||||
GST_QUARK_MAX = 83
|
GST_QUARK_EVENT_STEP = 83,
|
||||||
|
GST_QUARK_MESSAGE_STEP_DONE = 84,
|
||||||
|
GST_QUARK_AMOUNT = 85,
|
||||||
|
GST_QUARK_FLUSH = 86,
|
||||||
|
GST_QUARK_INTERMEDIATE = 87,
|
||||||
|
|
||||||
|
GST_QUARK_MAX = 88
|
||||||
} GstQuarkId;
|
} GstQuarkId;
|
||||||
|
|
||||||
extern GQuark _priv_gst_quark_table[GST_QUARK_MAX];
|
extern GQuark _priv_gst_quark_table[GST_QUARK_MAX];
|
||||||
|
|
|
@ -355,6 +355,7 @@ EXPORTS
|
||||||
gst_event_new_new_segment_full
|
gst_event_new_new_segment_full
|
||||||
gst_event_new_qos
|
gst_event_new_qos
|
||||||
gst_event_new_seek
|
gst_event_new_seek
|
||||||
|
gst_event_new_step
|
||||||
gst_event_new_tag
|
gst_event_new_tag
|
||||||
gst_event_parse_buffer_size
|
gst_event_parse_buffer_size
|
||||||
gst_event_parse_latency
|
gst_event_parse_latency
|
||||||
|
@ -362,6 +363,7 @@ EXPORTS
|
||||||
gst_event_parse_new_segment_full
|
gst_event_parse_new_segment_full
|
||||||
gst_event_parse_qos
|
gst_event_parse_qos
|
||||||
gst_event_parse_seek
|
gst_event_parse_seek
|
||||||
|
gst_event_parse_step
|
||||||
gst_event_parse_tag
|
gst_event_parse_tag
|
||||||
gst_event_set_seqnum
|
gst_event_set_seqnum
|
||||||
gst_event_type_flags_get_type
|
gst_event_type_flags_get_type
|
||||||
|
@ -489,6 +491,7 @@ EXPORTS
|
||||||
gst_message_new_segment_start
|
gst_message_new_segment_start
|
||||||
gst_message_new_state_changed
|
gst_message_new_state_changed
|
||||||
gst_message_new_state_dirty
|
gst_message_new_state_dirty
|
||||||
|
gst_message_new_step_done
|
||||||
gst_message_new_stream_status
|
gst_message_new_stream_status
|
||||||
gst_message_new_structure_change
|
gst_message_new_structure_change
|
||||||
gst_message_new_tag
|
gst_message_new_tag
|
||||||
|
@ -507,6 +510,7 @@ EXPORTS
|
||||||
gst_message_parse_segment_done
|
gst_message_parse_segment_done
|
||||||
gst_message_parse_segment_start
|
gst_message_parse_segment_start
|
||||||
gst_message_parse_state_changed
|
gst_message_parse_state_changed
|
||||||
|
gst_message_parse_step_done
|
||||||
gst_message_parse_stream_status
|
gst_message_parse_stream_status
|
||||||
gst_message_parse_structure_change
|
gst_message_parse_structure_change
|
||||||
gst_message_parse_tag
|
gst_message_parse_tag
|
||||||
|
|
Loading…
Reference in a new issue