mirror of
https://gitlab.freedesktop.org/gstreamer/gstreamer.git
synced 2024-12-28 03:00:35 +00:00
controller: move to core/gstobject
Move the controller to gstobject as a simple delegate. The controller and controlsource are not classes in core. The controlsources stay separate as a lib for now. This way we can avoid the qdata lookups. Also remove controller_init(). There is no more need to link to controller for elements. Also sanitize the API. We now have functions to add properties like we had methods to remove that. That avoids then ref count hacks we had in _new.
This commit is contained in:
parent
0f123cba23
commit
9a27b9c056
17 changed files with 512 additions and 612 deletions
|
@ -56,6 +56,8 @@ libgstreamer_@GST_MAJORMINOR@_la_SOURCES = \
|
|||
gstcaps.c \
|
||||
gstchildproxy.c \
|
||||
gstclock.c \
|
||||
gstcontroller.c \
|
||||
gstcontrolsource.c \
|
||||
gstdatetime.c \
|
||||
gstdebugutils.c \
|
||||
gstelement.c \
|
||||
|
@ -148,6 +150,8 @@ gst_headers = \
|
|||
gstchildproxy.h \
|
||||
gstclock.h \
|
||||
gstcompat.h \
|
||||
gstcontroller.h \
|
||||
gstcontrolsource.h \
|
||||
gstdatetime.h \
|
||||
gstdebugutils.h \
|
||||
gstelement.h \
|
||||
|
|
|
@ -44,6 +44,8 @@
|
|||
#include <gst/gstcaps.h>
|
||||
#include <gst/gstchildproxy.h>
|
||||
#include <gst/gstclock.h>
|
||||
#include <gst/gstcontroller.h>
|
||||
#include <gst/gstcontrolsource.h>
|
||||
#include <gst/gstdatetime.h>
|
||||
#include <gst/gstdebugutils.h>
|
||||
#include <gst/gstelement.h>
|
||||
|
|
|
@ -24,8 +24,6 @@
|
|||
#ifndef __GST_CLOCK_H__
|
||||
#define __GST_CLOCK_H__
|
||||
|
||||
#include <gst/gstobject.h>
|
||||
|
||||
G_BEGIN_DECLS
|
||||
|
||||
/* --- standard type macros --- */
|
||||
|
@ -375,6 +373,8 @@ struct _GstClockEntry {
|
|||
gboolean woken_up;
|
||||
};
|
||||
|
||||
#include <gst/gstobject.h>
|
||||
|
||||
/**
|
||||
* GstClockFlags:
|
||||
* @GST_CLOCK_FLAG_CAN_DO_SINGLE_SYNC: clock can do a single sync timeout request
|
||||
|
|
|
@ -1,7 +1,8 @@
|
|||
/* GStreamer
|
||||
*
|
||||
* Copyright (C) <2005> Stefan Kost <ensonic at users dot sf dot net>
|
||||
* Copyright (C) 2007 Sebastian Dröge <slomo@circular-chaos.org>
|
||||
* Copyright (C) 2005 Stefan Kost <ensonic at users dot sf dot net>
|
||||
* 2007 Sebastian Dröge <slomo@circular-chaos.org>
|
||||
* 2011 Stefan Sauer <ensonic at users dot sf dot net>
|
||||
*
|
||||
* gstcontroller.c: dynamic parameter control subsystem
|
||||
*
|
||||
|
@ -72,20 +73,19 @@
|
|||
* </orderedlist>
|
||||
*/
|
||||
|
||||
#ifdef HAVE_CONFIG_H
|
||||
# include "config.h"
|
||||
#endif
|
||||
#include "gst_private.h"
|
||||
|
||||
#include "gstobject.h"
|
||||
#include "gstclock.h"
|
||||
#include "gstinfo.h"
|
||||
#include "gstcontroller.h"
|
||||
#include "gstcontrollerprivate.h"
|
||||
#include "gstcontrolsource.h"
|
||||
#include "gstinterpolationcontrolsource.h"
|
||||
#include "gstparamspecs.h"
|
||||
|
||||
#define GST_CAT_DEFAULT controller_debug
|
||||
GST_DEBUG_CATEGORY_EXTERN (GST_CAT_DEFAULT);
|
||||
GST_DEBUG_CATEGORY (GST_CAT_DEFAULT);
|
||||
|
||||
static GObjectClass *parent_class = NULL;
|
||||
GQuark priv_gst_controller_key;
|
||||
|
||||
/* property ids */
|
||||
enum
|
||||
|
@ -101,6 +101,20 @@ struct _GstControllerPrivate
|
|||
|
||||
/* helper */
|
||||
|
||||
/*
|
||||
* GstControlledProperty:
|
||||
*/
|
||||
typedef struct _GstControlledProperty
|
||||
{
|
||||
GParamSpec *pspec; /* GParamSpec for this property */
|
||||
const gchar *name; /* name of the property */
|
||||
GstControlSource *csource; /* GstControlSource for this property */
|
||||
gboolean disabled;
|
||||
GValue last_value;
|
||||
} GstControlledProperty;
|
||||
|
||||
#define GST_CONTROLLED_PROPERTY(obj) ((GstControlledProperty *)(obj))
|
||||
|
||||
/*
|
||||
* gst_controlled_property_new:
|
||||
* @object: for which object the controlled property should be set up
|
||||
|
@ -112,7 +126,7 @@ struct _GstControllerPrivate
|
|||
* Returns: a freshly allocated structure or %NULL
|
||||
*/
|
||||
static GstControlledProperty *
|
||||
gst_controlled_property_new (GObject * object, const gchar * name)
|
||||
gst_controlled_property_new (GstObject * object, const gchar * name)
|
||||
{
|
||||
GstControlledProperty *prop = NULL;
|
||||
GParamSpec *pspec;
|
||||
|
@ -191,54 +205,56 @@ gst_controller_find_controlled_property (GstController * self,
|
|||
|
||||
/*
|
||||
* gst_controller_add_property:
|
||||
* @self: the controller object or %NULL if none yet exists
|
||||
* @object: object to bind the property
|
||||
* @self: the controller object
|
||||
* @name: name of projecty in @object
|
||||
* @ref_existing: pointer to flag that tracks if we need to ref an existing
|
||||
* controller still
|
||||
*
|
||||
* Creates a new #GstControlledProperty if there is none for property @name yet.
|
||||
* In case this is the first controlled propery, it creates the controller as
|
||||
* well.
|
||||
*
|
||||
* Returns: a newly created controller object or reffed existing one with the
|
||||
* given property bound.
|
||||
* Returns: %TRUE if the property has been added to the controller
|
||||
*/
|
||||
static GstController *
|
||||
gst_controller_add_property (GstController * self, GObject * object,
|
||||
const gchar * name, gboolean * ref_existing)
|
||||
static gboolean
|
||||
gst_controller_add_property (GstController * self, const gchar * name)
|
||||
{
|
||||
gboolean res = TRUE;
|
||||
|
||||
/* test if this property isn't yet controlled */
|
||||
if (!self || !gst_controller_find_controlled_property (self, name)) {
|
||||
if (!gst_controller_find_controlled_property (self, name)) {
|
||||
GstControlledProperty *prop;
|
||||
|
||||
/* create GstControlledProperty and add to self->propeties List */
|
||||
if ((prop = gst_controlled_property_new (object, name))) {
|
||||
/* if we don't have a controller object yet, now is the time to create one */
|
||||
if (!self) {
|
||||
self = g_object_newv (GST_TYPE_CONTROLLER, 0, NULL);
|
||||
self->object = g_object_ref (object);
|
||||
/* store the controller */
|
||||
g_object_set_qdata (object, priv_gst_controller_key, self);
|
||||
*ref_existing = FALSE;
|
||||
} else {
|
||||
/* only want one single _ref(), even for multiple properties */
|
||||
if (*ref_existing) {
|
||||
g_object_ref (self);
|
||||
*ref_existing = FALSE;
|
||||
GST_INFO ("returning existing controller");
|
||||
}
|
||||
}
|
||||
/* create GstControlledProperty and add to self->properties list */
|
||||
if ((prop = gst_controlled_property_new (self->object, name)))
|
||||
self->properties = g_list_prepend (self->properties, prop);
|
||||
}
|
||||
else
|
||||
res = FALSE;
|
||||
} else {
|
||||
GST_WARNING ("trying to control property %s again", name);
|
||||
if (*ref_existing) {
|
||||
g_object_ref (self);
|
||||
*ref_existing = FALSE;
|
||||
}
|
||||
}
|
||||
return self;
|
||||
return res;
|
||||
}
|
||||
|
||||
/*
|
||||
* gst_controller_remove_property:
|
||||
* @self: the controller object
|
||||
* @name: name of projecty in @object
|
||||
*
|
||||
* Removes a #GstControlledProperty for property @name.
|
||||
*
|
||||
* Returns: %TRUE if the property has been removed from the controller
|
||||
*/
|
||||
static gboolean
|
||||
gst_controller_remove_property (GstController * self, const gchar * name)
|
||||
{
|
||||
gboolean res = TRUE;
|
||||
GstControlledProperty *prop;
|
||||
|
||||
if ((prop = gst_controller_find_controlled_property (self, name))) {
|
||||
self->properties = g_list_remove (self->properties, prop);
|
||||
//g_signal_handler_disconnect (self->object, prop->notify_handler_id);
|
||||
gst_controlled_property_free (prop);
|
||||
} else {
|
||||
res = FALSE;
|
||||
}
|
||||
return res;
|
||||
}
|
||||
|
||||
/* methods */
|
||||
|
@ -253,25 +269,24 @@ gst_controller_add_property (GstController * self, GObject * object,
|
|||
* Returns: the new controller.
|
||||
*/
|
||||
GstController *
|
||||
gst_controller_new_valist (GObject * object, va_list var_args)
|
||||
gst_controller_new_valist (GstObject * object, va_list var_args)
|
||||
{
|
||||
GstController *self;
|
||||
gboolean ref_existing = TRUE;
|
||||
gchar *name;
|
||||
|
||||
g_return_val_if_fail (G_IS_OBJECT (object), NULL);
|
||||
|
||||
GST_INFO ("setting up a new controller");
|
||||
|
||||
self = g_object_get_qdata (object, priv_gst_controller_key);
|
||||
self = g_object_newv (GST_TYPE_CONTROLLER, 0, NULL);
|
||||
self->object = g_object_ref (object);
|
||||
|
||||
/* create GstControlledProperty for each property */
|
||||
while ((name = va_arg (var_args, gchar *))) {
|
||||
self = gst_controller_add_property (self, object, name, &ref_existing);
|
||||
gst_controller_add_property (self, name);
|
||||
}
|
||||
va_end (var_args);
|
||||
|
||||
if (self)
|
||||
GST_INFO ("controller->ref_count=%d", G_OBJECT (self)->ref_count);
|
||||
return self;
|
||||
}
|
||||
|
||||
|
@ -288,10 +303,9 @@ gst_controller_new_valist (GObject * object, va_list var_args)
|
|||
* Returns: the new controller.
|
||||
*/
|
||||
GstController *
|
||||
gst_controller_new_list (GObject * object, GList * list)
|
||||
gst_controller_new_list (GstObject * object, GList * list)
|
||||
{
|
||||
GstController *self;
|
||||
gboolean ref_existing = TRUE;
|
||||
gchar *name;
|
||||
GList *node;
|
||||
|
||||
|
@ -299,15 +313,15 @@ gst_controller_new_list (GObject * object, GList * list)
|
|||
|
||||
GST_INFO ("setting up a new controller");
|
||||
|
||||
self = g_object_get_qdata (object, priv_gst_controller_key);
|
||||
self = g_object_newv (GST_TYPE_CONTROLLER, 0, NULL);
|
||||
self->object = g_object_ref (object);
|
||||
|
||||
/* create GstControlledProperty for each property */
|
||||
for (node = list; node; node = g_list_next (node)) {
|
||||
name = (gchar *) node->data;
|
||||
self = gst_controller_add_property (self, object, name, &ref_existing);
|
||||
gst_controller_add_property (self, name);
|
||||
}
|
||||
|
||||
if (self)
|
||||
GST_INFO ("controller->ref_count=%d", G_OBJECT (self)->ref_count);
|
||||
return self;
|
||||
}
|
||||
|
||||
|
@ -321,7 +335,7 @@ gst_controller_new_list (GObject * object, GList * list)
|
|||
* Returns: the new controller.
|
||||
*/
|
||||
GstController *
|
||||
gst_controller_new (GObject * object, ...)
|
||||
gst_controller_new (GstObject * object, ...)
|
||||
{
|
||||
GstController *self;
|
||||
va_list var_args;
|
||||
|
@ -335,6 +349,63 @@ gst_controller_new (GObject * object, ...)
|
|||
return self;
|
||||
}
|
||||
|
||||
// FIXME: docs
|
||||
gboolean
|
||||
gst_controller_add_properties_valist (GstController * self, va_list var_args)
|
||||
{
|
||||
gboolean res = TRUE;
|
||||
gchar *name;
|
||||
|
||||
g_return_val_if_fail (GST_IS_CONTROLLER (self), FALSE);
|
||||
|
||||
while ((name = va_arg (var_args, gchar *))) {
|
||||
/* find the property in the properties list of the controller, remove and free it */
|
||||
g_mutex_lock (self->lock);
|
||||
res &= gst_controller_add_property (self, name);
|
||||
g_mutex_unlock (self->lock);
|
||||
}
|
||||
|
||||
return res;
|
||||
}
|
||||
|
||||
// FIXME: docs
|
||||
gboolean
|
||||
gst_controller_add_properties_list (GstController * self, GList * list)
|
||||
{
|
||||
gboolean res = TRUE;
|
||||
gchar *name;
|
||||
GList *tmp;
|
||||
|
||||
g_return_val_if_fail (GST_IS_CONTROLLER (self), FALSE);
|
||||
|
||||
for (tmp = list; tmp; tmp = g_list_next (tmp)) {
|
||||
name = (gchar *) tmp->data;
|
||||
|
||||
/* find the property in the properties list of the controller, remove and free it */
|
||||
g_mutex_lock (self->lock);
|
||||
res &= gst_controller_add_property (self, name);
|
||||
g_mutex_unlock (self->lock);
|
||||
}
|
||||
|
||||
return res;
|
||||
}
|
||||
|
||||
// FIXME: docs
|
||||
gboolean
|
||||
gst_controller_add_properties (GstController * self, ...)
|
||||
{
|
||||
gboolean res;
|
||||
va_list var_args;
|
||||
|
||||
g_return_val_if_fail (GST_IS_CONTROLLER (self), FALSE);
|
||||
|
||||
va_start (var_args, self);
|
||||
res = gst_controller_add_properties_valist (self, var_args);
|
||||
va_end (var_args);
|
||||
|
||||
return res;
|
||||
}
|
||||
|
||||
/**
|
||||
* gst_controller_remove_properties_valist:
|
||||
* @self: the controller object from which some properties should be removed
|
||||
|
@ -348,7 +419,6 @@ gboolean
|
|||
gst_controller_remove_properties_valist (GstController * self, va_list var_args)
|
||||
{
|
||||
gboolean res = TRUE;
|
||||
GstControlledProperty *prop;
|
||||
gchar *name;
|
||||
|
||||
g_return_val_if_fail (GST_IS_CONTROLLER (self), FALSE);
|
||||
|
@ -356,13 +426,7 @@ gst_controller_remove_properties_valist (GstController * self, va_list var_args)
|
|||
while ((name = va_arg (var_args, gchar *))) {
|
||||
/* find the property in the properties list of the controller, remove and free it */
|
||||
g_mutex_lock (self->lock);
|
||||
if ((prop = gst_controller_find_controlled_property (self, name))) {
|
||||
self->properties = g_list_remove (self->properties, prop);
|
||||
//g_signal_handler_disconnect (self->object, prop->notify_handler_id);
|
||||
gst_controlled_property_free (prop);
|
||||
} else {
|
||||
res = FALSE;
|
||||
}
|
||||
res &= gst_controller_remove_property (self, name);
|
||||
g_mutex_unlock (self->lock);
|
||||
}
|
||||
|
||||
|
@ -385,7 +449,6 @@ gboolean
|
|||
gst_controller_remove_properties_list (GstController * self, GList * list)
|
||||
{
|
||||
gboolean res = TRUE;
|
||||
GstControlledProperty *prop;
|
||||
gchar *name;
|
||||
GList *tmp;
|
||||
|
||||
|
@ -396,13 +459,7 @@ gst_controller_remove_properties_list (GstController * self, GList * list)
|
|||
|
||||
/* find the property in the properties list of the controller, remove and free it */
|
||||
g_mutex_lock (self->lock);
|
||||
if ((prop = gst_controller_find_controlled_property (self, name))) {
|
||||
self->properties = g_list_remove (self->properties, prop);
|
||||
//g_signal_handler_disconnect (self->object, prop->notify_handler_id);
|
||||
gst_controlled_property_free (prop);
|
||||
} else {
|
||||
res = FALSE;
|
||||
}
|
||||
res &= gst_controller_remove_property (self, name);
|
||||
g_mutex_unlock (self->lock);
|
||||
}
|
||||
|
||||
|
@ -598,7 +655,7 @@ gst_controller_get (GstController * self, const gchar * property_name,
|
|||
val = NULL;
|
||||
}
|
||||
} else {
|
||||
g_object_get_property (self->object, prop->name, val);
|
||||
g_object_get_property ((GObject *) self->object, prop->name, val);
|
||||
}
|
||||
}
|
||||
g_mutex_unlock (self->lock);
|
||||
|
@ -666,7 +723,7 @@ gst_controller_sync_values (GstController * self, GstClockTime timestamp)
|
|||
GST_LOG ("sync_values");
|
||||
|
||||
g_mutex_lock (self->lock);
|
||||
g_object_freeze_notify (self->object);
|
||||
g_object_freeze_notify ((GObject *) self->object);
|
||||
/* go over the controlled properties of the controller */
|
||||
for (node = self->properties; node; node = g_list_next (node)) {
|
||||
prop = node->data;
|
||||
|
@ -688,7 +745,7 @@ gst_controller_sync_values (GstController * self, GstClockTime timestamp)
|
|||
*/
|
||||
if ((timestamp < self->priv->last_sync) ||
|
||||
gst_value_compare (&value, &prop->last_value) != GST_VALUE_EQUAL) {
|
||||
g_object_set_property (self->object, prop->name, &value);
|
||||
g_object_set_property ((GObject *) self->object, prop->name, &value);
|
||||
g_value_copy (&value, &prop->last_value);
|
||||
}
|
||||
} else {
|
||||
|
@ -698,7 +755,7 @@ gst_controller_sync_values (GstController * self, GstClockTime timestamp)
|
|||
ret &= val_ret;
|
||||
}
|
||||
self->priv->last_sync = timestamp;
|
||||
g_object_thaw_notify (self->object);
|
||||
g_object_thaw_notify ((GObject *) self->object);
|
||||
|
||||
g_mutex_unlock (self->lock);
|
||||
|
||||
|
@ -871,8 +928,6 @@ _gst_controller_dispose (GObject * object)
|
|||
self->properties = NULL;
|
||||
}
|
||||
|
||||
/* remove controller from object's qdata list */
|
||||
g_object_set_qdata (self->object, priv_gst_controller_key, NULL);
|
||||
g_object_unref (self->object);
|
||||
self->object = NULL;
|
||||
g_mutex_unlock (self->lock);
|
||||
|
@ -919,8 +974,6 @@ _gst_controller_class_init (GstControllerClass * klass)
|
|||
gobject_class->dispose = _gst_controller_dispose;
|
||||
gobject_class->finalize = _gst_controller_finalize;
|
||||
|
||||
priv_gst_controller_key = g_quark_from_static_string ("gst::controller");
|
||||
|
||||
/* register properties */
|
||||
g_object_class_install_property (gobject_class, PROP_CONTROL_RATE,
|
||||
g_param_spec_uint64 ("control-rate",
|
||||
|
@ -929,8 +982,8 @@ _gst_controller_class_init (GstControllerClass * klass)
|
|||
1, G_MAXUINT, 100 * GST_MSECOND,
|
||||
G_PARAM_READWRITE | G_PARAM_STATIC_STRINGS));
|
||||
|
||||
/* register signals */
|
||||
/* set defaults for overridable methods */
|
||||
GST_DEBUG_CATEGORY_INIT (GST_CAT_DEFAULT, "gstcontroller", 0,
|
||||
"dynamic parameter control for gstreamer elements");
|
||||
}
|
||||
|
||||
GType
|
|
@ -1,8 +1,9 @@
|
|||
/* GStreamer
|
||||
*
|
||||
* Copyright (C) <2005> Stefan Kost <ensonic at users dot sf dot net>
|
||||
* Copyright (C) 2005 Stefan Kost <ensonic at users dot sf dot net>
|
||||
* 2011 Stefan Sauer <ensonic at users dot sf dot net>
|
||||
*
|
||||
* gst-controller.h: dynamic parameter control subsystem
|
||||
* gstcontroller.h: dynamic parameter control subsystem
|
||||
*
|
||||
* This library is free software; you can redistribute it and/or
|
||||
* modify it under the terms of the GNU Library General Public
|
||||
|
@ -23,15 +24,16 @@
|
|||
#ifndef __GST_CONTROLLER_H__
|
||||
#define __GST_CONTROLLER_H__
|
||||
|
||||
#include <gst/gstconfig.h>
|
||||
|
||||
#include <string.h>
|
||||
|
||||
#include <glib.h>
|
||||
#include <glib-object.h>
|
||||
#include <glib/gprintf.h>
|
||||
#include <gst/gst.h>
|
||||
|
||||
#include <gst/controller/gstcontrolsource.h>
|
||||
#include <gst/controller/gstinterpolationcontrolsource.h>
|
||||
#include <gst/gstobject.h>
|
||||
#include <gst/gstcontrolsource.h>
|
||||
|
||||
G_BEGIN_DECLS
|
||||
|
||||
|
@ -60,7 +62,7 @@ struct _GstController
|
|||
|
||||
GList *properties; /* List of GstControlledProperty */
|
||||
GMutex *lock; /* Secure property access, elements will access from threads */
|
||||
GObject *object; /* the object we control */
|
||||
GstObject *object; /* the object we control */
|
||||
|
||||
/*< private >*/
|
||||
GstControllerPrivate *priv;
|
||||
|
@ -79,14 +81,16 @@ GType gst_controller_get_type (void);
|
|||
|
||||
/* GstController functions */
|
||||
|
||||
GstController *gst_controller_new_valist (GObject * object, va_list var_args);
|
||||
GstController *gst_controller_new_list (GObject * object, GList *list);
|
||||
GstController *gst_controller_new (GObject * object, ...) G_GNUC_NULL_TERMINATED;
|
||||
GstController *gst_controller_new_valist (GstObject * object, va_list var_args);
|
||||
GstController *gst_controller_new_list (GstObject * object, GList *list);
|
||||
GstController *gst_controller_new (GstObject * object, ...) G_GNUC_NULL_TERMINATED;
|
||||
|
||||
gboolean gst_controller_remove_properties_valist (GstController * self,
|
||||
va_list var_args);
|
||||
gboolean gst_controller_remove_properties_list (GstController * self,
|
||||
GList *list);
|
||||
gboolean gst_controller_add_properties_valist (GstController * self, va_list var_args);
|
||||
gboolean gst_controller_add_properties_list (GstController * self, GList *list);
|
||||
gboolean gst_controller_add_properties (GstController * self, ...) G_GNUC_NULL_TERMINATED;
|
||||
|
||||
gboolean gst_controller_remove_properties_valist (GstController * self, va_list var_args);
|
||||
gboolean gst_controller_remove_properties_list (GstController * self, GList *list);
|
||||
gboolean gst_controller_remove_properties (GstController * self, ...) G_GNUC_NULL_TERMINATED;
|
||||
|
||||
void gst_controller_set_disabled (GstController *self, gboolean disabled);
|
||||
|
@ -105,32 +109,6 @@ gboolean gst_controller_get_value_arrays (GstController * self,
|
|||
gboolean gst_controller_get_value_array (GstController * self,
|
||||
GstClockTime timestamp, GstValueArray * value_array);
|
||||
|
||||
/* GObject convenience functions */
|
||||
|
||||
GstController *gst_object_control_properties (GObject * object, ...) G_GNUC_NULL_TERMINATED;
|
||||
gboolean gst_object_uncontrol_properties (GObject * object, ...) G_GNUC_NULL_TERMINATED;
|
||||
|
||||
GstController *gst_object_get_controller (GObject * object);
|
||||
gboolean gst_object_set_controller (GObject * object, GstController * controller);
|
||||
|
||||
GstClockTime gst_object_suggest_next_sync (GObject * object);
|
||||
gboolean gst_object_sync_values (GObject * object, GstClockTime timestamp);
|
||||
|
||||
gboolean gst_object_set_control_source (GObject *object, const gchar * property_name, GstControlSource *csource);
|
||||
GstControlSource * gst_object_get_control_source (GObject *object, const gchar * property_name);
|
||||
|
||||
gboolean gst_object_get_value_arrays (GObject * object,
|
||||
GstClockTime timestamp, GSList * value_arrays);
|
||||
gboolean gst_object_get_value_array (GObject * object,
|
||||
GstClockTime timestamp, GstValueArray * value_array);
|
||||
|
||||
GstClockTime gst_object_get_control_rate (GObject * object);
|
||||
void gst_object_set_control_rate (GObject * object, GstClockTime control_rate);
|
||||
|
||||
/* lib init/done */
|
||||
|
||||
gboolean gst_controller_init (int * argc, char ***argv);
|
||||
|
||||
|
||||
G_END_DECLS
|
||||
|
|
@ -41,6 +41,8 @@
|
|||
*
|
||||
*/
|
||||
|
||||
#include "gst_private.h"
|
||||
|
||||
#include <glib-object.h>
|
||||
#include <gst/gst.h>
|
||||
|
|
@ -23,8 +23,11 @@
|
|||
#ifndef __GST_CONTROL_SOURCE_H__
|
||||
#define __GST_CONTROL_SOURCE_H__
|
||||
|
||||
#include <gst/gstconfig.h>
|
||||
|
||||
#include <glib-object.h>
|
||||
#include <gst/gst.h>
|
||||
|
||||
#include <gst/gstclock.h>
|
||||
|
||||
G_BEGIN_DECLS
|
||||
|
303
gst/gstobject.c
303
gst/gstobject.c
|
@ -88,6 +88,7 @@
|
|||
|
||||
#include "gstobject.h"
|
||||
#include "gstmarshal.h"
|
||||
#include "gstcontroller.h"
|
||||
#include "gstinfo.h"
|
||||
#include "gstutils.h"
|
||||
|
||||
|
@ -342,6 +343,7 @@ gst_object_replace (GstObject ** oldobj, GstObject * newobj)
|
|||
static void
|
||||
gst_object_dispose (GObject * object)
|
||||
{
|
||||
GstObject *self = (GstObject *) object;
|
||||
GstObject *parent;
|
||||
|
||||
GST_CAT_TRACE_OBJECT (GST_CAT_REFCOUNTING, object, "dispose");
|
||||
|
@ -352,6 +354,11 @@ gst_object_dispose (GObject * object)
|
|||
GST_OBJECT_PARENT (object) = NULL;
|
||||
GST_OBJECT_UNLOCK (object);
|
||||
|
||||
if (self->ctrl) {
|
||||
g_object_unref (self->ctrl);
|
||||
self->ctrl = NULL;
|
||||
}
|
||||
|
||||
((GObjectClass *) gst_object_parent_class)->dispose (object);
|
||||
|
||||
return;
|
||||
|
@ -950,3 +957,299 @@ gst_object_get_path_string (GstObject * object)
|
|||
|
||||
return path;
|
||||
}
|
||||
|
||||
/* controller functions */
|
||||
|
||||
/**
|
||||
* gst_object_control_properties:
|
||||
* @object: the object of which some properties should be controlled
|
||||
* @...: %NULL terminated list of property names that should be controlled
|
||||
*
|
||||
* Creates a GstController that allows you to dynamically control one, or more,
|
||||
* GObject properties. If the given GstObject already has a GstController,
|
||||
* it adds the given properties to the existing
|
||||
* controller and returns that controller.
|
||||
*
|
||||
* Returns: %TRUE if the properties have been made controllable.
|
||||
*/
|
||||
gboolean
|
||||
gst_object_control_properties (GstObject * object, ...)
|
||||
{
|
||||
gboolean res = FALSE;
|
||||
va_list var_args;
|
||||
|
||||
g_return_val_if_fail (GST_IS_OBJECT (object), FALSE);
|
||||
|
||||
va_start (var_args, object);
|
||||
if (object->ctrl) {
|
||||
object->ctrl = gst_controller_new_valist (object, var_args);
|
||||
res = (object->ctrl != NULL);
|
||||
} else {
|
||||
res = gst_controller_add_properties_valist ((GstController *) object->ctrl,
|
||||
var_args);
|
||||
}
|
||||
va_end (var_args);
|
||||
return res;
|
||||
}
|
||||
|
||||
/**
|
||||
* gst_object_uncontrol_properties:
|
||||
* @object: the object of which some properties should not be controlled anymore
|
||||
* @...: %NULL terminated list of property names that should be controlled
|
||||
*
|
||||
* Removes the given element's properties from it's controller
|
||||
*
|
||||
* Returns: %FALSE if one of the given property names isn't handled by the
|
||||
* controller, %TRUE otherwise
|
||||
*/
|
||||
gboolean
|
||||
gst_object_uncontrol_properties (GstObject * object, ...)
|
||||
{
|
||||
gboolean res = FALSE;
|
||||
g_return_val_if_fail (GST_IS_OBJECT (object), FALSE);
|
||||
|
||||
if (object->ctrl) {
|
||||
va_list var_args;
|
||||
|
||||
va_start (var_args, object);
|
||||
res = gst_controller_remove_properties_valist (
|
||||
(GstController *) object->ctrl, var_args);
|
||||
va_end (var_args);
|
||||
}
|
||||
return (res);
|
||||
}
|
||||
|
||||
/**
|
||||
* gst_object_suggest_next_sync:
|
||||
* @object: the object that has controlled properties
|
||||
*
|
||||
* Convenience function for GObject
|
||||
*
|
||||
* Returns: same thing as gst_controller_suggest_next_sync()
|
||||
*/
|
||||
GstClockTime
|
||||
gst_object_suggest_next_sync (GstObject * object)
|
||||
{
|
||||
g_return_val_if_fail (GST_IS_OBJECT (object), GST_CLOCK_TIME_NONE);
|
||||
|
||||
if (object->ctrl)
|
||||
return gst_controller_suggest_next_sync ((GstController *) object->ctrl);
|
||||
return (GST_CLOCK_TIME_NONE);
|
||||
}
|
||||
|
||||
/**
|
||||
* gst_object_sync_values:
|
||||
* @object: the object that has controlled properties
|
||||
* @timestamp: the time that should be processed
|
||||
*
|
||||
* Convenience function for GObject
|
||||
*
|
||||
* Returns: same thing as gst_controller_sync_values()
|
||||
*/
|
||||
gboolean
|
||||
gst_object_sync_values (GstObject * object, GstClockTime timestamp)
|
||||
{
|
||||
g_return_val_if_fail (GST_IS_OBJECT (object), FALSE);
|
||||
|
||||
if (object->ctrl)
|
||||
return gst_controller_sync_values ((GstController *) object->ctrl,
|
||||
timestamp);
|
||||
/* this is no failure, its called by elements regardless if there is a
|
||||
* controller assigned or not */
|
||||
return (TRUE);
|
||||
}
|
||||
|
||||
// FIXME: docs
|
||||
void
|
||||
gst_object_set_automation_disabled (GstObject * object, gboolean disabled)
|
||||
{
|
||||
g_return_if_fail (GST_IS_OBJECT (object));
|
||||
|
||||
if (object->ctrl)
|
||||
gst_controller_set_disabled (object->ctrl, disabled);
|
||||
}
|
||||
|
||||
// FIXME: docs
|
||||
void
|
||||
gst_object_set_property_automation_disabled (GstObject * object,
|
||||
const gchar * property_name, gboolean disabled)
|
||||
{
|
||||
g_return_if_fail (GST_IS_OBJECT (object));
|
||||
g_return_if_fail (property_name);
|
||||
|
||||
if (object->ctrl)
|
||||
gst_controller_set_property_disabled ((GstController *) object->ctrl,
|
||||
property_name, disabled);
|
||||
}
|
||||
|
||||
/**
|
||||
* gst_object_set_control_source:
|
||||
* @object: the controller object
|
||||
* @property_name: name of the property for which the #GstControlSource should be set
|
||||
* @csource: the #GstControlSource that should be used for the property
|
||||
*
|
||||
* Sets the #GstControlSource for @property_name. If there already was a #GstControlSource
|
||||
* for this property it will be unreferenced.
|
||||
*
|
||||
* Returns: %FALSE if the given property isn't handled by the controller or the new #GstControlSource
|
||||
* couldn't be bound to the property, %TRUE if everything worked as expected.
|
||||
*/
|
||||
gboolean
|
||||
gst_object_set_control_source (GstObject * object, const gchar * property_name,
|
||||
GstControlSource * csource)
|
||||
{
|
||||
g_return_val_if_fail (GST_IS_OBJECT (object), FALSE);
|
||||
g_return_val_if_fail (property_name, FALSE);
|
||||
g_return_val_if_fail (GST_IS_CONTROL_SOURCE (csource), FALSE);
|
||||
|
||||
if (object->ctrl)
|
||||
return gst_controller_set_control_source ((GstController *) object->ctrl,
|
||||
property_name, csource);
|
||||
return FALSE;
|
||||
}
|
||||
|
||||
/**
|
||||
* gst_object_get_control_source:
|
||||
* @object: the object
|
||||
* @property_name: name of the property for which the #GstControlSource should be get
|
||||
*
|
||||
* Gets the corresponding #GstControlSource for the property. This should be unreferenced
|
||||
* again after use.
|
||||
*
|
||||
* Returns: (transfer full): the #GstControlSource for @property_name or NULL if
|
||||
* the property is not controlled by this controller or no #GstControlSource was
|
||||
* assigned yet.
|
||||
*/
|
||||
GstControlSource *
|
||||
gst_object_get_control_source (GstObject * object, const gchar * property_name)
|
||||
{
|
||||
g_return_val_if_fail (GST_IS_OBJECT (object), NULL);
|
||||
g_return_val_if_fail (property_name, NULL);
|
||||
|
||||
if (object->ctrl)
|
||||
return gst_controller_get_control_source ((GstController *) object->ctrl,
|
||||
property_name);
|
||||
return NULL;
|
||||
}
|
||||
|
||||
// FIXME: docs
|
||||
GValue *
|
||||
gst_object_get_value (GstObject * object, const gchar * property_name,
|
||||
GstClockTime timestamp)
|
||||
{
|
||||
g_return_val_if_fail (GST_IS_OBJECT (object), NULL);
|
||||
g_return_val_if_fail (property_name, NULL);
|
||||
|
||||
if (object->ctrl)
|
||||
return gst_controller_get (object->ctrl, property_name, timestamp);
|
||||
return NULL;
|
||||
}
|
||||
|
||||
/**
|
||||
* gst_object_get_value_arrays:
|
||||
* @object: the object that has controlled properties
|
||||
* @timestamp: the time that should be processed
|
||||
* @value_arrays: list to return the control-values in
|
||||
*
|
||||
* Function to be able to get an array of values for one or more given element
|
||||
* properties.
|
||||
*
|
||||
* If the GstValueArray->values array in list nodes is NULL, it will be created
|
||||
* by the function.
|
||||
* The type of the values in the array are the same as the property's type.
|
||||
*
|
||||
* The g_object_* functions are just convenience functions for GObject
|
||||
*
|
||||
* Returns: %TRUE if the given array(s) could be filled, %FALSE otherwise
|
||||
*/
|
||||
gboolean
|
||||
gst_object_get_value_arrays (GstObject * object, GstClockTime timestamp,
|
||||
GSList * value_arrays)
|
||||
{
|
||||
g_return_val_if_fail (GST_IS_OBJECT (object), FALSE);
|
||||
g_return_val_if_fail (GST_CLOCK_TIME_IS_VALID (timestamp), FALSE);
|
||||
|
||||
if (object->ctrl)
|
||||
return gst_controller_get_value_arrays ((GstController *) object->ctrl,
|
||||
timestamp, value_arrays);
|
||||
return (FALSE);
|
||||
}
|
||||
|
||||
/**
|
||||
* gst_object_get_value_array:
|
||||
* @object: the object that has controlled properties
|
||||
* @timestamp: the time that should be processed
|
||||
* @value_array: array to put control-values in
|
||||
*
|
||||
* Function to be able to get an array of values for one element properties
|
||||
*
|
||||
* If the GstValueArray->values array is NULL, it will be created by the function.
|
||||
* The type of the values in the array are the same as the property's type.
|
||||
*
|
||||
* The g_object_* functions are just convenience functions for GObject
|
||||
*
|
||||
* Returns: %TRUE if the given array(s) could be filled, %FALSE otherwise
|
||||
*/
|
||||
gboolean
|
||||
gst_object_get_value_array (GstObject * object, GstClockTime timestamp,
|
||||
GstValueArray * value_array)
|
||||
{
|
||||
g_return_val_if_fail (GST_IS_OBJECT (object), FALSE);
|
||||
g_return_val_if_fail (GST_CLOCK_TIME_IS_VALID (timestamp), FALSE);
|
||||
|
||||
if (object->ctrl)
|
||||
return gst_controller_get_value_array ((GstController *) object->ctrl,
|
||||
timestamp, value_array);
|
||||
return (FALSE);
|
||||
}
|
||||
|
||||
/**
|
||||
* gst_object_get_control_rate:
|
||||
* @object: the object that has controlled properties
|
||||
*
|
||||
* Obtain the control-rate for this @object. Audio processing #GstElement
|
||||
* objects will use this rate to sub-divide their processing loop and call
|
||||
* gst_object_sync_values() inbetween. The length of the processing segment
|
||||
* should be up to @control-rate nanoseconds.
|
||||
*
|
||||
* If the @object is not under property control, this will return
|
||||
* %GST_CLOCK_TIME_NONE. This allows the element to avoid the sub-dividing.
|
||||
*
|
||||
* The control-rate is not expected to change if the element is in
|
||||
* %GST_STATE_PAUSED or %GST_STATE_PLAYING.
|
||||
*
|
||||
* Returns: the control rate in nanoseconds
|
||||
*/
|
||||
GstClockTime
|
||||
gst_object_get_control_rate (GstObject * object)
|
||||
{
|
||||
GstClockTime control_rate = GST_CLOCK_TIME_NONE;
|
||||
|
||||
g_return_val_if_fail (GST_IS_OBJECT (object), FALSE);
|
||||
|
||||
if (object->ctrl)
|
||||
g_object_get (object->ctrl, "control-rate", &control_rate, NULL);
|
||||
return (control_rate);
|
||||
}
|
||||
|
||||
/**
|
||||
* gst_object_set_control_rate:
|
||||
* @object: the object that has controlled properties
|
||||
* @control_rate: the new control-rate in nanoseconds.
|
||||
*
|
||||
* Change the control-rate for this @object. Audio processing #GstElement
|
||||
* objects will use this rate to sub-divide their processing loop and call
|
||||
* gst_object_sync_values() inbetween. The length of the processing segment
|
||||
* should be up to @control-rate nanoseconds.
|
||||
*
|
||||
* The control-rate should not change if the element is in %GST_STATE_PAUSED or
|
||||
* %GST_STATE_PLAYING.
|
||||
*/
|
||||
void
|
||||
gst_object_set_control_rate (GstObject * object, GstClockTime control_rate)
|
||||
{
|
||||
g_return_if_fail (GST_IS_OBJECT (object));
|
||||
|
||||
if (object->ctrl)
|
||||
g_object_set (object->ctrl, "control-rate", control_rate, NULL);
|
||||
}
|
||||
|
|
|
@ -149,7 +149,6 @@ typedef enum
|
|||
*/
|
||||
#define GST_OBJECT_FLAG_UNSET(obj,flag) (GST_OBJECT_FLAGS (obj) &= ~(flag))
|
||||
|
||||
|
||||
typedef struct _GstObject GstObject;
|
||||
typedef struct _GstObjectClass GstObjectClass;
|
||||
|
||||
|
@ -172,6 +171,7 @@ struct _GstObject {
|
|||
guint32 flags;
|
||||
|
||||
/*< private >*/
|
||||
gpointer ctrl; /* time controlled properties */
|
||||
gpointer _gst_reserved;
|
||||
};
|
||||
|
||||
|
@ -228,6 +228,29 @@ gchar * gst_object_get_path_string (GstObject *object);
|
|||
/* misc utils */
|
||||
gboolean gst_object_check_uniqueness (GList *list, const gchar *name);
|
||||
|
||||
/* controller functions */
|
||||
#include <gst/gstclock.h>
|
||||
#include <gst/gstcontrolsource.h>
|
||||
|
||||
gboolean gst_object_control_properties (GstObject * object, ...) G_GNUC_NULL_TERMINATED;
|
||||
gboolean gst_object_uncontrol_properties (GstObject * object, ...) G_GNUC_NULL_TERMINATED;
|
||||
|
||||
GstClockTime gst_object_suggest_next_sync (GstObject * object);
|
||||
gboolean gst_object_sync_values (GstObject * object, GstClockTime timestamp);
|
||||
|
||||
void gst_object_set_automation_disabled (GstObject *object, gboolean disabled); // NEW was gst_controller_set_disabled
|
||||
void gst_object_set_property_automation_disabled (GstObject *object, const gchar * property_name, gboolean disabled); // NEW was gst_controller_set_property_disabled
|
||||
|
||||
gboolean gst_object_set_control_source (GstObject *object, const gchar * property_name, GstControlSource *csource);
|
||||
GstControlSource * gst_object_get_control_source (GstObject *object, const gchar * property_name);
|
||||
|
||||
GValue *gst_object_get_value (GstObject * object, const gchar * property_name, GstClockTime timestamp); // NEW was gst_controller_get
|
||||
gboolean gst_object_get_value_arrays (GstObject * object, GstClockTime timestamp, GSList * value_arrays);
|
||||
gboolean gst_object_get_value_array (GstObject * object, GstClockTime timestamp, GstValueArray * value_array);
|
||||
|
||||
GstClockTime gst_object_get_control_rate (GstObject * object);
|
||||
void gst_object_set_control_rate (GstObject * object, GstClockTime control_rate);
|
||||
|
||||
G_END_DECLS
|
||||
|
||||
#endif /* __GST_OBJECT_H__ */
|
||||
|
|
|
@ -2,22 +2,15 @@ lib_LTLIBRARIES = libgstcontroller-@GST_MAJORMINOR@.la
|
|||
|
||||
libgstcontroller_@GST_MAJORMINOR@_includedir = $(includedir)/gstreamer-@GST_MAJORMINOR@/gst/controller
|
||||
libgstcontroller_@GST_MAJORMINOR@_include_HEADERS = \
|
||||
gstcontroller.h \
|
||||
gstcontrolsource.h \
|
||||
gstinterpolationcontrolsource.h \
|
||||
gstlfocontrolsource.h
|
||||
|
||||
noinst_HEADERS = \
|
||||
gstcontrollerprivate.h \
|
||||
gstinterpolationcontrolsourceprivate.h \
|
||||
gstlfocontrolsourceprivate.h
|
||||
|
||||
libgstcontroller_@GST_MAJORMINOR@_la_SOURCES = \
|
||||
lib.c \
|
||||
gstcontroller.c \
|
||||
gstinterpolation.c \
|
||||
gsthelper.c \
|
||||
gstcontrolsource.c \
|
||||
gstinterpolationcontrolsource.c \
|
||||
gstlfocontrolsource.c
|
||||
|
||||
|
|
|
@ -1,53 +0,0 @@
|
|||
/* GStreamer
|
||||
*
|
||||
* Copyright (C) <2005> Stefan Kost <ensonic at users dot sf dot net>
|
||||
*
|
||||
* gstcontrollerprivate.h: dynamic parameter control subsystem
|
||||
*
|
||||
* This library is free software; you can redistribute it and/or
|
||||
* modify it under the terms of the GNU Library General Public
|
||||
* License as published by the Free Software Foundation; either
|
||||
* version 2 of the License, or (at your option) any later version.
|
||||
*
|
||||
* This library is distributed in the hope that it will be useful,
|
||||
* but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
|
||||
* Library General Public License for more details.
|
||||
*
|
||||
* You should have received a copy of the GNU Library General Public
|
||||
* License along with this library; if not, write to the
|
||||
* Free Software Foundation, Inc., 59 Temple Place - Suite 330,
|
||||
* Boston, MA 02111-1307, USA.
|
||||
*/
|
||||
|
||||
#ifndef __GST_CONTROLLER_PRIVATE_H__
|
||||
#define __GST_CONTROLLER_PRIVATE_H__
|
||||
|
||||
#include <glib.h>
|
||||
#include <glib-object.h>
|
||||
#include <gst/gst.h>
|
||||
|
||||
#include <gst/controller/gstcontroller.h>
|
||||
#include <gst/controller/gstcontrolsource.h>
|
||||
|
||||
G_BEGIN_DECLS
|
||||
|
||||
/**
|
||||
* GstControlledProperty:
|
||||
*/
|
||||
typedef struct _GstControlledProperty
|
||||
{
|
||||
GParamSpec *pspec; /* GParamSpec for this property */
|
||||
const gchar *name; /* name of the property */
|
||||
GstControlSource *csource; /* GstControlSource for this property */
|
||||
gboolean disabled;
|
||||
GValue last_value;
|
||||
} GstControlledProperty;
|
||||
|
||||
#define GST_CONTROLLED_PROPERTY(obj) ((GstControlledProperty *)(obj))
|
||||
|
||||
extern GQuark priv_gst_controller_key;
|
||||
|
||||
G_END_DECLS
|
||||
|
||||
#endif /* __GST_CONTROLLER_PRIVATE_H__ */
|
|
@ -1,357 +0,0 @@
|
|||
/* GStreamer
|
||||
*
|
||||
* Copyright (C) <2005> Stefan Kost <ensonic at users dot sf dot net>
|
||||
*
|
||||
* gsthelper.c: GObject convenience methods for using dynamic properties
|
||||
*
|
||||
* This library is free software; you can redistribute it and/or
|
||||
* modify it under the terms of the GNU Library General Public
|
||||
* License as published by the Free Software Foundation; either
|
||||
* version 2 of the License, or (at your option) any later version.
|
||||
*
|
||||
* This library is distributed in the hope that it will be useful,
|
||||
* but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
|
||||
* Library General Public License for more details.
|
||||
*
|
||||
* You should have received a copy of the GNU Library General Public
|
||||
* License along with this library; if not, write to the
|
||||
* Free Software Foundation, Inc., 59 Temple Place - Suite 330,
|
||||
* Boston, MA 02111-1307, USA.
|
||||
*/
|
||||
|
||||
/**
|
||||
* SECTION:gstcontrollergobject
|
||||
* @short_description: #GObject convenience methods for using dynamic properties
|
||||
* @see_also: #GstController
|
||||
*
|
||||
* These methods allow to use some #GstController functionality directly from
|
||||
* the #GObject class.
|
||||
*/
|
||||
|
||||
#ifdef HAVE_CONFIG_H
|
||||
# include "config.h"
|
||||
#endif
|
||||
|
||||
#include <stdarg.h>
|
||||
|
||||
#include "gstcontrollerprivate.h"
|
||||
#include "gstcontroller.h"
|
||||
|
||||
#define GST_CAT_DEFAULT controller_debug
|
||||
GST_DEBUG_CATEGORY_EXTERN (GST_CAT_DEFAULT);
|
||||
|
||||
/**
|
||||
* gst_object_control_properties:
|
||||
* @object: the object of which some properties should be controlled
|
||||
* @...: %NULL terminated list of property names that should be controlled
|
||||
*
|
||||
* Convenience function for GObject
|
||||
*
|
||||
* Creates a GstController that allows you to dynamically control one, or more, GObject properties.
|
||||
* If the given GObject already has a GstController, it adds the given properties to the existing
|
||||
* controller and returns that controller.
|
||||
*
|
||||
* Returns: (transfer full): The GstController with which the user can control the given properties dynamically or NULL if
|
||||
* one or more of the given properties aren't available, or cannot be controlled, for the given element.
|
||||
*/
|
||||
GstController *
|
||||
gst_object_control_properties (GObject * object, ...)
|
||||
{
|
||||
GstController *ctrl;
|
||||
va_list var_args;
|
||||
|
||||
g_return_val_if_fail (G_IS_OBJECT (object), NULL);
|
||||
|
||||
va_start (var_args, object);
|
||||
ctrl = gst_controller_new_valist (object, var_args);
|
||||
va_end (var_args);
|
||||
return (ctrl);
|
||||
}
|
||||
|
||||
/**
|
||||
* gst_object_uncontrol_properties:
|
||||
* @object: the object of which some properties should not be controlled anymore
|
||||
* @...: %NULL terminated list of property names that should be controlled
|
||||
*
|
||||
* Convenience function for GObject
|
||||
*
|
||||
* Removes the given element's properties from it's controller
|
||||
*
|
||||
* Returns: %FALSE if one of the given property names isn't handled by the
|
||||
* controller, %TRUE otherwise
|
||||
*/
|
||||
gboolean
|
||||
gst_object_uncontrol_properties (GObject * object, ...)
|
||||
{
|
||||
gboolean res = FALSE;
|
||||
GstController *ctrl;
|
||||
|
||||
g_return_val_if_fail (G_IS_OBJECT (object), FALSE);
|
||||
|
||||
if ((ctrl = g_object_get_qdata (object, priv_gst_controller_key))) {
|
||||
va_list var_args;
|
||||
|
||||
va_start (var_args, object);
|
||||
res = gst_controller_remove_properties_valist (ctrl, var_args);
|
||||
va_end (var_args);
|
||||
}
|
||||
return (res);
|
||||
}
|
||||
|
||||
/**
|
||||
* gst_object_get_controller:
|
||||
* @object: the object that has controlled properties
|
||||
*
|
||||
* Gets the controller for the given GObject
|
||||
*
|
||||
* Returns: (transfer full): the controller handling some of the given element's
|
||||
* properties, %NULL if no controller
|
||||
*/
|
||||
/* FIXME 0.11: This should return a new reference */
|
||||
GstController *
|
||||
gst_object_get_controller (GObject * object)
|
||||
{
|
||||
g_return_val_if_fail (G_IS_OBJECT (object), NULL);
|
||||
|
||||
return (g_object_get_qdata (object, priv_gst_controller_key));
|
||||
}
|
||||
|
||||
/**
|
||||
* gst_object_set_controller:
|
||||
* @object: the object that should get the controller
|
||||
* @controller: (transfer none): the controller object to plug in
|
||||
*
|
||||
* Sets the controller on the given GObject
|
||||
*
|
||||
* Returns: %FALSE if the GObject already has an controller, %TRUE otherwise
|
||||
*/
|
||||
/* FIXME 0.11: This should increase the refcount before storing */
|
||||
gboolean
|
||||
gst_object_set_controller (GObject * object, GstController * controller)
|
||||
{
|
||||
g_return_val_if_fail (G_IS_OBJECT (object), FALSE);
|
||||
g_return_val_if_fail (controller, FALSE);
|
||||
|
||||
if (!g_object_get_qdata (object, priv_gst_controller_key)) {
|
||||
g_object_set_qdata (object, priv_gst_controller_key, controller);
|
||||
return (TRUE);
|
||||
}
|
||||
return (FALSE);
|
||||
}
|
||||
|
||||
/**
|
||||
* gst_object_suggest_next_sync:
|
||||
* @object: the object that has controlled properties
|
||||
*
|
||||
* Convenience function for GObject
|
||||
*
|
||||
* Returns: same thing as gst_controller_suggest_next_sync()
|
||||
*/
|
||||
GstClockTime
|
||||
gst_object_suggest_next_sync (GObject * object)
|
||||
{
|
||||
GstController *ctrl = NULL;
|
||||
|
||||
g_return_val_if_fail (G_IS_OBJECT (object), GST_CLOCK_TIME_NONE);
|
||||
|
||||
if ((ctrl = g_object_get_qdata (object, priv_gst_controller_key))) {
|
||||
return gst_controller_suggest_next_sync (ctrl);
|
||||
}
|
||||
return (GST_CLOCK_TIME_NONE);
|
||||
}
|
||||
|
||||
/**
|
||||
* gst_object_sync_values:
|
||||
* @object: the object that has controlled properties
|
||||
* @timestamp: the time that should be processed
|
||||
*
|
||||
* Convenience function for GObject
|
||||
*
|
||||
* Returns: same thing as gst_controller_sync_values()
|
||||
*/
|
||||
gboolean
|
||||
gst_object_sync_values (GObject * object, GstClockTime timestamp)
|
||||
{
|
||||
GstController *ctrl = NULL;
|
||||
|
||||
g_return_val_if_fail (G_IS_OBJECT (object), FALSE);
|
||||
|
||||
if ((ctrl = g_object_get_qdata (object, priv_gst_controller_key))) {
|
||||
return gst_controller_sync_values (ctrl, timestamp);
|
||||
}
|
||||
/* this is no failure, its called by elements regardless if there is a
|
||||
* controller assigned or not
|
||||
*/
|
||||
return (TRUE);
|
||||
}
|
||||
|
||||
/**
|
||||
* gst_object_set_control_source:
|
||||
* @object: the controller object
|
||||
* @property_name: name of the property for which the #GstControlSource should be set
|
||||
* @csource: the #GstControlSource that should be used for the property
|
||||
*
|
||||
* Sets the #GstControlSource for @property_name. If there already was a #GstControlSource
|
||||
* for this property it will be unreferenced.
|
||||
*
|
||||
* Returns: %FALSE if the given property isn't handled by the controller or the new #GstControlSource
|
||||
* couldn't be bound to the property, %TRUE if everything worked as expected.
|
||||
*/
|
||||
gboolean
|
||||
gst_object_set_control_source (GObject * object, const gchar * property_name,
|
||||
GstControlSource * csource)
|
||||
{
|
||||
GstController *ctrl = NULL;
|
||||
|
||||
g_return_val_if_fail (G_IS_OBJECT (object), FALSE);
|
||||
g_return_val_if_fail (GST_IS_CONTROL_SOURCE (csource), FALSE);
|
||||
|
||||
if ((ctrl = g_object_get_qdata (object, priv_gst_controller_key))) {
|
||||
return gst_controller_set_control_source (ctrl, property_name, csource);
|
||||
}
|
||||
return FALSE;
|
||||
}
|
||||
|
||||
/**
|
||||
* gst_object_get_control_source:
|
||||
* @object: the object
|
||||
* @property_name: name of the property for which the #GstControlSource should be get
|
||||
*
|
||||
* Gets the corresponding #GstControlSource for the property. This should be unreferenced
|
||||
* again after use.
|
||||
*
|
||||
* Returns: (transfer full): the #GstControlSource for @property_name or NULL if
|
||||
* the property is not controlled by this controller or no #GstControlSource was
|
||||
* assigned yet.
|
||||
*/
|
||||
GstControlSource *
|
||||
gst_object_get_control_source (GObject * object, const gchar * property_name)
|
||||
{
|
||||
GstController *ctrl = NULL;
|
||||
|
||||
g_return_val_if_fail (G_IS_OBJECT (object), NULL);
|
||||
|
||||
if ((ctrl = g_object_get_qdata (object, priv_gst_controller_key))) {
|
||||
return gst_controller_get_control_source (ctrl, property_name);
|
||||
}
|
||||
return NULL;
|
||||
}
|
||||
|
||||
/**
|
||||
* gst_object_get_value_arrays:
|
||||
* @object: the object that has controlled properties
|
||||
* @timestamp: the time that should be processed
|
||||
* @value_arrays: list to return the control-values in
|
||||
*
|
||||
* Function to be able to get an array of values for one or more given element
|
||||
* properties.
|
||||
*
|
||||
* If the GstValueArray->values array in list nodes is NULL, it will be created
|
||||
* by the function.
|
||||
* The type of the values in the array are the same as the property's type.
|
||||
*
|
||||
* The g_object_* functions are just convenience functions for GObject
|
||||
*
|
||||
* Returns: %TRUE if the given array(s) could be filled, %FALSE otherwise
|
||||
*/
|
||||
gboolean
|
||||
gst_object_get_value_arrays (GObject * object, GstClockTime timestamp,
|
||||
GSList * value_arrays)
|
||||
{
|
||||
GstController *ctrl;
|
||||
|
||||
g_return_val_if_fail (G_IS_OBJECT (object), FALSE);
|
||||
g_return_val_if_fail (GST_CLOCK_TIME_IS_VALID (timestamp), FALSE);
|
||||
|
||||
if ((ctrl = g_object_get_qdata (object, priv_gst_controller_key))) {
|
||||
return gst_controller_get_value_arrays (ctrl, timestamp, value_arrays);
|
||||
}
|
||||
return (FALSE);
|
||||
}
|
||||
|
||||
/**
|
||||
* gst_object_get_value_array:
|
||||
* @object: the object that has controlled properties
|
||||
* @timestamp: the time that should be processed
|
||||
* @value_array: array to put control-values in
|
||||
*
|
||||
* Function to be able to get an array of values for one element properties
|
||||
*
|
||||
* If the GstValueArray->values array is NULL, it will be created by the function.
|
||||
* The type of the values in the array are the same as the property's type.
|
||||
*
|
||||
* The g_object_* functions are just convenience functions for GObject
|
||||
*
|
||||
* Returns: %TRUE if the given array(s) could be filled, %FALSE otherwise
|
||||
*/
|
||||
gboolean
|
||||
gst_object_get_value_array (GObject * object, GstClockTime timestamp,
|
||||
GstValueArray * value_array)
|
||||
{
|
||||
GstController *ctrl;
|
||||
|
||||
g_return_val_if_fail (G_IS_OBJECT (object), FALSE);
|
||||
g_return_val_if_fail (GST_CLOCK_TIME_IS_VALID (timestamp), FALSE);
|
||||
|
||||
if ((ctrl = g_object_get_qdata (object, priv_gst_controller_key))) {
|
||||
return gst_controller_get_value_array (ctrl, timestamp, value_array);
|
||||
}
|
||||
return (FALSE);
|
||||
}
|
||||
|
||||
/**
|
||||
* gst_object_get_control_rate:
|
||||
* @object: the object that has controlled properties
|
||||
*
|
||||
* Obtain the control-rate for this @object. Audio processing #GstElement
|
||||
* objects will use this rate to sub-divide their processing loop and call
|
||||
* gst_object_sync_values() inbetween. The length of the processing segment
|
||||
* should be up to @control-rate nanoseconds.
|
||||
*
|
||||
* If the @object is not under property control, this will return
|
||||
* %GST_CLOCK_TIME_NONE. This allows the element to avoid the sub-dividing.
|
||||
*
|
||||
* The control-rate is not expected to change if the element is in
|
||||
* %GST_STATE_PAUSED or %GST_STATE_PLAYING.
|
||||
*
|
||||
* Returns: the control rate in nanoseconds
|
||||
*/
|
||||
GstClockTime
|
||||
gst_object_get_control_rate (GObject * object)
|
||||
{
|
||||
GstController *ctrl;
|
||||
GstClockTime control_rate = GST_CLOCK_TIME_NONE;
|
||||
|
||||
g_return_val_if_fail (G_IS_OBJECT (object), FALSE);
|
||||
|
||||
if ((ctrl = g_object_get_qdata (object, priv_gst_controller_key))) {
|
||||
g_object_get (ctrl, "control-rate", &control_rate, NULL);
|
||||
}
|
||||
return (control_rate);
|
||||
}
|
||||
|
||||
/**
|
||||
* gst_object_set_control_rate:
|
||||
* @object: the object that has controlled properties
|
||||
* @control_rate: the new control-rate in nanoseconds.
|
||||
*
|
||||
* Change the control-rate for this @object. Audio processing #GstElement
|
||||
* objects will use this rate to sub-divide their processing loop and call
|
||||
* gst_object_sync_values() inbetween. The length of the processing segment
|
||||
* should be up to @control-rate nanoseconds.
|
||||
*
|
||||
* The control-rate should not change if the element is in %GST_STATE_PAUSED or
|
||||
* %GST_STATE_PLAYING.
|
||||
*/
|
||||
void
|
||||
gst_object_set_control_rate (GObject * object, GstClockTime control_rate)
|
||||
{
|
||||
GstController *ctrl;
|
||||
|
||||
g_return_if_fail (G_IS_OBJECT (object));
|
||||
|
||||
if ((ctrl = g_object_get_qdata (object, priv_gst_controller_key))) {
|
||||
g_object_set (ctrl, "control-rate", control_rate, NULL);
|
||||
}
|
||||
}
|
|
@ -40,15 +40,17 @@
|
|||
#include <glib-object.h>
|
||||
#include <gst/gst.h>
|
||||
|
||||
#include "gstcontrolsource.h"
|
||||
#include "gstinterpolationcontrolsource.h"
|
||||
#include "gstinterpolationcontrolsourceprivate.h"
|
||||
|
||||
#define GST_CAT_DEFAULT controller_debug
|
||||
GST_DEBUG_CATEGORY_EXTERN (GST_CAT_DEFAULT);
|
||||
GST_DEBUG_CATEGORY_STATIC (GST_CAT_DEFAULT);
|
||||
|
||||
G_DEFINE_TYPE (GstInterpolationControlSource, gst_interpolation_control_source,
|
||||
GST_TYPE_CONTROL_SOURCE);
|
||||
#define _do_init \
|
||||
GST_DEBUG_CATEGORY_INIT (GST_CAT_DEFAULT, "interpolation control source", 0, "timeline value interpolating control source")
|
||||
|
||||
G_DEFINE_TYPE_WITH_CODE (GstInterpolationControlSource,
|
||||
gst_interpolation_control_source, GST_TYPE_CONTROL_SOURCE, _do_init);
|
||||
|
||||
static GObjectClass *parent_class = NULL;
|
||||
|
||||
|
|
|
@ -27,7 +27,7 @@
|
|||
#include <glib-object.h>
|
||||
#include <gst/gst.h>
|
||||
|
||||
#include <gst/controller/gstcontrolsource.h>
|
||||
#include <gst/gstcontrolsource.h>
|
||||
|
||||
G_BEGIN_DECLS
|
||||
|
||||
|
|
|
@ -38,13 +38,17 @@
|
|||
|
||||
#include <glib-object.h>
|
||||
#include <gst/gst.h>
|
||||
#include <gst/gstcontrolsource.h>
|
||||
|
||||
#include "gstcontrolsource.h"
|
||||
#include "gstlfocontrolsource.h"
|
||||
#include "gstlfocontrolsourceprivate.h"
|
||||
|
||||
#include <gst/math-compat.h>
|
||||
|
||||
#define GST_CAT_DEFAULT controller_debug
|
||||
GST_DEBUG_CATEGORY_STATIC (GST_CAT_DEFAULT);
|
||||
|
||||
|
||||
#define EMPTY(x) (x)
|
||||
|
||||
/* FIXME: as % in C is not the modulo operator we need here for
|
||||
|
@ -603,8 +607,11 @@ gst_lfo_waveform_get_type (void)
|
|||
return (GType) gtype;
|
||||
}
|
||||
|
||||
G_DEFINE_TYPE (GstLFOControlSource, gst_lfo_control_source,
|
||||
GST_TYPE_CONTROL_SOURCE);
|
||||
#define _do_init \
|
||||
GST_DEBUG_CATEGORY_INIT (GST_CAT_DEFAULT, "lfo control source", 0, "low frequency oscillator control source")
|
||||
|
||||
G_DEFINE_TYPE_WITH_CODE (GstLFOControlSource, gst_lfo_control_source,
|
||||
GST_TYPE_CONTROL_SOURCE, _do_init);
|
||||
|
||||
static GObjectClass *parent_class = NULL;
|
||||
|
||||
|
|
|
@ -27,8 +27,6 @@
|
|||
#include <glib-object.h>
|
||||
#include <gst/gst.h>
|
||||
|
||||
#include <gst/controller/gstcontrolsource.h>
|
||||
|
||||
G_BEGIN_DECLS
|
||||
|
||||
#define GST_TYPE_LFO_CONTROL_SOURCE \
|
||||
|
|
|
@ -1,58 +0,0 @@
|
|||
/* GStreamer
|
||||
*
|
||||
* Copyright (C) <2005> Stefan Kost <ensonic at users dot sf dot net>
|
||||
*
|
||||
* lib.c: controller subsystem init
|
||||
*
|
||||
* This library is free software; you can redistribute it and/or
|
||||
* modify it under the terms of the GNU Library General Public
|
||||
* License as published by the Free Software Foundation; either
|
||||
* version 2 of the License, or (at your option) any later version.
|
||||
*
|
||||
* This library is distributed in the hope that it will be useful,
|
||||
* but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
|
||||
* Library General Public License for more details.
|
||||
*
|
||||
* You should have received a copy of the GNU Library General Public
|
||||
* License along with this library; if not, write to the
|
||||
* Free Software Foundation, Inc., 59 Temple Place - Suite 330,
|
||||
* Boston, MA 02111-1307, USA.
|
||||
*/
|
||||
|
||||
#ifdef HAVE_CONFIG_H
|
||||
# include "config.h"
|
||||
#endif
|
||||
#include <gst/gst.h>
|
||||
#include <gst/controller/gstcontroller.h>
|
||||
|
||||
/* library initialisation */
|
||||
|
||||
#define GST_CAT_DEFAULT controller_debug
|
||||
GST_DEBUG_CATEGORY (GST_CAT_DEFAULT);
|
||||
|
||||
/**
|
||||
* gst_controller_init:
|
||||
* @argc: pointer to the commandline argument count
|
||||
* @argv: pointer to the commandline argument values
|
||||
*
|
||||
* Initializes the use of the controller library. Suggested to be called right
|
||||
* after gst_init().
|
||||
*
|
||||
* Returns: the %TRUE for success.
|
||||
*/
|
||||
gboolean
|
||||
gst_controller_init (int *argc, char ***argv)
|
||||
{
|
||||
static gboolean _gst_controller_initialized = FALSE;
|
||||
|
||||
if (_gst_controller_initialized)
|
||||
return TRUE;
|
||||
|
||||
_gst_controller_initialized = TRUE;
|
||||
|
||||
GST_DEBUG_CATEGORY_INIT (GST_CAT_DEFAULT, "gstcontroller", 0,
|
||||
"dynamic parameter control for gstreamer elements");
|
||||
|
||||
return TRUE;
|
||||
}
|
Loading…
Reference in a new issue