我写了一个CCRotateFilter来继承CTransformFilter, 用来浏览视频的时候旋转
下面是几个基本相关函数
HRESULT BuildGraph(HWND hWnd)
{
HRESULT hr;
hr = CoCreateInstance(CLSID_FilterGraph, NULL,
CLSCTX_INPROC_SERVER, IID_IGraphBuilder, (void **)&m_pGraph);
// Create the Capture Graph Builder.
hr = CoCreateInstance(CLSID_CaptureGraphBuilder, NULL,
CLSCTX_INPROC_SERVER, IID_ICaptureGraphBuilder2,
(void **)&m_pBuilder);
hr = m_pGraph->AddFilter(m_pCap, L"Video Capture Source");
m_pBuilder->SetFiltergraph(m_pGraph);
hr = CoCreateInstance(CLSID_VideoRenderer, NULL,
CLSCTX_INPROC_SERVER, IID_IBaseFilter,
(void **)&m_pRenderP);
hr = m_pGraph->AddFilter(m_pRenderP, L"Video Render");
hr = m_pBuilder->RenderStream(&PIN_CATEGORY_PREVIEW,&MEDIATYPE_Video, m_pCap, NULL, m_pRenderP);
//////////////////////////////////////////////////////////////////////////
// 添加自定义Filter
CCRotateFilter *pRollTranc = new CCRotateFilter(NULL, &hr);
pRollTranc->AddRef();
hr = pRollTranc->QueryInterface(__uuidof(IBaseFilter), (void**)&m_pTrancFilter);
if (FAILED(hr))
{
MessageBox(NULL,TEXT("QueryInterface1 失败"),L"",MB_OK);
}
hr = m_pGraph->AddFilter(m_pTrancFilter, L"My Filter");
if (FAILED(hr))
{
MessageBox(NULL,TEXT("AddFilter 失败"),L"",MB_OK);
}
IEnumFilters* pEnum;
hr = m_pGraph->EnumFilters(&pEnum);
if (FAILED(hr))
{
MessageBox(NULL,TEXT("EnumFilters 失败"),L"",MB_OK);
}
// IVideoWindow接口找到Renderer Filter
IBaseFilter* pVR = NULL;
hr = FindFilterByInterface(IID_IVideoWindow, &pVR);
if (FAILED(hr))
{
MessageBox(NULL,TEXT("FindFilterByInterface 失败"),L"",MB_OK);
}
// 查找Renderer Filter 输入pin
IPin* pPinIn = InputPinOf(pVR);
if (!pPinIn)
{
MessageBox(NULL,TEXT("失败"),L"",MB_OK);
}
// 查找连接在Renderer Filter输入pin上的输出pin
IPin* pPinOut = NULL;
hr = pPinIn->ConnectedTo(&pPinOut);
if (FAILED(hr))
{
MessageBox(NULL,TEXT("失败"),L"",MB_OK);
}
// 断开当前pin连接
hr = m_pGraph->Disconnect(pPinOut);
if (SUCCEEDED(hr))
{
hr = m_pGraph->Disconnect(pPinIn);
}
// 通过连接输入pin和输出pin连接我们自定的filter
if (SUCCEEDED(hr))
{
IPin* pPinInXfm = InputPinOf(m_pTrancFilter);
hr = m_pGraph->Connect(pPinOut, pPinInXfm);
pPinInXfm->Release();
}
if (SUCCEEDED(hr))
{
IPin* pPinOutXfm = OutputPinOf(m_pTrancFilter);
hr = m_pGraph->Connect(pPinOutXfm, pPinIn);
pPinOutXfm->Release();
}
pPinIn->Release();
pPinOut->Release();
//////////////////////////////////////////////////////////////////////////
// 用于调试,输出graph中所有的filter,以及各filter的所有pin及其连接
EnumFilters(m_pGraph);
hr = m_pRenderP->QueryInterface(IID_IVideoWindow, (void**)&m_pVideoWindow);
// 设置视频播放的WINDOWS窗口
m_pVideoWindow->put_MessageDrain((OAHWND)hWnd);
m_pVideoWindow->put_Owner((OAHWND)hWnd);
m_pVideoWindow->put_WindowStyle(WS_CHILD | WS_CLIPSIBLINGS | WS_CLIPCHILDREN);
//设置视频尺寸
m_pVideoWindow->SetWindowPosition(VIDEO_SRCCEN_LEFT, VIDEO_SRCCEN_TOP, VIDEO_SRCCEN_WIDTH, VIDEO_SRCCEN_HEIGHT);
m_pVideoWindow->put_Visible(OATRUE);
return hr;
}
HRESULT InitCapFilter()
{
HRESULT hr = S_OK;
GUID clsid = DEVCLASS_CAMERA_GUID;
IPersistPropertyBag *pPropertyBag = NULL;
// Create Capture Filter
CHK(hr = CoCreateInstance(CLSID_VideoCapture, NULL, CLSCTX_INPROC_SERVER,IID_IBaseFilter,