天天看点

Gstreamer-缓冲区和事件(Buffers and Events)

缓冲区和事件

流经pipeline的数据由缓冲区和事件的组合构成。缓冲区包含实际的媒体数据。事件包含控制信息 ,例如seeking 信息和end-of-stream通知。在pipeline运行时,所有这些都是自动流经pipeline。本章主要是为了向您解释这个概念;你不需要为此做任何事情。

缓冲区

缓冲区包含将流经您创建的pipeline的数据。source element通常会创建一个新的缓冲区,并将其通过 pad 传递到链中的下一个element 。使用 GStreamer 基础架构创建媒体pipeline时,您不必自己处理缓冲区;elements 会为你做到这一点。

除其他外,缓冲区包括:

  • 指向内存对象的指针。内存对象封装内存中的一个区域。
  • 缓冲区的时间戳。
  • 一个引用计数,指示有多少elements正在使用此缓冲区。当没有element引用缓冲区时,此引用计数将用于销毁缓冲区。
  • 缓冲区标志。

简单的情况是创建一个缓冲区,分配内存,将数据放入其中,然后传递给下一个element。该element读取数据,执行某些操作(例如创建新缓冲区并对其进行解码),并取消引用缓冲区。这会导致数据被释放并销毁缓冲区。典型的视频或音频解码器是这样工作的。

不过,还有更复杂的场景。Elements可以就地修改缓冲区,即无需分配新缓冲区。Elements还可以写入硬件内存(例如来自video-capture sources)或从 X-server 分配的内存(使用 XShm)。缓冲区可以是只读的,等等。

事件

事件是与缓冲区一起在pipeline中向上游和向下游发送的控制粒子。下游事件通知流状态的其他elements。可能的事件包括seeking, flushes, end-of-stream等。上游事件用于application-element交互以及element-element交互以请求更改流状态,例如seeks。对于应用程序,只有上游事件是重要的。对下游事件的解释只是为了更全面地了解数据概念。

由于大多数应用程序以时间单位进行seek ,我们下面的示例也是这样做的:

static void
seek_to_time (GstElement *element,
          guint64     time_ns)
{
  GstEvent *event;

  event = gst_event_new_seek (1.0, GST_FORMAT_TIME,
                  GST_SEEK_FLAG_NONE,
                  GST_SEEK_METHOD_SET, time_ns,
                  GST_SEEK_TYPE_NONE, G_GUINT64_CONSTANT (0));
  gst_element_send_event (element, event);
}
           

函数gst_element_seek()是这种方法的快捷方式。这里主要是为了展示它是如何工作的。