[PATCH] WineD3D: Add a swapchain method to set the dest override=0A=
Stefan Doesinger
stefan at codeweavers.com
Mon Jul 28 22:34:32 CDT 2008
=0A=
DDraw can draw to the front buffer only, thus there's never a=0A=
Present call which could pass this window. Due to that a=0A=
drawing-independent method is needed.=0A=
=0A=
The Present parameter is still in place due to d3d8/9. The d3d8/9=0A=
override is used for one swap only, and changing it is supposed=0A=
to be cheap. This cannot be implemented properly with our current=0A=
GL utilities, but in the future we might implement such a dest=0A=
window override using GL_EXT_framebuffer_blit and write a=0A=
different swapchain implementation that makes a difference=0A=
between the two overrides=0A=
---=0A=
dlls/wined3d/swapchain.c | 73 =
+++++++++++++++++++++----------------=0A=
dlls/wined3d/swapchain_gdi.c | 8 ++++=0A=
include/wine/wined3d_interface.h | 2 +=0A=
3 files changed, 51 insertions(+), 32 deletions(-)=0A=
=0A=
diff --git a/dlls/wined3d/swapchain.c b/dlls/wined3d/swapchain.c=0A=
index 9ec296c..1a82ab8 100644=0A=
--- a/dlls/wined3d/swapchain.c=0A=
+++ b/dlls/wined3d/swapchain.c=0A=
@@ -144,38 +144,7 @@ static HRESULT WINAPI =
IWineD3DSwapChainImpl_Present(IWineD3DSwapChain *iface, CO=0A=
=0A=
/* Don't call checkGLcall, as glGetError is not applicable here */=0A=
if (hDestWindowOverride && This->win_handle !=3D =
hDestWindowOverride) {=0A=
- WINED3DLOCKED_RECT r;=0A=
- BYTE *mem;=0A=
-=0A=
- TRACE("Performing dest override of swapchain %p from window %p =
to %p\n", This, This->win_handle, hDestWindowOverride);=0A=
- if(This->context[0] =3D=3D This->wineD3DDevice->contexts[0]) {=0A=
- /* The primary context 'owns' all the opengl resources. =
Destroying and recreating that context requires downloading=0A=
- * all opengl resources, deleting the gl resources, =
destroying all other contexts, then recreating all other contexts=0A=
- * and reload the resources=0A=
- */=0A=
- delete_opengl_contexts((IWineD3DDevice *) =
This->wineD3DDevice, iface);=0A=
- This->win_handle =3D hDestWindowOverride;=0A=
- create_primary_opengl_context((IWineD3DDevice *) =
This->wineD3DDevice, iface);=0A=
- } else {=0A=
- This->win_handle =3D hDestWindowOverride;=0A=
-=0A=
- /* The old back buffer has to be copied over to the new =
back buffer. A lockrect - switchcontext - unlockrect=0A=
- * would suffice in theory, but it is rather nasty and may =
cause troubles with future changes of the locking code=0A=
- * So lock read only, copy the surface out, then lock with =
the discard flag and write back=0A=
- */=0A=
- IWineD3DSurface_LockRect(This->backBuffer[0], &r, NULL, =
WINED3DLOCK_READONLY);=0A=
- mem =3D HeapAlloc(GetProcessHeap(), 0, r.Pitch * =
((IWineD3DSurfaceImpl *) This->backBuffer[0])->currentDesc.Height);=0A=
- memcpy(mem, r.pBits, r.Pitch * ((IWineD3DSurfaceImpl *) =
This->backBuffer[0])->currentDesc.Height);=0A=
- IWineD3DSurface_UnlockRect(This->backBuffer[0]);=0A=
-=0A=
- DestroyContext(This->wineD3DDevice, This->context[0]);=0A=
- This->context[0] =3D CreateContext(This->wineD3DDevice, =
(IWineD3DSurfaceImpl *) This->frontBuffer, This->win_handle, FALSE /* =
pbuffer */, &This->presentParms);=0A=
-=0A=
- IWineD3DSurface_LockRect(This->backBuffer[0], &r, NULL, =
WINED3DLOCK_DISCARD);=0A=
- memcpy(r.pBits, mem, r.Pitch * ((IWineD3DSurfaceImpl *) =
This->backBuffer[0])->currentDesc.Height);=0A=
- HeapFree(GetProcessHeap(), 0, mem);=0A=
- IWineD3DSurface_UnlockRect(This->backBuffer[0]);=0A=
- }=0A=
+ IWineD3DSwapChain_SetDestWindowOverride(iface, =
hDestWindowOverride);=0A=
}=0A=
=0A=
SwapBuffers(This->context[0]->hdc); /* TODO: cycle through the =
swapchain buffers */=0A=
@@ -335,6 +304,45 @@ static HRESULT WINAPI =
IWineD3DSwapChainImpl_Present(IWineD3DSwapChain *iface, CO=0A=
return WINED3D_OK;=0A=
}=0A=
=0A=
+static HRESULT WINAPI =
IWineD3DSwapChainImpl_SetDestWindowOverride(IWineD3DSwapChain *iface, =
HWND window) {=0A=
+ IWineD3DSwapChainImpl *This =3D (IWineD3DSwapChainImpl *)iface;=0A=
+ WINED3DLOCKED_RECT r;=0A=
+ BYTE *mem;=0A=
+=0A=
+ if(window =3D=3D This->win_handle) return WINED3D_OK;=0A=
+=0A=
+ TRACE("Performing dest override of swapchain %p from window %p to =
%p\n", This, This->win_handle, window);=0A=
+ if(This->context[0] =3D=3D This->wineD3DDevice->contexts[0]) {=0A=
+ /* The primary context 'owns' all the opengl resources. =
Destroying and recreating that context requires downloading=0A=
+ * all opengl resources, deleting the gl resources, destroying =
all other contexts, then recreating all other contexts=0A=
+ * and reload the resources=0A=
+ */=0A=
+ delete_opengl_contexts((IWineD3DDevice *) This->wineD3DDevice, =
iface);=0A=
+ This->win_handle =3D window;=0A=
+ create_primary_opengl_context((IWineD3DDevice *) =
This->wineD3DDevice, iface);=0A=
+ } else {=0A=
+ This->win_handle =3D window;=0A=
+=0A=
+ /* The old back buffer has to be copied over to the new back =
buffer. A lockrect - switchcontext - unlockrect=0A=
+ * would suffice in theory, but it is rather nasty and may =
cause troubles with future changes of the locking code=0A=
+ * So lock read only, copy the surface out, then lock with the =
discard flag and write back=0A=
+ */=0A=
+ IWineD3DSurface_LockRect(This->backBuffer[0], &r, NULL, =
WINED3DLOCK_READONLY);=0A=
+ mem =3D HeapAlloc(GetProcessHeap(), 0, r.Pitch * =
((IWineD3DSurfaceImpl *) This->backBuffer[0])->currentDesc.Height);=0A=
+ memcpy(mem, r.pBits, r.Pitch * ((IWineD3DSurfaceImpl *) =
This->backBuffer[0])->currentDesc.Height);=0A=
+ IWineD3DSurface_UnlockRect(This->backBuffer[0]);=0A=
+=0A=
+ DestroyContext(This->wineD3DDevice, This->context[0]);=0A=
+ This->context[0] =3D CreateContext(This->wineD3DDevice, =
(IWineD3DSurfaceImpl *) This->frontBuffer, This->win_handle, FALSE /* =
pbuffer */, &This->presentParms);=0A=
+=0A=
+ IWineD3DSurface_LockRect(This->backBuffer[0], &r, NULL, =
WINED3DLOCK_DISCARD);=0A=
+ memcpy(r.pBits, mem, r.Pitch * ((IWineD3DSurfaceImpl *) =
This->backBuffer[0])->currentDesc.Height);=0A=
+ HeapFree(GetProcessHeap(), 0, mem);=0A=
+ IWineD3DSurface_UnlockRect(This->backBuffer[0]);=0A=
+ }=0A=
+ return WINED3D_OK;=0A=
+}=0A=
+=0A=
const IWineD3DSwapChainVtbl IWineD3DSwapChain_Vtbl =3D=0A=
{=0A=
/* IUnknown */=0A=
@@ -346,6 +354,7 @@ const IWineD3DSwapChainVtbl IWineD3DSwapChain_Vtbl =3D=0A=
IWineD3DSwapChainImpl_Destroy,=0A=
IWineD3DBaseSwapChainImpl_GetDevice,=0A=
IWineD3DSwapChainImpl_Present,=0A=
+ IWineD3DSwapChainImpl_SetDestWindowOverride,=0A=
IWineD3DBaseSwapChainImpl_GetFrontBufferData,=0A=
IWineD3DBaseSwapChainImpl_GetBackBuffer,=0A=
IWineD3DBaseSwapChainImpl_GetRasterStatus,=0A=
diff --git a/dlls/wined3d/swapchain_gdi.c b/dlls/wined3d/swapchain_gdi.c=0A=
index 7aa81c2..d76b9b5 100644=0A=
--- a/dlls/wined3d/swapchain_gdi.c=0A=
+++ b/dlls/wined3d/swapchain_gdi.c=0A=
@@ -156,6 +156,13 @@ void x11_copy_to_screen(IWineD3DSwapChainImpl =
*This, LPRECT rc) {=0A=
}=0A=
}=0A=
=0A=
+static HRESULT WINAPI =
IWineGDISwapChainImpl_SetDestWindowOverride(IWineD3DSwapChain *iface, =
HWND window) {=0A=
+ IWineD3DSwapChainImpl *This =3D (IWineD3DSwapChainImpl *)iface;=0A=
+=0A=
+ This->win_handle =3D window;=0A=
+ return WINED3D_OK;=0A=
+}=0A=
+=0A=
static HRESULT WINAPI IWineGDISwapChainImpl_Present(IWineD3DSwapChain =
*iface, CONST RECT *pSourceRect, CONST RECT *pDestRect, HWND =
hDestWindowOverride, CONST RGNDATA *pDirtyRegion, DWORD dwFlags) {=0A=
IWineD3DSwapChainImpl *This =3D (IWineD3DSwapChainImpl *) iface;=0A=
IWineD3DSurfaceImpl *front, *back;=0A=
@@ -254,6 +261,7 @@ const IWineD3DSwapChainVtbl IWineGDISwapChain_Vtbl =3D=0A=
IWineGDISwapChainImpl_Destroy,=0A=
IWineD3DBaseSwapChainImpl_GetDevice,=0A=
IWineGDISwapChainImpl_Present,=0A=
+ IWineGDISwapChainImpl_SetDestWindowOverride,=0A=
IWineD3DBaseSwapChainImpl_GetFrontBufferData,=0A=
IWineD3DBaseSwapChainImpl_GetBackBuffer,=0A=
IWineD3DBaseSwapChainImpl_GetRasterStatus,=0A=
diff --git a/include/wine/wined3d_interface.h =
b/include/wine/wined3d_interface.h=0A=
index 0768b0a..d2c8a2c 100644=0A=
--- a/include/wine/wined3d_interface.h=0A=
+++ b/include/wine/wined3d_interface.h=0A=
@@ -1421,6 +1421,7 @@ DECLARE_INTERFACE_(IWineD3DSwapChain,IWineD3DBase)=0A=
STDMETHOD_(void, Destroy)(THIS_ D3DCB_DESTROYSURFACEFN pFn) PURE;=0A=
STDMETHOD(GetDevice)(THIS_ IWineD3DDevice **ppDevice) PURE;=0A=
STDMETHOD(Present)(THIS_ CONST RECT *pSourceRect, CONST RECT =
*pDestRect, HWND hDestWindowOverride, CONST RGNDATA *pDirtyRegion, DWORD =
dwFlags) PURE;=0A=
+ STDMETHOD(SetDestWindowOverride)(THIS_ HWND window);=0A=
STDMETHOD(GetFrontBufferData)(THIS_ IWineD3DSurface *pDestSurface) =
PURE;=0A=
STDMETHOD(GetBackBuffer)(THIS_ UINT iBackBuffer, =
WINED3DBACKBUFFER_TYPE Type, IWineD3DSurface **ppBackBuffer) PURE;=0A=
STDMETHOD(GetRasterStatus)(THIS_ WINED3DRASTER_STATUS =
*pRasterStatus) PURE;=0A=
@@ -1442,6 +1443,7 @@ DECLARE_INTERFACE_(IWineD3DSwapChain,IWineD3DBase)=0A=
#define IWineD3DSwapChain_Destroy(p,a) =
(p)->lpVtbl->Destroy(p,a)=0A=
#define IWineD3DSwapChain_GetDevice(p,a) =
(p)->lpVtbl->GetDevice(p,a)=0A=
#define IWineD3DSwapChain_Present(p,a,b,c,d,e) =
(p)->lpVtbl->Present(p,a,b,c,d,e)=0A=
+#define IWineD3DSwapChain_SetDestWindowOverride(p,a) =
(p)->lpVtbl->SetDestWindowOverride(p,a)=0A=
#define IWineD3DSwapChain_GetFrontBufferData(p,a) =
(p)->lpVtbl->GetFrontBufferData(p,a)=0A=
#define IWineD3DSwapChain_GetBackBuffer(p,a,b,c) =
(p)->lpVtbl->GetBackBuffer(p,a,b,c)=0A=
#define IWineD3DSwapChain_GetRasterStatus(p,a) =
(p)->lpVtbl->GetRasterStatus(p,a)=0A=
-- =0A=
1.5.4.5=0A=
=0A=
------=_NextPart_000_0009_01C90123.D544AA60--
More information about the wine-patches
mailing list