Signed-off-by: Nikolay Sivov nsivov@codeweavers.com --- dlls/evr/presenter.c | 84 ++++++++++++++++++++++++++++++++++++++++++++ dlls/evr/tests/evr.c | 4 +++ 2 files changed, 88 insertions(+)
diff --git a/dlls/evr/presenter.c b/dlls/evr/presenter.c index 9bf4cda3725..c1f29d41e4e 100644 --- a/dlls/evr/presenter.c +++ b/dlls/evr/presenter.c @@ -66,6 +66,7 @@ struct video_presenter IMFRateSupport IMFRateSupport_iface; IMFGetService IMFGetService_iface; IMFVideoPositionMapper IMFVideoPositionMapper_iface; + IQualProp IQualProp_iface; IMFVideoSampleAllocatorNotify allocator_cb; IUnknown IUnknown_inner; IUnknown *outer_unk; @@ -137,6 +138,11 @@ static struct video_presenter *impl_from_IMFVideoSampleAllocatorNotify(IMFVideoS return CONTAINING_RECORD(iface, struct video_presenter, allocator_cb); }
+static struct video_presenter *impl_from_IQualProp(IQualProp *iface) +{ + return CONTAINING_RECORD(iface, struct video_presenter, IQualProp_iface); +} + static void video_presenter_notify_renderer(struct video_presenter *presenter, LONG event, LONG_PTR param1, LONG_PTR param2) { @@ -444,6 +450,10 @@ static HRESULT WINAPI video_presenter_inner_QueryInterface(IUnknown *iface, REFI { *obj = &presenter->IMFVideoPositionMapper_iface; } + else if (IsEqualIID(riid, &IID_IQualProp)) + { + *obj = &presenter->IQualProp_iface; + } else { WARN("Unimplemented interface %s.\n", debugstr_guid(riid)); @@ -1285,6 +1295,79 @@ static const IMFVideoSampleAllocatorNotifyVtbl video_presenter_allocator_cb_vtbl video_presenter_allocator_cb_NotifyRelease, };
+static HRESULT WINAPI video_presenter_qualprop_QueryInterface(IQualProp *iface, REFIID riid, void **obj) +{ + struct video_presenter *presenter = impl_from_IQualProp(iface); + return IMFVideoPresenter_QueryInterface(&presenter->IMFVideoPresenter_iface, riid, obj); +} + +static ULONG WINAPI video_presenter_qualprop_AddRef(IQualProp *iface) +{ + struct video_presenter *presenter = impl_from_IQualProp(iface); + return IMFVideoPresenter_AddRef(&presenter->IMFVideoPresenter_iface); +} + +static ULONG WINAPI video_presenter_qualprop_Release(IQualProp *iface) +{ + struct video_presenter *presenter = impl_from_IQualProp(iface); + return IMFVideoPresenter_Release(&presenter->IMFVideoPresenter_iface); +} + +static HRESULT WINAPI video_presenter_qualprop_get_FramesDroppedInRenderer(IQualProp *iface, int *frames) +{ + FIXME("%p, %p stub.\n", iface, frames); + + return E_NOTIMPL; +} + +static HRESULT WINAPI video_presenter_qualprop_get_FramesDrawn(IQualProp *iface, int *frames) +{ + FIXME("%p, %p stub.\n", iface, frames); + + return E_NOTIMPL; +} + +static HRESULT WINAPI video_presenter_qualprop_get_AvgFrameRate(IQualProp *iface, int *avg_frame_rate) +{ + FIXME("%p, %p stub.\n", iface, avg_frame_rate); + + return E_NOTIMPL; +} + +static HRESULT WINAPI video_presenter_qualprop_get_Jitter(IQualProp *iface, int *jitter) +{ + FIXME("%p, %p stub.\n", iface, jitter); + + return E_NOTIMPL; +} + +static HRESULT WINAPI video_presenter_qualprop_get_AvgSyncOffset(IQualProp *iface, int *offset) +{ + FIXME("%p, %p stub.\n", iface, offset); + + return E_NOTIMPL; +} + +static HRESULT WINAPI video_presenter_qualprop_get_DevSyncOffset(IQualProp *iface, int *devoffset) +{ + FIXME("%p, %p stub.\n", iface, devoffset); + + return E_NOTIMPL; +} + +static const IQualPropVtbl video_presenter_qualprop_vtbl = +{ + video_presenter_qualprop_QueryInterface, + video_presenter_qualprop_AddRef, + video_presenter_qualprop_Release, + video_presenter_qualprop_get_FramesDroppedInRenderer, + video_presenter_qualprop_get_FramesDrawn, + video_presenter_qualprop_get_AvgFrameRate, + video_presenter_qualprop_get_Jitter, + video_presenter_qualprop_get_AvgSyncOffset, + video_presenter_qualprop_get_DevSyncOffset, +}; + HRESULT WINAPI MFCreateVideoPresenter(IUnknown *owner, REFIID riid_device, REFIID riid, void **obj) { TRACE("%p, %s, %s, %p.\n", owner, debugstr_guid(riid_device), debugstr_guid(riid), obj); @@ -1353,6 +1436,7 @@ HRESULT evr_presenter_create(IUnknown *outer, void **out) object->IMFRateSupport_iface.lpVtbl = &video_presenter_rate_support_vtbl; object->IMFGetService_iface.lpVtbl = &video_presenter_getservice_vtbl; object->IMFVideoPositionMapper_iface.lpVtbl = &video_presenter_position_mapper_vtbl; + object->IQualProp_iface.lpVtbl = &video_presenter_qualprop_vtbl; object->allocator_cb.lpVtbl = &video_presenter_allocator_cb_vtbl; object->IUnknown_inner.lpVtbl = &video_presenter_inner_vtbl; object->outer_unk = outer ? outer : &object->IUnknown_inner; diff --git a/dlls/evr/tests/evr.c b/dlls/evr/tests/evr.c index b8a16fc7cc9..bdf3154c7e5 100644 --- a/dlls/evr/tests/evr.c +++ b/dlls/evr/tests/evr.c @@ -1122,6 +1122,10 @@ static void test_default_presenter(void) if (FAILED(hr)) return;
+ hr = IMFVideoPresenter_QueryInterface(presenter, &IID_IQualProp, (void **)&unk); + ok(hr == S_OK, "Unexpected hr %#x.\n", hr); + IUnknown_Release(unk); + hr = IMFVideoPresenter_QueryInterface(presenter, &IID_IMFVideoPositionMapper, (void **)&unk); ok(hr == S_OK, "Unexpected hr %#x.\n", hr); IUnknown_Release(unk);
Signed-off-by: Nikolay Sivov nsivov@codeweavers.com --- dlls/evr/presenter.c | 54 +++++++++++++++++- dlls/evr/tests/evr.c | 128 +++++++++++++++++++++++++++++-------------- 2 files changed, 139 insertions(+), 43 deletions(-)
diff --git a/dlls/evr/presenter.c b/dlls/evr/presenter.c index c1f29d41e4e..fc3a1b52c51 100644 --- a/dlls/evr/presenter.c +++ b/dlls/evr/presenter.c @@ -77,6 +77,9 @@ struct video_presenter IMediaEventSink *event_sink;
IDirect3DDeviceManager9 *device_manager; + IDirect3DSwapChain9 *swapchain; + HANDLE hdevice; + IMFVideoSampleAllocator *allocator; struct streaming_thread thread; IMFMediaType *media_type; @@ -164,6 +167,19 @@ static unsigned int get_gcd(unsigned int a, unsigned int b) return a; }
+static HRESULT video_presenter_get_device(struct video_presenter *presenter, IDirect3DDevice9 **device) +{ + HRESULT hr; + + if (!presenter->hdevice) + { + if (FAILED(hr = IDirect3DDeviceManager9_OpenDeviceHandle(presenter->device_manager, &presenter->hdevice))) + return hr; + } + + return IDirect3DDeviceManager9_LockDevice(presenter->device_manager, presenter->hdevice, device, TRUE); +} + static void video_presenter_get_native_video_size(struct video_presenter *presenter) { IMFMediaType *media_type; @@ -501,8 +517,13 @@ static ULONG WINAPI video_presenter_inner_Release(IUnknown *iface) video_presenter_clear_container(presenter); video_presenter_reset_media_type(presenter); DeleteCriticalSection(&presenter->cs); + if (presenter->swapchain) + IDirect3DSwapChain9_Release(presenter->swapchain); if (presenter->device_manager) + { + IDirect3DDeviceManager9_CloseDeviceHandle(presenter->device_manager, presenter->hdevice); IDirect3DDeviceManager9_Release(presenter->device_manager); + } if (presenter->allocator) IMFVideoSampleAllocator_Release(presenter->allocator); heap_free(presenter); @@ -995,9 +1016,32 @@ static HRESULT WINAPI video_presenter_control_GetAspectRatioMode(IMFVideoDisplay return S_OK; }
+static HRESULT video_presenter_create_swapchain(struct video_presenter *presenter) +{ + D3DPRESENT_PARAMETERS present_params = { 0 }; + IDirect3DDevice9 *d3d_device; + HRESULT hr; + + if (SUCCEEDED(hr = video_presenter_get_device(presenter, &d3d_device))) + { + present_params.hDeviceWindow = presenter->video_window; + present_params.Windowed = TRUE; + present_params.SwapEffect = D3DSWAPEFFECT_COPY; + present_params.Flags = D3DPRESENTFLAG_VIDEO; + present_params.PresentationInterval = D3DPRESENT_INTERVAL_IMMEDIATE; + hr = IDirect3DDevice9_CreateAdditionalSwapChain(d3d_device, &present_params, &presenter->swapchain); + + IDirect3DDevice9_Release(d3d_device); + IDirect3DDeviceManager9_UnlockDevice(presenter->device_manager, presenter->hdevice, FALSE); + } + + return hr; +} + static HRESULT WINAPI video_presenter_control_SetVideoWindow(IMFVideoDisplayControl *iface, HWND window) { struct video_presenter *presenter = impl_from_IMFVideoDisplayControl(iface); + HRESULT hr = S_OK;
TRACE("%p, %p.\n", iface, window);
@@ -1005,10 +1049,16 @@ static HRESULT WINAPI video_presenter_control_SetVideoWindow(IMFVideoDisplayCont return E_INVALIDARG;
EnterCriticalSection(&presenter->cs); - presenter->video_window = window; + if (presenter->video_window != window) + { + if (presenter->swapchain) + IDirect3DSwapChain9_Release(presenter->swapchain); + presenter->video_window = window; + hr = video_presenter_create_swapchain(presenter); + } LeaveCriticalSection(&presenter->cs);
- return S_OK; + return hr; }
static HRESULT WINAPI video_presenter_control_GetVideoWindow(IMFVideoDisplayControl *iface, HWND *window) diff --git a/dlls/evr/tests/evr.c b/dlls/evr/tests/evr.c index bdf3154c7e5..d4c2ffb0480 100644 --- a/dlls/evr/tests/evr.c +++ b/dlls/evr/tests/evr.c @@ -1096,18 +1096,13 @@ done:
static void test_default_presenter(void) { - D3DDEVICE_CREATION_PARAMETERS device_params = { 0 }; - D3DPRESENT_PARAMETERS present_params = { 0 }; IMFVideoDisplayControl *display_control; - IDirect3DSwapChain9 *swapchain; IMFVideoPresenter *presenter; IMFRateSupport *rate_support; - IDirect3DDevice9 *d3d_device; IDirect3DDeviceManager9 *dm; IMFVideoDeviceID *deviceid; IMFGetService *gs; HWND hwnd, hwnd2; - HANDLE handle; IUnknown *unk; DWORD flags; float rate; @@ -1176,33 +1171,6 @@ static void test_default_presenter(void) hr = IMFVideoPresenter_QueryInterface(presenter, &IID_IMFVideoDisplayControl, (void **)&display_control); ok(hr == S_OK, "Unexpected hr %#x.\n", hr);
- hr = IDirect3DDeviceManager9_OpenDeviceHandle(dm, &handle); - ok(hr == S_OK, "Unexpected hr %#x.\n", hr); - - hr = IDirect3DDeviceManager9_LockDevice(dm, handle, &d3d_device, FALSE); - ok(hr == S_OK, "Unexpected hr %#x.\n", hr); - - hr = IDirect3DDevice9_GetCreationParameters(d3d_device, &device_params); - ok(hr == S_OK, "Unexpected hr %#x.\n", hr); - ok(device_params.hFocusWindow == GetDesktopWindow(), "Unexpected window %p.\n", device_params.hFocusWindow); - - hr = IDirect3DDevice9_GetSwapChain(d3d_device, 0, &swapchain); - ok(hr == S_OK, "Unexpected hr %#x.\n", hr); - - hr = IDirect3DSwapChain9_GetPresentParameters(swapchain, &present_params); - ok(hr == S_OK, "Unexpected hr %#x.\n", hr); - - ok(present_params.hDeviceWindow == GetDesktopWindow(), "Unexpected device window.\n"); - ok(present_params.Windowed, "Unexpected windowed mode.\n"); - ok(present_params.SwapEffect == D3DSWAPEFFECT_COPY, "Unexpected swap effect.\n"); - ok(present_params.Flags & D3DPRESENTFLAG_VIDEO, "Unexpected flags %#x.\n", present_params.Flags); - ok(present_params.PresentationInterval == D3DPRESENT_INTERVAL_IMMEDIATE, "Unexpected present interval.\n"); - - IDirect3DDevice9_Release(d3d_device); - - hr = IDirect3DDeviceManager9_UnlockDevice(dm, handle, FALSE); - ok(hr == S_OK, "Unexpected hr %#x.\n", hr); - /* Video window */ hwnd = create_window(); ok(!!hwnd, "Failed to create a test window.\n"); @@ -1229,15 +1197,6 @@ static void test_default_presenter(void) ok(hr == S_OK, "Unexpected hr %#x.\n", hr); ok(hwnd2 == hwnd, "Unexpected window %p.\n", hwnd2);
- /* Video position */ - hr = IDirect3DDeviceManager9_CloseDeviceHandle(dm, handle); - ok(hr == S_OK, "Unexpected hr %#x.\n", hr); - - IDirect3DDeviceManager9_Release(dm); - - IMFVideoDisplayControl_Release(display_control); - IMFGetService_Release(gs); - /* Rate support. */ hr = IMFVideoPresenter_QueryInterface(presenter, &IID_IMFRateSupport, (void **)&rate_support); ok(hr == S_OK, "Unexpected hr %#x.\n", hr); @@ -1920,6 +1879,92 @@ static void test_presenter_ar_mode(void) IMFVideoDisplayControl_Release(display_control); }
+static void test_presenter_video_window(void) +{ + D3DDEVICE_CREATION_PARAMETERS device_params = { 0 }; + IMFVideoDisplayControl *display_control; + IDirect3DDeviceManager9 *dm; + IDirect3DDevice9 *d3d_device; + HANDLE hdevice; + HRESULT hr; + IDirect3DSwapChain9 *swapchain; + D3DPRESENT_PARAMETERS present_params = { 0 }; + HWND window; + + hr = MFCreateVideoPresenter(NULL, &IID_IDirect3DDevice9, &IID_IMFVideoDisplayControl, (void **)&display_control); + ok(hr == S_OK, "Failed to create default presenter, hr %#x.\n", hr); + + hr = MFGetService((IUnknown *)display_control, &MR_VIDEO_ACCELERATION_SERVICE, + &IID_IDirect3DDeviceManager9, (void **)&dm); + + hr = IDirect3DDeviceManager9_OpenDeviceHandle(dm, &hdevice); + ok(hr == S_OK, "Unexpected hr %#x.\n", hr); + + hr = IDirect3DDeviceManager9_LockDevice(dm, hdevice, &d3d_device, FALSE); + ok(hr == S_OK, "Unexpected hr %#x.\n", hr); + + hr = IDirect3DDevice9_GetCreationParameters(d3d_device, &device_params); + ok(hr == S_OK, "Unexpected hr %#x.\n", hr); + ok(device_params.hFocusWindow == GetDesktopWindow(), "Unexpected window %p.\n", device_params.hFocusWindow); + + hr = IDirect3DDevice9_GetSwapChain(d3d_device, 0, &swapchain); + ok(hr == S_OK, "Unexpected hr %#x.\n", hr); + + hr = IDirect3DSwapChain9_GetPresentParameters(swapchain, &present_params); + ok(hr == S_OK, "Unexpected hr %#x.\n", hr); + + ok(present_params.hDeviceWindow == GetDesktopWindow(), "Unexpected device window.\n"); + ok(present_params.Windowed, "Unexpected windowed mode.\n"); + ok(present_params.SwapEffect == D3DSWAPEFFECT_COPY, "Unexpected swap effect.\n"); + ok(present_params.Flags & D3DPRESENTFLAG_VIDEO, "Unexpected flags %#x.\n", present_params.Flags); + ok(present_params.PresentationInterval == D3DPRESENT_INTERVAL_IMMEDIATE, "Unexpected present interval.\n"); + + IDirect3DSwapChain9_Release(swapchain); + IDirect3DDevice9_Release(d3d_device); + + hr = IDirect3DDeviceManager9_UnlockDevice(dm, hdevice, FALSE); + ok(hr == S_OK, "Unexpected hr %#x.\n", hr); + + /* Setting window. */ + hr = IMFVideoDisplayControl_GetVideoWindow(display_control, &window); + ok(hr == S_OK, "Unexpected hr %#x.\n", hr); + ok(!window, "Unexpected window %p.\n", window); + + window = create_window(); + + hr = IMFVideoDisplayControl_SetVideoWindow(display_control, window); + ok(hr == S_OK, "Unexpected hr %#x.\n", hr); + + /* Device is not recreated or reset on window change. */ + hr = IDirect3DDeviceManager9_LockDevice(dm, hdevice, &d3d_device, FALSE); + ok(hr == S_OK, "Unexpected hr %#x.\n", hr); + + hr = IDirect3DDevice9_GetSwapChain(d3d_device, 0, &swapchain); + ok(hr == S_OK, "Unexpected hr %#x.\n", hr); + + hr = IDirect3DSwapChain9_GetPresentParameters(swapchain, &present_params); + ok(hr == S_OK, "Unexpected hr %#x.\n", hr); + + ok(present_params.hDeviceWindow == GetDesktopWindow(), "Unexpected device window.\n"); + ok(present_params.Windowed, "Unexpected windowed mode.\n"); + ok(present_params.SwapEffect == D3DSWAPEFFECT_COPY, "Unexpected swap effect.\n"); + ok(present_params.Flags & D3DPRESENTFLAG_VIDEO, "Unexpected flags %#x.\n", present_params.Flags); + ok(present_params.PresentationInterval == D3DPRESENT_INTERVAL_IMMEDIATE, "Unexpected present interval.\n"); + + IDirect3DSwapChain9_Release(swapchain); + IDirect3DDevice9_Release(d3d_device); + + hr = IDirect3DDeviceManager9_UnlockDevice(dm, hdevice, FALSE); + ok(hr == S_OK, "Unexpected hr %#x.\n", hr); + + hr = IDirect3DDeviceManager9_CloseDeviceHandle(dm, hdevice); + ok(hr == S_OK, "Unexpected hr %#x.\n", hr); + + IMFVideoDisplayControl_Release(display_control); + + DestroyWindow(window); +} + static void test_mixer_output_rectangle(void) { IMFVideoMixerControl *mixer_control; @@ -2370,6 +2415,7 @@ START_TEST(evr) test_presenter_video_position(); test_presenter_native_video_size(); test_presenter_ar_mode(); + test_presenter_video_window(); test_mixer_output_rectangle(); test_mixer_zorder(); test_mixer_samples();
Signed-off-by: Nikolay Sivov nsivov@codeweavers.com --- dlls/evr/presenter.c | 80 ++++++++++++++++++++++++++++++++++++++++++++ dlls/evr/tests/evr.c | 62 +++++++++++----------------------- 2 files changed, 100 insertions(+), 42 deletions(-)
diff --git a/dlls/evr/presenter.c b/dlls/evr/presenter.c index fc3a1b52c51..97b9029c70e 100644 --- a/dlls/evr/presenter.c +++ b/dlls/evr/presenter.c @@ -67,6 +67,7 @@ struct video_presenter IMFGetService IMFGetService_iface; IMFVideoPositionMapper IMFVideoPositionMapper_iface; IQualProp IQualProp_iface; + IMFQualityAdvise IMFQualityAdvise_iface; IMFVideoSampleAllocatorNotify allocator_cb; IUnknown IUnknown_inner; IUnknown *outer_unk; @@ -146,6 +147,11 @@ static struct video_presenter *impl_from_IQualProp(IQualProp *iface) return CONTAINING_RECORD(iface, struct video_presenter, IQualProp_iface); }
+static struct video_presenter *impl_from_IMFQualityAdvise(IMFQualityAdvise *iface) +{ + return CONTAINING_RECORD(iface, struct video_presenter, IMFQualityAdvise_iface); +} + static void video_presenter_notify_renderer(struct video_presenter *presenter, LONG event, LONG_PTR param1, LONG_PTR param2) { @@ -470,6 +476,10 @@ static HRESULT WINAPI video_presenter_inner_QueryInterface(IUnknown *iface, REFI { *obj = &presenter->IQualProp_iface; } + else if (IsEqualIID(riid, &IID_IMFQualityAdvise)) + { + *obj = &presenter->IMFQualityAdvise_iface; + } else { WARN("Unimplemented interface %s.\n", debugstr_guid(riid)); @@ -1418,6 +1428,75 @@ static const IQualPropVtbl video_presenter_qualprop_vtbl = video_presenter_qualprop_get_DevSyncOffset, };
+static HRESULT WINAPI video_presenter_quality_advise_QueryInterface(IMFQualityAdvise *iface, REFIID riid, void **out) +{ + struct video_presenter *presenter = impl_from_IMFQualityAdvise(iface); + return IMFVideoPresenter_QueryInterface(&presenter->IMFVideoPresenter_iface, riid, out); +} + +static ULONG WINAPI video_presenter_quality_advise_AddRef(IMFQualityAdvise *iface) +{ + struct video_presenter *presenter = impl_from_IMFQualityAdvise(iface); + return IMFVideoPresenter_AddRef(&presenter->IMFVideoPresenter_iface); +} + +static ULONG WINAPI video_presenter_quality_advise_Release(IMFQualityAdvise *iface) +{ + struct video_presenter *presenter = impl_from_IMFQualityAdvise(iface); + return IMFVideoPresenter_Release(&presenter->IMFVideoPresenter_iface); +} + +static HRESULT WINAPI video_presenter_quality_advise_SetDropMode(IMFQualityAdvise *iface, + MF_QUALITY_DROP_MODE mode) +{ + FIXME("%p, %u.\n", iface, mode); + + return E_NOTIMPL; +} + +static HRESULT WINAPI video_presenter_quality_advise_SetQualityLevel(IMFQualityAdvise *iface, + MF_QUALITY_LEVEL level) +{ + FIXME("%p, %u.\n", iface, level); + + return E_NOTIMPL; +} + +static HRESULT WINAPI video_presenter_quality_advise_GetDropMode(IMFQualityAdvise *iface, + MF_QUALITY_DROP_MODE *mode) +{ + FIXME("%p, %p.\n", iface, mode); + + return E_NOTIMPL; +} + +static HRESULT WINAPI video_presenter_quality_advise_GetQualityLevel(IMFQualityAdvise *iface, + MF_QUALITY_LEVEL *level) +{ + FIXME("%p, %p.\n", iface, level); + + return E_NOTIMPL; +} + +static HRESULT WINAPI video_presenter_quality_advise_DropTime(IMFQualityAdvise *iface, LONGLONG interval) +{ + FIXME("%p, %s.\n", iface, wine_dbgstr_longlong(interval)); + + return E_NOTIMPL; +} + +static const IMFQualityAdviseVtbl video_presenter_quality_advise_vtbl = +{ + video_presenter_quality_advise_QueryInterface, + video_presenter_quality_advise_AddRef, + video_presenter_quality_advise_Release, + video_presenter_quality_advise_SetDropMode, + video_presenter_quality_advise_SetQualityLevel, + video_presenter_quality_advise_GetDropMode, + video_presenter_quality_advise_GetQualityLevel, + video_presenter_quality_advise_DropTime, +}; + HRESULT WINAPI MFCreateVideoPresenter(IUnknown *owner, REFIID riid_device, REFIID riid, void **obj) { TRACE("%p, %s, %s, %p.\n", owner, debugstr_guid(riid_device), debugstr_guid(riid), obj); @@ -1487,6 +1566,7 @@ HRESULT evr_presenter_create(IUnknown *outer, void **out) object->IMFGetService_iface.lpVtbl = &video_presenter_getservice_vtbl; object->IMFVideoPositionMapper_iface.lpVtbl = &video_presenter_position_mapper_vtbl; object->IQualProp_iface.lpVtbl = &video_presenter_qualprop_vtbl; + object->IMFQualityAdvise_iface.lpVtbl = &video_presenter_quality_advise_vtbl; object->allocator_cb.lpVtbl = &video_presenter_allocator_cb_vtbl; object->IUnknown_inner.lpVtbl = &video_presenter_inner_vtbl; object->outer_unk = outer ? outer : &object->IUnknown_inner; diff --git a/dlls/evr/tests/evr.c b/dlls/evr/tests/evr.c index d4c2ffb0480..882d61b9d37 100644 --- a/dlls/evr/tests/evr.c +++ b/dlls/evr/tests/evr.c @@ -461,17 +461,16 @@ static void test_default_mixer(void) hr = MFCreateVideoMixer(NULL, &IID_IDirect3DDevice9, &IID_IMFTransform, (void **)&transform); ok(hr == S_OK, "Failed to create default mixer, hr %#x.\n", hr);
- hr = IMFTransform_QueryInterface(transform, &IID_IMFQualityAdvise, (void **)&unk); - ok(hr == S_OK, "Unexpected hr %#x.\n", hr); - IUnknown_Release(unk); - - hr = IMFTransform_QueryInterface(transform, &IID_IMFClockStateSink, (void **)&unk); - ok(hr == S_OK, "Unexpected hr %#x.\n", hr); - IUnknown_Release(unk); - - hr = IMFTransform_QueryInterface(transform, &IID_IMFTopologyServiceLookupClient, (void **)&unk); - ok(hr == S_OK, "Unexpected hr %#x.\n", hr); - IUnknown_Release(unk); + check_interface(transform, &IID_IMFQualityAdvise, TRUE); + check_interface(transform, &IID_IMFClockStateSink, TRUE); + check_interface(transform, &IID_IMFTopologyServiceLookupClient, TRUE); + check_interface(transform, &IID_IMFGetService, TRUE); + check_interface(transform, &IID_IMFAttributes, TRUE); + check_interface(transform, &IID_IMFVideoMixerBitmap, TRUE); + check_interface(transform, &IID_IMFVideoPositionMapper, TRUE); + check_interface(transform, &IID_IMFVideoProcessor, TRUE); + check_interface(transform, &IID_IMFVideoMixerControl, TRUE); + check_interface(transform, &IID_IMFVideoDeviceID, TRUE);
hr = IMFTransform_QueryInterface(transform, &IID_IMFGetService, (void **)&gs); ok(hr == S_OK, "Unexpected hr %#x.\n", hr); @@ -534,22 +533,6 @@ todo_wine
IMFGetService_Release(gs);
- hr = IMFTransform_QueryInterface(transform, &IID_IMFVideoMixerBitmap, (void **)&unk); - ok(hr == S_OK, "Unexpected hr %#x.\n", hr); - IUnknown_Release(unk); - - hr = IMFTransform_QueryInterface(transform, &IID_IMFVideoPositionMapper, (void **)&unk); - ok(hr == S_OK, "Unexpected hr %#x.\n", hr); - IUnknown_Release(unk); - - hr = IMFTransform_QueryInterface(transform, &IID_IMFVideoProcessor, (void **)&unk); - ok(hr == S_OK, "Unexpected hr %#x.\n", hr); - IUnknown_Release(unk); - - hr = IMFTransform_QueryInterface(transform, &IID_IMFVideoMixerControl, (void **)&unk); - ok(hr == S_OK, "Unexpected hr %#x.\n", hr); - IUnknown_Release(unk); - hr = IMFTransform_SetOutputBounds(transform, 100, 10); ok(hr == S_OK, "Unexpected hr %#x.\n", hr);
@@ -1117,13 +1100,16 @@ static void test_default_presenter(void) if (FAILED(hr)) return;
- hr = IMFVideoPresenter_QueryInterface(presenter, &IID_IQualProp, (void **)&unk); - ok(hr == S_OK, "Unexpected hr %#x.\n", hr); - IUnknown_Release(unk); - - hr = IMFVideoPresenter_QueryInterface(presenter, &IID_IMFVideoPositionMapper, (void **)&unk); - ok(hr == S_OK, "Unexpected hr %#x.\n", hr); - IUnknown_Release(unk); + check_interface(presenter, &IID_IQualProp, TRUE); + check_interface(presenter, &IID_IMFVideoPositionMapper, TRUE); + check_interface(presenter, &IID_IMFTopologyServiceLookupClient, TRUE); + check_interface(presenter, &IID_IMFVideoDisplayControl, TRUE); + check_interface(presenter, &IID_IMFRateSupport, TRUE); + check_interface(presenter, &IID_IMFGetService, TRUE); + check_interface(presenter, &IID_IMFClockStateSink, TRUE); + check_interface(presenter, &IID_IMFVideoPresenter, TRUE); + check_interface(presenter, &IID_IMFVideoDeviceID, TRUE); + check_interface(presenter, &IID_IMFQualityAdvise, TRUE);
hr = MFGetService((IUnknown *)presenter, &MR_VIDEO_RENDER_SERVICE, &IID_IMFVideoPositionMapper, (void **)&unk); ok(hr == S_OK, "Unexpected hr %#x.\n", hr); @@ -1141,14 +1127,6 @@ static void test_default_presenter(void)
IMFVideoDeviceID_Release(deviceid);
- hr = IMFVideoPresenter_QueryInterface(presenter, &IID_IMFTopologyServiceLookupClient, (void **)&unk); - ok(hr == S_OK, "Unexpected hr %#x.\n", hr); - IUnknown_Release(unk); - - hr = IMFVideoPresenter_QueryInterface(presenter, &IID_IMFVideoDisplayControl, (void **)&unk); - ok(hr == S_OK, "Unexpected hr %#x.\n", hr); - IUnknown_Release(unk); - hr = IMFVideoPresenter_QueryInterface(presenter, &IID_IMFGetService, (void **)&gs); ok(hr == S_OK, "Unexpected hr %#x.\n", hr);
Signed-off-by: Nikolay Sivov nsivov@codeweavers.com --- dlls/evr/mixer.c | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-)
diff --git a/dlls/evr/mixer.c b/dlls/evr/mixer.c index 8eba3e3611b..66cb9b021a7 100644 --- a/dlls/evr/mixer.c +++ b/dlls/evr/mixer.c @@ -2207,7 +2207,7 @@ static ULONG WINAPI video_mixer_quality_advise_AddRef(IMFQualityAdvise *iface) return IMFTransform_AddRef(&mixer->IMFTransform_iface); }
-static ULONG WINAPI video_mixer_quality_Release(IMFQualityAdvise *iface) +static ULONG WINAPI video_mixer_quality_advise_Release(IMFQualityAdvise *iface) { struct video_mixer *mixer = impl_from_IMFQualityAdvise(iface); return IMFTransform_Release(&mixer->IMFTransform_iface); @@ -2252,7 +2252,7 @@ static const IMFQualityAdviseVtbl video_mixer_quality_advise_vtbl = { video_mixer_quality_advise_QueryInterface, video_mixer_quality_advise_AddRef, - video_mixer_quality_Release, + video_mixer_quality_advise_Release, video_mixer_quality_advise_SetDropMode, video_mixer_quality_advise_SetQualityLevel, video_mixer_quality_advise_GetDropMode,
Signed-off-by: Nikolay Sivov nsivov@codeweavers.com --- dlls/mf/tests/mf.c | 80 ++++++++++++++++++++-------------------------- 1 file changed, 34 insertions(+), 46 deletions(-)
diff --git a/dlls/mf/tests/mf.c b/dlls/mf/tests/mf.c index 9eccafee633..bd38785ea51 100644 --- a/dlls/mf/tests/mf.c +++ b/dlls/mf/tests/mf.c @@ -56,6 +56,21 @@ static void _expect_ref(IUnknown* obj, ULONG expected_refcount, int line) expected_refcount); }
+#define check_interface(a, b, c) check_interface_(__LINE__, a, b, c) +static void check_interface_(unsigned int line, void *iface_ptr, REFIID iid, BOOL supported) +{ + IUnknown *iface = iface_ptr; + HRESULT hr, expected_hr; + IUnknown *unk; + + expected_hr = supported ? S_OK : E_NOINTERFACE; + + hr = IUnknown_QueryInterface(iface, iid, (void **)&unk); + ok_(__FILE__, line)(hr == expected_hr, "Got hr %#x, expected %#x.\n", hr, expected_hr); + if (SUCCEEDED(hr)) + IUnknown_Release(unk); +} + static HWND create_window(void) { RECT r = {0, 0, 640, 480}; @@ -1028,7 +1043,6 @@ static void test_MFGetService(void)
static void test_sequencer_source(void) { - IMFMediaSourceTopologyProvider *provider; IMFSequencerSource *seq_source; HRESULT hr;
@@ -1038,9 +1052,7 @@ static void test_sequencer_source(void) hr = MFCreateSequencerSource(NULL, &seq_source); ok(hr == S_OK, "Failed to create sequencer source, hr %#x.\n", hr);
- hr = IMFSequencerSource_QueryInterface(seq_source, &IID_IMFMediaSourceTopologyProvider, (void **)&provider); - ok(hr == S_OK, "Failed to get provider interface, hr %#x.\n", hr); - IMFMediaSourceTopologyProvider_Release(provider); + check_interface(seq_source, &IID_IMFMediaSourceTopologyProvider, TRUE);
IMFSequencerSource_Release(seq_source);
@@ -1743,7 +1755,6 @@ static void test_presentation_clock(void) MFTIME systime, time; LONGLONG clock_time; MFCLOCK_STATE state; - IMFTimer *timer; unsigned int i; DWORD value; float rate; @@ -1756,6 +1767,12 @@ static void test_presentation_clock(void) hr = MFCreatePresentationClock(&clock); ok(hr == S_OK, "Failed to create presentation clock, hr %#x.\n", hr);
+ check_interface(clock, &IID_IMFTimer, TRUE); + check_interface(clock, &IID_IMFRateControl, TRUE); + check_interface(clock, &IID_IMFPresentationClock, TRUE); + check_interface(clock, &IID_IMFShutdown, TRUE); + check_interface(clock, &IID_IMFClock, TRUE); + hr = IMFPresentationClock_QueryInterface(clock, &IID_IMFRateControl, (void **)&rate_control); ok(hr == S_OK, "Failed to get rate control interface, hr %#x.\n", hr);
@@ -1945,10 +1962,6 @@ static void test_presentation_clock(void)
IMFRateControl_Release(rate_control);
- hr = IMFPresentationClock_QueryInterface(clock, &IID_IMFTimer, (void **)&timer); - ok(hr == S_OK, "Failed to get timer interface, hr %#x.\n", hr); - IMFTimer_Release(timer); - hr = IMFPresentationClock_QueryInterface(clock, &IID_IMFShutdown, (void **)&shutdown); ok(hr == S_OK, "Failed to get shutdown interface, hr %#x.\n", hr);
@@ -2084,7 +2097,6 @@ static void test_sample_grabber(void) IMFPresentationTimeSource *time_source; IMFPresentationClock *clock, *clock2; IMFStreamSink *stream, *stream2; - IMFClockStateSink *clocksink; IMFMediaEventGenerator *eg; IMFMediaSink *sink, *sink2; DWORD flags, count, id; @@ -2135,9 +2147,7 @@ static void test_sample_grabber(void) hr = IMFMediaSink_GetStreamSinkByIndex(sink, 0, &stream); ok(hr == S_OK, "Failed to get sink stream, hr %#x.\n", hr);
- hr = IMFStreamSink_QueryInterface(stream, &IID_IMFMediaEventGenerator, (void **)&unk); - ok(hr == S_OK, "Failed to get interface, hr %#x.\n", hr); - IUnknown_Release(unk); + check_interface(stream, &IID_IMFMediaEventGenerator, TRUE);
hr = IMFStreamSink_GetIdentifier(stream, &id); ok(hr == S_OK, "Failed to get stream id, hr %#x.\n", hr); @@ -2163,9 +2173,7 @@ static void test_sample_grabber(void) hr = IMFMediaSink_RemoveStreamSink(sink, 1); ok(hr == MF_E_STREAMSINKS_FIXED, "Unexpected hr %#x.\n", hr);
- hr = IMFMediaSink_QueryInterface(sink, &IID_IMFClockStateSink, (void **)&clocksink); - ok(hr == S_OK, "Failed to get interface, hr %#x.\n", hr); - IMFClockStateSink_Release(clocksink); + check_interface(sink, &IID_IMFClockStateSink, TRUE);
/* Event generator. */ hr = IMFMediaSink_QueryInterface(sink, &IID_IMFMediaEventGenerator, (void **)&eg); @@ -2915,14 +2923,9 @@ if (SUCCEEDED(hr)) ok(hr == S_OK, "Unexpected hr %#x.\n", hr); ok(flags == (MEDIASINK_FIXED_STREAMS | MEDIASINK_CAN_PREROLL), "Unexpected flags %#x.\n", flags);
- hr = IMFMediaSink_QueryInterface(sink, &IID_IMFMediaSinkPreroll, (void **)&unk); - ok(hr == S_OK, "Failed to get interface, hr %#x.\n", hr); - IUnknown_Release(unk); - - /* Events */ - hr = IMFMediaSink_QueryInterface(sink, &IID_IMFMediaEventGenerator, (void **)&unk); - ok(hr == S_OK, "Failed to get interface, hr %#x.\n", hr); - IUnknown_Release(unk); + check_interface(sink, &IID_IMFMediaSinkPreroll, TRUE); + check_interface(sink, &IID_IMFMediaEventGenerator, TRUE); + check_interface(sink, &IID_IMFClockStateSink, TRUE);
/* Clock */ hr = IMFMediaSink_QueryInterface(sink, &IID_IMFClockStateSink, (void **)&state_sink); @@ -2971,9 +2974,7 @@ todo_wine hr = IMFMediaSink_GetStreamSinkByIndex(sink, 0, &stream_sink); ok(hr == S_OK, "Failed to get a stream, hr %#x.\n", hr);
- hr = IMFStreamSink_QueryInterface(stream_sink, &IID_IMFMediaEventGenerator, (void **)&unk); - ok(hr == S_OK, "Failed to get interface, hr %#x.\n", hr); - IUnknown_Release(unk); + check_interface(stream_sink, &IID_IMFMediaEventGenerator, TRUE);
hr = IMFStreamSink_GetIdentifier(stream_sink, &id); ok(hr == S_OK, "Unexpected hr %#x.\n", hr); @@ -3236,12 +3237,9 @@ static void test_evr(void) IMFStreamSink *stream_sink, *stream_sink2; IMFVideoDisplayControl *display_control; IMFMediaType *media_type, *media_type2; - IMFMediaEventGenerator *ev_generator; IMFVideoSampleAllocator *allocator; IMFMediaTypeHandler *type_handler; IMFVideoRenderer *video_renderer; - IMFClockStateSink *clock_sink; - IMFMediaSinkPreroll *preroll; IMFMediaSink *sink, *sink2; IMFAttributes *attributes; IMFActivate *activate; @@ -3281,6 +3279,12 @@ static void test_evr(void) hr = IMFActivate_ActivateObject(activate, &IID_IMFMediaSink, (void **)&sink); ok(hr == S_OK, "Unexpected hr %#x.\n", hr);
+ check_interface(sink, &IID_IMFMediaSinkPreroll, TRUE); + check_interface(sink, &IID_IMFVideoRenderer, TRUE); + check_interface(sink, &IID_IMFMediaEventGenerator, TRUE); + check_interface(sink, &IID_IMFClockStateSink, TRUE); + check_interface(sink, &IID_IMFGetService, TRUE); + hr = MFGetService((IUnknown *)sink, &MR_VIDEO_RENDER_SERVICE, &IID_IMFVideoDisplayControl, (void **)&display_control); ok(hr == S_OK, "Unexpected hr %#x.\n", hr); @@ -3443,22 +3447,6 @@ static void test_evr(void) ok(hr == S_OK, "Unexpected hr %#x.\n", hr); ok(flags == (MEDIASINK_CAN_PREROLL | MEDIASINK_CLOCK_REQUIRED), "Unexpected flags %#x.\n", flags);
- hr = IMFMediaSink_QueryInterface(sink, &IID_IMFMediaSinkPreroll, (void **)&preroll); - ok(hr == S_OK, "Unexpected hr %#x.\n", hr); - IMFMediaSinkPreroll_Release(preroll); - - hr = IMFMediaSink_QueryInterface(sink, &IID_IMFVideoRenderer, (void **)&video_renderer); - ok(hr == S_OK, "Unexpected hr %#x.\n", hr); - IMFVideoRenderer_Release(video_renderer); - - hr = IMFMediaSink_QueryInterface(sink, &IID_IMFMediaEventGenerator, (void **)&ev_generator); - ok(hr == S_OK, "Unexpected hr %#x.\n", hr); - IMFMediaEventGenerator_Release(ev_generator); - - hr = IMFMediaSink_QueryInterface(sink, &IID_IMFClockStateSink, (void **)&clock_sink); - ok(hr == S_OK, "Unexpected hr %#x.\n", hr); - IMFClockStateSink_Release(clock_sink); - hr = IMFMediaSink_QueryInterface(sink, &IID_IMFGetService, (void **)&gs); ok(hr == S_OK, "Unexpected hr %#x.\n", hr);
Signed-off-by: Nikolay Sivov nsivov@codeweavers.com --- dlls/mf/evr.c | 80 ++++++++++++++++++++++++++++++++++++++++++++++ dlls/mf/tests/mf.c | 1 + 2 files changed, 81 insertions(+)
diff --git a/dlls/mf/evr.c b/dlls/mf/evr.c index f14f2f46612..8fa4e33f4e3 100644 --- a/dlls/mf/evr.c +++ b/dlls/mf/evr.c @@ -76,6 +76,7 @@ struct video_renderer IMFTopologyServiceLookup IMFTopologyServiceLookup_iface; IMediaEventSink IMediaEventSink_iface; IMFAttributes IMFAttributes_iface; + IMFQualityAdvise IMFQualityAdvise_iface; LONG refcount;
IMFMediaEventQueue *event_queue; @@ -141,6 +142,11 @@ static struct video_renderer *impl_from_IMFAttributes(IMFAttributes *iface) return CONTAINING_RECORD(iface, struct video_renderer, IMFAttributes_iface); }
+static struct video_renderer *impl_from_IMFQualityAdvise(IMFQualityAdvise *iface) +{ + return CONTAINING_RECORD(iface, struct video_renderer, IMFQualityAdvise_iface); +} + static struct video_stream *impl_from_IMFStreamSink(IMFStreamSink *iface) { return CONTAINING_RECORD(iface, struct video_stream, IMFStreamSink_iface); @@ -657,6 +663,10 @@ static HRESULT WINAPI video_renderer_sink_QueryInterface(IMFMediaSink *iface, RE { *obj = &renderer->IMFAttributes_iface; } + else if (IsEqualIID(riid, &IID_IMFQualityAdvise)) + { + *obj = &renderer->IMFQualityAdvise_iface; + } else { WARN("Unsupported interface %s.\n", debugstr_guid(riid)); @@ -2120,6 +2130,75 @@ static const IMFAttributesVtbl video_renderer_attributes_vtbl = video_renderer_attributes_CopyAllItems, };
+static HRESULT WINAPI video_renderer_quality_advise_QueryInterface(IMFQualityAdvise *iface, REFIID riid, void **out) +{ + struct video_renderer *renderer = impl_from_IMFQualityAdvise(iface); + return IMFMediaSink_QueryInterface(&renderer->IMFMediaSink_iface, riid, out); +} + +static ULONG WINAPI video_renderer_quality_advise_AddRef(IMFQualityAdvise *iface) +{ + struct video_renderer *renderer = impl_from_IMFQualityAdvise(iface); + return IMFMediaSink_AddRef(&renderer->IMFMediaSink_iface); +} + +static ULONG WINAPI video_renderer_quality_Release(IMFQualityAdvise *iface) +{ + struct video_renderer *renderer = impl_from_IMFQualityAdvise(iface); + return IMFMediaSink_Release(&renderer->IMFMediaSink_iface); +} + +static HRESULT WINAPI video_renderer_quality_advise_SetDropMode(IMFQualityAdvise *iface, + MF_QUALITY_DROP_MODE mode) +{ + FIXME("%p, %u.\n", iface, mode); + + return E_NOTIMPL; +} + +static HRESULT WINAPI video_renderer_quality_advise_SetQualityLevel(IMFQualityAdvise *iface, + MF_QUALITY_LEVEL level) +{ + FIXME("%p, %u.\n", iface, level); + + return E_NOTIMPL; +} + +static HRESULT WINAPI video_renderer_quality_advise_GetDropMode(IMFQualityAdvise *iface, + MF_QUALITY_DROP_MODE *mode) +{ + FIXME("%p, %p.\n", iface, mode); + + return E_NOTIMPL; +} + +static HRESULT WINAPI video_renderer_quality_advise_GetQualityLevel(IMFQualityAdvise *iface, + MF_QUALITY_LEVEL *level) +{ + FIXME("%p, %p.\n", iface, level); + + return E_NOTIMPL; +} + +static HRESULT WINAPI video_renderer_quality_advise_DropTime(IMFQualityAdvise *iface, LONGLONG interval) +{ + FIXME("%p, %s.\n", iface, wine_dbgstr_longlong(interval)); + + return E_NOTIMPL; +} + +static const IMFQualityAdviseVtbl video_renderer_quality_advise_vtbl = +{ + video_renderer_quality_advise_QueryInterface, + video_renderer_quality_advise_AddRef, + video_renderer_quality_Release, + video_renderer_quality_advise_SetDropMode, + video_renderer_quality_advise_SetQualityLevel, + video_renderer_quality_advise_GetDropMode, + video_renderer_quality_advise_GetQualityLevel, + video_renderer_quality_advise_DropTime, +}; + static HRESULT evr_create_object(IMFAttributes *attributes, void *user_context, IUnknown **obj) { struct video_renderer *object; @@ -2141,6 +2220,7 @@ static HRESULT evr_create_object(IMFAttributes *attributes, void *user_context, object->IMFTopologyServiceLookup_iface.lpVtbl = &video_renderer_service_lookup_vtbl; object->IMediaEventSink_iface.lpVtbl = &media_event_sink_vtbl; object->IMFAttributes_iface.lpVtbl = &video_renderer_attributes_vtbl; + object->IMFQualityAdvise_iface.lpVtbl = &video_renderer_quality_advise_vtbl; object->refcount = 1; InitializeCriticalSection(&object->cs);
diff --git a/dlls/mf/tests/mf.c b/dlls/mf/tests/mf.c index bd38785ea51..43dc9a49ee7 100644 --- a/dlls/mf/tests/mf.c +++ b/dlls/mf/tests/mf.c @@ -3284,6 +3284,7 @@ static void test_evr(void) check_interface(sink, &IID_IMFMediaEventGenerator, TRUE); check_interface(sink, &IID_IMFClockStateSink, TRUE); check_interface(sink, &IID_IMFGetService, TRUE); + check_interface(sink, &IID_IMFQualityAdvise, TRUE);
hr = MFGetService((IUnknown *)sink, &MR_VIDEO_RENDER_SERVICE, &IID_IMFVideoDisplayControl, (void **)&display_control);