媒体基础 EVR 和 DirectX 11

Media Foundation EVR and DirectX 11

我正在尝试在 Windows 10(桌面)上使用 DirectX 11 为 Media Foundation 编写 EVR。 到目前为止我找到的唯一解决方案是 here 不幸的是,我(和其他许多人一样)不知道如何正确使用它。 有人可以为我指明如何将 MF 与 DirectX 11/12 结合的正确方向吗?

我正在使用激活我的 EVR 的代码:

hr = MFCreateVideoRendererActivate(hwndVideo, &pRendererActivate);
hr = pRendererActivate->SetGUID(MF_ACTIVATE_CUSTOM_VIDEO_PRESENTER_CLSID, CLSID_DX11VideoRenderer);

我到了 MF 请求 GetDeviceID 并且在 kernel.dll 中引发异常的地步。我认为混合器和渲染器设备之间存在不匹配。他们的默认设备是 DX9。在我的示例中,我必须提供 DirectX 11 设备 CLSID。

DX11VideoRenderer 是展示如何使用基于 Dx11 的 Presenter 的一个很好的例子。但是没有太多的代码片段来演示如何使用它。

您可以通过两种方式查看:

  1. 使用regsvr32注册编译好的DX11VideoRenderer COM CLSID,并添加到TopoEdit中。
  2. 无需注册即可使用。

    • 调用 LoadLibrary() 到 dll。
    • 调用 GetProcAddress() 获取 DllGetClassObject() 的 pfn。
    • 使用 CLSID_DX11VideoRenderer 和 IID_IClassFactory 调用上面的 pfn 以检索媒体接收器工厂。
    • 使用媒体接收器工厂创建媒体接收器。
    • 将媒体接收器添加到拓扑。

代码片段:

typedef HRESULT(_stdcall *PFN_GetClassObject)(REFCLSID, REFIID, LPVOID*);
HMODULE hSink = NULL;
PFN_GetClassObject pfn = NULL;
HRESULT hr = E_FAIL;
IClassFactory *pMediaSinkFactory = NULL;
IMFMediaSink *pMediaSink = NULL;

hSink = ::LoadLibraryEx(L“DX11VideoRenderer.dll”, 
            NULL, 
            LOAD_LIBRARY_SEARCH_DEFAULT_DIRS | LOAD_LIBRARY_SEARCH_DLL_LOAD_DIR);

if(hSink)
    pfn = (PFN_GetClassObject)GetProcAddress(
            hSink, 
            "DllGetClassObject");

if(pfn)
    hr = pfn(CLSID_DX11VideoRenderer, 
            IID_IClassFactory, 
            (LPVOID*)&pMediaSinkFactory);

if(pMediaSinkFactory){
    pMediaSinkFactory->CreateInstance(NULL, 
        __uuidof(IMFMediaSink), 
        (LPVOID*)&pMediaSink);
    pMediaSinkFactory->Release();
}