1
I. 介绍
GStreamer 是一个非常强大而且通用的流媒体应用程序框架。 GStreamer 所具备的很多优点来源于
其框架的模块化: GStreamer 能够无缝的合并新的插件。 但是, 由于追求模块化和高效率, 使得 GStreamer
在整个框架上变的复杂, 也同时因为复杂度的提高, 使得开发一个新的应用程序显得不是那么的简单。
这个指南试图帮助你了解 GStreamer 的框架(version 0.10.3.1)以方便你在 GStreamer 框架的基础上
做开发。 第一章节将重点关注如何开发一个简单的音频播放器, 通过对整个过程的讲解,力图使你能够
理解有关 GStreamer 的一些概念。 在之后的章节中,我们将讨论一些关于媒体播放(playback)控制的高级
问题, 这些问题包括了录音、录象和编辑等等。
目 录
1. 序言
1.1. GStreamer 是什么?
1.2. 谁需要读这个手册?
1.3. 预备知识
1.4. 本手册结构
2. 动机与目标
2.1. 当前问题
2.1.1. 大量的代码复制
2.1.2. “一个目标”媒体播放器/媒体库
2.1.3. 没有统一的插件管理机制
2.1.4. 拙劣的用户感
2.1.5. 网络透明度的规定
2.1.6. 与 Windows™ 的产品还存在差距
2.2. 设计目标
2.2.1. 结构清晰且威力强大
2.2.2. 面向对象的编程思想
2.2.3. 灵活的可扩展性能
2.2.4. 支持插件以二进制形式发布
2.2.5. 高性能
2.2.6. 核心库与插件(core/plugins)分离
2.2.7. 为多媒体数字信号编解码实验提供一个框架
3. 基础概念介绍
3.1. 元件(Elements)
3.2. 箱柜(Bins)和管道(pipelines)
3.3. 衬垫(Pads)
2
第 1 章. 序言
本章将从技术的角度来描述本手册的总体结构。
1.1. GStreamer 是什么 ?
GStreamer 是一个创建流媒体应用程序的框架。其基本设计思想来自于俄勒冈(Oregon)研究生学院
有关视频管道的创意, 同时也借鉴了 DirectShow 的设计思想。
GStreamer 的程序开发框架使得编写任意类型的流媒体应用程序成为了可能。在编写处理音频、视
频或者两者皆有的应用程序时, GStreamer 可以让你的工作变得简单。GStreamer 并不受限于音频和视频
处理, 它能够处理任意类型的数据流。管道设计的方法对于实际应用的滤波器几乎没有负荷, 它甚至可
以用来设计出对延时有很高要求的高端音频应用程序。
GStreamer 最显著的用途是在构建一个播放器上。GStreamer 已经支持很多格式的文件了, 包括:
MP3、Ogg/Vorbis、MPEG-1/2、AVI、Quicktime、 mod 等等。从这个角度看,GStreamer 更象是一个播
放器。但是它主要的优点却是在于: 它的可插入组件能够很方便的接入到任意的管道当中。这个优点使
得利用 GStreamer 编写一个万能的可编辑音视频应用程序成为可能。
GStreamer 框架是基于插件的, 有些插件中提供了各种各样的多媒体数字信号编解码器,也有些提
供了其他的功能。所有的插件都能够被链接到任意的已经定义了的数据流管道中。GStreamer 的管道能
够被 GUI 编辑器编辑, 能够以 XML 文件来保存。这样的设计使得管道程序库的消耗变得非常少。
GStreamer 核心库函数是一个处理插件、数据流和媒体操作的框架。 GStreamer 核心库还提供了一
个 API, 这个 API 是开放给程序员使用的---当程序员需要使用其他的插件来编写他所需要的应用程序的
时候可以使用它。
1.2. 谁需要读这个手册?
本手册是从一个程序开发人员的角度来描述 GStreamer 的: 它叙述了如何利用 GStreamer 的开发库
以及工具来编写一个基于 GStreamer 的应用程序。对于想学习"如何编写插件"的朋友们, 我们建议你去
参考<<插件编写指南(Plugin Writers Guide)>>。
1.3. 预备知识
为了更好的理解本手册的内容, 你应该具备基本的 C 语言基础。由于 GStreamer 一直采用 GObject
编程模式, 所以本手册也假定你已经理解了 GObject 的基本概念。你可能还需要一些 GTK+和 GDK 的
知识, 这方面的知识你可以参照 Eric Harlow 的书 Developing Linux Applications with GTK+ and GDK。
另外, 当你读完本手册后, 请读一下 GStreamer Plugin Writer's Guide。 当然,你还需要关注一下其
它的 GStreamer 文档。
1.4. 本手册结构
为了帮助你更好的学习本手册, 我们将本手册分为几个大的部分, 每一部分阐述了一个在
GStreamer 应用程序开发过程中特殊而又有用的话题。如下所示:
Part I --- GStreamer 应用程序开发手册 (0.10.9.1)给你一个关于 GStreamer 总的概况叙述。
Part II --- GStreamer 应用程序开发手册 (0.10.9.1)阐述 GStreamer 应用程序开发的基本概念。本章结
束后, 你将可以使用 GStreamer 来开发你自己的音频播放器。
Part III --- GStreamer 应用程序开发手册 (0.10.9.1)我们将继续讨论一些有关 GStreamer 深层次的主
题, 这些主题告诉了我们为什么 GStreamer 能在众多的竞争者当中脱颖而出。我们将使用动态参数和动
态接口来讨论应用程序中管道的交讯问题, 我们还将讨论线程同步、时钟同步、以及其他同步问题。这
些问题的讨论不仅向你讲述如何使用 GStreamer 的 API, 而且还将告诉你一些基于 GStreamer 应用程序
开发过程中所经常遇到的问题的解决办法, 通过这些知识的学习使你更加深刻的理解 GStreamer 的基本
概念。
Part IV --- GStreamer 应用程序开发手册 (0.10.9.1)我们将进入 GStreamer 的高级编程领域。你不需
4
第 2 章. 动机和目标
从历史的角度来看,Linux 在多媒体方面已经远远落后于其他的操作系统。Microsoft's Windows 和
Apple's MacOS 它们对多媒体设备、多媒体创作、播放和实时处理等方面已经有了很好的支持。另一方
面,Linux 对多媒体应用的综合贡献比较少,这也使得 Linux 很难在专业级别的软件上与 MS Windows
和 MacOS 去竞争。
GStreamer 正是为解决 Linux 多媒体方面当前问题而设计的。
2.1. 当前的问题
我们描述了当今 Linux 平台下媒体处理的一些典型问题。
2.1.1. 大量的代码复制
对于那些想要播放一个声音文件的 Linux 用户来说,他们必须搜索各种声音播放器来播放不同格式
文件,而在这些播放器中,大部分的都一遍又一遍地重复使用了相同的代码。
对于那些想在应用程序中嵌入视频剪辑的 Linux 开发人员来说,他们必须要用粗略的 hacks 来运行
外部的视频播放器,因为没有一套可用的库提供给开发人员来创建可定制的播放器。
2.1.2. “一个目标”媒体播放器/媒体库
典型的 MPEG 播放器可以播放 MPEG 视频和音频,多数的播放器实现了完整的底层构造来达到他
们的唯一目标:播放。没有一套有效的机制可以提供对于音频和视频数据过滤和效果处理,更没有制定
在视频或音频数据中添加滤波器或特殊效果的任何规定。
如果你希望将 MPEG-2 视频流转为 AVI 文件,那么你的最佳选择是,将所有的 MPEG-2 解码算法
从播放器分离出来,并复制到你的 AVI 编码器中,因为这类算法不能简单的在应用程序之间共享。
开发人员曾经尝试着创建一个可以处理多种媒体类型的库,但由于缺乏通用的 API,所以如何集成
就成了重要的工作了。因为在集成的过程中,我们需要关注一些特殊的媒体类型(avi 文件,libmpeg2,
...),而集成这些媒体类型文件需要一个统一的接口。GStreamer 允许将这些库与通用的 API 一起打包,
这样就简化了集成和复用。
2.1.3. 没有统一的插件管理机制
典型的播放器对于不同的媒体类型会有不同的插件,两个媒体播放器会实现各自不同的插件机制,
所以编解码器不能方便的交换。每一个典型的媒体播放器的插管理件系统是具有其特定应用程序的需求
。
缺少统一的插件机制,已经严重阻碍了二进制编解码器的发展,因为没有一家公司希望将代码移植
到不同的插件机制。
GStreamer 当然也采用自己的插件系统,它为插件开发者提供了一个非常丰富的框架,从而保证这
些插件能够广泛应用,并与其他插件能够无缝的交互。GStreamer 为插件提供的框架是非常灵活,它足
以满足大多数插件的需求。
2.1.4. 拙劣的用户感
因为上述问题的原因,使得应用程序开发人员将相当多的时间花在如何处理后端、插件机制等等问
题上。从而耽误了大部分的项目时间,这样就常常导致后端和用户界面都只完成了一半,于是就导致了
拙劣的用户感。
2.1.5. 没有网络透明度的规定
当前还没有一个底层框架出现,来允许对网络透明媒体的操作。有趣的是,一个分布式的 MPEG
编码器能够复制非分布式编码器的相同的算法。
并没有关于使用 GNOME 和 KDE 桌面平台的技术的规定被制定出来,因为 GNOME 和 KDE 桌面
5
平台本身还在改进和完善,所以很难将多媒体恰当地集成到很多用户的环境中。注意到 GStreamer 还提
供很多种方法,这些方法提供将 GSreamer 与不同的桌面系统进行集成(见附录里的集成一节),而这些
方法往往都不是网络透明化。
GStreamer 内核在最底层没有采用网络透明技术,只是在顶层加了作为本地使用,这就是说,创建
一个核心组件的包就变得比较容易了。GStreamer 允许管道在 TCP 协议上分离,使用 tcp 插件来实现
GStreamer 数据协议,这个被包含在 gst-plugins 模块,目录 gst/tcp
2.1.6. 与 Windows™的产品还存在差距
我们要想看到 Linux 桌面系统的成功就要立足于可靠的媒体处理。
我们必须为商业编解码器和多媒体应用扫清障碍,这样 Linux 才能成为多媒体领域的一个选择。
2.2. 设计目标
我们将阐述在 GStreamer 开发中的目标.
2.2.1. 结构清晰且威力强大
GStreamer 提供一套清晰的接口给以下一些开发人员:
希望构建媒体管道的应用程序员。程序员可以使用一系列强有利的工具来创建媒体管道,而不
用去写一行代码,从而使得复杂的媒体控制变得非常简单。
插件程序员。GStreamer 向插件程序员提供了简洁而简单的 API 来创建 self-plugin(自包含)插件
,同时还集成了大量的调试和跟踪机制和工具。GStreamer 也提供了一系列现实例子。
2.2.2. 面向对象的编程思想
GStreamer 是依附于 GLib 2.0 对象模型的,熟悉 GLib 或者旧版本的 GTK+的程序员对 GStreamer 将
会驾轻就熟。
GStreamer 采用了信号与对象属性的机制。
所有对象的属性和功能都能在运行态被查询。
GStreamer 与 GTK+的编程方法非常相似,需要对象模型,对象所有(ownership of objects),参考计
算(reference counting)...
2.2.3. 灵活的可扩展性能
所有的 GStreamer 对象都可以采用 GObject 继承的方法进行扩展。
所有的插件都可以被动态装载,可以独立的扩展或升级。
2.2.4. 支持插件以二进制形式发布
作为共享库发布的插件能够在运行态直接加载,插件的所有属性可以由 GObject 属性来设置,而无
需(事实上决不)去安装插件的头文件。
我们更多的关注在插件能够独立化,运行的时候还需要很多与插件相关的因素。
2.2.5. 高性能
高性能主要体现在:
使用 GLib 的 g_mem_chunk 和非模块化分配算法使得内存分配尽可能最小。
插件之间的连接非常轻型(light-weight)。数据在管道中的传递使用最小的消耗,管道中插件之
间的数据传递只会涉及指针废弃。
提供了一套对目标内存直接进行操作的机制。例如,插件可以向 X server 共享的内存空间直接
写数据,缓冲区也可以指向任意的内存,如声卡的内部硬件缓冲区。
refcounting 和写拷贝将 memcpy 减少到最低。子缓冲区有效地将缓冲区分离为易于管理的块。
使用线程联合(cothreads)减少线程消耗。线程联合(cothreads)是简单又高速的方法来切换子程序
评论0