Signed-off-by: Zebediah Figura z.figura12@gmail.com --- dlls/wined3d/device.c | 1 + 1 file changed, 1 insertion(+)
diff --git a/dlls/wined3d/device.c b/dlls/wined3d/device.c index 38b488cba81..13d9057f3a8 100644 --- a/dlls/wined3d/device.c +++ b/dlls/wined3d/device.c @@ -1213,6 +1213,7 @@ void wined3d_device_uninit_3d(struct wined3d_device *device) wine_rb_clear(&device->samplers, device_free_sampler, NULL); wine_rb_clear(&device->rasterizer_states, device_free_rasterizer_state, NULL); wine_rb_clear(&device->blend_states, device_free_blend_state, NULL); + wine_rb_clear(&device->depth_stencil_states, device_free_depth_stencil_state, NULL);
LIST_FOR_EACH_ENTRY_SAFE(resource, cursor, &device->resources, struct wined3d_resource, resource_list_entry) {
Signed-off-by: Zebediah Figura z.figura12@gmail.com --- dlls/d3d11/device.c | 4 ---- dlls/d3d11/state.c | 1 + dlls/wined3d/adapter_vk.c | 29 ++++++++++++++--------------- dlls/wined3d/context_gl.c | 2 +- dlls/wined3d/context_vk.c | 5 +++-- dlls/wined3d/device.c | 2 ++ dlls/wined3d/directx.c | 1 - dlls/wined3d/state.c | 29 ++++++++++++----------------- dlls/wined3d/texture.c | 4 ++-- dlls/wined3d/wined3d_private.h | 5 +++-- include/wine/wined3d.h | 1 + 11 files changed, 39 insertions(+), 44 deletions(-)
diff --git a/dlls/d3d11/device.c b/dlls/d3d11/device.c index ca9975d6a22..a8cba49e039 100644 --- a/dlls/d3d11/device.c +++ b/dlls/d3d11/device.c @@ -726,7 +726,6 @@ static void STDMETHODCALLTYPE d3d11_immediate_context_OMSetBlendState(ID3D11Devi
static void set_default_depth_stencil_state(struct wined3d_device *wined3d_device) { - wined3d_device_set_render_state(wined3d_device, WINED3D_RS_ZWRITEENABLE, D3D11_DEPTH_WRITE_MASK_ALL); wined3d_device_set_render_state(wined3d_device, WINED3D_RS_ZFUNC, WINED3D_CMP_LESS); wined3d_device_set_render_state(wined3d_device, WINED3D_RS_STENCILENABLE, FALSE); } @@ -759,10 +758,7 @@ static void STDMETHODCALLTYPE d3d11_immediate_context_OMSetDepthStencilState(ID3 back = &desc->BackFace;
if (desc->DepthEnable) - { - wined3d_device_set_render_state(device->wined3d_device, WINED3D_RS_ZWRITEENABLE, desc->DepthWriteMask); wined3d_device_set_render_state(device->wined3d_device, WINED3D_RS_ZFUNC, desc->DepthFunc); - }
wined3d_device_set_render_state(device->wined3d_device, WINED3D_RS_STENCILENABLE, desc->StencilEnable); if (desc->StencilEnable) diff --git a/dlls/d3d11/state.c b/dlls/d3d11/state.c index 5d4c3526595..d0513543c80 100644 --- a/dlls/d3d11/state.c +++ b/dlls/d3d11/state.c @@ -795,6 +795,7 @@ HRESULT d3d_depthstencil_state_create(struct d3d_device *device, const D3D11_DEP }
wined3d_desc.depth = desc->DepthEnable; + wined3d_desc.depth_write = desc->DepthWriteMask;
/* We cannot fail after creating a wined3d_depth_stencil_state object. It * would lead to double free. */ diff --git a/dlls/wined3d/adapter_vk.c b/dlls/wined3d/adapter_vk.c index 7b0c0c89897..2045cf181cb 100644 --- a/dlls/wined3d/adapter_vk.c +++ b/dlls/wined3d/adapter_vk.c @@ -106,9 +106,8 @@ static const struct wined3d_state_entry_template misc_state_template_vk[] = {STATE_RENDER(WINED3D_RS_MONOENABLE), {STATE_RENDER(WINED3D_RS_MONOENABLE), state_nop}}, {STATE_RENDER(WINED3D_RS_ROP2), {STATE_RENDER(WINED3D_RS_ROP2), state_nop}}, {STATE_RENDER(WINED3D_RS_PLANEMASK), {STATE_RENDER(WINED3D_RS_PLANEMASK), state_nop}}, - {STATE_RENDER(WINED3D_RS_ZWRITEENABLE), {STATE_RENDER(WINED3D_RS_ZWRITEENABLE), state_nop}}, {STATE_RENDER(WINED3D_RS_LASTPIXEL), {STATE_RENDER(WINED3D_RS_LASTPIXEL), state_nop}}, - {STATE_RENDER(WINED3D_RS_ZFUNC), {STATE_RENDER(WINED3D_RS_ZWRITEENABLE)}}, + {STATE_RENDER(WINED3D_RS_ZFUNC), {STATE_RENDER(WINED3D_RS_ZFUNC), state_nop}}, {STATE_RENDER(WINED3D_RS_DITHERENABLE), {STATE_RENDER(WINED3D_RS_DITHERENABLE), state_nop}}, {STATE_RENDER(WINED3D_RS_SUBPIXEL), {STATE_RENDER(WINED3D_RS_SUBPIXEL), state_nop}}, {STATE_RENDER(WINED3D_RS_SUBPIXELX), {STATE_RENDER(WINED3D_RS_SUBPIXELX), state_nop}}, @@ -118,19 +117,19 @@ static const struct wined3d_state_entry_template misc_state_template_vk[] = {STATE_RENDER(WINED3D_RS_ANISOTROPY), {STATE_RENDER(WINED3D_RS_ANISOTROPY), state_nop}}, {STATE_RENDER(WINED3D_RS_FLUSHBATCH), {STATE_RENDER(WINED3D_RS_FLUSHBATCH), state_nop}}, {STATE_RENDER(WINED3D_RS_TRANSLUCENTSORTINDEPENDENT), {STATE_RENDER(WINED3D_RS_TRANSLUCENTSORTINDEPENDENT), state_nop}}, - {STATE_RENDER(WINED3D_RS_STENCILENABLE), {STATE_RENDER(WINED3D_RS_ZWRITEENABLE)}}, - {STATE_RENDER(WINED3D_RS_STENCILFAIL), {STATE_RENDER(WINED3D_RS_ZWRITEENABLE)}}, - {STATE_RENDER(WINED3D_RS_STENCILZFAIL), {STATE_RENDER(WINED3D_RS_ZWRITEENABLE)}}, - {STATE_RENDER(WINED3D_RS_STENCILPASS), {STATE_RENDER(WINED3D_RS_ZWRITEENABLE)}}, - {STATE_RENDER(WINED3D_RS_STENCILFUNC), {STATE_RENDER(WINED3D_RS_ZWRITEENABLE)}}, - {STATE_RENDER(WINED3D_RS_STENCILREF), {STATE_RENDER(WINED3D_RS_ZWRITEENABLE)}}, - {STATE_RENDER(WINED3D_RS_STENCILMASK), {STATE_RENDER(WINED3D_RS_ZWRITEENABLE)}}, - {STATE_RENDER(WINED3D_RS_STENCILWRITEMASK), {STATE_RENDER(WINED3D_RS_ZWRITEENABLE)}}, - {STATE_RENDER(WINED3D_RS_TWOSIDEDSTENCILMODE), {STATE_RENDER(WINED3D_RS_ZWRITEENABLE)}}, - {STATE_RENDER(WINED3D_RS_BACK_STENCILFAIL), {STATE_RENDER(WINED3D_RS_ZWRITEENABLE)}}, - {STATE_RENDER(WINED3D_RS_BACK_STENCILZFAIL), {STATE_RENDER(WINED3D_RS_ZWRITEENABLE)}}, - {STATE_RENDER(WINED3D_RS_BACK_STENCILPASS), {STATE_RENDER(WINED3D_RS_ZWRITEENABLE)}}, - {STATE_RENDER(WINED3D_RS_BACK_STENCILFUNC), {STATE_RENDER(WINED3D_RS_ZWRITEENABLE)}}, + {STATE_RENDER(WINED3D_RS_STENCILENABLE), {STATE_RENDER(WINED3D_RS_ZFUNC)}}, + {STATE_RENDER(WINED3D_RS_STENCILFAIL), {STATE_RENDER(WINED3D_RS_ZFUNC)}}, + {STATE_RENDER(WINED3D_RS_STENCILZFAIL), {STATE_RENDER(WINED3D_RS_ZFUNC)}}, + {STATE_RENDER(WINED3D_RS_STENCILPASS), {STATE_RENDER(WINED3D_RS_ZFUNC)}}, + {STATE_RENDER(WINED3D_RS_STENCILFUNC), {STATE_RENDER(WINED3D_RS_ZFUNC)}}, + {STATE_RENDER(WINED3D_RS_STENCILREF), {STATE_RENDER(WINED3D_RS_ZFUNC)}}, + {STATE_RENDER(WINED3D_RS_STENCILMASK), {STATE_RENDER(WINED3D_RS_ZFUNC)}}, + {STATE_RENDER(WINED3D_RS_STENCILWRITEMASK), {STATE_RENDER(WINED3D_RS_ZFUNC)}}, + {STATE_RENDER(WINED3D_RS_TWOSIDEDSTENCILMODE), {STATE_RENDER(WINED3D_RS_ZFUNC)}}, + {STATE_RENDER(WINED3D_RS_BACK_STENCILFAIL), {STATE_RENDER(WINED3D_RS_ZFUNC)}}, + {STATE_RENDER(WINED3D_RS_BACK_STENCILZFAIL), {STATE_RENDER(WINED3D_RS_ZFUNC)}}, + {STATE_RENDER(WINED3D_RS_BACK_STENCILPASS), {STATE_RENDER(WINED3D_RS_ZFUNC)}}, + {STATE_RENDER(WINED3D_RS_BACK_STENCILFUNC), {STATE_RENDER(WINED3D_RS_ZFUNC)}}, {STATE_RENDER(WINED3D_RS_WRAP0), {STATE_RENDER(WINED3D_RS_WRAP0), state_nop}}, {STATE_RENDER(WINED3D_RS_WRAP1), {STATE_RENDER(WINED3D_RS_WRAP0)}}, {STATE_RENDER(WINED3D_RS_WRAP2), {STATE_RENDER(WINED3D_RS_WRAP0)}}, diff --git a/dlls/wined3d/context_gl.c b/dlls/wined3d/context_gl.c index 186d70b45ad..8c247afa02a 100644 --- a/dlls/wined3d/context_gl.c +++ b/dlls/wined3d/context_gl.c @@ -4507,7 +4507,7 @@ void draw_primitive(struct wined3d_device *device, const struct wined3d_state *s return; }
- if (dsv && state->render_states[WINED3D_RS_ZWRITEENABLE]) + if (dsv && (!state->depth_stencil_state || state->depth_stencil_state->desc.depth_write)) { DWORD location = context->render_offscreen ? dsv->resource->draw_binding : WINED3D_LOCATION_DRAWABLE;
diff --git a/dlls/wined3d/context_vk.c b/dlls/wined3d/context_vk.c index 356fec27a78..4a646504b3e 100644 --- a/dlls/wined3d/context_vk.c +++ b/dlls/wined3d/context_vk.c @@ -2042,12 +2042,13 @@ static bool wined3d_context_vk_update_graphics_pipeline_key(struct wined3d_conte if (d) { key->ds_desc.depthTestEnable = d->desc.depth; + key->ds_desc.depthWriteEnable = d->desc.depth_write; } else { key->ds_desc.depthTestEnable = VK_TRUE; + key->ds_desc.depthWriteEnable = VK_TRUE; } - key->ds_desc.depthWriteEnable = !!state->render_states[WINED3D_RS_ZWRITEENABLE]; key->ds_desc.depthCompareOp = vk_compare_op_from_wined3d(state->render_states[WINED3D_RS_ZFUNC]); key->ds_desc.stencilTestEnable = state->fb.depth_stencil && state->render_states[WINED3D_RS_STENCILENABLE]; if (key->ds_desc.stencilTestEnable) @@ -2862,7 +2863,7 @@ VkCommandBuffer wined3d_context_vk_apply_draw_state(struct wined3d_context_vk *c wined3d_rendertarget_view_load_location(dsv, &context_vk->c, dsv->resource->draw_binding); else wined3d_rendertarget_view_prepare_location(dsv, &context_vk->c, dsv->resource->draw_binding); - if (state->render_states[WINED3D_RS_ZWRITEENABLE]) + if (!state->depth_stencil_state || state->depth_stencil_state->desc.depth_write) wined3d_rendertarget_view_invalidate_location(dsv, ~dsv->resource->draw_binding);
sample_count = max(1, wined3d_resource_get_sample_count(dsv->resource)); diff --git a/dlls/wined3d/device.c b/dlls/wined3d/device.c index 13d9057f3a8..5c94fae0a98 100644 --- a/dlls/wined3d/device.c +++ b/dlls/wined3d/device.c @@ -3686,6 +3686,7 @@ void CDECL wined3d_device_apply_stateblock(struct wined3d_device *device, break;
case WINED3D_RS_ZENABLE: + case WINED3D_RS_ZWRITEENABLE: set_depth_stencil_state = TRUE; break;
@@ -3839,6 +3840,7 @@ void CDECL wined3d_device_apply_stateblock(struct wined3d_device *device, default: FIXME("Unrecognized depth buffer type %#x.\n", state->rs[WINED3D_RS_ZENABLE]); } + desc.depth_write = state->rs[WINED3D_RS_ZWRITEENABLE];
if ((entry = wine_rb_get(&device->depth_stencil_states, &desc))) { diff --git a/dlls/wined3d/directx.c b/dlls/wined3d/directx.c index fced1eb110c..cf355438c45 100644 --- a/dlls/wined3d/directx.c +++ b/dlls/wined3d/directx.c @@ -2428,7 +2428,6 @@ static const struct wined3d_state_entry_template misc_state_template_no3d[] = {STATE_RENDER(WINED3D_RS_MONOENABLE), {STATE_VDECL}}, {STATE_RENDER(WINED3D_RS_ROP2), {STATE_VDECL}}, {STATE_RENDER(WINED3D_RS_PLANEMASK), {STATE_VDECL}}, - {STATE_RENDER(WINED3D_RS_ZWRITEENABLE), {STATE_VDECL}}, {STATE_RENDER(WINED3D_RS_LASTPIXEL), {STATE_VDECL}}, {STATE_RENDER(WINED3D_RS_ZFUNC), {STATE_VDECL}}, {STATE_RENDER(WINED3D_RS_DITHERENABLE), {STATE_VDECL}}, diff --git a/dlls/wined3d/state.c b/dlls/wined3d/state.c index d77722c00d4..7a9e69f775c 100644 --- a/dlls/wined3d/state.c +++ b/dlls/wined3d/state.c @@ -359,22 +359,6 @@ static void state_ditherenable(struct wined3d_context *context, const struct win } }
-static void state_zwriteenable(struct wined3d_context *context, const struct wined3d_state *state, DWORD state_id) -{ - const struct wined3d_gl_info *gl_info = wined3d_context_gl(context)->gl_info; - - if (state->render_states[WINED3D_RS_ZWRITEENABLE]) - { - gl_info->gl_ops.gl.p_glDepthMask(1); - checkGLcall("glDepthMask(1)"); - } - else - { - gl_info->gl_ops.gl.p_glDepthMask(0); - checkGLcall("glDepthMask(0)"); - } -} - GLenum wined3d_gl_compare_func(enum wined3d_cmp_func f) { switch (f) @@ -1226,6 +1210,17 @@ static void depth_stencil(struct wined3d_context *context, const struct wined3d_ checkGLcall("glDisable GL_DEPTH_TEST"); }
+ if (!d || d->desc.depth_write) + { + gl_info->gl_ops.gl.p_glDepthMask(GL_TRUE); + checkGLcall("glDepthMask(GL_TRUE)"); + } + else + { + gl_info->gl_ops.gl.p_glDepthMask(GL_FALSE); + checkGLcall("glDepthMask(GL_FALSE)"); + } + if (context->last_was_rhw && !isStateDirty(context, STATE_TRANSFORM(WINED3D_TS_PROJECTION))) context_apply_state(context, state, STATE_TRANSFORM(WINED3D_TS_PROJECTION)); } @@ -4751,7 +4746,6 @@ const struct wined3d_state_entry_template misc_state_template_gl[] = { STATE_RENDER(WINED3D_RS_MONOENABLE), { STATE_RENDER(WINED3D_RS_MONOENABLE), state_monoenable }, WINED3D_GL_EXT_NONE }, { STATE_RENDER(WINED3D_RS_ROP2), { STATE_RENDER(WINED3D_RS_ROP2), state_rop2 }, WINED3D_GL_EXT_NONE }, { STATE_RENDER(WINED3D_RS_PLANEMASK), { STATE_RENDER(WINED3D_RS_PLANEMASK), state_planemask }, WINED3D_GL_EXT_NONE }, - { STATE_RENDER(WINED3D_RS_ZWRITEENABLE), { STATE_RENDER(WINED3D_RS_ZWRITEENABLE), state_zwriteenable }, WINED3D_GL_EXT_NONE }, { STATE_RENDER(WINED3D_RS_LASTPIXEL), { STATE_RENDER(WINED3D_RS_LASTPIXEL), state_lastpixel }, WINED3D_GL_EXT_NONE }, { STATE_RENDER(WINED3D_RS_ZFUNC), { STATE_RENDER(WINED3D_RS_ZFUNC), state_zfunc }, WINED3D_GL_EXT_NONE }, { STATE_RENDER(WINED3D_RS_DITHERENABLE), { STATE_RENDER(WINED3D_RS_DITHERENABLE), state_ditherenable }, WINED3D_GL_EXT_NONE }, @@ -5569,6 +5563,7 @@ static void validate_state_table(struct wined3d_state_entry *state_table) { 1, 1}, { 3, 3}, { 7, 8}, + { 14, 14}, { 17, 22}, { 27, 27}, { 40, 40}, diff --git a/dlls/wined3d/texture.c b/dlls/wined3d/texture.c index 8e05c6ae194..911ee0e6262 100644 --- a/dlls/wined3d/texture.c +++ b/dlls/wined3d/texture.c @@ -505,7 +505,7 @@ static void texture2d_depth_blt_fbo(const struct wined3d_device *device, struct if (gl_mask & GL_DEPTH_BUFFER_BIT) { gl_info->gl_ops.gl.p_glDepthMask(GL_TRUE); - context_invalidate_state(context, STATE_RENDER(WINED3D_RS_ZWRITEENABLE)); + context_invalidate_state(context, STATE_DEPTH_STENCIL); } if (gl_mask & GL_STENCIL_BUFFER_BIT) { @@ -5403,7 +5403,7 @@ static void ffp_blitter_clear_rendertargets(struct wined3d_device *device, unsig if (flags & WINED3DCLEAR_ZBUFFER) { gl_info->gl_ops.gl.p_glDepthMask(GL_TRUE); - context_invalidate_state(context, STATE_RENDER(WINED3D_RS_ZWRITEENABLE)); + context_invalidate_state(context, STATE_DEPTH_STENCIL); gl_info->gl_ops.gl.p_glClearDepth(depth); checkGLcall("glClearDepth"); clear_mask = clear_mask | GL_DEPTH_BUFFER_BIT; diff --git a/dlls/wined3d/wined3d_private.h b/dlls/wined3d/wined3d_private.h index da3974973a1..c44c4eac911 100644 --- a/dlls/wined3d/wined3d_private.h +++ b/dlls/wined3d/wined3d_private.h @@ -3643,8 +3643,9 @@ struct wined3d_state
static inline bool wined3d_state_uses_depth_buffer(const struct wined3d_state *state) { - return state->render_states[WINED3D_RS_ZWRITEENABLE] - || !state->depth_stencil_state || state->depth_stencil_state->desc.depth; + if (!state->depth_stencil_state) + return true; + return state->depth_stencil_state->desc.depth || state->depth_stencil_state->desc.depth_write; }
struct wined3d_dummy_textures diff --git a/include/wine/wined3d.h b/include/wine/wined3d.h index 77dbb775532..ef2a7de4580 100644 --- a/include/wine/wined3d.h +++ b/include/wine/wined3d.h @@ -2039,6 +2039,7 @@ struct wined3d_blend_state_desc struct wined3d_depth_stencil_state_desc { BOOL depth; + BOOL depth_write; };
struct wined3d_rasterizer_state_desc
Signed-off-by: Henri Verbeet hverbeet@codeweavers.com
Signed-off-by: Zebediah Figura z.figura12@gmail.com --- dlls/d3d11/device.c | 2 -- dlls/d3d11/state.c | 1 + dlls/wined3d/adapter_vk.c | 1 - dlls/wined3d/context_gl.c | 5 ++- dlls/wined3d/context_vk.c | 66 ++++++++++++++++++++------------------- dlls/wined3d/cs.c | 1 - dlls/wined3d/device.c | 5 ++- dlls/wined3d/directx.c | 1 - dlls/wined3d/state.c | 46 +++++++++++++-------------- include/wine/wined3d.h | 1 + 10 files changed, 63 insertions(+), 66 deletions(-)
diff --git a/dlls/d3d11/device.c b/dlls/d3d11/device.c index a8cba49e039..cac72e614e5 100644 --- a/dlls/d3d11/device.c +++ b/dlls/d3d11/device.c @@ -727,7 +727,6 @@ static void STDMETHODCALLTYPE d3d11_immediate_context_OMSetBlendState(ID3D11Devi static void set_default_depth_stencil_state(struct wined3d_device *wined3d_device) { wined3d_device_set_render_state(wined3d_device, WINED3D_RS_ZFUNC, WINED3D_CMP_LESS); - wined3d_device_set_render_state(wined3d_device, WINED3D_RS_STENCILENABLE, FALSE); }
static void STDMETHODCALLTYPE d3d11_immediate_context_OMSetDepthStencilState(ID3D11DeviceContext1 *iface, @@ -760,7 +759,6 @@ static void STDMETHODCALLTYPE d3d11_immediate_context_OMSetDepthStencilState(ID3 if (desc->DepthEnable) wined3d_device_set_render_state(device->wined3d_device, WINED3D_RS_ZFUNC, desc->DepthFunc);
- wined3d_device_set_render_state(device->wined3d_device, WINED3D_RS_STENCILENABLE, desc->StencilEnable); if (desc->StencilEnable) { wined3d_device_set_render_state(device->wined3d_device, WINED3D_RS_STENCILMASK, desc->StencilReadMask); diff --git a/dlls/d3d11/state.c b/dlls/d3d11/state.c index d0513543c80..609c5e4c103 100644 --- a/dlls/d3d11/state.c +++ b/dlls/d3d11/state.c @@ -796,6 +796,7 @@ HRESULT d3d_depthstencil_state_create(struct d3d_device *device, const D3D11_DEP
wined3d_desc.depth = desc->DepthEnable; wined3d_desc.depth_write = desc->DepthWriteMask; + wined3d_desc.stencil = desc->StencilEnable;
/* We cannot fail after creating a wined3d_depth_stencil_state object. It * would lead to double free. */ diff --git a/dlls/wined3d/adapter_vk.c b/dlls/wined3d/adapter_vk.c index 2045cf181cb..9c9da418406 100644 --- a/dlls/wined3d/adapter_vk.c +++ b/dlls/wined3d/adapter_vk.c @@ -117,7 +117,6 @@ static const struct wined3d_state_entry_template misc_state_template_vk[] = {STATE_RENDER(WINED3D_RS_ANISOTROPY), {STATE_RENDER(WINED3D_RS_ANISOTROPY), state_nop}}, {STATE_RENDER(WINED3D_RS_FLUSHBATCH), {STATE_RENDER(WINED3D_RS_FLUSHBATCH), state_nop}}, {STATE_RENDER(WINED3D_RS_TRANSLUCENTSORTINDEPENDENT), {STATE_RENDER(WINED3D_RS_TRANSLUCENTSORTINDEPENDENT), state_nop}}, - {STATE_RENDER(WINED3D_RS_STENCILENABLE), {STATE_RENDER(WINED3D_RS_ZFUNC)}}, {STATE_RENDER(WINED3D_RS_STENCILFAIL), {STATE_RENDER(WINED3D_RS_ZFUNC)}}, {STATE_RENDER(WINED3D_RS_STENCILZFAIL), {STATE_RENDER(WINED3D_RS_ZFUNC)}}, {STATE_RENDER(WINED3D_RS_STENCILPASS), {STATE_RENDER(WINED3D_RS_ZFUNC)}}, diff --git a/dlls/wined3d/context_gl.c b/dlls/wined3d/context_gl.c index 8c247afa02a..73d520e5709 100644 --- a/dlls/wined3d/context_gl.c +++ b/dlls/wined3d/context_gl.c @@ -2817,16 +2817,15 @@ void wined3d_context_gl_apply_blit_state(struct wined3d_context_gl *context_gl, gl_info->gl_ops.gl.p_glDisable(GL_ALPHA_TEST); context_invalidate_state(context, STATE_RENDER(WINED3D_RS_ALPHATESTENABLE)); } - gl_info->gl_ops.gl.p_glDisable(GL_DEPTH_TEST); - context_invalidate_state(context, STATE_DEPTH_STENCIL); gl_info->gl_ops.gl.p_glDisable(GL_BLEND); gl_info->gl_ops.gl.p_glColorMask(GL_TRUE, GL_TRUE, GL_TRUE, GL_TRUE); context_invalidate_state(context, STATE_BLEND); gl_info->gl_ops.gl.p_glDisable(GL_CULL_FACE); gl_info->gl_ops.gl.p_glDisable(GL_SCISSOR_TEST); context_invalidate_state(context, STATE_RASTERIZER); + gl_info->gl_ops.gl.p_glDisable(GL_DEPTH_TEST); gl_info->gl_ops.gl.p_glDisable(GL_STENCIL_TEST); - context_invalidate_state(context, STATE_RENDER(WINED3D_RS_STENCILENABLE)); + context_invalidate_state(context, STATE_DEPTH_STENCIL); if (gl_info->supported[ARB_POINT_SPRITE]) { gl_info->gl_ops.gl.p_glDisable(GL_POINT_SPRITE_ARB); diff --git a/dlls/wined3d/context_vk.c b/dlls/wined3d/context_vk.c index 4a646504b3e..6eaee71c54a 100644 --- a/dlls/wined3d/context_vk.c +++ b/dlls/wined3d/context_vk.c @@ -2043,45 +2043,47 @@ static bool wined3d_context_vk_update_graphics_pipeline_key(struct wined3d_conte { key->ds_desc.depthTestEnable = d->desc.depth; key->ds_desc.depthWriteEnable = d->desc.depth_write; + key->ds_desc.stencilTestEnable = state->fb.depth_stencil && d->desc.stencil; + if (key->ds_desc.stencilTestEnable) + { + key->ds_desc.front.failOp = vk_stencil_op_from_wined3d(state->render_states[WINED3D_RS_STENCILFAIL]); + key->ds_desc.front.passOp = vk_stencil_op_from_wined3d(state->render_states[WINED3D_RS_STENCILPASS]); + key->ds_desc.front.depthFailOp = vk_stencil_op_from_wined3d( + state->render_states[WINED3D_RS_STENCILZFAIL]); + key->ds_desc.front.compareOp = vk_compare_op_from_wined3d(state->render_states[WINED3D_RS_STENCILFUNC]); + key->ds_desc.front.compareMask = state->render_states[WINED3D_RS_STENCILMASK]; + key->ds_desc.front.writeMask = state->render_states[WINED3D_RS_STENCILWRITEMASK]; + key->ds_desc.front.reference = state->render_states[WINED3D_RS_STENCILREF] + & ((1 << state->fb.depth_stencil->format->stencil_size) - 1); + + if (state->render_states[WINED3D_RS_TWOSIDEDSTENCILMODE]) + { + key->ds_desc.back.failOp = vk_stencil_op_from_wined3d( + state->render_states[WINED3D_RS_BACK_STENCILFAIL]); + key->ds_desc.back.passOp = vk_stencil_op_from_wined3d( + state->render_states[WINED3D_RS_BACK_STENCILPASS]); + key->ds_desc.back.depthFailOp = vk_stencil_op_from_wined3d( + state->render_states[WINED3D_RS_BACK_STENCILZFAIL]); + key->ds_desc.back.compareOp = vk_compare_op_from_wined3d( + state->render_states[WINED3D_RS_BACK_STENCILFUNC]); + key->ds_desc.back.compareMask = state->render_states[WINED3D_RS_STENCILMASK]; + key->ds_desc.back.writeMask = state->render_states[WINED3D_RS_STENCILWRITEMASK]; + key->ds_desc.back.reference = state->render_states[WINED3D_RS_STENCILREF] + & ((1 << state->fb.depth_stencil->format->stencil_size) - 1); + } + else + { + key->ds_desc.back = key->ds_desc.front; + } + } } else { key->ds_desc.depthTestEnable = VK_TRUE; key->ds_desc.depthWriteEnable = VK_TRUE; + key->ds_desc.stencilTestEnable = VK_FALSE; } key->ds_desc.depthCompareOp = vk_compare_op_from_wined3d(state->render_states[WINED3D_RS_ZFUNC]); - key->ds_desc.stencilTestEnable = state->fb.depth_stencil && state->render_states[WINED3D_RS_STENCILENABLE]; - if (key->ds_desc.stencilTestEnable) - { - key->ds_desc.front.failOp = vk_stencil_op_from_wined3d(state->render_states[WINED3D_RS_STENCILFAIL]); - key->ds_desc.front.passOp = vk_stencil_op_from_wined3d(state->render_states[WINED3D_RS_STENCILPASS]); - key->ds_desc.front.depthFailOp = vk_stencil_op_from_wined3d(state->render_states[WINED3D_RS_STENCILZFAIL]); - key->ds_desc.front.compareOp = vk_compare_op_from_wined3d(state->render_states[WINED3D_RS_STENCILFUNC]); - key->ds_desc.front.compareMask = state->render_states[WINED3D_RS_STENCILMASK]; - key->ds_desc.front.writeMask = state->render_states[WINED3D_RS_STENCILWRITEMASK]; - key->ds_desc.front.reference = state->render_states[WINED3D_RS_STENCILREF] - & ((1 << state->fb.depth_stencil->format->stencil_size) - 1); - - if (state->render_states[WINED3D_RS_TWOSIDEDSTENCILMODE]) - { - key->ds_desc.back.failOp = vk_stencil_op_from_wined3d( - state->render_states[WINED3D_RS_BACK_STENCILFAIL]); - key->ds_desc.back.passOp = vk_stencil_op_from_wined3d( - state->render_states[WINED3D_RS_BACK_STENCILPASS]); - key->ds_desc.back.depthFailOp = vk_stencil_op_from_wined3d( - state->render_states[WINED3D_RS_BACK_STENCILZFAIL]); - key->ds_desc.back.compareOp = vk_compare_op_from_wined3d( - state->render_states[WINED3D_RS_BACK_STENCILFUNC]); - key->ds_desc.back.compareMask = state->render_states[WINED3D_RS_STENCILMASK]; - key->ds_desc.back.writeMask = state->render_states[WINED3D_RS_STENCILWRITEMASK]; - key->ds_desc.back.reference = state->render_states[WINED3D_RS_STENCILREF] - & ((1 << state->fb.depth_stencil->format->stencil_size) - 1); - } - else - { - key->ds_desc.back = key->ds_desc.front; - } - }
update = true; } diff --git a/dlls/wined3d/cs.c b/dlls/wined3d/cs.c index 6509887afa9..66a67ce239b 100644 --- a/dlls/wined3d/cs.c +++ b/dlls/wined3d/cs.c @@ -1227,7 +1227,6 @@ static void wined3d_cs_exec_set_depth_stencil_view(struct wined3d_cs *cs, const { /* Swapping NULL / non NULL depth stencil affects the depth and tests */ device_invalidate_state(device, STATE_DEPTH_STENCIL); - device_invalidate_state(device, STATE_RENDER(WINED3D_RS_STENCILENABLE)); device_invalidate_state(device, STATE_RENDER(WINED3D_RS_STENCILWRITEMASK)); device_invalidate_state(device, STATE_RASTERIZER); } diff --git a/dlls/wined3d/device.c b/dlls/wined3d/device.c index 5c94fae0a98..1dcf4fcb93c 100644 --- a/dlls/wined3d/device.c +++ b/dlls/wined3d/device.c @@ -3685,6 +3685,7 @@ void CDECL wined3d_device_apply_stateblock(struct wined3d_device *device, set_blend_state = TRUE; break;
+ case WINED3D_RS_STENCILENABLE: case WINED3D_RS_ZENABLE: case WINED3D_RS_ZWRITEENABLE: set_depth_stencil_state = TRUE; @@ -3841,6 +3842,7 @@ void CDECL wined3d_device_apply_stateblock(struct wined3d_device *device, FIXME("Unrecognized depth buffer type %#x.\n", state->rs[WINED3D_RS_ZENABLE]); } desc.depth_write = state->rs[WINED3D_RS_ZWRITEENABLE]; + desc.stencil = state->rs[WINED3D_RS_STENCILENABLE];
if ((entry = wine_rb_get(&device->depth_stencil_states, &desc))) { @@ -4360,7 +4362,8 @@ HRESULT CDECL wined3d_device_validate_device(const struct wined3d_device *device } }
- if (wined3d_state_uses_depth_buffer(state) || state->render_states[WINED3D_RS_STENCILENABLE]) + if (wined3d_state_uses_depth_buffer(state) + || (state->depth_stencil_state && state->depth_stencil_state->desc.stencil)) { struct wined3d_rendertarget_view *rt = device->state.fb.render_targets[0]; struct wined3d_rendertarget_view *ds = device->state.fb.depth_stencil; diff --git a/dlls/wined3d/directx.c b/dlls/wined3d/directx.c index cf355438c45..0395c8dc24b 100644 --- a/dlls/wined3d/directx.c +++ b/dlls/wined3d/directx.c @@ -2439,7 +2439,6 @@ static const struct wined3d_state_entry_template misc_state_template_no3d[] = {STATE_RENDER(WINED3D_RS_ANISOTROPY), {STATE_VDECL}}, {STATE_RENDER(WINED3D_RS_FLUSHBATCH), {STATE_VDECL}}, {STATE_RENDER(WINED3D_RS_TRANSLUCENTSORTINDEPENDENT), {STATE_VDECL}}, - {STATE_RENDER(WINED3D_RS_STENCILENABLE), {STATE_VDECL}}, {STATE_RENDER(WINED3D_RS_STENCILFAIL), {STATE_VDECL}}, {STATE_RENDER(WINED3D_RS_STENCILZFAIL), {STATE_VDECL}}, {STATE_RENDER(WINED3D_RS_STENCILPASS), {STATE_VDECL}}, diff --git a/dlls/wined3d/state.c b/dlls/wined3d/state.c index 7a9e69f775c..0f88b4a2677 100644 --- a/dlls/wined3d/state.c +++ b/dlls/wined3d/state.c @@ -1053,10 +1053,10 @@ static GLenum gl_stencil_op(enum wined3d_stencil_op op) } }
-static void state_stencil(struct wined3d_context *context, const struct wined3d_state *state, DWORD state_id) +static void state_stencil(struct wined3d_context *context, const struct wined3d_state *state) { const struct wined3d_gl_info *gl_info = wined3d_context_gl(context)->gl_info; - DWORD onesided_enable; + const struct wined3d_depth_stencil_state *d = state->depth_stencil_state; DWORD twosided_enable; GLint func; GLint func_back; @@ -1070,14 +1070,13 @@ static void state_stencil(struct wined3d_context *context, const struct wined3d_ GLint depthFail_back;
/* No stencil test without a stencil buffer. */ - if (!state->fb.depth_stencil) + if (!state->fb.depth_stencil || !d || !d->desc.stencil) { gl_info->gl_ops.gl.p_glDisable(GL_STENCIL_TEST); checkGLcall("glDisable GL_STENCIL_TEST"); return; }
- onesided_enable = state->render_states[WINED3D_RS_STENCILENABLE]; twosided_enable = state->render_states[WINED3D_RS_TWOSIDEDSTENCILMODE]; if (!(func = wined3d_gl_compare_func(state->render_states[WINED3D_RS_STENCILFUNC]))) func = GL_ALWAYS; @@ -1092,14 +1091,14 @@ static void state_stencil(struct wined3d_context *context, const struct wined3d_ depthFail_back = gl_stencil_op(state->render_states[WINED3D_RS_BACK_STENCILZFAIL]); stencilPass_back = gl_stencil_op(state->render_states[WINED3D_RS_BACK_STENCILPASS]);
- TRACE("(onesided %d, twosided %d, ref %x, mask %x, " + TRACE("(twosided %d, ref %x, mask %x, " "GL_FRONT: func: %x, fail %x, zfail %x, zpass %x " "GL_BACK: func: %x, fail %x, zfail %x, zpass %x)\n", - onesided_enable, twosided_enable, ref, mask, + twosided_enable, ref, mask, func, stencilFail, depthFail, stencilPass, func_back, stencilFail_back, depthFail_back, stencilPass_back);
- if (twosided_enable && onesided_enable) + if (twosided_enable) { gl_info->gl_ops.gl.p_glEnable(GL_STENCIL_TEST); checkGLcall("glEnable GL_STENCIL_TEST"); @@ -1139,7 +1138,7 @@ static void state_stencil(struct wined3d_context *context, const struct wined3d_ FIXME("Separate (two sided) stencil not supported on this version of OpenGL. Caps weren't honored?\n"); } } - else if(onesided_enable) + else { if (gl_info->supported[EXT_STENCIL_TWO_SIDE]) { @@ -1157,11 +1156,6 @@ static void state_stencil(struct wined3d_context *context, const struct wined3d_ gl_info->gl_ops.gl.p_glStencilOp(stencilFail, depthFail, stencilPass); checkGLcall("glStencilOp(...)"); } - else - { - gl_info->gl_ops.gl.p_glDisable(GL_STENCIL_TEST); - checkGLcall("glDisable GL_STENCIL_TEST"); - } }
static void state_stencilwrite2s_ext(struct wined3d_context *context, const struct wined3d_state *state, DWORD state_id) @@ -1221,6 +1215,8 @@ static void depth_stencil(struct wined3d_context *context, const struct wined3d_ checkGLcall("glDepthMask(GL_FALSE)"); }
+ state_stencil(context, state); + if (context->last_was_rhw && !isStateDirty(context, STATE_TRANSFORM(WINED3D_TS_PROJECTION))) context_apply_state(context, state, STATE_TRANSFORM(WINED3D_TS_PROJECTION)); } @@ -4757,20 +4753,19 @@ const struct wined3d_state_entry_template misc_state_template_gl[] = { STATE_RENDER(WINED3D_RS_ANISOTROPY), { STATE_RENDER(WINED3D_RS_ANISOTROPY), state_anisotropy }, WINED3D_GL_EXT_NONE }, { STATE_RENDER(WINED3D_RS_FLUSHBATCH), { STATE_RENDER(WINED3D_RS_FLUSHBATCH), state_flushbatch }, WINED3D_GL_EXT_NONE }, { STATE_RENDER(WINED3D_RS_TRANSLUCENTSORTINDEPENDENT),{ STATE_RENDER(WINED3D_RS_TRANSLUCENTSORTINDEPENDENT),state_translucentsi }, WINED3D_GL_EXT_NONE }, - { STATE_RENDER(WINED3D_RS_STENCILENABLE), { STATE_RENDER(WINED3D_RS_STENCILENABLE), state_stencil }, WINED3D_GL_EXT_NONE }, - { STATE_RENDER(WINED3D_RS_STENCILFAIL), { STATE_RENDER(WINED3D_RS_STENCILENABLE), NULL }, WINED3D_GL_EXT_NONE }, - { STATE_RENDER(WINED3D_RS_STENCILZFAIL), { STATE_RENDER(WINED3D_RS_STENCILENABLE), NULL }, WINED3D_GL_EXT_NONE }, - { STATE_RENDER(WINED3D_RS_STENCILPASS), { STATE_RENDER(WINED3D_RS_STENCILENABLE), NULL }, WINED3D_GL_EXT_NONE }, - { STATE_RENDER(WINED3D_RS_STENCILFUNC), { STATE_RENDER(WINED3D_RS_STENCILENABLE), NULL }, WINED3D_GL_EXT_NONE }, - { STATE_RENDER(WINED3D_RS_STENCILREF), { STATE_RENDER(WINED3D_RS_STENCILENABLE), NULL }, WINED3D_GL_EXT_NONE }, - { STATE_RENDER(WINED3D_RS_STENCILMASK), { STATE_RENDER(WINED3D_RS_STENCILENABLE), NULL }, WINED3D_GL_EXT_NONE }, + { STATE_RENDER(WINED3D_RS_STENCILFAIL), { STATE_DEPTH_STENCIL, NULL }, WINED3D_GL_EXT_NONE }, + { STATE_RENDER(WINED3D_RS_STENCILZFAIL), { STATE_DEPTH_STENCIL, NULL }, WINED3D_GL_EXT_NONE }, + { STATE_RENDER(WINED3D_RS_STENCILPASS), { STATE_DEPTH_STENCIL, NULL }, WINED3D_GL_EXT_NONE }, + { STATE_RENDER(WINED3D_RS_STENCILFUNC), { STATE_DEPTH_STENCIL, NULL }, WINED3D_GL_EXT_NONE }, + { STATE_RENDER(WINED3D_RS_STENCILREF), { STATE_DEPTH_STENCIL, NULL }, WINED3D_GL_EXT_NONE }, + { STATE_RENDER(WINED3D_RS_STENCILMASK), { STATE_DEPTH_STENCIL, NULL }, WINED3D_GL_EXT_NONE }, { STATE_RENDER(WINED3D_RS_STENCILWRITEMASK), { STATE_RENDER(WINED3D_RS_STENCILWRITEMASK), state_stencilwrite2s_ext}, EXT_STENCIL_TWO_SIDE }, { STATE_RENDER(WINED3D_RS_STENCILWRITEMASK), { STATE_RENDER(WINED3D_RS_STENCILWRITEMASK), state_stencilwrite }, WINED3D_GL_EXT_NONE }, - { STATE_RENDER(WINED3D_RS_TWOSIDEDSTENCILMODE), { STATE_RENDER(WINED3D_RS_STENCILENABLE), NULL }, WINED3D_GL_EXT_NONE }, - { STATE_RENDER(WINED3D_RS_BACK_STENCILFAIL), { STATE_RENDER(WINED3D_RS_STENCILENABLE), NULL }, WINED3D_GL_EXT_NONE }, - { STATE_RENDER(WINED3D_RS_BACK_STENCILZFAIL), { STATE_RENDER(WINED3D_RS_STENCILENABLE), NULL }, WINED3D_GL_EXT_NONE }, - { STATE_RENDER(WINED3D_RS_BACK_STENCILPASS), { STATE_RENDER(WINED3D_RS_STENCILENABLE), NULL }, WINED3D_GL_EXT_NONE }, - { STATE_RENDER(WINED3D_RS_BACK_STENCILFUNC), { STATE_RENDER(WINED3D_RS_STENCILENABLE), NULL }, WINED3D_GL_EXT_NONE }, + { STATE_RENDER(WINED3D_RS_TWOSIDEDSTENCILMODE), { STATE_DEPTH_STENCIL, NULL }, WINED3D_GL_EXT_NONE }, + { STATE_RENDER(WINED3D_RS_BACK_STENCILFAIL), { STATE_DEPTH_STENCIL, NULL }, WINED3D_GL_EXT_NONE }, + { STATE_RENDER(WINED3D_RS_BACK_STENCILZFAIL), { STATE_DEPTH_STENCIL, NULL }, WINED3D_GL_EXT_NONE }, + { STATE_RENDER(WINED3D_RS_BACK_STENCILPASS), { STATE_DEPTH_STENCIL, NULL }, WINED3D_GL_EXT_NONE }, + { STATE_RENDER(WINED3D_RS_BACK_STENCILFUNC), { STATE_DEPTH_STENCIL, NULL }, WINED3D_GL_EXT_NONE }, { STATE_RENDER(WINED3D_RS_WRAP0), { STATE_RENDER(WINED3D_RS_WRAP0), state_wrap }, WINED3D_GL_EXT_NONE }, { STATE_RENDER(WINED3D_RS_WRAP1), { STATE_RENDER(WINED3D_RS_WRAP0), NULL }, WINED3D_GL_EXT_NONE }, { STATE_RENDER(WINED3D_RS_WRAP2), { STATE_RENDER(WINED3D_RS_WRAP0), NULL }, WINED3D_GL_EXT_NONE }, @@ -5569,6 +5564,7 @@ static void validate_state_table(struct wined3d_state_entry *state_table) { 40, 40}, { 42, 45}, { 47, 47}, + { 52, 52}, { 61, 127}, {149, 150}, {162, 162}, diff --git a/include/wine/wined3d.h b/include/wine/wined3d.h index ef2a7de4580..ad860a1eae2 100644 --- a/include/wine/wined3d.h +++ b/include/wine/wined3d.h @@ -2040,6 +2040,7 @@ struct wined3d_depth_stencil_state_desc { BOOL depth; BOOL depth_write; + BOOL stencil; };
struct wined3d_rasterizer_state_desc
Signed-off-by: Henri Verbeet hverbeet@codeweavers.com
Signed-off-by: Zebediah Figura z.figura12@gmail.com --- dlls/d3d11/device.c | 1 - dlls/d3d11/state.c | 1 + dlls/wined3d/adapter_vk.c | 1 - dlls/wined3d/context_vk.c | 4 ++-- dlls/wined3d/device.c | 2 ++ dlls/wined3d/directx.c | 1 - dlls/wined3d/state.c | 4 ++-- include/wine/wined3d.h | 1 + 8 files changed, 8 insertions(+), 7 deletions(-)
diff --git a/dlls/d3d11/device.c b/dlls/d3d11/device.c index cac72e614e5..7ed8dc8bd71 100644 --- a/dlls/d3d11/device.c +++ b/dlls/d3d11/device.c @@ -761,7 +761,6 @@ static void STDMETHODCALLTYPE d3d11_immediate_context_OMSetDepthStencilState(ID3
if (desc->StencilEnable) { - wined3d_device_set_render_state(device->wined3d_device, WINED3D_RS_STENCILMASK, desc->StencilReadMask); wined3d_device_set_render_state(device->wined3d_device, WINED3D_RS_STENCILWRITEMASK, desc->StencilWriteMask); wined3d_device_set_render_state(device->wined3d_device, WINED3D_RS_STENCILREF, stencil_ref);
diff --git a/dlls/d3d11/state.c b/dlls/d3d11/state.c index 609c5e4c103..78540d35117 100644 --- a/dlls/d3d11/state.c +++ b/dlls/d3d11/state.c @@ -797,6 +797,7 @@ HRESULT d3d_depthstencil_state_create(struct d3d_device *device, const D3D11_DEP wined3d_desc.depth = desc->DepthEnable; wined3d_desc.depth_write = desc->DepthWriteMask; wined3d_desc.stencil = desc->StencilEnable; + wined3d_desc.stencil_read_mask = desc->StencilReadMask;
/* We cannot fail after creating a wined3d_depth_stencil_state object. It * would lead to double free. */ diff --git a/dlls/wined3d/adapter_vk.c b/dlls/wined3d/adapter_vk.c index 9c9da418406..ee5390006a0 100644 --- a/dlls/wined3d/adapter_vk.c +++ b/dlls/wined3d/adapter_vk.c @@ -122,7 +122,6 @@ static const struct wined3d_state_entry_template misc_state_template_vk[] = {STATE_RENDER(WINED3D_RS_STENCILPASS), {STATE_RENDER(WINED3D_RS_ZFUNC)}}, {STATE_RENDER(WINED3D_RS_STENCILFUNC), {STATE_RENDER(WINED3D_RS_ZFUNC)}}, {STATE_RENDER(WINED3D_RS_STENCILREF), {STATE_RENDER(WINED3D_RS_ZFUNC)}}, - {STATE_RENDER(WINED3D_RS_STENCILMASK), {STATE_RENDER(WINED3D_RS_ZFUNC)}}, {STATE_RENDER(WINED3D_RS_STENCILWRITEMASK), {STATE_RENDER(WINED3D_RS_ZFUNC)}}, {STATE_RENDER(WINED3D_RS_TWOSIDEDSTENCILMODE), {STATE_RENDER(WINED3D_RS_ZFUNC)}}, {STATE_RENDER(WINED3D_RS_BACK_STENCILFAIL), {STATE_RENDER(WINED3D_RS_ZFUNC)}}, diff --git a/dlls/wined3d/context_vk.c b/dlls/wined3d/context_vk.c index 6eaee71c54a..f91a1e2e8e9 100644 --- a/dlls/wined3d/context_vk.c +++ b/dlls/wined3d/context_vk.c @@ -2051,7 +2051,7 @@ static bool wined3d_context_vk_update_graphics_pipeline_key(struct wined3d_conte key->ds_desc.front.depthFailOp = vk_stencil_op_from_wined3d( state->render_states[WINED3D_RS_STENCILZFAIL]); key->ds_desc.front.compareOp = vk_compare_op_from_wined3d(state->render_states[WINED3D_RS_STENCILFUNC]); - key->ds_desc.front.compareMask = state->render_states[WINED3D_RS_STENCILMASK]; + key->ds_desc.front.compareMask = d->desc.stencil_read_mask; key->ds_desc.front.writeMask = state->render_states[WINED3D_RS_STENCILWRITEMASK]; key->ds_desc.front.reference = state->render_states[WINED3D_RS_STENCILREF] & ((1 << state->fb.depth_stencil->format->stencil_size) - 1); @@ -2066,7 +2066,7 @@ static bool wined3d_context_vk_update_graphics_pipeline_key(struct wined3d_conte state->render_states[WINED3D_RS_BACK_STENCILZFAIL]); key->ds_desc.back.compareOp = vk_compare_op_from_wined3d( state->render_states[WINED3D_RS_BACK_STENCILFUNC]); - key->ds_desc.back.compareMask = state->render_states[WINED3D_RS_STENCILMASK]; + key->ds_desc.back.compareMask = d->desc.stencil_read_mask; key->ds_desc.back.writeMask = state->render_states[WINED3D_RS_STENCILWRITEMASK]; key->ds_desc.back.reference = state->render_states[WINED3D_RS_STENCILREF] & ((1 << state->fb.depth_stencil->format->stencil_size) - 1); diff --git a/dlls/wined3d/device.c b/dlls/wined3d/device.c index 1dcf4fcb93c..054fc528383 100644 --- a/dlls/wined3d/device.c +++ b/dlls/wined3d/device.c @@ -3686,6 +3686,7 @@ void CDECL wined3d_device_apply_stateblock(struct wined3d_device *device, break;
case WINED3D_RS_STENCILENABLE: + case WINED3D_RS_STENCILMASK: case WINED3D_RS_ZENABLE: case WINED3D_RS_ZWRITEENABLE: set_depth_stencil_state = TRUE; @@ -3843,6 +3844,7 @@ void CDECL wined3d_device_apply_stateblock(struct wined3d_device *device, } desc.depth_write = state->rs[WINED3D_RS_ZWRITEENABLE]; desc.stencil = state->rs[WINED3D_RS_STENCILENABLE]; + desc.stencil_read_mask = state->rs[WINED3D_RS_STENCILMASK];
if ((entry = wine_rb_get(&device->depth_stencil_states, &desc))) { diff --git a/dlls/wined3d/directx.c b/dlls/wined3d/directx.c index 0395c8dc24b..6829fc9ef76 100644 --- a/dlls/wined3d/directx.c +++ b/dlls/wined3d/directx.c @@ -2444,7 +2444,6 @@ static const struct wined3d_state_entry_template misc_state_template_no3d[] = {STATE_RENDER(WINED3D_RS_STENCILPASS), {STATE_VDECL}}, {STATE_RENDER(WINED3D_RS_STENCILFUNC), {STATE_VDECL}}, {STATE_RENDER(WINED3D_RS_STENCILREF), {STATE_VDECL}}, - {STATE_RENDER(WINED3D_RS_STENCILMASK), {STATE_VDECL}}, {STATE_RENDER(WINED3D_RS_STENCILWRITEMASK), {STATE_VDECL}}, {STATE_RENDER(WINED3D_RS_TWOSIDEDSTENCILMODE), {STATE_VDECL}}, {STATE_RENDER(WINED3D_RS_BACK_STENCILFAIL), {STATE_VDECL}}, diff --git a/dlls/wined3d/state.c b/dlls/wined3d/state.c index 0f88b4a2677..32076289ac6 100644 --- a/dlls/wined3d/state.c +++ b/dlls/wined3d/state.c @@ -1082,7 +1082,7 @@ static void state_stencil(struct wined3d_context *context, const struct wined3d_ func = GL_ALWAYS; if (!(func_back = wined3d_gl_compare_func(state->render_states[WINED3D_RS_BACK_STENCILFUNC]))) func_back = GL_ALWAYS; - mask = state->render_states[WINED3D_RS_STENCILMASK]; + mask = d->desc.stencil_read_mask; ref = state->render_states[WINED3D_RS_STENCILREF] & ((1 << state->fb.depth_stencil->format->stencil_size) - 1); stencilFail = gl_stencil_op(state->render_states[WINED3D_RS_STENCILFAIL]); depthFail = gl_stencil_op(state->render_states[WINED3D_RS_STENCILZFAIL]); @@ -4758,7 +4758,6 @@ const struct wined3d_state_entry_template misc_state_template_gl[] = { STATE_RENDER(WINED3D_RS_STENCILPASS), { STATE_DEPTH_STENCIL, NULL }, WINED3D_GL_EXT_NONE }, { STATE_RENDER(WINED3D_RS_STENCILFUNC), { STATE_DEPTH_STENCIL, NULL }, WINED3D_GL_EXT_NONE }, { STATE_RENDER(WINED3D_RS_STENCILREF), { STATE_DEPTH_STENCIL, NULL }, WINED3D_GL_EXT_NONE }, - { STATE_RENDER(WINED3D_RS_STENCILMASK), { STATE_DEPTH_STENCIL, NULL }, WINED3D_GL_EXT_NONE }, { STATE_RENDER(WINED3D_RS_STENCILWRITEMASK), { STATE_RENDER(WINED3D_RS_STENCILWRITEMASK), state_stencilwrite2s_ext}, EXT_STENCIL_TWO_SIDE }, { STATE_RENDER(WINED3D_RS_STENCILWRITEMASK), { STATE_RENDER(WINED3D_RS_STENCILWRITEMASK), state_stencilwrite }, WINED3D_GL_EXT_NONE }, { STATE_RENDER(WINED3D_RS_TWOSIDEDSTENCILMODE), { STATE_DEPTH_STENCIL, NULL }, WINED3D_GL_EXT_NONE }, @@ -5565,6 +5564,7 @@ static void validate_state_table(struct wined3d_state_entry *state_table) { 42, 45}, { 47, 47}, { 52, 52}, + { 58, 58}, { 61, 127}, {149, 150}, {162, 162}, diff --git a/include/wine/wined3d.h b/include/wine/wined3d.h index ad860a1eae2..e2db42766fb 100644 --- a/include/wine/wined3d.h +++ b/include/wine/wined3d.h @@ -2041,6 +2041,7 @@ struct wined3d_depth_stencil_state_desc BOOL depth; BOOL depth_write; BOOL stencil; + unsigned int stencil_read_mask; };
struct wined3d_rasterizer_state_desc
Signed-off-by: Henri Verbeet hverbeet@codeweavers.com
Signed-off-by: Zebediah Figura z.figura12@gmail.com --- dlls/d3d11/device.c | 1 - dlls/d3d11/state.c | 1 + dlls/wined3d/adapter_vk.c | 1 - dlls/wined3d/context_vk.c | 4 +-- dlls/wined3d/cs.c | 1 - dlls/wined3d/device.c | 2 ++ dlls/wined3d/directx.c | 1 - dlls/wined3d/state.c | 69 +++++++++++++++++++++++---------------- dlls/wined3d/texture.c | 4 +-- include/wine/wined3d.h | 1 + 10 files changed, 48 insertions(+), 37 deletions(-)
diff --git a/dlls/d3d11/device.c b/dlls/d3d11/device.c index 7ed8dc8bd71..159d3f36334 100644 --- a/dlls/d3d11/device.c +++ b/dlls/d3d11/device.c @@ -761,7 +761,6 @@ static void STDMETHODCALLTYPE d3d11_immediate_context_OMSetDepthStencilState(ID3
if (desc->StencilEnable) { - wined3d_device_set_render_state(device->wined3d_device, WINED3D_RS_STENCILWRITEMASK, desc->StencilWriteMask); wined3d_device_set_render_state(device->wined3d_device, WINED3D_RS_STENCILREF, stencil_ref);
wined3d_device_set_render_state(device->wined3d_device, WINED3D_RS_STENCILFAIL, front->StencilFailOp); diff --git a/dlls/d3d11/state.c b/dlls/d3d11/state.c index 78540d35117..c0be2fe592b 100644 --- a/dlls/d3d11/state.c +++ b/dlls/d3d11/state.c @@ -798,6 +798,7 @@ HRESULT d3d_depthstencil_state_create(struct d3d_device *device, const D3D11_DEP wined3d_desc.depth_write = desc->DepthWriteMask; wined3d_desc.stencil = desc->StencilEnable; wined3d_desc.stencil_read_mask = desc->StencilReadMask; + wined3d_desc.stencil_write_mask = desc->StencilWriteMask;
/* We cannot fail after creating a wined3d_depth_stencil_state object. It * would lead to double free. */ diff --git a/dlls/wined3d/adapter_vk.c b/dlls/wined3d/adapter_vk.c index ee5390006a0..80b06482e64 100644 --- a/dlls/wined3d/adapter_vk.c +++ b/dlls/wined3d/adapter_vk.c @@ -122,7 +122,6 @@ static const struct wined3d_state_entry_template misc_state_template_vk[] = {STATE_RENDER(WINED3D_RS_STENCILPASS), {STATE_RENDER(WINED3D_RS_ZFUNC)}}, {STATE_RENDER(WINED3D_RS_STENCILFUNC), {STATE_RENDER(WINED3D_RS_ZFUNC)}}, {STATE_RENDER(WINED3D_RS_STENCILREF), {STATE_RENDER(WINED3D_RS_ZFUNC)}}, - {STATE_RENDER(WINED3D_RS_STENCILWRITEMASK), {STATE_RENDER(WINED3D_RS_ZFUNC)}}, {STATE_RENDER(WINED3D_RS_TWOSIDEDSTENCILMODE), {STATE_RENDER(WINED3D_RS_ZFUNC)}}, {STATE_RENDER(WINED3D_RS_BACK_STENCILFAIL), {STATE_RENDER(WINED3D_RS_ZFUNC)}}, {STATE_RENDER(WINED3D_RS_BACK_STENCILZFAIL), {STATE_RENDER(WINED3D_RS_ZFUNC)}}, diff --git a/dlls/wined3d/context_vk.c b/dlls/wined3d/context_vk.c index f91a1e2e8e9..26cd3f5a4ef 100644 --- a/dlls/wined3d/context_vk.c +++ b/dlls/wined3d/context_vk.c @@ -2052,7 +2052,7 @@ static bool wined3d_context_vk_update_graphics_pipeline_key(struct wined3d_conte state->render_states[WINED3D_RS_STENCILZFAIL]); key->ds_desc.front.compareOp = vk_compare_op_from_wined3d(state->render_states[WINED3D_RS_STENCILFUNC]); key->ds_desc.front.compareMask = d->desc.stencil_read_mask; - key->ds_desc.front.writeMask = state->render_states[WINED3D_RS_STENCILWRITEMASK]; + key->ds_desc.front.writeMask = d->desc.stencil_write_mask; key->ds_desc.front.reference = state->render_states[WINED3D_RS_STENCILREF] & ((1 << state->fb.depth_stencil->format->stencil_size) - 1);
@@ -2067,7 +2067,7 @@ static bool wined3d_context_vk_update_graphics_pipeline_key(struct wined3d_conte key->ds_desc.back.compareOp = vk_compare_op_from_wined3d( state->render_states[WINED3D_RS_BACK_STENCILFUNC]); key->ds_desc.back.compareMask = d->desc.stencil_read_mask; - key->ds_desc.back.writeMask = state->render_states[WINED3D_RS_STENCILWRITEMASK]; + key->ds_desc.back.writeMask = d->desc.stencil_write_mask; key->ds_desc.back.reference = state->render_states[WINED3D_RS_STENCILREF] & ((1 << state->fb.depth_stencil->format->stencil_size) - 1); } diff --git a/dlls/wined3d/cs.c b/dlls/wined3d/cs.c index 66a67ce239b..48b73a71fe4 100644 --- a/dlls/wined3d/cs.c +++ b/dlls/wined3d/cs.c @@ -1227,7 +1227,6 @@ static void wined3d_cs_exec_set_depth_stencil_view(struct wined3d_cs *cs, const { /* Swapping NULL / non NULL depth stencil affects the depth and tests */ device_invalidate_state(device, STATE_DEPTH_STENCIL); - device_invalidate_state(device, STATE_RENDER(WINED3D_RS_STENCILWRITEMASK)); device_invalidate_state(device, STATE_RASTERIZER); } else if (prev) diff --git a/dlls/wined3d/device.c b/dlls/wined3d/device.c index 054fc528383..754dd7693c9 100644 --- a/dlls/wined3d/device.c +++ b/dlls/wined3d/device.c @@ -3687,6 +3687,7 @@ void CDECL wined3d_device_apply_stateblock(struct wined3d_device *device,
case WINED3D_RS_STENCILENABLE: case WINED3D_RS_STENCILMASK: + case WINED3D_RS_STENCILWRITEMASK: case WINED3D_RS_ZENABLE: case WINED3D_RS_ZWRITEENABLE: set_depth_stencil_state = TRUE; @@ -3845,6 +3846,7 @@ void CDECL wined3d_device_apply_stateblock(struct wined3d_device *device, desc.depth_write = state->rs[WINED3D_RS_ZWRITEENABLE]; desc.stencil = state->rs[WINED3D_RS_STENCILENABLE]; desc.stencil_read_mask = state->rs[WINED3D_RS_STENCILMASK]; + desc.stencil_write_mask = state->rs[WINED3D_RS_STENCILWRITEMASK];
if ((entry = wine_rb_get(&device->depth_stencil_states, &desc))) { diff --git a/dlls/wined3d/directx.c b/dlls/wined3d/directx.c index 6829fc9ef76..c31cf06ec26 100644 --- a/dlls/wined3d/directx.c +++ b/dlls/wined3d/directx.c @@ -2444,7 +2444,6 @@ static const struct wined3d_state_entry_template misc_state_template_no3d[] = {STATE_RENDER(WINED3D_RS_STENCILPASS), {STATE_VDECL}}, {STATE_RENDER(WINED3D_RS_STENCILFUNC), {STATE_VDECL}}, {STATE_RENDER(WINED3D_RS_STENCILREF), {STATE_VDECL}}, - {STATE_RENDER(WINED3D_RS_STENCILWRITEMASK), {STATE_VDECL}}, {STATE_RENDER(WINED3D_RS_TWOSIDEDSTENCILMODE), {STATE_VDECL}}, {STATE_RENDER(WINED3D_RS_BACK_STENCILFAIL), {STATE_VDECL}}, {STATE_RENDER(WINED3D_RS_BACK_STENCILZFAIL), {STATE_VDECL}}, diff --git a/dlls/wined3d/state.c b/dlls/wined3d/state.c index 32076289ac6..4a1a7c80b8f 100644 --- a/dlls/wined3d/state.c +++ b/dlls/wined3d/state.c @@ -1158,30 +1158,7 @@ static void state_stencil(struct wined3d_context *context, const struct wined3d_ } }
-static void state_stencilwrite2s_ext(struct wined3d_context *context, const struct wined3d_state *state, DWORD state_id) -{ - DWORD mask = state->fb.depth_stencil ? state->render_states[WINED3D_RS_STENCILWRITEMASK] : 0; - const struct wined3d_gl_info *gl_info = wined3d_context_gl(context)->gl_info; - - GL_EXTCALL(glActiveStencilFaceEXT(GL_BACK)); - checkGLcall("glActiveStencilFaceEXT(GL_BACK)"); - gl_info->gl_ops.gl.p_glStencilMask(mask); - checkGLcall("glStencilMask"); - GL_EXTCALL(glActiveStencilFaceEXT(GL_FRONT)); - checkGLcall("glActiveStencilFaceEXT(GL_FRONT)"); - gl_info->gl_ops.gl.p_glStencilMask(mask); -} - -static void state_stencilwrite(struct wined3d_context *context, const struct wined3d_state *state, DWORD state_id) -{ - DWORD mask = state->fb.depth_stencil ? state->render_states[WINED3D_RS_STENCILWRITEMASK] : 0; - const struct wined3d_gl_info *gl_info = wined3d_context_gl(context)->gl_info; - - gl_info->gl_ops.gl.p_glStencilMask(mask); - checkGLcall("glStencilMask"); -} - -static void depth_stencil(struct wined3d_context *context, const struct wined3d_state *state, DWORD state_id) +static void depth(struct wined3d_context *context, const struct wined3d_state *state) { const struct wined3d_gl_info *gl_info = wined3d_context_gl(context)->gl_info; const struct wined3d_depth_stencil_state *d = state->depth_stencil_state; @@ -1215,12 +1192,47 @@ static void depth_stencil(struct wined3d_context *context, const struct wined3d_ checkGLcall("glDepthMask(GL_FALSE)"); }
- state_stencil(context, state); - if (context->last_was_rhw && !isStateDirty(context, STATE_TRANSFORM(WINED3D_TS_PROJECTION))) context_apply_state(context, state, STATE_TRANSFORM(WINED3D_TS_PROJECTION)); }
+static void depth_stencil(struct wined3d_context *context, const struct wined3d_state *state, DWORD state_id) +{ + const struct wined3d_gl_info *gl_info = wined3d_context_gl(context)->gl_info; + const struct wined3d_depth_stencil_state *d = state->depth_stencil_state; + GLuint stencil_write_mask = 0; + + depth(context, state); + state_stencil(context, state); + + if (state->fb.depth_stencil) + stencil_write_mask = d ? d->desc.stencil_write_mask : ~0u; + + gl_info->gl_ops.gl.p_glStencilMask(stencil_write_mask); + checkGLcall("glStencilMask"); +} + +static void depth_stencil_2s(struct wined3d_context *context, const struct wined3d_state *state, DWORD state_id) +{ + const struct wined3d_gl_info *gl_info = wined3d_context_gl(context)->gl_info; + const struct wined3d_depth_stencil_state *d = state->depth_stencil_state; + GLuint stencil_write_mask = 0; + + depth(context, state); + state_stencil(context, state); + + if (state->fb.depth_stencil) + stencil_write_mask = d ? d->desc.stencil_write_mask : ~0u; + + GL_EXTCALL(glActiveStencilFaceEXT(GL_BACK)); + checkGLcall("glActiveStencilFaceEXT(GL_BACK)"); + gl_info->gl_ops.gl.p_glStencilMask(stencil_write_mask); + checkGLcall("glStencilMask"); + GL_EXTCALL(glActiveStencilFaceEXT(GL_FRONT)); + checkGLcall("glActiveStencilFaceEXT(GL_FRONT)"); + gl_info->gl_ops.gl.p_glStencilMask(stencil_write_mask); +} + static void state_fog_vertexpart(struct wined3d_context *context, const struct wined3d_state *state, DWORD state_id) { const struct wined3d_gl_info *gl_info = wined3d_context_gl(context)->gl_info; @@ -4667,6 +4679,7 @@ const struct wined3d_state_entry_template misc_state_template_gl[] = { STATE_BLEND_FACTOR, { STATE_BLEND_FACTOR, state_blend_factor_w}, WINED3D_GL_EXT_NONE }, { STATE_SAMPLE_MASK, { STATE_SAMPLE_MASK, state_sample_mask }, ARB_TEXTURE_MULTISAMPLE }, { STATE_SAMPLE_MASK, { STATE_SAMPLE_MASK, state_sample_mask_w }, WINED3D_GL_EXT_NONE }, + { STATE_DEPTH_STENCIL, { STATE_DEPTH_STENCIL, depth_stencil_2s }, EXT_STENCIL_TWO_SIDE }, { STATE_DEPTH_STENCIL, { STATE_DEPTH_STENCIL, depth_stencil }, WINED3D_GL_EXT_NONE }, { STATE_STREAMSRC, { STATE_STREAMSRC, streamsrc }, WINED3D_GL_EXT_NONE }, { STATE_VDECL, { STATE_VDECL, vdecl_miscpart }, WINED3D_GL_EXT_NONE }, @@ -4758,8 +4771,6 @@ const struct wined3d_state_entry_template misc_state_template_gl[] = { STATE_RENDER(WINED3D_RS_STENCILPASS), { STATE_DEPTH_STENCIL, NULL }, WINED3D_GL_EXT_NONE }, { STATE_RENDER(WINED3D_RS_STENCILFUNC), { STATE_DEPTH_STENCIL, NULL }, WINED3D_GL_EXT_NONE }, { STATE_RENDER(WINED3D_RS_STENCILREF), { STATE_DEPTH_STENCIL, NULL }, WINED3D_GL_EXT_NONE }, - { STATE_RENDER(WINED3D_RS_STENCILWRITEMASK), { STATE_RENDER(WINED3D_RS_STENCILWRITEMASK), state_stencilwrite2s_ext}, EXT_STENCIL_TWO_SIDE }, - { STATE_RENDER(WINED3D_RS_STENCILWRITEMASK), { STATE_RENDER(WINED3D_RS_STENCILWRITEMASK), state_stencilwrite }, WINED3D_GL_EXT_NONE }, { STATE_RENDER(WINED3D_RS_TWOSIDEDSTENCILMODE), { STATE_DEPTH_STENCIL, NULL }, WINED3D_GL_EXT_NONE }, { STATE_RENDER(WINED3D_RS_BACK_STENCILFAIL), { STATE_DEPTH_STENCIL, NULL }, WINED3D_GL_EXT_NONE }, { STATE_RENDER(WINED3D_RS_BACK_STENCILZFAIL), { STATE_DEPTH_STENCIL, NULL }, WINED3D_GL_EXT_NONE }, @@ -5564,7 +5575,7 @@ static void validate_state_table(struct wined3d_state_entry *state_table) { 42, 45}, { 47, 47}, { 52, 52}, - { 58, 58}, + { 58, 59}, { 61, 127}, {149, 150}, {162, 162}, diff --git a/dlls/wined3d/texture.c b/dlls/wined3d/texture.c index 911ee0e6262..3381252e75d 100644 --- a/dlls/wined3d/texture.c +++ b/dlls/wined3d/texture.c @@ -515,7 +515,7 @@ static void texture2d_depth_blt_fbo(const struct wined3d_device *device, struct context_invalidate_state(context, STATE_RENDER(WINED3D_RS_TWOSIDEDSTENCILMODE)); } gl_info->gl_ops.gl.p_glStencilMask(~0U); - context_invalidate_state(context, STATE_RENDER(WINED3D_RS_STENCILWRITEMASK)); + context_invalidate_state(context, STATE_DEPTH_STENCIL); }
gl_info->gl_ops.gl.p_glDisable(GL_SCISSOR_TEST); @@ -5394,7 +5394,7 @@ static void ffp_blitter_clear_rendertargets(struct wined3d_device *device, unsig context_invalidate_state(context, STATE_RENDER(WINED3D_RS_TWOSIDEDSTENCILMODE)); } gl_info->gl_ops.gl.p_glStencilMask(~0u); - context_invalidate_state(context, STATE_RENDER(WINED3D_RS_STENCILWRITEMASK)); + context_invalidate_state(context, STATE_DEPTH_STENCIL); gl_info->gl_ops.gl.p_glClearStencil(stencil); checkGLcall("glClearStencil"); clear_mask = clear_mask | GL_STENCIL_BUFFER_BIT; diff --git a/include/wine/wined3d.h b/include/wine/wined3d.h index e2db42766fb..f77f7dec7eb 100644 --- a/include/wine/wined3d.h +++ b/include/wine/wined3d.h @@ -2042,6 +2042,7 @@ struct wined3d_depth_stencil_state_desc BOOL depth_write; BOOL stencil; unsigned int stencil_read_mask; + unsigned int stencil_write_mask; };
struct wined3d_rasterizer_state_desc
Signed-off-by: Henri Verbeet hverbeet@codeweavers.com