[gst-cvs] gst-plugins-good: audiofxbasefirfilter: Add property for not draining the history on kernel changes
Sebastian Dröge
slomo at kemper.freedesktop.org
Thu Jan 7 08:28:51 PST 2010
Module: gst-plugins-good
Branch: master
Commit: a9a5e0c7e1a3731c3ead52b6336d815a1603ac9c
URL: http://cgit.freedesktop.org/gstreamer/gst-plugins-good/commit/?id=a9a5e0c7e1a3731c3ead52b6336d815a1603ac9c
Author: Sebastian Dröge <sebastian.droege at collabora.co.uk>
Date: Thu Jan 7 17:25:05 2010 +0100
audiofxbasefirfilter: Add property for not draining the history on kernel changes
Currently this only works if the kernel size doesn't change, in the future
it will be possible to change the kernel size too without draining
the complete history and without loosing anything.
Partially based on a patch by
Thiago Santos <thiago.sousa.santos at collabora.co.uk>
---
gst/audiofx/audiofirfilter.c | 7 +----
gst/audiofx/audiofxbasefirfilter.c | 59 ++++++++++++++++++++++++++++-------
gst/audiofx/audiofxbasefirfilter.h | 3 ++
3 files changed, 51 insertions(+), 18 deletions(-)
diff --git a/gst/audiofx/audiofirfilter.c b/gst/audiofx/audiofirfilter.c
index df4e2dc..b6102ae 100644
--- a/gst/audiofx/audiofirfilter.c
+++ b/gst/audiofx/audiofirfilter.c
@@ -148,9 +148,6 @@ gst_audio_fir_filter_update_kernel (GstAudioFIRFilter * self, GValueArray * va)
gdouble *kernel;
guint i;
- gst_audio_fx_base_fir_filter_push_residue (GST_AUDIO_FX_BASE_FIR_FILTER
- (self));
-
if (va) {
if (self->kernel)
g_value_array_free (self->kernel);
@@ -231,9 +228,7 @@ gst_audio_fir_filter_set_property (GObject * object, guint prop_id,
switch (prop_id) {
case PROP_KERNEL:
g_mutex_lock (self->lock);
- gst_audio_fx_base_fir_filter_push_residue (GST_AUDIO_FX_BASE_FIR_FILTER
- (self));
-
+ /* update kernel already pushes residues */
gst_audio_fir_filter_update_kernel (self, g_value_dup_boxed (value));
g_mutex_unlock (self->lock);
break;
diff --git a/gst/audiofx/audiofxbasefirfilter.c b/gst/audiofx/audiofxbasefirfilter.c
index fde7fb4..37fa639 100644
--- a/gst/audiofx/audiofxbasefirfilter.c
+++ b/gst/audiofx/audiofxbasefirfilter.c
@@ -59,10 +59,12 @@ GST_DEBUG_CATEGORY_STATIC (GST_CAT_DEFAULT);
enum
{
PROP_0 = 0,
- PROP_LOW_LATENCY
+ PROP_LOW_LATENCY,
+ PROP_DRAIN_ON_CHANGES
};
#define DEFAULT_LOW_LATENCY FALSE
+#define DEFAULT_DRAIN_ON_CHANGES TRUE
GST_BOILERPLATE_FULL (GstAudioFXBaseFIRFilter, gst_audio_fx_base_fir_filter,
GstAudioFilter, GST_TYPE_AUDIO_FILTER, DEBUG_INIT);
@@ -290,6 +292,8 @@ process_fft_##channels##_##width (GstAudioFXBaseFIRFilter * self, const g##ctype
self->buffer_fill = buffer_fill = kernel_length - 1; \
} \
\
+ g_assert (self->buffer_length == block_length); \
+ \
while (input_samples) { \
pass = MIN (buffer_length - buffer_fill, input_samples); \
\
@@ -505,6 +509,12 @@ gst_audio_fx_base_fir_filter_set_property (GObject * object, guint prop_id,
GST_BASE_TRANSFORM_UNLOCK (self);
break;
}
+ case PROP_DRAIN_ON_CHANGES:{
+ GST_BASE_TRANSFORM_LOCK (self);
+ self->drain_on_changes = g_value_get_boolean (value);
+ GST_BASE_TRANSFORM_UNLOCK (self);
+ break;
+ }
default:
G_OBJECT_WARN_INVALID_PROPERTY_ID (object, prop_id, pspec);
break;
@@ -521,6 +531,9 @@ gst_audio_fx_base_fir_filter_get_property (GObject * object, guint prop_id,
case PROP_LOW_LATENCY:
g_value_set_boolean (value, self->low_latency);
break;
+ case PROP_DRAIN_ON_CHANGES:
+ g_value_set_boolean (value, self->drain_on_changes);
+ break;
default:
G_OBJECT_WARN_INVALID_PROPERTY_ID (object, prop_id, pspec);
break;
@@ -564,6 +577,22 @@ gst_audio_fx_base_fir_filter_class_init (GstAudioFXBaseFIRFilterClass * klass)
"Can only be changed in states < PAUSED!", DEFAULT_LOW_LATENCY,
G_PARAM_READWRITE | G_PARAM_STATIC_STRINGS));
+ /**
+ * GstAudioFXBaseFIRFilter::drain-on-changes:
+ *
+ * Whether the filter should be drained when its coeficients change
+ *
+ * Note: Currently this only works if the kernel size is not changed!
+ * Support for drainless kernel size changes will be added in the future.
+ *
+ * Since: 0.10.18
+ */
+ g_object_class_install_property (gobject_class, PROP_DRAIN_ON_CHANGES,
+ g_param_spec_boolean ("drain-on-changes", "Drain on changes",
+ "Drains the filter when its coeficients change",
+ DEFAULT_DRAIN_ON_CHANGES,
+ G_PARAM_READWRITE | G_PARAM_STATIC_STRINGS));
+
trans_class->transform =
GST_DEBUG_FUNCPTR (gst_audio_fx_base_fir_filter_transform);
trans_class->start = GST_DEBUG_FUNCPTR (gst_audio_fx_base_fir_filter_start);
@@ -588,6 +617,7 @@ gst_audio_fx_base_fir_filter_init (GstAudioFXBaseFIRFilter * self,
self->nsamples_in = 0;
self->low_latency = DEFAULT_LOW_LATENCY;
+ self->drain_on_changes = DEFAULT_DRAIN_ON_CHANGES;
gst_pad_set_query_function (GST_BASE_TRANSFORM (self)->srcpad,
gst_audio_fx_base_fir_filter_query);
@@ -1009,7 +1039,16 @@ gst_audio_fx_base_fir_filter_set_kernel (GstAudioFXBaseFIRFilter * self,
g_return_if_fail (self != NULL);
GST_BASE_TRANSFORM_LOCK (self);
- if (self->buffer) {
+
+ latency_changed = (self->latency != latency
+ || (!self->low_latency && self->kernel_length < FFT_THRESHOLD
+ && kernel_length >= FFT_THRESHOLD)
+ || (!self->low_latency && self->kernel_length >= FFT_THRESHOLD
+ && kernel_length < FFT_THRESHOLD));
+
+ /* FIXME: If the latency changes, the buffer size changes too and we
+ * have to drain in any case until this is fixed in the future */
+ if (self->buffer && (!self->drain_on_changes || latency_changed)) {
gst_audio_fx_base_fir_filter_push_residue (self);
self->start_ts = GST_CLOCK_TIME_NONE;
self->start_off = GST_BUFFER_OFFSET_NONE;
@@ -1018,17 +1057,13 @@ gst_audio_fx_base_fir_filter_set_kernel (GstAudioFXBaseFIRFilter * self,
self->buffer_fill = 0;
}
- latency_changed = (self->latency != latency
- || (!self->low_latency && self->kernel_length < FFT_THRESHOLD
- && kernel_length >= FFT_THRESHOLD)
- || (!self->low_latency && self->kernel_length >= FFT_THRESHOLD
- && kernel_length < FFT_THRESHOLD));
-
g_free (self->kernel);
- g_free (self->buffer);
- self->buffer = NULL;
- self->buffer_fill = 0;
- self->buffer_length = 0;
+ if (!self->drain_on_changes || latency_changed) {
+ g_free (self->buffer);
+ self->buffer = NULL;
+ self->buffer_fill = 0;
+ self->buffer_length = 0;
+ }
self->kernel = kernel;
self->kernel_length = kernel_length;
diff --git a/gst/audiofx/audiofxbasefirfilter.h b/gst/audiofx/audiofxbasefirfilter.h
index ed0ec75..c9eeb1b 100644
--- a/gst/audiofx/audiofxbasefirfilter.h
+++ b/gst/audiofx/audiofxbasefirfilter.h
@@ -62,6 +62,9 @@ struct _GstAudioFXBaseFIRFilter {
guint64 latency; /* pre-latency of the filter kernel */
gboolean low_latency; /* work in slower low latency mode */
+ gboolean drain_on_changes; /* If the filter should be drained when
+ * coeficients change */
+
/* < private > */
GstAudioFXBaseFIRFilterProcessFunc process;
More information about the Gstreamer-commits
mailing list