Playbin with custom audiosink bin audio/x-raw conversion

Nick_law nicholas at umantec.net
Tue May 18 12:26:16 UTC 2021


Afternoon,
I am trying to get gstreamer to simply loop a .wav file to a filesink.
for testing purposes the filesink will be a .wav file but actually want to
write raw audio to a fifo.

I tried to combine these two concepts:
https://tristanswork.blogspot.com/2010/10/looping-playback-with-gstreamer.html
https://gstreamer.freedesktop.org/documentation/tutorials/playback/custom-playbin-sinks.html?gi-language=c

and the pipeline does run but the audio in the .wav is corrupted. I then
tried adding a decodebin with audio/x-raw caps but now there is no audio
written out.

So in essence I think it should be simple, I just need the playbin to
playout raw audio or to somehow convert whatever playbin outputs to
raw-audio.

any help would be greatly appreciated. 

gboolean bus_callback(GstBus* bus, GstMessage* msg, gpointer data)
{
	GstElement* play = GST_ELEMENT(data);
	switch (GST_MESSAGE_TYPE(msg)) {
		case GST_MESSAGE_EOS:
			/* restart playback if at end */
			if (!gst_element_seek(play,
								  1.0, GST_FORMAT_TIME, GST_SEEK_FLAG_FLUSH,
								  GST_SEEK_TYPE_SET, 0,
								  GST_SEEK_TYPE_NONE, GST_CLOCK_TIME_NONE)) {
				g_print("Seek failed!\n");
			}
			break;
		default:
			break;
	}
	return TRUE;
}

void Playfile()
{
	GMainLoop* loop;
	GstElement* play;
	GstBus* bus;

	/* init GStreamer */
	gst_init(NULL, NULL);
	loop = g_main_loop_new(NULL, FALSE);

	/* set up */
	play = gst_element_factory_make("playbin", "play");
	g_object_set(G_OBJECT(play), "uri", "file:/tmp/tone_sink_1.wav", NULL);

	GstElement *audio_sink{nullptr}, *wav_convert{nullptr}, *wavenc{nullptr};

	GstElement* decodebin{nullptr};
	decodebin = gst_element_factory_make("decodebin", NULL);

	audio_sink = gst_element_factory_make("filesink", NULL);
	wav_convert = gst_element_factory_make("audioconvert", NULL);
	wavenc = gst_element_factory_make("wavenc", NULL);

	if (!decodebin ||
		!audio_sink ||
		!wav_convert ||
		!wavenc) {
		throw std::runtime_error("sink elements could be created.");
	}
	g_object_set(audio_sink, "location", "tester.wav", NULL);

	GstCaps* in_filtercaps = gst_caps_new_simple("audio/x-raw",
												 "format", G_TYPE_STRING, "F32LE",
												 "rate", G_TYPE_INT, 48000,
												 NULL);

	g_object_set(decodebin, "caps", in_filtercaps, NULL);
	gst_caps_unref(in_filtercaps);

	GstElement* bin = gst_bin_new("audio_sink_bin");

	gst_bin_add_many(GST_BIN(bin),
					 decodebin,
					 wav_convert,
					 wavenc,
					 audio_sink,
					 NULL);

	gst_element_link_many(decodebin, wav_convert, wavenc, audio_sink, NULL);

	GstPad *pad, *ghost_pad;

	pad = gst_element_get_static_pad(decodebin, "sink");
	ghost_pad = gst_ghost_pad_new("sink", pad);
	gst_pad_set_active(ghost_pad, TRUE);
	gst_element_add_pad(bin, ghost_pad);
	gst_object_unref(pad);

	g_object_set(GST_OBJECT(play), "audio-sink", bin, NULL);

	bus = gst_pipeline_get_bus(GST_PIPELINE(play));
	gst_bus_add_watch(bus, bus_callback, play);
	gst_object_unref(bus);

	gst_element_set_state(play, GST_STATE_PLAYING);
	std::string name = "test";
	GST_DEBUG_BIN_TO_DOT_FILE(GST_BIN(play), GST_DEBUG_GRAPH_SHOW_ALL,
name.c_str());

	/* now run */
	g_main_loop_run(loop);

	/* also clean up */
	gst_element_set_state(play, GST_STATE_NULL);
	gst_object_unref(GST_OBJECT(play));
}




--
Sent from: http://gstreamer-devel.966125.n4.nabble.com/


More information about the gstreamer-devel mailing list