#include <windows.h>
#include <dshow.h>
// 初始化 DirectShow
HRESULT InitializeDirectShow(HWND hwnd) {
// 初始化 COM
CoInitialize(NULL);
// 创建 Filter Graph Manager
IGraphBuilder *pGraph = NULL;
CoCreateInstance(CLSID_FilterGraph, NULL, CLSCTX_INPROC_SERVER, IID_IGraphBuilder, (void **)&pGraph);
// 创建 Capture Graph Builder
ICaptureGraphBuilder2 *pCaptureGraphBuilder = NULL;
CoCreateInstance(CLSID_CaptureGraphBuilder2, NULL, CLSCTX_INPROC_SERVER, IID_ICaptureGraphBuilder2, (void **)&pCaptureGraphBuilder);
// 设置 Filter Graph Manager 到 Capture Graph Builder
pCaptureGraphBuilder->SetFiltergraph(pGraph);
// 创建设备过滤器,比如摄像头
IBaseFilter *pDeviceFilter = NULL;
CoCreateInstance(CLSID_VideoInputDeviceCategory, NULL, CLSCTX_INPROC_SERVER, IID_IBaseFilter, (void **)&pDeviceFilter);
// 将设备过滤器添加到 Filter Graph Manager
pGraph->AddFilter(pDeviceFilter, L"Video Capture");
// 渲染流到窗口
pCaptureGraphBuilder->RenderStream(&PIN_CATEGORY_PREVIEW, &MEDIATYPE_Video, pDeviceFilter, NULL, NULL);
// 获取 IMediaEvent 接口
IMediaEvent *pMediaEvent = NULL;
pGraph->QueryInterface(IID_IMediaEvent, (void **)&pMediaEvent);
// 设置窗口句柄以接收事件
pMediaEvent->SetNotifyWindow((OAHWND)hwnd, WM_GRAPHNOTIFY, 0);
// 释放资源
pDeviceFilter->Release();
pCaptureGraphBuilder->Release();
return S_OK;
}
// 处理消息的窗口过程
LRESULT CALLBACK WindowProc(HWND hwnd, UINT uMsg, WPARAM wParam, LPARAM lParam) {
switch (uMsg) {
case WM_CREATE:
// 在窗口创建时初始化 DirectShow
InitializeDirectShow(hwnd);
break;
case WM_DESTROY:
// 在窗口销毁时清理资源
CoUninitialize();
PostQuitMessage(0);
break;
case WM_GRAPHNOTIFY:
// 处理媒体事件
HandleMediaEvent(hwnd);
break;
default:
return DefWindowProc(hwnd, uMsg, wParam, lParam);
}
return 0;
}
// 处理媒体事件的函数
void HandleMediaEvent(HWND hwnd) {
long evCode, param1, param2;
IMediaEvent *pMediaEvent = NULL;
// 获取 IMediaEvent 接口
pGraph->QueryInterface(IID_IMediaEvent, (void **)&pMediaEvent);
// 处理所有待处理的事件
while (pMediaEvent->GetEvent(&evCode, ¶m1, ¶m2, 0) == S_OK) {
// 在这里处理事件,可以根据事件类型执行相应的操作
switch (evCode) {
case EC_COMPLETE:
// 播放完成事件
break;
case EC_USERABORT:
// 用户中断事件
break;
// 其他事件类型可以在这里处理
default:
break;
}
// 释放事件资源
pMediaEvent->FreeEventParams(evCode, param1, param2);
}
pMediaEvent->Release();
}
请注意,这只是一个简单的示例代码,实际使用时可能需要根据具体需求进行更详细的处理。此外,需要注意在使用 DirectShow 时,要包含正确的头文件和链接正确的库文件。
转载请注明出处:http://www.zyzy.cn/article/detail/25103/Win32 API/Control.h/IMediaEvent