directshow原理分析之filter到filter的智能连接

先看几个函数:

IFilterGraph::AddFilter:参数为一个Filter对象,将其加入到Filter Graph中

IFilterGraph::ConnectDirect:参数为一个输出Pin,一个出入Pin以及媒体类型,进行直接的链接

IGraphBuilder::AddSourceFilter:参数为源文件名,自动将一个Source Filter加入到Filter Graph中

IGraphBuilder::Connect:参数为输入Pin和输出Pin,如果连接失败,自动在中间加入必要的格式转化Filter

IGraphBuilder::Render:参数为输出Pin,自动加入必要的Filter完成剩下部分Filter Graph的构建

IGraphBuilder::RenderFile:参数提供源文件,自动加入必要的filter完成文件的回放


我们看到后四种均有"自动"一词,dshow中,这种功能叫做"智能连接"。


先来看一下Filter的Merit的值:

Merit可以理解为Filter被智能连接所使用的优先级:

enum {

MERIT_PREFERRED             = 0X800000,

MERIT_NORMAL              = 0X600000,

MERIT_UNLIKELY                   = 0X400000,

MERIT_DO_NOT_USE           = 0X200000,

MERIT_SW_COMPRESSOR = 0X100000,

MERIT_HW_COMPRESSOR = 0X100050

};

Filter的值只有在大于MERIT_DO_NOT_USE时,才有可能被智能连接。同等功能下,Merit的值越大,被连接的优先级越高。

修改Filter注册的Merit值:

打开注册表,在Filter的信息的注册部分都会发现一个为FilterData的二进制串类型的值,就是Merit。如下定义:

directshow原理分析之filter到filter的智能连接_第1张图片

typedef struct{

DWORD dwVersion;//版本号

DWORD dwMerit;//Merit的值

DWORD dwPinCount;//Pin的数量

DWORD dwReserver;//保留

}FILTER_HEADER;


下面介绍4中智能连接的具体实现:

IGraphBuilder::AddSourceFilter

该方法给出一个源文件路径:

 virtual HRESULT STDMETHODCALLTYPE AddSourceFilter( 
            /* [in] */ LPCWSTR lpcwstrFileName,
            /* [annotation][unique][in] */ 
            __in_opt  LPCWSTR lpcwstrFilterName,
            /* [annotation][out] */ 
            __out  IBaseFilter **ppFilter) = 0;

Filter Graph能够为该源文件路径加载一个Source Filter。该过程是一个文件解析的过程及查询注册表的过程。

首先,分析文件路径中是否有协议名(如http,htp等)若有,则在一下位置找:


首先在如下位置寻找这个协议名:

HKEY_CLASSES_ROOT

<protocol(比如rtsp)>

Source Filter = <Source filter CLSID>

Extensions

<.ext1> = <Source filter CLSID>

<.ext2> = <Source filter CLSID>


win7下是这个德行:


找到后,现在Extension子键下匹配扩展名。如果扩展名匹配不成功,则用Source Filter指定的CLSID。默认情况下,

注册表中找不到文件路径中的协议名,会创建一个File Source(URL)的filter。


如果文件中不包含协议名,就分析扩展名。去一下路径匹配扩展名:

HKEY_CLASSES_ROOT

MediaType

Extensions

directshow原理分析之filter到filter的智能连接_第2张图片


找不到就根据Source Filter键值指定的CLSID创建Filter。


















你可能感兴趣的:(directshow)