第一部分:背景知识 
 
 
 DirectShow 
 是微软公司提供的一套在 
 Windows 
 平台上进行流媒体处理的开发包,与 
 DirectX 
 开发包一起发布。它经过 
 DirectX 6.0 
 中的 
 DirectX Media 
 发展而来,集成了 
 DirectX 
 家族中的其他成员( 
 DirectDraw 
 、 
 DirectSound 
 等),可以说是一位 
 “ 
 集大成者 
 ” 
 。 
               
 
 
 DirectShow 
 能做些什么? 
  DirectShow 
 为多媒体流的捕捉和回放提供了强有力的支持。运用 
 DirectShow 
 ,可以很方便地从支持 
 WDM 
 驱动模型的采集卡上捕获数据,并且进行相应的后期处理乃至存储到文件中。它广泛地支持各种媒体格式,包括 
 Asf 
 、 
 Mpeg 
 、 
 Avi 
 、 
 Dv 
 、 
 Mp3 
 、 
 Wave 
 等等,使得多媒体数据的回放变得轻而易举。另外, 
 DirectShow 
 直接支持 
 DVD 
 的播放,视频的非线性编辑,以及与数字摄像机的数据交换。更值得一提的是, 
 DirectShow 
 提供的是一种开放式的开发环境,每个功能模块都采取 
 COM 
 组件方式,称为 
 Filter 
 ,开发者也可以开发自己的功能 
 Filter 
 来扩展 
 DirectShow 
 的应用。按照功能来划分, 
 Filter 
 分为 
 3 
 类: 
 Source Filter, Transform Filter, Rendering Filter 
 。前者负责获取数据,数据源可以是文件、数字摄像机等,然后将数据往下传输;中间者负责数据的格式转换,比如数据流的分离与合成、编码解码等,然后把数据继续往下传输;后者负责数据的去向 
 —— 
 给声卡、显卡进行播放或者输出到文件存储。 
 
 
 第二部分 
 核心技术 
 
 
 DirectShow 
 的开发实际就是 
 Filter 
 的开发, 
 DirectShow 
 自身提供了,下面就是 
 Filter 
 概述。 
 
 
 1 
 、 
 DirectShow 
 的 
  Filter
Filter 一般分为下面几种类型。
 
( 1 )源过滤器( source filter ):源过滤器引入数据到过滤器图表中,数据来源可以是文件、网络、照相机等。不同的源过滤器处理不同类型的数据源。
 
( 2 )变换过滤器( transform filter ):变换过滤器的工作是获取输入流,处理数据,并生成输出流。变换过滤器对数据的处理包括编解码、格式转换、压缩解压缩等。
 
( 3 )提交过滤器( renderer filter ):提交过滤器在过滤器图表里处于最后一级,它们接收数据并把数据提交给外设。
 
( 4 )分割过滤器( splitter filter ):分割过滤器把输入流分割成多个输出。例如, AVI 分割过滤器把一个 AVI 格式的字节流分割成视频流和音频流。
 
( 5 )混合过滤器( mux filter ):混合过滤器把多个输入组合成一个单独的数据流。例如, AVI 混合过滤器把视频流和音频流合成一个 AVI 格式的字节流。
 
过滤器的这些分类并不是绝对的,例如一个 ASF 读过滤器( ASF Reader filter )既是一个源过滤器又是一个分割过滤器。
 
2 、关于 Filter Graph Manager
 
Filter Graph Manager 也是一个 com 对象,用来控制 Filter graph 中的所有的 filter ,主要有以下的功能:
 
1) 用来协调 filter 之间的状态改变,从而使 graph 中的所有的 filter 的状态的改变应该一致。
 
2) 建立一个参考时钟。
 
3) 将 filter 的消息通知返回给应用程序
 
4) 提供用来建立 filter graph 的方法。
 
简单描述, Graph 就是各个 Filter 组成的一个流程图。
 
Filter 一般分为下面几种类型。
( 1 )源过滤器( source filter ):源过滤器引入数据到过滤器图表中,数据来源可以是文件、网络、照相机等。不同的源过滤器处理不同类型的数据源。
( 2 )变换过滤器( transform filter ):变换过滤器的工作是获取输入流,处理数据,并生成输出流。变换过滤器对数据的处理包括编解码、格式转换、压缩解压缩等。
( 3 )提交过滤器( renderer filter ):提交过滤器在过滤器图表里处于最后一级,它们接收数据并把数据提交给外设。
( 4 )分割过滤器( splitter filter ):分割过滤器把输入流分割成多个输出。例如, AVI 分割过滤器把一个 AVI 格式的字节流分割成视频流和音频流。
( 5 )混合过滤器( mux filter ):混合过滤器把多个输入组合成一个单独的数据流。例如, AVI 混合过滤器把视频流和音频流合成一个 AVI 格式的字节流。
过滤器的这些分类并不是绝对的,例如一个 ASF 读过滤器( ASF Reader filter )既是一个源过滤器又是一个分割过滤器。
2 、关于 Filter Graph Manager
Filter Graph Manager 也是一个 com 对象,用来控制 Filter graph 中的所有的 filter ,主要有以下的功能:
1) 用来协调 filter 之间的状态改变,从而使 graph 中的所有的 filter 的状态的改变应该一致。
2) 建立一个参考时钟。
3) 将 filter 的消息通知返回给应用程序
4) 提供用来建立 filter graph 的方法。
简单描述, Graph 就是各个 Filter 组成的一个流程图。
 
       SourceFilter----|-----SpliterFilter-------------(Video-pin)>-----TransFormFilter--->VideoRender 
 
 
                                            |---------------------(Audio-pin)->----ACMWraperFilter--->DirectSoundFilter 
 
 
 程序启动过程,先创建各个 
 filter 
 的 
 com 
 对象,然后使用 
 FilterGraph.Addfilter 
 加入到 
 Graph 
 中,然后把每个 
 Filter 
 按照 
 
 
 数据流把 
 OutPin 
 和 
 inpuin 
 连接起来。最好启动 
 FilterGraph.play 
 即可。 
 
Directshow 是基于模块化,每个功能模块都采取 COM 组件方式,称为 Filter 。 Directshow 提供了一系列的标准的模块可用于应用开发,开发者也可以开发自己的功能 Filter 来扩展 Directshow 的应用。下面我们用一个例子来说明如何采取 Filter 来播放一个 AVI 的视频文件。
1) 首先从一个文件中读取 AVI 数据,形成字节流。(这个工作由源 Filter 完成)
2) 检查 AVI 数据流的头格式,然后通过 AVI 分割 Filter 将视频流和音频流分开。
3) 解码视频流,根据压缩格式的不同,选取不同的 decoder filters 。
4) 通过 Renderer Filter 重画视频图像。
5) 音频流送到声卡进行播放,一般采用缺省的 DirectSound Device Filter 。
 
 状态改变, 
 Graph 
 中的 
 filter 
 的状态改变应该一致,因此,应用程序并将状态改变的命令直接发给 
 filter 
 ,而是将相应的状态改变的命令发送给 
 Filter graph Manager 
 ,由 
 manager 
 将命令分发给 
 graph 
 中每一个 
 filter 
 。 
 Seeking 
 也是同样的方式工作,首先由应用程序将 
 seek 
 命令发送到 
 filter graph  
 管理器,然后由其分发给每个 
 filter 
 。 
 
 
参考时钟, graph 中的 filter 都采用的同一个时钟,称为参考时钟( reference clock ),参考时钟可以确保所有的数据流同步,视频桢或者音频桢应该被提交的时间称为 presentation time.presentation time 是相对于参考时钟来确定的。 Filter graph Manager 应该选择一个参考时钟,可以选择声卡上的时钟,也可以选择系统时钟。
 
Graph 事件, Graph 管理器采用事件机制将 graph 中发生的事件通知给应用程序,这个机制类似于 windows 的消息循环机制。
 
Graph 构建的方法, graph 管理器给应用程序提供了将 filter 添加进 graph 的方法,连接 filter 的方法,断开 filter 连接的方法。
 
但是, graph 管理器没有提供如何将数据从一个 filter 发送到另一个 filter 的方法,这个工作是由 filter 在内部通过 pin 来独立完成的。
 
参考时钟, graph 中的 filter 都采用的同一个时钟,称为参考时钟( reference clock ),参考时钟可以确保所有的数据流同步,视频桢或者音频桢应该被提交的时间称为 presentation time.presentation time 是相对于参考时钟来确定的。 Filter graph Manager 应该选择一个参考时钟,可以选择声卡上的时钟,也可以选择系统时钟。
Graph 事件, Graph 管理器采用事件机制将 graph 中发生的事件通知给应用程序,这个机制类似于 windows 的消息循环机制。
Graph 构建的方法, graph 管理器给应用程序提供了将 filter 添加进 graph 的方法,连接 filter 的方法,断开 filter 连接的方法。
但是, graph 管理器没有提供如何将数据从一个 filter 发送到另一个 filter 的方法,这个工作是由 filter 在内部通过 pin 来独立完成的。
 
 3 
 、媒体类型 
 
 
因为 Directshow 是基于 com 组件的,就需要有一种方式来描述 filter graph 每一个点的数据格式,例如,我们还以播放 AVI 文件为例,数据以 RIFF 块的形式进入 graph 中,然后被分割成视频和音频流,视频流有一系列的压缩的视频桢组成,解压后,视频流由一系列的无压缩的位图组成,音频流也要走同样的步骤。
 
因为 Directshow 是基于 com 组件的,就需要有一种方式来描述 filter graph 每一个点的数据格式,例如,我们还以播放 AVI 文件为例,数据以 RIFF 块的形式进入 graph 中,然后被分割成视频和音频流,视频流有一系列的压缩的视频桢组成,解压后,视频流由一系列的无压缩的位图组成,音频流也要走同样的步骤。
 
 媒体类型是一种很普遍的,可以扩展的用来描述数字媒体格式的方法,当两个 
 filter 
 连接的时候,他们会就采用某一种媒体类型达成一致的协议。媒体类型定义了处于源头的 
 filter 
 将要给下游的 
 filter 
 发送什么样的数据,以及数据的 
 physical layout 
 。如果两个 
 filter 
 不能够支持同一种的媒体类型,那么他们就没法连接起来。 
 
 
对于大多数的应用来说,也许你不用考虑媒体类型,但是,有些应用程序中,你会直接应用到媒体类型的。
 
媒体类型是通过 AM_MEDIA_TYPE 结构定义的。
 
对于大多数的应用来说,也许你不用考虑媒体类型,但是,有些应用程序中,你会直接应用到媒体类型的。
媒体类型是通过 AM_MEDIA_TYPE 结构定义的。
 
 Filters 
 通过 
 pin 
 的连接来传递数据,数据流是从一个 
 filter 
 的输出 
 pin 
 流向相连的 
 filter 
 的输入 
 pin 
 。输出 
 pin 
 常用的传递数据的方式是调用输入 
 pin 
 上的 
 IMemInputPin::Receive 
 方法。 
 
 
 对于 
 filter 
 来说,可以有好几种方式来分配媒体数据使用的内存块,可以在堆上分配,可以在 
 DirectDraw 
 的表面,也可以采用 
 GDI 
 共享内存,还有其他的一些方法,在 
 Directshow 
 中用来进行内存分配任务的是内存分配器( 
 allocator 
 ),也是一个 
 COM 
 对象,暴露了一个 
 IMemAllocator 
 接口。 
 
 
当两个 pin 连接的时候,必须有一个 pin 提供一个 allocator , Directshow 定义了一系列函数调用用来确定由哪个 pin 提供 allocator ,以及 buffer 的数量和大小。
                当两个 pin 连接的时候,必须有一个 pin 提供一个 allocator , Directshow 定义了一系列函数调用用来确定由哪个 pin 提供 allocator ,以及 buffer 的数量和大小。

                  
                  
                  
                  
本文介绍了基于Delphi的DirectShow开发,详细阐述了DirectShow的核心概念,包括Filter、Filter Graph Manager以及媒体类型。DirectShow用于多媒体流的处理,支持多种数据源和格式,允许开发者自定义Filter扩展功能。文章还探讨了Filter的分类和连接,以及如何在Delphi中创建和连接Filter,为Delphi程序员提供了DirectShow开发的基础知识。
          
最低0.47元/天 解锁文章
                          
                      
      
          
                
                
                
                
              
                
                
                
                
                
              
                
                
              
            
                  
					6518
					
被折叠的  条评论
		 为什么被折叠?
		 
		 
		
    
  
    
  
            


            