2012-06-21 3 views
6

Direct3D 응용 프로그램의 여러 스레드와 개체간에 하나의 Direct3D 장치를 공유하고 싶습니다.Direct3D 장치 관리자는 어떻게 사용합니까?

// Create the device manager 
    UINT resetToken = 0; 
    IDirect3DDeviceManager9* deviceManager = NULL; 
    if (FAILED(DXVA2CreateDirect3DDeviceManager9(&resetToken, &deviceManager))) 
    return false; 

    // Add the device to the device manager 
    if (FAILED(deviceManager->ResetDevice(device, resetToken))) 
    return false; 

    deviceManager->AddRef(); 
: 나는 다음과 같은 일을 해요 내 코드에서 http://msdn.microsoft.com/en-us/library/windows/desktop/aa965267(v=vs.85).aspx

: 어떤 비디오 프로세싱이나 비디오 가속을하고 있지 않다하더라도 나는, 내가 원하는처럼 보이는 Direct3D를 장치 관리자를 건너 왔어요

Direct3D 장치 관리자를 만든 후에는 장치 관리자에 대한 포인터를 전달하지 않고 direct3d 장치 관리자를 다른 개체와 어떻게 공유합니까? 마이크로 소프트는 특히 다음을 수행 말했다,하지만 난 정말 다음 무엇을 의미하는지 단서가 없다 :

장치 소유자가 다른 개체가 IDirect3DDeviceManager9 인터페이스에 대한 포인터 을 얻을 수있는 방법을 제공해야합니다. 표준 메커니즘은 IMFGetService 인터페이스를 구현하는 것입니다. 서비스 GUID는 MR_VIDEO_ACCELERATION_SERVICE입니다.

누군가 IMFGetService 인터페이스를 사용하여 장치 관리자를 공유하는 방법을 보여줄 수 있습니까?

답변

4

비디오 처리를하지 않으면 IDirect3DDeviceManager9 인터페이스를 구현하거나 사용하는 데 아무런 의미가 없습니다.

Direct3D 장치의 수명을 관리하는 방법을 구현하여 개체/스레드에서 인터페이스 포인터를 사용할 수있게하고 동기화를 수행하기 만하면됩니다. Direct3D 장치는 IDirect3DDeviceManager9을 사용하여 개체/스레드간에 만 공유 할 수있는 마법 같은 것이 아닙니다. 다른 리소스와 같습니다. 올바르게 초기화하면 다른 스레드 (즉, 다른 스레드에 의해 변경 될 수있는 장치 상태에 의존하지 않는 거의 모든 것)에서 특정 메소드를 동시에 호출 할 수도 있습니다.

인터페이스 포인터를 사용 가능하게 만드는 것은 포인터를 보유하는 싱글 톤을 갖는 것처럼 간단 할 수 있습니다. 또는 개체/스레드가 이미 어떤 방법으로 공동 작업을 수행하는 경우 이미 정보를 교환 할 수있는 방법이 있어야합니다. 그래서 당신이 이미 Direct3D 장치에 대한 개체/스레드 액세스 권한을 부여하기 위해 확장 할 수 있어야한다고 생각합니다. 그리고 동기화는 CRITICAL_SECTION을 사용하여 쉽게 수행 할 수 있습니다.

IDirect3DDeviceManager9을 실제로 사용하려면 - 이해하는 한 - IDirect3DDeviceManager9에 액세스하려는 모든 개체에 IMFGetService 인터페이스를 구현해야합니다. GetService 함수를 구현하여 MR_VIDEO_ACCELERATION_SERVICE/IDirect3DDeviceManager9을 요청하면 Direct3D 장치를 관리하는 개체에 대한 인터페이스 포인터를 반환합니다. 코드 샘플에 대해서는 :


편집 여기에 주어진 설명이 충분 바랍니다. 여러 스레드간에 물건을 공유하는 것은 짧은 코드 샘플로 설명하려고하지 않을 것입니다. 멀티 스레드 응용 프로그램을 작성하는 방법을 알고 있다면 Direct3D 장치를 사용하는 것이 다른 리소스로 수행 된 방법과 다르지 않습니다. 멀티 스레드 응용 프로그램을 작성하는 방법을 모르는 경우에는 단일 스택 오버플로 응답에서 너무 복잡합니다.

MS가 IDirect3DDeviceManager9을 사용하도록 권장하는 질문에 관해서는 ... 음, 나는 그런 일반적인 권장 사항을 알지 못합니다.비디오 처리 (DXVA, EVR 등 사용)를 할 때 권장됩니다. 또는 위임 된 것보다; 예를 들어 D3D 기기를 공유 할 수 있는지 확실하지 않습니다. D3D 장치 매니저를 사용하지 않고, Enhanced Video Renderer 결국 D3D 장치 관리자가 만들어졌습니다. VMR9를 사용하여 렌더러와 장치를 공유하는 것은 다음 두 가지 방법으로 만 가능했습니다.

문서화 된 방법 :은 VMR9의 "현재"콜백에서 장치에 액세스합니다. 다소 제한적입니다. 동영상의 프레임 속도로 제한됩니다.

문서화되지 않은 방법 :IVMRFilterConfig9::SetNumberOfStreams을 호출하지 않고 하나의 입력 스트림 만 연결합니다. 그렇게하면 VMR9는 "믹서 모드"로 전환하지 않으며 "믹서 모드"가 아닌 경우 VMR9는 어떠한 장치 상태도 변경하지 않습니다. 따라서 D3D 장치가 멀티 스레드로 초기화 된 경우 VMR9가 동일한 장치를 사용하는 동안 D3D 장치를 자유롭게 사용할 수 있습니다.

또한 VMR9에서는 다른 DirectShow 필터에서 D3D 장치를 전혀 사용할 수 없었습니다. D3D 장치 관리자는 필터와 자신의 응용 프로그램 코드에 상태를 변경하는 것을 포함하여 D3D 장치를 사용할 수있는 기능을 제공합니다. 그러나 D3D 장치를 직접 사용할 모든 구성 요소를 구현하면 D3D 장치 관리자가 실제로 사용하지 않을 것입니다. D3D 장치가 필요한 타사 구성 요소를 사용하는 경우에도 해당 구성 요소가 D3D 장치 관리자를 지원할 경우에만 D3D 장치 관리자를 사용할 수 있습니다. 이러한 구성 요소가 DirectShow 또는 MediaFoundation 필터/구성 요소가 아닌 경우에는 그렇지 않을 수 있습니다.