--- dlls/wined3d/context.c | 25 +++++++++++++++++++------ dlls/wined3d/device.c | 13 ++++++++++--- dlls/wined3d/surface.c | 12 ++++++++---- 3 files changed, 37 insertions(+), 13 deletions(-) diff --git a/dlls/wined3d/context.c b/dlls/wined3d/context.c index 4701f9a..efa1006 100644 --- a/dlls/wined3d/context.c +++ b/dlls/wined3d/context.c @@ -640,7 +640,7 @@ static inline void set_blit_dimension(UINT width, UINT height) { * *****************************************************************************/ static inline void SetupForBlit(IWineD3DDeviceImpl *This, WineD3DContext *context, UINT width, UINT height) { - int i; + int i, sampler; const struct StateEntry *StateTable = This->StateTable; TRACE("Setting up context %p for blitting\n", context); @@ -677,6 +677,7 @@ static inline void SetupForBlit(IWineD3DDeviceImpl *This, WineD3DContext *contex * function texture unit. No need to care for higher samplers */ for(i = GL_LIMITS(textures) - 1; i > 0 ; i--) { + sampler = This->rev_tex_unit_map[i]; GL_EXTCALL(glActiveTextureARB(GL_TEXTURE0_ARB + i)); checkGLcall("glActiveTextureARB"); @@ -692,12 +693,19 @@ static inline void SetupForBlit(IWineD3DDeviceImpl *This, WineD3DContext *contex glTexEnvi(GL_TEXTURE_ENV, GL_TEXTURE_ENV_MODE, GL_REPLACE); checkGLcall("glTexEnvi(GL_TEXTURE_ENV, GL_TEXTURE_ENV_MODE, GL_REPLACE);"); - Context_MarkStateDirty(context, STATE_TEXTURESTAGE(i, WINED3DTSS_COLOROP), StateTable); - Context_MarkStateDirty(context, STATE_SAMPLER(i), StateTable); + if (sampler != -1) { + if (sampler < MAX_TEXTURES) { + Context_MarkStateDirty(context, STATE_TEXTURESTAGE(sampler, WINED3DTSS_COLOROP), StateTable); + } + Context_MarkStateDirty(context, STATE_SAMPLER(sampler), StateTable); + } } GL_EXTCALL(glActiveTextureARB(GL_TEXTURE0_ARB)); checkGLcall("glActiveTextureARB"); } + + sampler = This->rev_tex_unit_map[0]; + if(GL_SUPPORT(ARB_TEXTURE_CUBE_MAP)) { glDisable(GL_TEXTURE_CUBE_MAP_ARB); checkGLcall("glDisable GL_TEXTURE_CUBE_MAP_ARB"); @@ -713,7 +721,6 @@ static inline void SetupForBlit(IWineD3DDeviceImpl *This, WineD3DContext *contex checkGLcall("glMatrixMode(GL_TEXTURE)"); glLoadIdentity(); checkGLcall("glLoadIdentity()"); - Context_MarkStateDirty(context, STATE_TRANSFORM(WINED3DTS_TEXTURE0), StateTable); if (GL_SUPPORT(EXT_TEXTURE_LOD_BIAS)) { glTexEnvf(GL_TEXTURE_FILTER_CONTROL_EXT, @@ -721,8 +728,14 @@ static inline void SetupForBlit(IWineD3DDeviceImpl *This, WineD3DContext *contex 0.0); checkGLcall("glTexEnvi GL_TEXTURE_LOD_BIAS_EXT ..."); } - Context_MarkStateDirty(context, STATE_SAMPLER(0), StateTable); - Context_MarkStateDirty(context, STATE_TEXTURESTAGE(0, WINED3DTSS_COLOROP), StateTable); + + if (sampler != -1) { + if (sampler < MAX_TEXTURES) { + Context_MarkStateDirty(context, STATE_TRANSFORM(WINED3DTS_TEXTURE0 + sampler), StateTable); + Context_MarkStateDirty(context, STATE_TEXTURESTAGE(sampler, WINED3DTSS_COLOROP), StateTable); + } + Context_MarkStateDirty(context, STATE_SAMPLER(sampler), StateTable); + } /* Other misc states */ glDisable(GL_ALPHA_TEST); diff --git a/dlls/wined3d/device.c b/dlls/wined3d/device.c index 6c78ec4..0e7c21a 100644 --- a/dlls/wined3d/device.c +++ b/dlls/wined3d/device.c @@ -5752,6 +5752,7 @@ static HRESULT WINAPI IWineD3DDeviceImpl_UpdateSurface(IWineD3DDevice *iface, int rowoffset = 0; /* how many bytes to add onto the end of a row to wraparound to the beginning of the next */ glDescriptor *glDescription = NULL; GLenum dummy; + int sampler; int bpp; CONVERT_TYPES convert = NO_CONVERSION; @@ -5922,7 +5923,10 @@ static HRESULT WINAPI IWineD3DDeviceImpl_UpdateSurface(IWineD3DDevice *iface, LEAVE_GL(); IWineD3DSurface_ModifyLocation(pDestinationSurface, SFLAG_INTEXTURE, TRUE); - IWineD3DDeviceImpl_MarkStateDirty(This, STATE_SAMPLER(0)); + sampler = This->rev_tex_unit_map[0]; + if (sampler != -1) { + IWineD3DDeviceImpl_MarkStateDirty(This, STATE_SAMPLER(sampler)); + } return WINED3D_OK; } @@ -6854,7 +6858,7 @@ static HRESULT WINAPI IWineD3DDeviceImpl_SetCursorProperties(IWineD3DDevice* i INT height = This->cursorHeight; INT width = This->cursorWidth; INT bpp = tableEntry->bpp; - INT i; + INT i, sampler; /* Reformat the texture memory (pitch and width can be * different) */ @@ -6874,7 +6878,10 @@ static HRESULT WINAPI IWineD3DDeviceImpl_SetCursorProperties(IWineD3DDevice* i GL_EXTCALL(glActiveTextureARB(GL_TEXTURE0_ARB)); checkGLcall("glActiveTextureARB"); } - IWineD3DDeviceImpl_MarkStateDirty(This, STATE_SAMPLER(0)); + sampler = This->rev_tex_unit_map[0]; + if (sampler != -1) { + IWineD3DDeviceImpl_MarkStateDirty(This, STATE_SAMPLER(sampler)); + } /* Create a new cursor texture */ glGenTextures(1, &This->cursorTexture); checkGLcall("glGenTextures"); diff --git a/dlls/wined3d/surface.c b/dlls/wined3d/surface.c index 57b5c92..53070f2 100644 --- a/dlls/wined3d/surface.c +++ b/dlls/wined3d/surface.c @@ -40,7 +40,7 @@ static inline void clear_unused_channels(IWineD3DSurfaceImpl *This); static void surface_remove_pbo(IWineD3DSurfaceImpl *This); static void surface_bind_and_dirtify(IWineD3DSurfaceImpl *This) { - GLint active_texture; + int active_sampler; /* We don't need a specific texture unit, but after binding the texture the current unit is dirty. * Read the unit back instead of switching to 0, this avoids messing around with the state manager's @@ -49,14 +49,18 @@ static void surface_bind_and_dirtify(IWineD3DSurfaceImpl *This) { * TODO: Track the current active texture per GL context instead of using glGet */ if (GL_SUPPORT(ARB_MULTITEXTURE)) { + GLint active_texture; ENTER_GL(); glGetIntegerv(GL_ACTIVE_TEXTURE, &active_texture); LEAVE_GL(); - active_texture -= GL_TEXTURE0_ARB; + active_sampler = This->resource.wineD3DDevice->rev_tex_unit_map[active_texture - GL_TEXTURE0_ARB]; } else { - active_texture = 0; + active_sampler = 0; + } + + if (active_sampler != -1) { + IWineD3DDeviceImpl_MarkStateDirty(This->resource.wineD3DDevice, STATE_SAMPLER(active_sampler)); } - IWineD3DDeviceImpl_MarkStateDirty(This->resource.wineD3DDevice, STATE_SAMPLER(active_texture)); IWineD3DSurface_BindTexture((IWineD3DSurface *)This); }