summaryrefslogtreecommitdiff
path: root/src
diff options
context:
space:
mode:
authorGravatar Yuri Kunde Schlesner2015-08-05 23:22:06 -0300
committerGravatar Yuri Kunde Schlesner2015-08-06 00:59:37 -0300
commit254582aa35306c7bdebb90b0cd2dda88fe188087 (patch)
tree35cd21873666116fba7a3fac3df1580e8d59b79a /src
parentOpenGL: Remove redundant texture.enable_2d field from OpenGLState (diff)
downloadyuzu-254582aa35306c7bdebb90b0cd2dda88fe188087.tar.gz
yuzu-254582aa35306c7bdebb90b0cd2dda88fe188087.tar.xz
yuzu-254582aa35306c7bdebb90b0cd2dda88fe188087.zip
OpenGL: Fix state tracking in situations with reused object handles
If an OpenGL object is created, bound to a binding using the state tracker, and then destroyed, a newly created object can be assigned the same numeric handle by OpenGL. However, even though it is a new object, and thus needs to be bound to the binding again, the state tracker compared the current and previous handles and concluded that no change needed to be made, leading to failure to bind objects in certain cases. This manifested as broken text in VVVVVV, which this commit fixes along with similar texturing problems in other games.
Diffstat (limited to 'src')
-rw-r--r--src/video_core/renderer_opengl/gl_rasterizer_cache.cpp1
-rw-r--r--src/video_core/renderer_opengl/gl_resource_manager.h6
-rw-r--r--src/video_core/renderer_opengl/gl_state.cpp32
-rw-r--r--src/video_core/renderer_opengl/gl_state.h6
4 files changed, 45 insertions, 0 deletions
diff --git a/src/video_core/renderer_opengl/gl_rasterizer_cache.cpp b/src/video_core/renderer_opengl/gl_rasterizer_cache.cpp
index dc3ffdf22..70f0ba5f1 100644
--- a/src/video_core/renderer_opengl/gl_rasterizer_cache.cpp
+++ b/src/video_core/renderer_opengl/gl_rasterizer_cache.cpp
@@ -30,6 +30,7 @@ void RasterizerCacheOpenGL::LoadAndBindTexture(OpenGLState &state, unsigned text
30 new_texture->texture.Create(); 30 new_texture->texture.Create();
31 state.texture_units[texture_unit].texture_2d = new_texture->texture.handle; 31 state.texture_units[texture_unit].texture_2d = new_texture->texture.handle;
32 state.Apply(); 32 state.Apply();
33 glActiveTexture(GL_TEXTURE0 + texture_unit);
33 34
34 glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MAG_FILTER, PicaToGL::TextureFilterMode(config.config.mag_filter)); 35 glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MAG_FILTER, PicaToGL::TextureFilterMode(config.config.mag_filter));
35 glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MIN_FILTER, PicaToGL::TextureFilterMode(config.config.min_filter)); 36 glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MIN_FILTER, PicaToGL::TextureFilterMode(config.config.min_filter));
diff --git a/src/video_core/renderer_opengl/gl_resource_manager.h b/src/video_core/renderer_opengl/gl_resource_manager.h
index 6f9dc012d..82173d59a 100644
--- a/src/video_core/renderer_opengl/gl_resource_manager.h
+++ b/src/video_core/renderer_opengl/gl_resource_manager.h
@@ -10,6 +10,7 @@
10 10
11#include "video_core/renderer_opengl/generated/gl_3_2_core.h" 11#include "video_core/renderer_opengl/generated/gl_3_2_core.h"
12#include "video_core/renderer_opengl/gl_shader_util.h" 12#include "video_core/renderer_opengl/gl_shader_util.h"
13#include "video_core/renderer_opengl/gl_state.h"
13 14
14class OGLTexture : private NonCopyable { 15class OGLTexture : private NonCopyable {
15public: 16public:
@@ -28,6 +29,7 @@ public:
28 void Release() { 29 void Release() {
29 if (handle == 0) return; 30 if (handle == 0) return;
30 glDeleteTextures(1, &handle); 31 glDeleteTextures(1, &handle);
32 OpenGLState::ResetTexture(handle);
31 handle = 0; 33 handle = 0;
32 } 34 }
33 35
@@ -51,6 +53,7 @@ public:
51 void Release() { 53 void Release() {
52 if (handle == 0) return; 54 if (handle == 0) return;
53 glDeleteProgram(handle); 55 glDeleteProgram(handle);
56 OpenGLState::ResetProgram(handle);
54 handle = 0; 57 handle = 0;
55 } 58 }
56 59
@@ -74,6 +77,7 @@ public:
74 void Release() { 77 void Release() {
75 if (handle == 0) return; 78 if (handle == 0) return;
76 glDeleteBuffers(1, &handle); 79 glDeleteBuffers(1, &handle);
80 OpenGLState::ResetBuffer(handle);
77 handle = 0; 81 handle = 0;
78 } 82 }
79 83
@@ -97,6 +101,7 @@ public:
97 void Release() { 101 void Release() {
98 if (handle == 0) return; 102 if (handle == 0) return;
99 glDeleteVertexArrays(1, &handle); 103 glDeleteVertexArrays(1, &handle);
104 OpenGLState::ResetVertexArray(handle);
100 handle = 0; 105 handle = 0;
101 } 106 }
102 107
@@ -120,6 +125,7 @@ public:
120 void Release() { 125 void Release() {
121 if (handle == 0) return; 126 if (handle == 0) return;
122 glDeleteFramebuffers(1, &handle); 127 glDeleteFramebuffers(1, &handle);
128 OpenGLState::ResetFramebuffer(handle);
123 handle = 0; 129 handle = 0;
124 } 130 }
125 131
diff --git a/src/video_core/renderer_opengl/gl_state.cpp b/src/video_core/renderer_opengl/gl_state.cpp
index 7ccf474e1..871324014 100644
--- a/src/video_core/renderer_opengl/gl_state.cpp
+++ b/src/video_core/renderer_opengl/gl_state.cpp
@@ -174,3 +174,35 @@ void OpenGLState::Apply() {
174 174
175 cur_state = *this; 175 cur_state = *this;
176} 176}
177
178void OpenGLState::ResetTexture(GLuint id) {
179 for (auto& unit : cur_state.texture_units) {
180 if (unit.texture_2d == id) {
181 unit.texture_2d = 0;
182 }
183 }
184}
185
186void OpenGLState::ResetProgram(GLuint id) {
187 if (cur_state.draw.shader_program == id) {
188 cur_state.draw.shader_program = 0;
189 }
190}
191
192void OpenGLState::ResetBuffer(GLuint id) {
193 if (cur_state.draw.vertex_buffer == id) {
194 cur_state.draw.vertex_buffer = 0;
195 }
196}
197
198void OpenGLState::ResetVertexArray(GLuint id) {
199 if (cur_state.draw.vertex_array == id) {
200 cur_state.draw.vertex_array = 0;
201 }
202}
203
204void OpenGLState::ResetFramebuffer(GLuint id) {
205 if (cur_state.draw.framebuffer == id) {
206 cur_state.draw.framebuffer = 0;
207 }
208}
diff --git a/src/video_core/renderer_opengl/gl_state.h b/src/video_core/renderer_opengl/gl_state.h
index 03b7e26f7..3e2379021 100644
--- a/src/video_core/renderer_opengl/gl_state.h
+++ b/src/video_core/renderer_opengl/gl_state.h
@@ -73,6 +73,12 @@ public:
73 /// Apply this state as the current OpenGL state 73 /// Apply this state as the current OpenGL state
74 void Apply(); 74 void Apply();
75 75
76 static void ResetTexture(GLuint id);
77 static void ResetProgram(GLuint id);
78 static void ResetBuffer(GLuint id);
79 static void ResetVertexArray(GLuint id);
80 static void ResetFramebuffer(GLuint id);
81
76private: 82private:
77 static OpenGLState cur_state; 83 static OpenGLState cur_state;
78}; 84};