summaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authorLuiz Augusto von Dentz <luiz.dentz@openbossa.org>2007-10-18 21:46:49 +0000
committerLuiz Augusto von Dentz <luiz.dentz@openbossa.org>2007-10-18 21:46:49 +0000
commit5dee78747cac71ad970b513dc229712be1348290 (patch)
treeaa148798ead6340ba92aaf26cbbe3b128d6505b4
parentfcbcc7bfdfe61d57f38bd44cbc7a2edcea23e7a8 (diff)
Fixes for gstsbcenc.
-rw-r--r--audio/gstsbcenc.c156
-rw-r--r--audio/gstsbcenc.h5
2 files changed, 146 insertions, 15 deletions
diff --git a/audio/gstsbcenc.c b/audio/gstsbcenc.c
index 812c1193..ea97563e 100644
--- a/audio/gstsbcenc.c
+++ b/audio/gstsbcenc.c
@@ -28,6 +28,13 @@
#include <string.h>
#include "gstsbcenc.h"
+#include "gstsbcutil.h"
+
+
+#define SBC_ENC_DEFAULT_MODE CFG_MODE_AUTO
+#define SBC_ENC_DEFAULT_BLOCKS 16
+#define SBC_ENC_DEFAULT_SUB_BANDS 8
+#define SBC_ENC_DEFAULT_ALLOCATION CFG_ALLOCATION_AUTO
GST_DEBUG_CATEGORY_STATIC(sbc_enc_debug);
#define GST_CAT_DEFAULT sbc_enc_debug
@@ -52,9 +59,31 @@ static GType gst_sbc_mode_get_type(void)
return sbc_mode_type;
}
+#define GST_TYPE_SBC_ALLOCATION (gst_sbc_allocation_get_type())
+
+static GType gst_sbc_allocation_get_type(void)
+{
+ static GType sbc_allocation_type = 0;
+ static GEnumValue sbc_allocations[] = {
+ { CFG_ALLOCATION_AUTO, "Auto", "auto" },
+ { CFG_ALLOCATION_LOUDNESS, "Loudness", "loudness" },
+ { CFG_ALLOCATION_SNR, "SNR", "snr" },
+ { -1, NULL, NULL}
+ };
+
+ if (!sbc_allocation_type)
+ sbc_allocation_type = g_enum_register_static(
+ "GstSbcAllocation", sbc_allocations);
+
+ return sbc_allocation_type;
+}
+
enum {
PROP_0,
PROP_MODE,
+ PROP_ALLOCATION,
+ PROP_BLOCKS,
+ PROP_SUB_BANDS
};
GST_BOILERPLATE(GstSbcEnc, gst_sbc_enc, GstElement, GST_TYPE_ELEMENT);
@@ -85,27 +114,81 @@ static GstStaticPadTemplate sbc_enc_src_factory =
"subbands = (int) { 4, 8 }, "
"allocation = (string) { snr, loudness }"));
+
+static GstCaps* sbc_enc_generate_srcpad_caps(GstSbcEnc *enc, GstCaps *caps)
+{
+ gint rate;
+ gint channels;
+ GstCaps* src_caps;
+ GstStructure *structure;
+
+ structure = gst_caps_get_structure(caps, 0);
+
+ if (!gst_structure_get_int (structure, "rate", &rate))
+ return NULL;
+ if (!gst_structure_get_int (structure, "channels", &channels))
+ return NULL;
+
+ enc->sbc.rate = rate;
+ enc->sbc.channels = channels;
+
+ if (enc->mode == 0)
+ enc->sbc.joint = CFG_MODE_JOINT_STEREO;
+ else
+ enc->sbc.joint = enc->mode;
+
+ enc->sbc.blocks = enc->blocks;
+ enc->sbc.subbands = enc->subbands;
+ if (enc->allocation == 0)
+ enc->sbc.allocation = CFG_ALLOCATION_LOUDNESS;
+ else
+ enc->sbc.allocation = enc->allocation;
+
+ src_caps = gst_caps_new_simple("audio/x-sbc", "rate", G_TYPE_INT,
+ enc->sbc.rate, "channels", G_TYPE_INT,
+ enc->sbc.channels, "mode", G_TYPE_STRING,
+ gst_sbc_get_mode_string(enc->sbc.joint), "subbands",
+ G_TYPE_INT, enc->sbc.subbands, "blocks", G_TYPE_INT,
+ enc->sbc.blocks, "allocation", G_TYPE_STRING,
+ gst_sbc_get_allocation_string(enc->sbc.allocation),
+ NULL);
+
+ return src_caps;
+}
+
+static gboolean sbc_enc_sink_setcaps (GstPad * pad, GstCaps * caps)
+{
+ GstSbcEnc *enc;
+ GstStructure *structure;
+ GstCaps *othercaps;
+
+ enc = GST_SBC_ENC(GST_PAD_PARENT (pad));
+ structure = gst_caps_get_structure(caps, 0);
+
+ othercaps = sbc_enc_generate_srcpad_caps(enc, caps);
+ if (othercaps == NULL)
+ goto error;
+
+ gst_pad_set_caps (enc->srcpad, othercaps);
+ gst_caps_unref(othercaps);
+
+ return TRUE;
+
+error:
+ GST_ERROR_OBJECT (enc, "invalid input caps");
+ return FALSE;
+}
+
static GstFlowReturn sbc_enc_chain(GstPad *pad, GstBuffer *buffer)
{
GstSbcEnc *enc = GST_SBC_ENC(gst_pad_get_parent(pad));
GstFlowReturn res = GST_FLOW_OK;
- GstStructure *structure;
- gint rate, channels;
guint size, offset = 0;
guint8 *data;
data = GST_BUFFER_DATA(buffer);
size = GST_BUFFER_SIZE(buffer);
- structure = gst_caps_get_structure(GST_PAD_CAPS(pad), 0);
- gst_structure_get_int(structure, "rate", &rate);
- gst_structure_get_int(structure, "channels", &channels);
-
- enc->sbc.rate = rate;
- enc->sbc.channels = channels;
- enc->sbc.subbands = 8;
- enc->sbc.joint = 0;
-
while (offset < size) {
GstBuffer *output;
GstCaps *caps;
@@ -184,11 +267,23 @@ static void gst_sbc_enc_set_property(GObject *object, guint prop_id,
{
GstSbcEnc *enc = GST_SBC_ENC(object);
+ /* TODO - CAN ONLY BE CHANGED ON READY AND BELOW */
+
switch (prop_id) {
case PROP_MODE:
enc->mode = g_value_get_enum(value);
break;
-
+ case PROP_ALLOCATION:
+ enc->allocation = g_value_get_enum(value);
+ break;
+ case PROP_BLOCKS:
+ /* TODO - verify consistency */
+ enc->blocks = g_value_get_int(value);
+ break;
+ case PROP_SUB_BANDS:
+ /* TODO - verify consistency */
+ enc->subbands = g_value_get_int(value);
+ break;
default:
G_OBJECT_WARN_INVALID_PROPERTY_ID(object, prop_id, pspec);
break;
@@ -204,7 +299,15 @@ static void gst_sbc_enc_get_property(GObject *object, guint prop_id,
case PROP_MODE:
g_value_set_enum(value, enc->mode);
break;
-
+ case PROP_ALLOCATION:
+ g_value_set_enum(value, enc->allocation);
+ break;
+ case PROP_BLOCKS:
+ g_value_set_int(value, enc->blocks);
+ break;
+ case PROP_SUB_BANDS:
+ g_value_set_int(value, enc->subbands);
+ break;
default:
G_OBJECT_WARN_INVALID_PROPERTY_ID(object, prop_id, pspec);
break;
@@ -224,8 +327,24 @@ static void gst_sbc_enc_class_init(GstSbcEncClass *klass)
element_class->change_state = GST_DEBUG_FUNCPTR(sbc_enc_change_state);
g_object_class_install_property(object_class, PROP_MODE,
- g_param_spec_enum("mode", "Mode", "Encoding mode",
- GST_TYPE_SBC_MODE, 0, G_PARAM_READWRITE));
+ g_param_spec_enum("mode", "Mode",
+ "Encoding mode", GST_TYPE_SBC_MODE,
+ SBC_ENC_DEFAULT_MODE, G_PARAM_READWRITE));
+
+ g_object_class_install_property(object_class, PROP_ALLOCATION,
+ g_param_spec_enum("allocation", "Allocation",
+ "Allocation mode", GST_TYPE_SBC_ALLOCATION,
+ SBC_ENC_DEFAULT_ALLOCATION, G_PARAM_READWRITE));
+
+ g_object_class_install_property(object_class, PROP_BLOCKS,
+ g_param_spec_int("blocks", "Blocks",
+ "Blocks", 0, G_MAXINT,
+ SBC_ENC_DEFAULT_BLOCKS, G_PARAM_READWRITE));
+
+ g_object_class_install_property(object_class, PROP_SUB_BANDS,
+ g_param_spec_int("subbands", "Sub Bands",
+ "Sub Bands", 0, G_MAXINT,
+ SBC_ENC_DEFAULT_SUB_BANDS, G_PARAM_READWRITE));
GST_DEBUG_CATEGORY_INIT(sbc_enc_debug, "sbcenc", 0,
"SBC encoding element");
@@ -234,9 +353,16 @@ static void gst_sbc_enc_class_init(GstSbcEncClass *klass)
static void gst_sbc_enc_init(GstSbcEnc *self, GstSbcEncClass *klass)
{
self->sinkpad = gst_pad_new_from_static_template(&sbc_enc_sink_factory, "sink");
+ gst_pad_set_setcaps_function (self->sinkpad,
+ GST_DEBUG_FUNCPTR (sbc_enc_sink_setcaps));
gst_element_add_pad(GST_ELEMENT(self), self->sinkpad);
self->srcpad = gst_pad_new_from_static_template(&sbc_enc_src_factory, "src");
gst_pad_set_chain_function(self->sinkpad, GST_DEBUG_FUNCPTR(sbc_enc_chain));
gst_element_add_pad(GST_ELEMENT(self), self->srcpad);
+
+ self->subbands = SBC_ENC_DEFAULT_SUB_BANDS;
+ self->blocks = SBC_ENC_DEFAULT_BLOCKS;
+ self->mode = SBC_ENC_DEFAULT_MODE;
+ self->allocation = SBC_ENC_DEFAULT_ALLOCATION;
}
diff --git a/audio/gstsbcenc.h b/audio/gstsbcenc.h
index e7daf2d3..0a95bcef 100644
--- a/audio/gstsbcenc.h
+++ b/audio/gstsbcenc.h
@@ -24,6 +24,8 @@
#include <gst/gst.h>
#include "sbc.h"
+#include "ipc.h"
+
G_BEGIN_DECLS
@@ -48,6 +50,9 @@ struct _GstSbcEnc {
GstPad *srcpad;
gint mode;
+ gint blocks;
+ gint allocation;
+ gint subbands;
sbc_t sbc;
};