controller: expand the api to offer functions for plain and GValue arrays

Rename the _get_value_array() functions to _get_g_value_array() and reintroduce
the former to operate on plain unboxed c datatypes (like in 0.10). The _g_value
variants are for bindings while the _value ones are more suited to processing
in elements.
This commit is contained in:
Stefan Sauer 2012-04-25 09:47:10 +02:00
parent 12eefc0442
commit 772c58e255
12 changed files with 344 additions and 40 deletions

View file

@ -615,6 +615,7 @@ GstControlBindingConvert
gst_control_binding_sync_values
gst_control_binding_get_value
gst_control_binding_get_value_array
gst_control_binding_get_g_value_array
gst_control_binding_set_disabled
gst_control_binding_is_disabled
<SUBSECTION Standard>
@ -1560,6 +1561,7 @@ gst_object_get_control_binding
gst_object_remove_control_binding
gst_object_get_value
gst_object_get_value_array
gst_object_get_g_value_array
gst_object_get_control_rate
gst_object_set_control_rate

View file

@ -31,6 +31,13 @@
* gst_control_binding_constructor()
* - the weak-ref on object is not nice, as is the same as gst_object_parent()
* once the object is added to the parent
*
* - another option would be do defer what I am doing in _constructor to when
* the parent is set (need to listen to the signal then)
* then basically I could
* a) remove the obj arg and wait the binding to be added or
* b) add the binding from constructor, unref object there and make obj
* writeonly
*/
#include "gst_private.h"
@ -273,19 +280,23 @@ gst_control_binding_get_value (GstControlBinding * self, GstClockTime timestamp)
* @n_values: the number of values
* @values: array to put control-values in
*
* Gets a number of values for the given controllered property starting at the
* Gets a number of values for the given controlled property starting at the
* requested time. The array @values need to hold enough space for @n_values of
* the same type as the objects property's type.
*
* This function is useful if one wants to e.g. draw a graph of the control
* curve or apply a control curve sample by sample.
*
* The values are unboxed and ready to be used. The similar function
* gst_control_binding_get_g_value_array() returns the array as #GValues and is
* better suites for bindings.
*
* Returns: %TRUE if the given array could be filled, %FALSE otherwise
*/
gboolean
gst_control_binding_get_value_array (GstControlBinding * self,
GstClockTime timestamp, GstClockTime interval, guint n_values,
GValue * values)
gpointer values)
{
GstControlBindingClass *klass;
gboolean ret = FALSE;
@ -305,6 +316,48 @@ gst_control_binding_get_value_array (GstControlBinding * self,
return ret;
}
/**
* gst_control_binding_get_g_value_array:
* @self: the control binding
* @timestamp: the time that should be processed
* @interval: the time spacing between subsequent values
* @n_values: the number of values
* @values: array to put control-values in
*
* Gets a number of #GValues for the given controlled property starting at the
* requested time. The array @values need to hold enough space for @n_values of
* #GValue.
*
* This function is useful if one wants to e.g. draw a graph of the control
* curve or apply a control curve sample by sample.
*
* Returns: %TRUE if the given array could be filled, %FALSE otherwise
*/
gboolean
gst_control_binding_get_g_value_array (GstControlBinding * self,
GstClockTime timestamp, GstClockTime interval, guint n_values,
GValue * values)
{
GstControlBindingClass *klass;
gboolean ret = FALSE;
g_return_val_if_fail (GST_IS_CONTROL_BINDING (self), FALSE);
g_return_val_if_fail (GST_CLOCK_TIME_IS_VALID (timestamp), FALSE);
g_return_val_if_fail (GST_CLOCK_TIME_IS_VALID (interval), FALSE);
g_return_val_if_fail (values, FALSE);
klass = GST_CONTROL_BINDING_GET_CLASS (self);
if (G_LIKELY (klass->get_g_value_array != NULL)) {
ret =
klass->get_g_value_array (self, timestamp, interval, n_values, values);
} else {
GST_WARNING_OBJECT (self, "missing get_g_value_array implementation");
// FIXME(ensonic): emulate
}
return ret;
}
/**
* gst_control_binding_set_disabled:
* @self: the control binding

View file

@ -93,7 +93,8 @@ struct _GstControlBindingClass
/* virtual methods */
gboolean (* sync_values) (GstControlBinding *self, GstObject *object, GstClockTime timestamp, GstClockTime last_sync);
GValue * (* get_value) (GstControlBinding *self, GstClockTime timestamp);
gboolean (* get_value_array) (GstControlBinding *self, GstClockTime timestamp,GstClockTime interval, guint n_values, GValue *values);
gboolean (* get_value_array) (GstControlBinding *self, GstClockTime timestamp,GstClockTime interval, guint n_values, gpointer values);
gboolean (* get_g_value_array) (GstControlBinding *self, GstClockTime timestamp,GstClockTime interval, guint n_values, GValue *values);
/*< private >*/
gpointer _gst_reserved[GST_PADDING];
@ -110,6 +111,8 @@ gboolean gst_control_binding_sync_values (GstControlBinding *
GValue * gst_control_binding_get_value (GstControlBinding *binding,
GstClockTime timestamp);
gboolean gst_control_binding_get_value_array (GstControlBinding *binding, GstClockTime timestamp,
GstClockTime interval, guint n_values, gpointer values);
gboolean gst_control_binding_get_g_value_array (GstControlBinding *binding, GstClockTime timestamp,
GstClockTime interval, guint n_values, GValue *values);
void gst_control_binding_set_disabled (GstControlBinding * self, gboolean disabled);

View file

@ -122,7 +122,8 @@ gst_control_source_get_value (GstControlSource * self, GstClockTime timestamp,
* @n_values: the number of values to fetch
* @value_array: array to put control-values in
*
* Gets an array of values for for this #GstControlSource.
* Gets an array of values for for this #GstControlSource. Values that are
* undefined contain NANs.
*
* Returns: %TRUE if the given array could be filled, %FALSE otherwise
*/

View file

@ -1300,17 +1300,62 @@ gst_object_get_value (GstObject * object, const gchar * property_name,
* @n_values: the number of values
* @values: array to put control-values in
*
* Gets a number of values for the given controllered property starting at the
* Gets a number of values for the given controlled property starting at the
* requested time. The array @values need to hold enough space for @n_values of
* the same type as the objects property's type.
*
* This function is useful if one wants to e.g. draw a graph of the control
* curve or apply a control curve sample by sample.
*
* The values are unboxed and ready to be used. The similar function
* gst_object_get_g_value_array() returns the array as #GValues and is
* better suites for bindings.
*
* Returns: %TRUE if the given array could be filled, %FALSE otherwise
*/
gboolean
gst_object_get_value_array (GstObject * object, const gchar * property_name,
GstClockTime timestamp, GstClockTime interval, guint n_values,
gpointer values)
{
gboolean res = FALSE;
GstControlBinding *binding;
g_return_val_if_fail (GST_IS_OBJECT (object), FALSE);
g_return_val_if_fail (property_name, FALSE);
g_return_val_if_fail (GST_CLOCK_TIME_IS_VALID (timestamp), FALSE);
g_return_val_if_fail (GST_CLOCK_TIME_IS_VALID (interval), FALSE);
g_return_val_if_fail (values, FALSE);
GST_OBJECT_LOCK (object);
if ((binding = gst_object_find_control_binding (object, property_name))) {
res = gst_control_binding_get_value_array (binding, timestamp, interval,
n_values, values);
}
GST_OBJECT_UNLOCK (object);
return res;
}
/**
* gst_object_get_g_value_array:
* @object: the object that has controlled properties
* @property_name: the name of the property to get
* @timestamp: the time that should be processed
* @interval: the time spacing between subsequent values
* @n_values: the number of values
* @values: array to put control-values in
*
* Gets a number of #GValues for the given controlled property starting at the
* requested time. The array @values need to hold enough space for @n_values of
* #GValue.
*
* This function is useful if one wants to e.g. draw a graph of the control
* curve or apply a control curve sample by sample.
*
* Returns: %TRUE if the given array could be filled, %FALSE otherwise
*/
gboolean
gst_object_get_value_array (GstObject * object, const gchar * property_name,
gst_object_get_g_value_array (GstObject * object, const gchar * property_name,
GstClockTime timestamp, GstClockTime interval, guint n_values,
GValue * values)
{
@ -1325,7 +1370,7 @@ gst_object_get_value_array (GstObject * object, const gchar * property_name,
GST_OBJECT_LOCK (object);
if ((binding = gst_object_find_control_binding (object, property_name))) {
res = gst_control_binding_get_value_array (binding, timestamp, interval,
res = gst_control_binding_get_g_value_array (binding, timestamp, interval,
n_values, values);
}
GST_OBJECT_UNLOCK (object);

View file

@ -252,6 +252,9 @@ gboolean gst_object_remove_control_binding (GstObject * object, GstContro
GValue * gst_object_get_value (GstObject * object, const gchar * property_name,
GstClockTime timestamp);
gboolean gst_object_get_value_array (GstObject * object, const gchar * property_name,
GstClockTime timestamp, GstClockTime interval,
guint n_values, gpointer values);
gboolean gst_object_get_g_value_array (GstObject * object, const gchar * property_name,
GstClockTime timestamp, GstClockTime interval,
guint n_values, GValue *values);

View file

@ -52,6 +52,9 @@ static gboolean gst_argb_control_binding_sync_values (GstControlBinding * _self,
static GValue *gst_argb_control_binding_get_value (GstControlBinding * _self,
GstClockTime timestamp);
static gboolean gst_argb_control_binding_get_value_array (GstControlBinding *
_self, GstClockTime timestamp, GstClockTime interval, guint n_values,
gpointer values);
static gboolean gst_argb_control_binding_get_g_value_array (GstControlBinding *
_self, GstClockTime timestamp, GstClockTime interval, guint n_values,
GValue * values);
@ -94,6 +97,8 @@ gst_argb_control_binding_class_init (GstARGBControlBindingClass * klass)
control_binding_class->get_value = gst_argb_control_binding_get_value;
control_binding_class->get_value_array =
gst_argb_control_binding_get_value_array;
control_binding_class->get_g_value_array =
gst_argb_control_binding_get_g_value_array;
properties[PROP_CS_A] =
g_param_spec_object ("control-source-a", "ControlSource A",
@ -315,6 +320,71 @@ gst_argb_control_binding_get_value (GstControlBinding * _self,
static gboolean
gst_argb_control_binding_get_value_array (GstControlBinding * _self,
GstClockTime timestamp, GstClockTime interval, guint n_values,
gpointer values_)
{
GstARGBControlBinding *self = GST_ARGB_CONTROL_BINDING (_self);
gint i;
gdouble *src_val_a = NULL, *src_val_r = NULL, *src_val_g = NULL, *src_val_b =
NULL;
guint *values = (guint *) values_;
gboolean ret = TRUE;
g_return_val_if_fail (GST_IS_ARGB_CONTROL_BINDING (self), FALSE);
g_return_val_if_fail (GST_CLOCK_TIME_IS_VALID (timestamp), FALSE);
g_return_val_if_fail (GST_CLOCK_TIME_IS_VALID (interval), FALSE);
g_return_val_if_fail (values, FALSE);
g_return_val_if_fail (GST_CONTROL_BINDING_PSPEC (self), FALSE);
if (self->cs_a) {
src_val_a = g_new0 (gdouble, n_values);
ret &= gst_control_source_get_value_array (self->cs_a, timestamp,
interval, n_values, src_val_a);
}
if (self->cs_r) {
src_val_r = g_new0 (gdouble, n_values);
ret &= gst_control_source_get_value_array (self->cs_r, timestamp,
interval, n_values, src_val_r);
}
if (self->cs_g) {
src_val_g = g_new0 (gdouble, n_values);
ret &= gst_control_source_get_value_array (self->cs_g, timestamp,
interval, n_values, src_val_g);
}
if (self->cs_b) {
src_val_b = g_new0 (gdouble, n_values);
ret &= gst_control_source_get_value_array (self->cs_b, timestamp,
interval, n_values, src_val_b);
}
if (G_LIKELY (ret)) {
for (i = 0; i < n_values; i++) {
gdouble a = 1.0, r = 0.0, g = 0.0, b = 0.0;
if (src_val_a && !isnan (src_val_a[i]))
a = src_val_a[i];
if (src_val_r && !isnan (src_val_r[i]))
r = src_val_r[i];
if (src_val_g && !isnan (src_val_g[i]))
g = src_val_g[i];
if (src_val_b && !isnan (src_val_b[i]))
b = src_val_b[i];
values[i] = (((guint) (CLAMP (a, 0.0, 1.0) * 255)) << 24) |
(((guint) (CLAMP (r, 0.0, 1.0) * 255)) << 16) |
(((guint) (CLAMP (g, 0.0, 1.0) * 255)) << 8) |
((guint) (CLAMP (b, 0.0, 1.0) * 255));
}
} else {
GST_LOG ("failed to get control value for property %s at ts %"
GST_TIME_FORMAT, _self->name, GST_TIME_ARGS (timestamp));
}
g_free (src_val_a);
g_free (src_val_r);
g_free (src_val_g);
g_free (src_val_b);
return ret;
}
static gboolean
gst_argb_control_binding_get_g_value_array (GstControlBinding * _self,
GstClockTime timestamp, GstClockTime interval, guint n_values,
GValue * values)
{

View file

@ -52,6 +52,9 @@ static GValue *gst_direct_control_binding_get_value (GstControlBinding * _self,
GstClockTime timestamp);
static gboolean gst_direct_control_binding_get_value_array (GstControlBinding *
_self, GstClockTime timestamp, GstClockTime interval, guint n_values,
gpointer values);
static gboolean gst_direct_control_binding_get_g_value_array (GstControlBinding
* _self, GstClockTime timestamp, GstClockTime interval, guint n_values,
GValue * values);
#define _do_init \
@ -75,7 +78,7 @@ static GParamSpec *properties[PROP_LAST];
#define DEFINE_CONVERT(type,Type,TYPE) \
static void \
convert_to_##type (GstDirectControlBinding *self, gdouble s, GValue *d) \
convert_g_value_to_##type (GstDirectControlBinding *self, gdouble s, GValue *d) \
{ \
GParamSpec##Type *pspec = G_PARAM_SPEC_##TYPE (((GstControlBinding *)self)->pspec); \
g##type v; \
@ -83,8 +86,19 @@ convert_to_##type (GstDirectControlBinding *self, gdouble s, GValue *d) \
s = CLAMP (s, 0.0, 1.0); \
v = pspec->minimum + (g##type) ((pspec->maximum - pspec->minimum) * s); \
g_value_set_##type (d, v); \
} \
\
static void \
convert_value_to_##type (GstDirectControlBinding *self, gdouble s, gpointer d_) \
{ \
GParamSpec##Type *pspec = G_PARAM_SPEC_##TYPE (((GstControlBinding *)self)->pspec); \
g##type *d = (g##type *)d_; \
\
s = CLAMP (s, 0.0, 1.0); \
*d = pspec->minimum + (g##type) ((pspec->maximum - pspec->minimum) * s); \
}
DEFINE_CONVERT (int, Int, INT);
DEFINE_CONVERT (uint, UInt, UINT);
DEFINE_CONVERT (long, Long, LONG);
@ -95,14 +109,25 @@ DEFINE_CONVERT (float, Float, FLOAT);
DEFINE_CONVERT (double, Double, DOUBLE);
static void
convert_to_boolean (GstDirectControlBinding * self, gdouble s, GValue * d)
convert_g_value_to_boolean (GstDirectControlBinding * self, gdouble s,
GValue * d)
{
s = CLAMP (s, 0.0, 1.0);
g_value_set_boolean (d, (gboolean) (s + 0.5));
}
static void
convert_to_enum (GstDirectControlBinding * self, gdouble s, GValue * d)
convert_value_to_boolean (GstDirectControlBinding * self, gdouble s,
gpointer d_)
{
gboolean *d = (gboolean *) d_;
s = CLAMP (s, 0.0, 1.0);
*d = (gboolean) (s + 0.5);
}
static void
convert_g_value_to_enum (GstDirectControlBinding * self, gdouble s, GValue * d)
{
GParamSpecEnum *pspec =
G_PARAM_SPEC_ENUM (((GstControlBinding *) self)->pspec);
@ -114,6 +139,18 @@ convert_to_enum (GstDirectControlBinding * self, gdouble s, GValue * d)
g_value_set_enum (d, e->values[v].value);
}
static void
convert_value_to_enum (GstDirectControlBinding * self, gdouble s, gpointer d_)
{
GParamSpecEnum *pspec =
G_PARAM_SPEC_ENUM (((GstControlBinding *) self)->pspec);
GEnumClass *e = pspec->enum_class;
gint *d = (gint *) d_;
s = CLAMP (s, 0.0, 1.0);
*d = e->values[(gint) (s * (e->n_values - 1))].value;
}
/* vmethods */
static void
@ -133,6 +170,8 @@ gst_direct_control_binding_class_init (GstDirectControlBindingClass * klass)
control_binding_class->get_value = gst_direct_control_binding_get_value;
control_binding_class->get_value_array =
gst_direct_control_binding_get_value_array;
control_binding_class->get_g_value_array =
gst_direct_control_binding_get_g_value_array;
properties[PROP_CS] =
g_param_spec_object ("control-source", "ControlSource",
@ -171,34 +210,54 @@ gst_direct_control_binding_constructor (GType type, guint n_construct_params,
// select mapping function
switch (base) {
case G_TYPE_INT:
self->convert = convert_to_int;
self->convert_g_value = convert_g_value_to_int;
self->convert_value = convert_value_to_int;
self->byte_size = sizeof (gint);
break;
case G_TYPE_UINT:
self->convert = convert_to_uint;
self->convert_g_value = convert_g_value_to_uint;
self->convert_value = convert_value_to_uint;
self->byte_size = sizeof (guint);
break;
case G_TYPE_LONG:
self->convert = convert_to_long;
self->convert_g_value = convert_g_value_to_long;
self->convert_value = convert_value_to_long;
self->byte_size = sizeof (glong);
break;
case G_TYPE_ULONG:
self->convert = convert_to_ulong;
self->convert_g_value = convert_g_value_to_ulong;
self->convert_value = convert_value_to_ulong;
self->byte_size = sizeof (gulong);
break;
case G_TYPE_INT64:
self->convert = convert_to_int64;
self->convert_g_value = convert_g_value_to_int64;
self->convert_value = convert_value_to_int64;
self->byte_size = sizeof (gint64);
break;
case G_TYPE_UINT64:
self->convert = convert_to_uint64;
self->convert_g_value = convert_g_value_to_uint64;
self->convert_value = convert_value_to_uint64;
self->byte_size = sizeof (guint64);
break;
case G_TYPE_FLOAT:
self->convert = convert_to_float;
self->convert_g_value = convert_g_value_to_float;
self->convert_value = convert_value_to_float;
self->byte_size = sizeof (gfloat);
break;
case G_TYPE_DOUBLE:
self->convert = convert_to_double;
self->convert_g_value = convert_g_value_to_double;
self->convert_value = convert_value_to_double;
self->byte_size = sizeof (gdouble);
break;
case G_TYPE_BOOLEAN:
self->convert = convert_to_boolean;
self->convert_g_value = convert_g_value_to_boolean;
self->convert_value = convert_value_to_boolean;
self->byte_size = sizeof (gboolean);
break;
case G_TYPE_ENUM:
self->convert = convert_to_enum;
self->convert_g_value = convert_g_value_to_enum;
self->convert_value = convert_value_to_enum;
self->byte_size = sizeof (gint);
break;
default:
GST_WARNING ("incomplete implementation for paramspec type '%s'",
@ -290,7 +349,7 @@ gst_direct_control_binding_sync_values (GstControlBinding * _self,
GST_LOG_OBJECT (object, " mapping %s to value of type %s", _self->name,
G_VALUE_TYPE_NAME (dst_val));
/* run mapping function to convert gdouble to GValue */
self->convert (self, src_val, dst_val);
self->convert_g_value (self, src_val, dst_val);
/* we can make this faster
* http://bugzilla.gnome.org/show_bug.cgi?id=536939
*/
@ -319,7 +378,7 @@ gst_direct_control_binding_get_value (GstControlBinding * _self,
if (gst_control_source_get_value (self->cs, timestamp, &src_val)) {
dst_val = g_new0 (GValue, 1);
g_value_init (dst_val, G_PARAM_SPEC_VALUE_TYPE (_self->pspec));
self->convert (self, src_val, dst_val);
self->convert_g_value (self, src_val, dst_val);
} else {
GST_LOG ("no control value for property %s at ts %" GST_TIME_FORMAT,
_self->name, GST_TIME_ARGS (timestamp));
@ -331,14 +390,15 @@ gst_direct_control_binding_get_value (GstControlBinding * _self,
static gboolean
gst_direct_control_binding_get_value_array (GstControlBinding * _self,
GstClockTime timestamp, GstClockTime interval, guint n_values,
GValue * values)
gpointer values_)
{
GstDirectControlBinding *self = GST_DIRECT_CONTROL_BINDING (_self);
gint i;
gdouble *src_val;
gboolean res = FALSE;
GType type;
GstDirectControlBindingConvert convert;
GstDirectControlBindingConvertValue convert;
gint byte_size;
guint8 *values = (guint8 *) values_;
g_return_val_if_fail (GST_IS_DIRECT_CONTROL_BINDING (self), FALSE);
g_return_val_if_fail (GST_CLOCK_TIME_IS_VALID (timestamp), FALSE);
@ -346,7 +406,48 @@ gst_direct_control_binding_get_value_array (GstControlBinding * _self,
g_return_val_if_fail (values, FALSE);
g_return_val_if_fail (GST_CONTROL_BINDING_PSPEC (self), FALSE);
convert = self->convert;
convert = self->convert_value;
byte_size = self->byte_size;
src_val = g_new0 (gdouble, n_values);
if ((res = gst_control_source_get_value_array (self->cs, timestamp,
interval, n_values, src_val))) {
for (i = 0; i < n_values; i++) {
if (!isnan (src_val[i])) {
convert (self, src_val[i], (gpointer) values);
} else {
GST_LOG ("no control value for property %s at index %d", _self->name,
i);
}
values += byte_size;
}
} else {
GST_LOG ("failed to get control value for property %s at ts %"
GST_TIME_FORMAT, _self->name, GST_TIME_ARGS (timestamp));
}
g_free (src_val);
return res;
}
static gboolean
gst_direct_control_binding_get_g_value_array (GstControlBinding * _self,
GstClockTime timestamp, GstClockTime interval, guint n_values,
GValue * values)
{
GstDirectControlBinding *self = GST_DIRECT_CONTROL_BINDING (_self);
gint i;
gdouble *src_val;
gboolean res = FALSE;
GType type;
GstDirectControlBindingConvertGValue convert;
g_return_val_if_fail (GST_IS_DIRECT_CONTROL_BINDING (self), FALSE);
g_return_val_if_fail (GST_CLOCK_TIME_IS_VALID (timestamp), FALSE);
g_return_val_if_fail (GST_CLOCK_TIME_IS_VALID (interval), FALSE);
g_return_val_if_fail (values, FALSE);
g_return_val_if_fail (GST_CONTROL_BINDING_PSPEC (self), FALSE);
convert = self->convert_g_value;
type = G_PARAM_SPEC_VALUE_TYPE (_self->pspec);
src_val = g_new0 (gdouble, n_values);

View file

@ -48,14 +48,24 @@ typedef struct _GstDirectControlBinding GstDirectControlBinding;
typedef struct _GstDirectControlBindingClass GstDirectControlBindingClass;
/**
* GstDirectControlBindingConvert:
* GstDirectControlBindingConvertValue:
* @self: the #GstDirectControlBinding instance
* @src_value: the value returned by the cotnrol source
* @dest_value: the target location
*
* Function to map a control-value to the target plain data type.
*/
typedef void (* GstDirectControlBindingConvertValue) (GstDirectControlBinding *self, gdouble src_value, gpointer dest_value);
/**
* GstDirectControlBindingConvertGValue:
* @self: the #GstDirectControlBinding instance
* @src_value: the value returned by the cotnrol source
* @dest_value: the target GValue
*
* Function to map a control-value to the target GValue.
*/
typedef void (* GstDirectControlBindingConvert) (GstDirectControlBinding *self, gdouble src_value, GValue *dest_value);
typedef void (* GstDirectControlBindingConvertGValue) (GstDirectControlBinding *self, gdouble src_value, GValue *dest_value);
/**
* GstDirectControlBinding:
@ -70,8 +80,10 @@ struct _GstDirectControlBinding {
GstControlSource *cs; /* GstControlSource for this property */
GValue cur_value;
gdouble last_value;
gint byte_size;
GstDirectControlBindingConvert convert;
GstDirectControlBindingConvertValue convert_value;
GstDirectControlBindingConvertGValue convert_g_value;
gpointer _gst_reserved[GST_PADDING];
};

View file

@ -605,6 +605,7 @@ GST_START_TEST (controller_interpolation_linear_value_array)
GstElement *elem;
gdouble *raw_values;
GValue *g_values;
gint *values;
elem = gst_element_factory_make ("testobj", NULL);
@ -633,10 +634,10 @@ GST_START_TEST (controller_interpolation_linear_value_array)
g_free (raw_values);
/* now pull in mapped values for some timestamps */
/* now pull in mapped GValues for some timestamps */
g_values = g_new0 (GValue, 3);
fail_unless (gst_object_get_value_array (GST_OBJECT (elem), "int",
fail_unless (gst_object_get_g_value_array (GST_OBJECT (elem), "int",
0, GST_SECOND / 2, 3, g_values));
fail_unless_equals_int (g_value_get_int (&g_values[0]), 0);
fail_unless_equals_int (g_value_get_int (&g_values[1]), 50);
@ -644,6 +645,17 @@ GST_START_TEST (controller_interpolation_linear_value_array)
g_free (g_values);
/* now pull in mapped values for some timestamps */
values = g_new0 (gint, 3);
fail_unless (gst_object_get_value_array (GST_OBJECT (elem), "int",
0, GST_SECOND / 2, 3, values));
fail_unless_equals_int (values[0], 0);
fail_unless_equals_int (values[1], 50);
fail_unless_equals_int (values[2], 100);
g_free (values);
gst_object_unref (cs);
gst_object_unref (elem);
}

View file

@ -230,15 +230,15 @@ test_interpolation (void)
g_object_set (cs, "mode", GST_INTERPOLATION_MODE_NONE, NULL);
v1 = g_new0 (GValue, n_values);
gst_object_get_value_array (e, "int", 0, GST_SECOND / 10, n_values, v1);
gst_object_get_g_value_array (e, "int", 0, GST_SECOND / 10, n_values, v1);
g_object_set (cs, "mode", GST_INTERPOLATION_MODE_LINEAR, NULL);
v2 = g_new0 (GValue, n_values);
gst_object_get_value_array (e, "int", 0, GST_SECOND / 10, n_values, v2);
gst_object_get_g_value_array (e, "int", 0, GST_SECOND / 10, n_values, v2);
g_object_set (cs, "mode", GST_INTERPOLATION_MODE_CUBIC, NULL);
v3 = g_new0 (GValue, n_values);
gst_object_get_value_array (e, "int", 0, GST_SECOND / 10, n_values, v3);
gst_object_get_g_value_array (e, "int", 0, GST_SECOND / 10, n_values, v3);
for (t = 0; t < n_values; t++) {
i1 = g_value_get_int (&v1[t]);
@ -320,23 +320,23 @@ test_lfo (void)
g_object_set (cs, "waveform", GST_LFO_WAVEFORM_SINE, NULL);
v1 = g_new0 (GValue, n_values);
gst_object_get_value_array (e, "int", 0, GST_SECOND / 10, n_values, v1);
gst_object_get_g_value_array (e, "int", 0, GST_SECOND / 10, n_values, v1);
g_object_set (cs, "waveform", GST_LFO_WAVEFORM_SQUARE, NULL);
v2 = g_new0 (GValue, n_values);
gst_object_get_value_array (e, "int", 0, GST_SECOND / 10, n_values, v2);
gst_object_get_g_value_array (e, "int", 0, GST_SECOND / 10, n_values, v2);
g_object_set (cs, "waveform", GST_LFO_WAVEFORM_SAW, NULL);
v3 = g_new0 (GValue, n_values);
gst_object_get_value_array (e, "int", 0, GST_SECOND / 10, n_values, v3);
gst_object_get_g_value_array (e, "int", 0, GST_SECOND / 10, n_values, v3);
g_object_set (cs, "waveform", GST_LFO_WAVEFORM_REVERSE_SAW, NULL);
v4 = g_new0 (GValue, n_values);
gst_object_get_value_array (e, "int", 0, GST_SECOND / 10, n_values, v4);
gst_object_get_g_value_array (e, "int", 0, GST_SECOND / 10, n_values, v4);
g_object_set (cs, "waveform", GST_LFO_WAVEFORM_TRIANGLE, NULL);
v5 = g_new0 (GValue, n_values);
gst_object_get_value_array (e, "int", 0, GST_SECOND / 10, n_values, v5);
gst_object_get_g_value_array (e, "int", 0, GST_SECOND / 10, n_values, v5);
for (t = 0; t < n_values; t++) {
i1 = g_value_get_int (&v1[t]);
@ -418,7 +418,7 @@ test_chained_lfo (void)
n_values = 40 * 10;
v1 = g_new0 (GValue, n_values);
gst_object_get_value_array (e, "int", 0, GST_SECOND / 10, n_values, v1);
gst_object_get_g_value_array (e, "int", 0, GST_SECOND / 10, n_values, v1);
for (t = 0; t < n_values; t++) {
i1 = g_value_get_int (&v1[t]);

View file

@ -254,6 +254,7 @@ EXPORTS
gst_clock_single_shot_id_reinit
gst_clock_type_get_type
gst_clock_unadjust_unlocked
gst_control_binding_get_g_value_array
gst_control_binding_get_type
gst_control_binding_get_value
gst_control_binding_get_value_array
@ -605,6 +606,7 @@ EXPORTS
gst_object_flags_get_type
gst_object_get_control_binding
gst_object_get_control_rate
gst_object_get_g_value_array
gst_object_get_name
gst_object_get_parent
gst_object_get_path_string