From: Conor McCarthy cmccarthy@codeweavers.com
Signed-off-by: Conor McCarthy cmccarthy@codeweavers.com Signed-off-by: Józef Kucia jkucia@codeweavers.com --- dlls/dxgi/dxgi_private.h | 2 + dlls/dxgi/output.c | 69 ++++++++++++++++++++++++++++++++ dlls/dxgi/swapchain.c | 82 ++++++++++++++++++++++++++++++++------- dlls/wined3d/swapchain.c | 58 --------------------------- dlls/wined3d/wined3d.spec | 1 - include/wine/wined3d.h | 2 - 6 files changed, 138 insertions(+), 76 deletions(-)
diff --git a/dlls/dxgi/dxgi_private.h b/dlls/dxgi/dxgi_private.h index 553eacee3b80..2f21d8e5b0ca 100644 --- a/dlls/dxgi/dxgi_private.h +++ b/dlls/dxgi/dxgi_private.h @@ -148,6 +148,8 @@ struct dxgi_output };
HRESULT dxgi_output_create(struct dxgi_adapter *adapter, struct dxgi_output **output) DECLSPEC_HIDDEN; +HRESULT dxgi_output_get_display_mode(IDXGIOutput *iface, DXGI_MODE_DESC *mode) DECLSPEC_HIDDEN; +HRESULT dxgi_output_set_display_mode(IDXGIOutput *iface, DXGI_MODE_DESC *mode) DECLSPEC_HIDDEN;
/* IDXGIAdapter */ struct dxgi_adapter diff --git a/dlls/dxgi/output.c b/dlls/dxgi/output.c index 123dee8c99e2..3dcbb5d6e540 100644 --- a/dlls/dxgi/output.c +++ b/dlls/dxgi/output.c @@ -522,6 +522,14 @@ static const struct IDXGIOutput4Vtbl dxgi_output_vtbl = dxgi_output_CheckOverlayColorSpaceSupport, };
+static struct dxgi_output *unsafe_impl_from_IDXGIOutput(IDXGIOutput *iface) +{ + if (!iface) + return NULL; + assert(iface->lpVtbl == (IDXGIOutputVtbl *)&dxgi_output_vtbl); + return CONTAINING_RECORD(iface, struct dxgi_output, IDXGIOutput4_iface); +} + static void dxgi_output_init(struct dxgi_output *output, struct dxgi_adapter *adapter) { output->IDXGIOutput4_iface.lpVtbl = &dxgi_output_vtbl; @@ -539,3 +547,64 @@ HRESULT dxgi_output_create(struct dxgi_adapter *adapter, struct dxgi_output **ou dxgi_output_init(*output, adapter); return S_OK; } + +HRESULT dxgi_output_get_display_mode(IDXGIOutput *iface, DXGI_MODE_DESC *mode) +{ + struct wined3d_display_mode wined3d_mode; + struct dxgi_adapter *adapter; + struct dxgi_output *target; + struct wined3d *wined3d; + HRESULT hr; + + target = unsafe_impl_from_IDXGIOutput(iface); + adapter = target->adapter; + wined3d = adapter->factory->wined3d; + + wined3d_mutex_lock(); + hr = wined3d_get_adapter_display_mode(wined3d, adapter->ordinal, &wined3d_mode, NULL); + wined3d_mutex_unlock(); + + if (FAILED(hr)) + { + WARN("Failed to get display mode, hr %#x.\n", hr); + return DXGI_ERROR_INVALID_CALL; + } + + dxgi_mode_from_wined3d(mode, &wined3d_mode); + + TRACE("Returning %s.\n", debug_dxgi_mode(mode)); + + return S_OK; +} + +HRESULT dxgi_output_set_display_mode(IDXGIOutput *iface, DXGI_MODE_DESC *mode) +{ + struct wined3d_display_mode wined3d_mode; + struct dxgi_adapter *adapter; + struct dxgi_output *target; + struct wined3d *wined3d; + HRESULT hr; + + target = unsafe_impl_from_IDXGIOutput(iface); + adapter = target->adapter; + wined3d = adapter->factory->wined3d; + + wined3d_display_mode_from_dxgi(&wined3d_mode, mode); + + if (FAILED(hr = dxgi_output_find_closest_matching_mode(target, &wined3d_mode, NULL))) + WARN("Failed to find closest matching mode, hr %#x.\n", hr); + else /* Copy the actual mode back to the caller */ + dxgi_mode_from_wined3d(mode, &wined3d_mode); + + wined3d_mutex_lock(); + hr = wined3d_set_adapter_display_mode(wined3d, adapter->ordinal, &wined3d_mode); + wined3d_mutex_unlock(); + + if (FAILED(hr)) + { + WARN("Failed to set display mode, hr %#x.\n", hr); + return DXGI_ERROR_INVALID_CALL; + } + + return S_OK; +} diff --git a/dlls/dxgi/swapchain.c b/dlls/dxgi/swapchain.c index 8dbbfab805d3..b7a4fd5cbad8 100644 --- a/dlls/dxgi/swapchain.c +++ b/dlls/dxgi/swapchain.c @@ -152,6 +152,70 @@ static HRESULT dxgi_get_output_from_window(IDXGIAdapter *adapter, HWND window, I return DXGI_ERROR_NOT_FOUND; }
+static HRESULT dxgi_swapchain_resize_target(IDXGISwapChain1 *iface, + const DXGI_SWAP_CHAIN_DESC *desc, const DXGI_MODE_DESC *mode) +{ + RECT original_window_rect, window_rect; + HWND window = desc->OutputWindow; + HRESULT hr; + + if (!mode) + { + WARN("Invalid pointer.\n"); + return DXGI_ERROR_INVALID_CALL; + } + + TRACE("Mode: %s.\n", debug_dxgi_mode(mode)); + + if (mode->Scaling) + FIXME("Ignoring scaling %#x.\n", mode->Scaling); + + if (desc->Windowed) + { + SetRect(&window_rect, 0, 0, mode->Width, mode->Height); + AdjustWindowRectEx(&window_rect, + GetWindowLongW(window, GWL_STYLE), FALSE, + GetWindowLongW(window, GWL_EXSTYLE)); + SetRect(&window_rect, 0, 0, + window_rect.right - window_rect.left, window_rect.bottom - window_rect.top); + GetWindowRect(window, &original_window_rect); + OffsetRect(&window_rect, original_window_rect.left, original_window_rect.top); + } + else + { + DXGI_MODE_DESC actual_mode; + IDXGIOutput *target; + + if (FAILED(hr = IDXGISwapChain1_GetContainingOutput(iface, &target))) + { + WARN("Failed to get output, hr %#x.\n", hr); + return hr; + } + + if (desc->Flags & DXGI_SWAP_CHAIN_FLAG_ALLOW_MODE_SWITCH) + { + actual_mode = *mode; + hr = dxgi_output_set_display_mode(target, &actual_mode); + } + else + { + hr = dxgi_output_get_display_mode(target, &actual_mode); + } + + IDXGIOutput_Release(target); + + if (FAILED(hr)) + return hr; + + SetRect(&window_rect, 0, 0, actual_mode.Width, actual_mode.Height); + } + + MoveWindow(window, window_rect.left, window_rect.top, + window_rect.right - window_rect.left, window_rect.bottom - window_rect.top, TRUE); + + return S_OK; +} + static HWND d3d11_swapchain_get_hwnd(struct d3d11_swapchain *swapchain) { struct wined3d_swapchain_desc wined3d_desc; @@ -507,25 +571,13 @@ static HRESULT STDMETHODCALLTYPE d3d11_swapchain_ResizeBuffers(IDXGISwapChain1 * static HRESULT STDMETHODCALLTYPE d3d11_swapchain_ResizeTarget(IDXGISwapChain1 *iface, const DXGI_MODE_DESC *target_mode_desc) { - struct d3d11_swapchain *swapchain = d3d11_swapchain_from_IDXGISwapChain1(iface); - struct wined3d_display_mode mode; + DXGI_SWAP_CHAIN_DESC swap_chain_desc;
TRACE("iface %p, target_mode_desc %p.\n", iface, target_mode_desc);
- if (!target_mode_desc) - { - WARN("Invalid pointer.\n"); - return DXGI_ERROR_INVALID_CALL; - } - - TRACE("Mode: %s.\n", debug_dxgi_mode(target_mode_desc)); - - if (target_mode_desc->Scaling) - FIXME("Ignoring scaling %#x.\n", target_mode_desc->Scaling); - - wined3d_display_mode_from_dxgi(&mode, target_mode_desc); + d3d11_swapchain_GetDesc(iface, &swap_chain_desc);
- return wined3d_swapchain_resize_target(swapchain->wined3d_swapchain, &mode); + return dxgi_swapchain_resize_target(iface, &swap_chain_desc, target_mode_desc); }
static HRESULT STDMETHODCALLTYPE d3d11_swapchain_GetContainingOutput(IDXGISwapChain1 *iface, IDXGIOutput **output) diff --git a/dlls/wined3d/swapchain.c b/dlls/wined3d/swapchain.c index b75aead1e831..8aa8b92a0a98 100644 --- a/dlls/wined3d/swapchain.c +++ b/dlls/wined3d/swapchain.c @@ -1361,64 +1361,6 @@ static HRESULT wined3d_swapchain_set_display_mode(struct wined3d_swapchain *swap return WINED3D_OK; }
-HRESULT CDECL wined3d_swapchain_resize_target(struct wined3d_swapchain *swapchain, - const struct wined3d_display_mode *mode) -{ - struct wined3d_display_mode actual_mode; - RECT original_window_rect, window_rect; - struct wined3d_device *device; - HWND window; - HRESULT hr; - - TRACE("swapchain %p, mode %p.\n", swapchain, mode); - - wined3d_mutex_lock(); - - device = swapchain->device; - window = swapchain->device_window; - - if (swapchain->desc.windowed) - { - SetRect(&window_rect, 0, 0, mode->width, mode->height); - AdjustWindowRectEx(&window_rect, - GetWindowLongW(window, GWL_STYLE), FALSE, - GetWindowLongW(window, GWL_EXSTYLE)); - SetRect(&window_rect, 0, 0, - window_rect.right - window_rect.left, window_rect.bottom - window_rect.top); - GetWindowRect(window, &original_window_rect); - OffsetRect(&window_rect, original_window_rect.left, original_window_rect.top); - } - else if (swapchain->desc.flags & WINED3D_SWAPCHAIN_ALLOW_MODE_SWITCH) - { - actual_mode = *mode; - if (FAILED(hr = wined3d_swapchain_set_display_mode(swapchain, &actual_mode))) - { - wined3d_mutex_unlock(); - return hr; - } - SetRect(&window_rect, 0, 0, actual_mode.width, actual_mode.height); - } - else - { - if (FAILED(hr = wined3d_get_adapter_display_mode(device->wined3d, device->adapter->ordinal, - &actual_mode, NULL))) - { - ERR("Failed to get display mode, hr %#x.\n", hr); - wined3d_mutex_unlock(); - return hr; - } - - SetRect(&window_rect, 0, 0, actual_mode.width, actual_mode.height); - } - - wined3d_mutex_unlock(); - - MoveWindow(window, window_rect.left, window_rect.top, - window_rect.right - window_rect.left, window_rect.bottom - window_rect.top, TRUE); - - return WINED3D_OK; -} - HRESULT CDECL wined3d_swapchain_set_fullscreen(struct wined3d_swapchain *swapchain, const struct wined3d_swapchain_desc *swapchain_desc, const struct wined3d_display_mode *mode) { diff --git a/dlls/wined3d/wined3d.spec b/dlls/wined3d/wined3d.spec index 59f99c91e075..904bb3461ffb 100644 --- a/dlls/wined3d/wined3d.spec +++ b/dlls/wined3d/wined3d.spec @@ -274,7 +274,6 @@ @ cdecl wined3d_swapchain_incref(ptr) @ cdecl wined3d_swapchain_present(ptr ptr ptr ptr long long) @ cdecl wined3d_swapchain_resize_buffers(ptr long long long long long long) -@ cdecl wined3d_swapchain_resize_target(ptr ptr) @ cdecl wined3d_swapchain_set_fullscreen(ptr ptr ptr) @ cdecl wined3d_swapchain_set_gamma_ramp(ptr long ptr) @ cdecl wined3d_swapchain_set_palette(ptr ptr) diff --git a/include/wine/wined3d.h b/include/wine/wined3d.h index abef3f0ad021..d1d3ca42e599 100644 --- a/include/wine/wined3d.h +++ b/include/wine/wined3d.h @@ -2690,8 +2690,6 @@ HRESULT __cdecl wined3d_swapchain_present(struct wined3d_swapchain *swapchain, c HRESULT __cdecl wined3d_swapchain_resize_buffers(struct wined3d_swapchain *swapchain, unsigned int buffer_count, unsigned int width, unsigned int height, enum wined3d_format_id format_id, enum wined3d_multisample_type multisample_type, unsigned int multisample_quality); -HRESULT __cdecl wined3d_swapchain_resize_target(struct wined3d_swapchain *swapchain, - const struct wined3d_display_mode *mode); HRESULT __cdecl wined3d_swapchain_set_fullscreen(struct wined3d_swapchain *swapchain, const struct wined3d_swapchain_desc *desc, const struct wined3d_display_mode *mode); HRESULT __cdecl wined3d_swapchain_set_gamma_ramp(const struct wined3d_swapchain *swapchain,