实际的GST版本是1.8.1。
目前,我有接收gstreamer编码流并通过声卡播放它的代码。我想对其进行修改,以使我的应用程序可以访问未经压缩的原始音频数据。这将导致一个整数声音样本的数组,如果我将它们绘制成图,我会看到音频波形(例如,完美的音调将是一个不错的正弦波),并且如果我将最新的数组附加到回调收到的最后一个我不会看到任何中断。
这是当前的播放代码:
https://github.com/lucasw/audio_common/blob/master/audio_play/src/audio_play.cpp
我想我需要将alsasink更改为appsink,并设置一个回调,该回调将在通过解码器后获取最新的音频块。这是从https://github.com/jojva/gst-plugins-base/blob/master/tests/examples/app/appsink-src.c改编而成:
_sink = gst_element_factory_make("appsink", "sink");
g_object_set (G_OBJECT (_sink), "emit-signals", TRUE,
"sync", FALSE, NULL);
g_signal_connect (_sink, "new-sample",
G_CALLBACK (on_new_sample_from_sink), this);
然后是回调:
static GstFlowReturn
on_new_sample_from_sink (GstElement * elt, gpointer data)
{
RosGstProcess *client = reinterpret_cast<RosGstProcess*>(data);
GstSample *sample;
GstBuffer *app_buffer, *buffer;
GstElement *source;
/* get the sample from appsink */
sample = gst_app_sink_pull_sample (GST_APP_SINK (elt));
buffer = gst_sample_get_buffer (sample);
/* make a copy */
app_buffer = gst_buffer_copy (buffer);
/* we don't need the appsink sample anymore */
gst_sample_unref (sample);
/* get source and push new buffer */
source = gst_bin_get_by_name (GST_BIN (client->_sink), "app_source");
return gst_app_src_push_buffer (GST_APP_SRC (source), app_buffer);
}
我可以获取该回调中的数据吗?我应该如何处理GstFlowReturn?如果那是将数据传递到另一个管道元素,我不想这样做,那么我宁愿在那里完成它。
https://github.com/lucasw/audio_common/blob/appsink/audio_process/src/audio_process.cpp
将gpointer数据传递给该回调函数正是我想要的(广播到gint16数组吗?),否则我该如何转换和访问它?
最佳答案
GstFlowReturn仅仅是基础基类的返回值。如果您将返回错误,则管道可能会停止,因为..嗯,这是严重错误。
cb_need_data事件由您的appsrc元素触发。如果需要,可以将其用作节流机制。由于您可能在纯推送模式下使用appsrc(一旦有东西到达appsink,然后将其推送到appsrc),则可以忽略这些。您还可以在appsrc元素上显式禁用这些事件。 (或者您仍然使用那个?)
缓冲区中的数据格式取决于解码器和应用接收器同意的上限。通常,这是解码器的首选格式。您可能会根据解码器对该格式进行一些控制,或者将其转换为您喜欢的格式。可能值得检查一下格式,Float32并不少见。
恐怕我有点忘记了您的实际问题。
关于audio - 使用gstreamer 1.0解码流音频并访问波形数据?,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/38542953/