[gst-devel] setting packet time on playbin

Alfred E. Heggestad aeh at db.org
Thu Oct 25 20:05:53 CEST 2007


René Stadler wrote:
> Alfred E. Heggestad schrieb:
<snip>
>>
>> while it is possible to detect this in run-time using
>> gst_structure_get_int(s, "width", &width); on the Buffer's CAPS 
>> structure,
>> and decode accordingly, I would rather prefer to *always* get the format
>> of the GstBuffer in 16-bit signed int. Do you know if this is possible,
>> and how this can be achieved when setting up the pipeline, playbin etc?
>>
>>
>> thanks again for your help :)
>>
>>
>>
>> /alfred
> 
> This is usually done with a combination of an audioconvert, 
> audioresample and a capsfilter element.  Before your sink, you need to 
> have these three elements in a row.  Capsfilter has a property named 
> "caps", set this to the fixed caps you want as output.  This forces 
> upstream to deliver data in this format, the audioconvert and 
> audioresample elements will handle all conversions that are needed.
> 
> Since you are using playbin, there is no need to need for audioconvert 
> and audioresample since playbin adds these before the audio sink 
> already.  So for playbin usage, create a bin which you set as audio-sink 
> later.  Inside the bin, put a capsfilter linked to your fakesink.  Add a 
> ghost pad named "sink" to the bin which proxies the sink pad of the 
> capsfilter.  This makes the bin look like a regular audio sink which 
> supports a single format to the outside world.
> 


René, many thanks for your help. Your suggestion is indeed what I am looking
for, and after some hard thinking I managed to set it up. The hard work is now
done inside the gstreamer playbin, including resampling etc, and the audio
samples are delivered to my callback handler in 16-bit signed format.


For the reference (and for other people doing similar stuff) I am posting
my working code below:


/alfred




static void set_caps(struct gst *g)
{
	GstCaps *caps;

	/* Set the capabilities we want */
	caps = gst_caps_new_simple("audio/x-raw-int",
				   "rate",     G_TYPE_INT,     g->cfg.srate,
				   "channels", G_TYPE_INT,     1,
				   "width",    G_TYPE_INT,     16,
				   "signed",   G_TYPE_BOOLEAN, true,
				   NULL);

	g_object_set(G_OBJECT(g->capsfilt), "caps", caps, NULL);
}



static int gst_setup(struct gst *g)
{
	GstBus *bus;
	GstPad *pad;

	gst_init(0, NULL);
	g->loop = g_main_loop_new(NULL, FALSE);

	g->pipeline = gst_pipeline_new("pipeline");
	if (!g->pipeline) {
		DEBUG_WARNING("failed to create pipeline element\n");
		return ENOMEM;
	}

	/********************* Player BIN **************************/

	g->source = gst_element_factory_make("playbin", "source");
	if (!g->source) {
		DEBUG_WARNING("failed to create playbin source element\n");
		return ENOMEM;
	}

	/********************* My BIN **************************/

	g->bin = gst_bin_new("mybin");

	g->capsfilt = gst_element_factory_make("capsfilter", NULL);
	if (!g->capsfilt) {
		DEBUG_WARNING("failed to create capsfilter element\n");
		return ENOMEM;
	}

	set_caps(g);

	g->sink = gst_element_factory_make("fakesink", "sink");
	if (!g->sink) {
		DEBUG_WARNING("failed to create sink element\n");
		return ENOMEM;
	}

	gst_bin_add_many(GST_BIN(g->bin), g->capsfilt, g->sink, NULL);
	gst_element_link_many(g->capsfilt, g->sink, NULL);

	/* add ghostpad */
	pad = gst_element_get_pad(g->capsfilt, "sink");
	gst_element_add_pad(g->bin, gst_ghost_pad_new("sink", pad));
	gst_object_unref(GST_OBJECT(pad));

	/* put all elements in a bin */
	gst_bin_add_many(GST_BIN(g->pipeline), g->source, NULL);

	/* Override audio-sink handoff handler */
	g_object_set(G_OBJECT(g->sink), "signal-handoffs", TRUE, NULL);
	g_signal_connect(g->sink, "handoff", G_CALLBACK(handoff_handler), g);
	g_object_set(G_OBJECT(g->source), "audio-sink", g->bin, NULL);

	/********************* Misc **************************/

	/* Bus watch */
	bus = gst_pipeline_get_bus(GST_PIPELINE(g->pipeline));
	gst_bus_add_watch(bus, bus_watch_handler, g);
	gst_object_unref(bus);

	/* Set URI */
	g_object_set(G_OBJECT(g->source), "uri", g->uri, NULL);

	return 0;
}





More information about the gstreamer-devel mailing list