Commit b9fcf71c authored by Henri Verbeet's avatar Henri Verbeet Committed by Alexandre Julliard

ddraw: Use real flips.

parent 1aeee59b
...@@ -5642,35 +5642,43 @@ static HRESULT CDECL device_parent_create_surface(struct wined3d_device_parent * ...@@ -5642,35 +5642,43 @@ static HRESULT CDECL device_parent_create_surface(struct wined3d_device_parent *
return D3D_OK; return D3D_OK;
} }
static void STDMETHODCALLTYPE ddraw_frontbuffer_destroyed(void *parent)
{
struct IDirectDrawImpl *ddraw = parent;
ddraw->wined3d_frontbuffer = NULL;
}
static const struct wined3d_parent_ops ddraw_frontbuffer_parent_ops =
{
ddraw_frontbuffer_destroyed,
};
static HRESULT CDECL device_parent_create_rendertarget(struct wined3d_device_parent *device_parent, static HRESULT CDECL device_parent_create_rendertarget(struct wined3d_device_parent *device_parent,
void *container_parent, UINT width, UINT height, enum wined3d_format_id format, void *container_parent, UINT width, UINT height, enum wined3d_format_id format,
WINED3DMULTISAMPLE_TYPE multisample_type, DWORD multisample_quality, BOOL lockable, WINED3DMULTISAMPLE_TYPE multisample_type, DWORD multisample_quality, BOOL lockable,
struct wined3d_surface **surface) struct wined3d_surface **surface)
{ {
struct IDirectDrawImpl *ddraw = ddraw_from_device_parent(device_parent); struct IDirectDrawImpl *ddraw = ddraw_from_device_parent(device_parent);
IDirectDrawSurfaceImpl *d3d_surface = ddraw->d3d_target; HRESULT hr;
TRACE("device_parent %p, container_parent %p, width %u, height %u, format %#x, multisample_type %#x,\n" TRACE("device_parent %p, container_parent %p, width %u, height %u, format %#x, multisample_type %#x,\n"
"\tmultisample_quality %u, lockable %u, surface %p.\n", "\tmultisample_quality %u, lockable %u, surface %p.\n",
device_parent, container_parent, width, height, format, multisample_type, device_parent, container_parent, width, height, format, multisample_type,
multisample_quality, lockable, surface); multisample_quality, lockable, surface);
/* TODO: Return failure if the dimensions do not match, but this shouldn't if (ddraw->wined3d_frontbuffer)
* happen. */
if (d3d_surface->isRenderTarget)
{ {
ERR("Frontbuffer already created.\n"); ERR("Frontbuffer already created.\n");
return E_FAIL; return E_FAIL;
} }
d3d_surface->isRenderTarget = TRUE;
*surface = d3d_surface->wined3d_surface;
wined3d_surface_incref(*surface);
TRACE("Returning wineD3DSurface %p, it belongs to surface %p\n", *surface, d3d_surface); hr = wined3d_surface_create(ddraw->wined3d_device, width, height, format, lockable, FALSE, 0,
WINED3DUSAGE_RENDERTARGET, WINED3DPOOL_DEFAULT, multisample_type, multisample_quality,
DefaultSurfaceType, ddraw, &ddraw_frontbuffer_parent_ops, surface);
if (SUCCEEDED(hr))
ddraw->wined3d_frontbuffer = *surface;
return D3D_OK; return hr;
} }
static HRESULT CDECL device_parent_create_depth_stencil(struct wined3d_device_parent *device_parent, static HRESULT CDECL device_parent_create_depth_stencil(struct wined3d_device_parent *device_parent,
......
...@@ -89,6 +89,7 @@ struct IDirectDrawImpl ...@@ -89,6 +89,7 @@ struct IDirectDrawImpl
BOOL d3d_initialized; BOOL d3d_initialized;
IDirectDrawSurfaceImpl *primary; IDirectDrawSurfaceImpl *primary;
struct wined3d_surface *wined3d_frontbuffer;
/* DirectDraw things, which are not handled by WineD3D */ /* DirectDraw things, which are not handled by WineD3D */
DWORD cooperative_level; DWORD cooperative_level;
...@@ -184,9 +185,6 @@ struct IDirectDrawSurfaceImpl ...@@ -184,9 +185,6 @@ struct IDirectDrawSurfaceImpl
DWORD uniqueness_value; DWORD uniqueness_value;
UINT mipmap_level; UINT mipmap_level;
/* For D3DDevice creation */
BOOL isRenderTarget;
/* Clipper objects */ /* Clipper objects */
IDirectDrawClipperImpl *clipper; IDirectDrawClipperImpl *clipper;
......
...@@ -39,6 +39,12 @@ static inline IDirectDrawSurfaceImpl *impl_from_IDirectDrawGammaControl(IDirectD ...@@ -39,6 +39,12 @@ static inline IDirectDrawSurfaceImpl *impl_from_IDirectDrawGammaControl(IDirectD
return CONTAINING_RECORD(iface, IDirectDrawSurfaceImpl, IDirectDrawGammaControl_iface); return CONTAINING_RECORD(iface, IDirectDrawSurfaceImpl, IDirectDrawGammaControl_iface);
} }
static HRESULT ddraw_surface_update_frontbuffer(IDirectDrawSurfaceImpl *surface)
{
return wined3d_surface_blt(surface->ddraw->wined3d_frontbuffer, NULL,
surface->wined3d_surface, NULL, 0, NULL, WINED3DTEXF_POINT);
}
/***************************************************************************** /*****************************************************************************
* IUnknown parts follow * IUnknown parts follow
*****************************************************************************/ *****************************************************************************/
...@@ -1072,6 +1078,8 @@ static HRESULT WINAPI ddraw_surface7_Unlock(IDirectDrawSurface7 *iface, RECT *pR ...@@ -1072,6 +1078,8 @@ static HRESULT WINAPI ddraw_surface7_Unlock(IDirectDrawSurface7 *iface, RECT *pR
hr = wined3d_surface_unmap(This->wined3d_surface); hr = wined3d_surface_unmap(This->wined3d_surface);
if (SUCCEEDED(hr)) if (SUCCEEDED(hr))
{ {
if (This->surface_desc.ddsCaps.dwCaps & DDSCAPS_FRONTBUFFER)
hr = ddraw_surface_update_frontbuffer(This);
This->surface_desc.lpSurface = NULL; This->surface_desc.lpSurface = NULL;
} }
LeaveCriticalSection(&ddraw_cs); LeaveCriticalSection(&ddraw_cs);
...@@ -1170,6 +1178,9 @@ static HRESULT WINAPI ddraw_surface7_Flip(IDirectDrawSurface7 *iface, IDirectDra ...@@ -1170,6 +1178,9 @@ static HRESULT WINAPI ddraw_surface7_Flip(IDirectDrawSurface7 *iface, IDirectDra
} }
hr = wined3d_surface_flip(This->wined3d_surface, Override->wined3d_surface, Flags); hr = wined3d_surface_flip(This->wined3d_surface, Override->wined3d_surface, Flags);
if (SUCCEEDED(hr) && This->surface_desc.ddsCaps.dwCaps & DDSCAPS_FRONTBUFFER)
hr = ddraw_surface_update_frontbuffer(This);
LeaveCriticalSection(&ddraw_cs); LeaveCriticalSection(&ddraw_cs);
return hr; return hr;
} }
...@@ -1268,6 +1279,8 @@ static HRESULT WINAPI ddraw_surface7_Blt(IDirectDrawSurface7 *iface, RECT *DestR ...@@ -1268,6 +1279,8 @@ static HRESULT WINAPI ddraw_surface7_Blt(IDirectDrawSurface7 *iface, RECT *DestR
* struct are supported anyway. */ * struct are supported anyway. */
hr = wined3d_surface_blt(This->wined3d_surface, DestRect, Src ? Src->wined3d_surface : NULL, hr = wined3d_surface_blt(This->wined3d_surface, DestRect, Src ? Src->wined3d_surface : NULL,
SrcRect, Flags, (WINEDDBLTFX *)DDBltFx, WINED3DTEXF_LINEAR); SrcRect, Flags, (WINEDDBLTFX *)DDBltFx, WINED3DTEXF_LINEAR);
if (SUCCEEDED(hr) && (This->surface_desc.ddsCaps.dwCaps & DDSCAPS_FRONTBUFFER))
hr = ddraw_surface_update_frontbuffer(This);
LeaveCriticalSection(&ddraw_cs); LeaveCriticalSection(&ddraw_cs);
switch(hr) switch(hr)
...@@ -1828,6 +1841,8 @@ static HRESULT WINAPI ddraw_surface7_ReleaseDC(IDirectDrawSurface7 *iface, HDC h ...@@ -1828,6 +1841,8 @@ static HRESULT WINAPI ddraw_surface7_ReleaseDC(IDirectDrawSurface7 *iface, HDC h
EnterCriticalSection(&ddraw_cs); EnterCriticalSection(&ddraw_cs);
hr = wined3d_surface_releasedc(This->wined3d_surface, hdc); hr = wined3d_surface_releasedc(This->wined3d_surface, hdc);
if (SUCCEEDED(hr) && (This->surface_desc.ddsCaps.dwCaps & DDSCAPS_FRONTBUFFER))
hr = ddraw_surface_update_frontbuffer(This);
LeaveCriticalSection(&ddraw_cs); LeaveCriticalSection(&ddraw_cs);
return hr; return hr;
} }
...@@ -3673,6 +3688,8 @@ static HRESULT WINAPI ddraw_surface7_BltFast(IDirectDrawSurface7 *iface, DWORD d ...@@ -3673,6 +3688,8 @@ static HRESULT WINAPI ddraw_surface7_BltFast(IDirectDrawSurface7 *iface, DWORD d
EnterCriticalSection(&ddraw_cs); EnterCriticalSection(&ddraw_cs);
hr = wined3d_surface_bltfast(This->wined3d_surface, dstx, dsty, hr = wined3d_surface_bltfast(This->wined3d_surface, dstx, dsty,
src->wined3d_surface, rsrc, trans); src->wined3d_surface, rsrc, trans);
if (SUCCEEDED(hr) && (This->surface_desc.ddsCaps.dwCaps & DDSCAPS_FRONTBUFFER))
hr = ddraw_surface_update_frontbuffer(This);
LeaveCriticalSection(&ddraw_cs); LeaveCriticalSection(&ddraw_cs);
switch(hr) switch(hr)
{ {
...@@ -4298,6 +4315,14 @@ static HRESULT WINAPI ddraw_surface7_SetPalette(IDirectDrawSurface7 *iface, IDir ...@@ -4298,6 +4315,14 @@ static HRESULT WINAPI ddraw_surface7_SetPalette(IDirectDrawSurface7 *iface, IDir
/* Release the old palette */ /* Release the old palette */
if(oldPal) IDirectDrawPalette_Release(oldPal); if(oldPal) IDirectDrawPalette_Release(oldPal);
/* Update the wined3d frontbuffer if this is the frontbuffer. */
if ((This->surface_desc.ddsCaps.dwCaps & DDSCAPS_FRONTBUFFER) && This->ddraw->wined3d_frontbuffer)
{
hr = wined3d_surface_set_palette(This->ddraw->wined3d_frontbuffer, PalImpl ? PalImpl->wineD3DPalette : NULL);
if (FAILED(hr))
ERR("Failed to set frontbuffer palette, hr %#x.\n", hr);
}
/* If this is a front buffer, also update the back buffers /* If this is a front buffer, also update the back buffers
* TODO: How do things work for palettized cube textures? * TODO: How do things work for palettized cube textures?
*/ */
......
...@@ -3793,11 +3793,9 @@ HRESULT CDECL wined3d_surface_flip(struct wined3d_surface *surface, struct wined ...@@ -3793,11 +3793,9 @@ HRESULT CDECL wined3d_surface_flip(struct wined3d_surface *surface, struct wined
WARN("Ignoring flags %#x.\n", flags); WARN("Ignoring flags %#x.\n", flags);
} }
/* FIXME: This will also prevent overlay flips, since overlays aren't on if (surface->container.type == WINED3D_CONTAINER_SWAPCHAIN)
* a swapchain either. */
if (surface->container.type != WINED3D_CONTAINER_SWAPCHAIN)
{ {
ERR("Flipped surface is not on a swapchain.\n"); ERR("Not supported on swapchain surfaces.\n");
return WINEDDERR_NOTFLIPPABLE; return WINEDDERR_NOTFLIPPABLE;
} }
...@@ -3808,18 +3806,13 @@ HRESULT CDECL wined3d_surface_flip(struct wined3d_surface *surface, struct wined ...@@ -3808,18 +3806,13 @@ HRESULT CDECL wined3d_surface_flip(struct wined3d_surface *surface, struct wined
return WINEDDERR_NOTFLIPPABLE; return WINEDDERR_NOTFLIPPABLE;
} }
if (surface->resource.usage & WINED3DUSAGE_OVERLAY)
{
flip_surface(surface, override); flip_surface(surface, override);
/* Update the overlay if it is visible */ /* Update overlays if they're visible. */
if (surface->overlay_dest) if ((surface->resource.usage & WINED3DUSAGE_OVERLAY) && surface->overlay_dest)
return surface->surface_ops->surface_draw_overlay(surface); return surface->surface_ops->surface_draw_overlay(surface);
else
return WINED3D_OK;
}
return wined3d_surface_blt(surface, NULL, override, NULL, 0, NULL, WINED3DTEXF_POINT); return WINED3D_OK;
} }
/* Do not call while under the GL lock. */ /* Do not call while under the GL lock. */
......
Markdown is supported
0% or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment