DirectShow入门之构建Graph图常用技术
2008-04-09 04:10:46来源:互联网 阅读 ()
作者:智慧的鱼
摘要:本文主要讲述了Graph图构建过程中常用的技巧,主要的内容如下:
·如何根据CLSID向graph中添加filter
·如何查找filter空闲的pin
·如何连接两个Filter
·如何获得filter或者pin的接口指针
·如何查找和某个filter的上下相连的filter
·如何删除graph中的所有filter
·如何利用Capture Graph Builder构建Graph图表
如何根据CLSID向graph中添加filter
下面的代码演示了如何利用CLSID生成一个filter,然后将其加入到graph图中
IGraphBuilder *pGraph, // Pointer to the Filter Graph Manager.
const GUID& clsid, // CLSID of the filter to create.
LPCWSTR wszName, // A name for the filter.
IBaseFilter **ppF) // Receives a pointer to the filter.
{
if (!pGraph || ! ppF) return E_POINTER;
*ppF = 0;
IBaseFilter *pF = 0;
HRESULT hr = CoCreateInstance(clsid, 0, CLSCTX_INPROC_SERVER,
IID_IBaseFilter, reinterpret_cast
if (SUCCEEDED(hr))
{
hr = pGraph->AddFilter(pF, wszName);
if (SUCCEEDED(hr))
*ppF = pF;
else
pF->Release();
}
return hr;
}
在你的应用程序中,你可以这样用这个函数
IBaseFilter *pMux;
hr = AddFilterByCLSID(pGraph, CLSID_AviDest, L"AVI Mux", &pMux);
if (SUCCEEDED(hr))
{
/* ... */
pMux->Release();
}
注:有些filter是不能通过with CoCreateInstance方法创建的。例如AVI Compressor Filter和WDM Video Capture filter
如何查找filter空闲的pin
看代码吧:
HRESULT GetUnconnectedPin(
IBaseFilter *pFilter, // Pointer to the filter.
PIN_DIRECTION PinDir, // Direction of the pin to find.
IPin **ppPin) // Receives a pointer to the pin.
{
*ppPin = 0;
IEnumPins *pEnum = 0;
IPin *pPin = 0;
HRESULT hr = pFilter->EnumPins(&pEnum);
if (FAILED(hr))
{
return hr;
}
while (pEnum->Next(1, &pPin, NULL) == S_OK)
{
PIN_DIRECTION ThisPinDir;
pPin->QueryDirection(&ThisPinDir);
if (ThisPinDir == PinDir)
{
IPin *pTmp = 0;
hr = pPin->ConnectedTo(&pTmp);
if (SUCCEEDED(hr)) // Already connected, not the pin we want.
{
pTmp->Release();
}
else // Unconnected, 这就是我们想要的pin,空闲的pin
{
pEnum->Release();
*ppPin = pPin;
return S_OK;
}
}
pPin->Release();
}
pEnum->Release();
// Did not find a matching pin.
return E_FAIL;
}
下面的代码演示了如何利用上面的函数来在一个filter查找一个输出的空闲的pin。
IPin *pOut = NULL;
HRESULT hr = GetUnconnectedPin(pFilter, PINDIR_OUTPUT, &pOut);
if (SUCCEEDED(hr))
{
/* ... */
pOut->Release();
}
如何连接两个Filter
下面的函数演示了如何将一个filter的输出pin和另一个filter的第一个空闲的输入pin进行连接。
HRESULT ConnectFilters(
IGraphBuilder *pGraph, // Filter Graph Manager.
IPin *pOut, // Output pin on the upstream filter.
IBaseFilter *pDest) // Downstream filter.
{
if ((pGraph == NULL) || (pOut == NULL) || (pDest == NULL))
{
return E_POINTER;
}
#ifdef debug
PIN_DIRECTION PinDir;
pOut->QueryDirection(&PinDir);
_ASSERTE(PinDir == PINDIR_OUTPUT);
#endif
//找一个空闲的输入pin
IPin *pIn = 0;
HRESULT hr = GetUnconnectedPin(pDest, PINDIR_INPUT, &pIn);
if (FAILED(hr))
{
return hr;
}
// Try to connect them.
hr = pGraph->Connect(pOut, pIn);
pIn->Release();
return hr;
}
下面是ConnectFilters的一个重载函数,但是第二个参数是一个指向filter的指针,而不是指向pin的指针,这个函数将两个filter连接起来。
HRESULT ConnectFilters(
IGraphBuilder *pGraph,
IBaseFilter *pSrc,
IBaseFilter *pDest)
{
if ((pGraph == NULL) || (pSrc == NULL) || (pDest == NULL))
{
return E_POINTER;
}
// 首先在第一个filter上查询一个输出的pin接口
IPin *pOut = 0;
HRESULT hr = GetUnconnectedPin(pSrc, PINDIR_OUTPUT, &pOut);
if (FAILED(hr))
{
return hr;
}
//然后将它和第二个filter的输入接口衔接。
hr = ConnectFilters(pGraph, pOut, pDest);
pOut->Release();
return hr;
}
下面的函数演示了利用这个函数来连接AVIMux 过滤器和File Writer过滤器,这个例子也使用了AddFilterByCLSID函数。
IBaseFilter *pMux, *pWrite;
hr = AddFilterByCLSID(pGraph, CLSID_AviDest, L"AVI Mux", &pMux);
if (SUCCEEDED(hr))
{
hr = AddFilterByCLSID(pGraph, CLSID_FileWriter, L"File Writer", &pWrite);
if (SUCCEEDED(hr))
标签:
版权申明:本站文章部分自网络,如有侵权,请联系:west999com@outlook.com
特别注意:本站所有转载文章言论不代表本站观点,本站所提供的摄影照片,插画,设计作品,如需使用,请与原作者联系,版权归原作者所有
下一篇:三种常见中文内码的转换方法
IDC资讯: 主机资讯 注册资讯 托管资讯 vps资讯 网站建设
网站运营: 建站经验 策划盈利 搜索优化 网站推广 免费资源
网络编程: Asp.Net编程 Asp编程 Php编程 Xml编程 Access Mssql Mysql 其它
服务器技术: Web服务器 Ftp服务器 Mail服务器 Dns服务器 安全防护
软件技巧: 其它软件 Word Excel Powerpoint Ghost Vista QQ空间 QQ FlashGet 迅雷
网页制作: FrontPages Dreamweaver Javascript css photoshop fireworks Flash