all repos — mgba @ ee6cd3640222dbd95f9f245a51ba1fa34aced9bd

mGBA Game Boy Advance Emulator

OpenGL: Use VAOs
Vicki Pfau vi@endrift.com
Tue, 14 May 2019 22:23:18 -0700
commit

ee6cd3640222dbd95f9f245a51ba1fa34aced9bd

parent

4bd788f7153ced2403def6478af29da7d0e3cbd5

M README.mdREADME.md

@@ -85,7 +85,7 @@ Other Unix-like platforms, such as OpenBSD, are known to work as well, but are untested and not fully supported.

### System requirements -Requirements are minimal. Any computer that can run Windows Vista or newer should be able to handle emulation. Support for OpenGL 1.1 or newer is also required. +Requirements are minimal. Any computer that can run Windows Vista or newer should be able to handle emulation. Support for OpenGL 1.1 or newer is also required, with OpenGL 3.0 or newer for shaders and advanced features. Downloads ---------
M include/mgba/internal/gba/renderers/gl.hinclude/mgba/internal/gba/renderers/gl.h

@@ -125,6 +125,12 @@

GBA_GL_UNIFORM_MAX = 12 }; +struct GBAVideoGLShader { + GLuint program; + GLuint vao; + GLuint uniforms[GBA_GL_UNIFORM_MAX]; +}; + struct GBAVideoGLRenderer { struct GBAVideoRenderer d;

@@ -136,6 +142,7 @@ struct GBAVideoRendererSprite sprites[128];

GLuint fbo[GBA_GL_FBO_MAX]; GLuint layers[GBA_GL_TEX_MAX]; + GLuint vbo; GLuint outputTex;

@@ -148,15 +155,10 @@

GLuint vramTex; unsigned vramDirty; - GLuint bgProgram[6]; - GLuint bgUniforms[6][GBA_GL_UNIFORM_MAX]; - GLuint objProgram[2]; - GLuint objUniforms[2][GBA_GL_UNIFORM_MAX]; - - GLuint compositeProgram; - GLuint compositeUniforms[GBA_GL_UNIFORM_MAX]; - GLuint finalizeProgram; - GLuint finalizeUniforms[GBA_GL_UNIFORM_MAX]; + struct GBAVideoGLShader bgShader[6]; + struct GBAVideoGLShader objShader[2]; + struct GBAVideoGLShader compositeShader; + struct GBAVideoGLShader finalizeShader; GBARegisterDISPCNT dispcnt;
M src/gba/renderers/gl.csrc/gba/renderers/gl.c

@@ -399,7 +399,10 @@

renderer->scale = 1; } -void _compileShader(struct GBAVideoGLRenderer* glRenderer, GLuint program, const char** shaderBuffer, int shaderBufferLines, GLuint vs, char* log) { +void _compileShader(struct GBAVideoGLRenderer* glRenderer, struct GBAVideoGLShader* shader, const char** shaderBuffer, int shaderBufferLines, GLuint vs, const struct GBAVideoGLUniform* uniforms, char* log) { + GLuint program = glCreateProgram(); + shader->program = program; + GLuint fs = glCreateShader(GL_FRAGMENT_SHADER); glAttachShader(program, vs); glAttachShader(program, fs);

@@ -419,6 +422,18 @@ #ifndef BUILD_GLES3

glBindFragDataLocation(program, 0, "color"); glBindFragDataLocation(program, 1, "flags"); #endif + + glGenVertexArrays(1, &shader->vao); + glBindVertexArray(shader->vao); + glBindBuffer(GL_ARRAY_BUFFER, glRenderer->vbo); + GLuint positionLocation = glGetAttribLocation(program, "position"); + glVertexAttribPointer(positionLocation, 2, GL_INT, GL_FALSE, 0, NULL); + glEnableVertexAttribArray(positionLocation); + + size_t i; + for (i = 0; uniforms[i].name; ++i) { + shader->uniforms[uniforms[i].type] = glGetUniformLocation(program, uniforms[i].name); + } } static void _initFramebufferTexture(GLuint tex, GLenum format, GLenum attachment, int scale) {

@@ -431,13 +446,6 @@ glTexImage2D(GL_TEXTURE_2D, 0, format, GBA_VIDEO_HORIZONTAL_PIXELS * scale, GBA_VIDEO_VERTICAL_PIXELS * scale, 0, format, GL_UNSIGNED_BYTE, 0);

glFramebufferTexture2D(GL_FRAMEBUFFER, attachment, GL_TEXTURE_2D, tex, 0); } -static void _lookupUniforms(GLuint program, GLuint* out, const struct GBAVideoGLUniform* uniforms) { - size_t i; - for (i = 0; uniforms[i].name; ++i) { - out[uniforms[i].type] = glGetUniformLocation(program, uniforms[i].name); - } -} - void GBAVideoGLRendererInit(struct GBAVideoRenderer* renderer) { struct GBAVideoGLRenderer* glRenderer = (struct GBAVideoGLRenderer*) renderer; glGenFramebuffers(GBA_GL_FBO_MAX, glRenderer->fbo);

@@ -472,6 +480,10 @@ _initFramebufferTexture(glRenderer->outputTex, GL_RGB, GL_COLOR_ATTACHMENT0, glRenderer->scale);

glBindFramebuffer(GL_FRAMEBUFFER, 0); + glGenBuffers(1, &glRenderer->vbo); + glBindBuffer(GL_ARRAY_BUFFER, glRenderer->vbo); + glBufferData(GL_ARRAY_BUFFER, sizeof(_vertices), _vertices, GL_STATIC_DRAW); + int i; for (i = 0; i < 4; ++i) { struct GBAVideoGLBackground* bg = &glRenderer->bg[i];

@@ -505,17 +517,6 @@ _initFramebufferTexture(bg->flags, GL_RGBA, GL_COLOR_ATTACHMENT1, glRenderer->scale);

glBindFramebuffer(GL_FRAMEBUFFER, 0); } - glRenderer->compositeProgram = glCreateProgram(); - glRenderer->finalizeProgram = glCreateProgram(); - glRenderer->objProgram[0] = glCreateProgram(); - glRenderer->objProgram[1] = glCreateProgram(); - glRenderer->bgProgram[0] = glCreateProgram(); - glRenderer->bgProgram[1] = glCreateProgram(); - glRenderer->bgProgram[2] = glCreateProgram(); - glRenderer->bgProgram[3] = glCreateProgram(); - glRenderer->bgProgram[4] = glCreateProgram(); - glRenderer->bgProgram[5] = glCreateProgram(); - char log[1024]; const GLchar* shaderBuffer[8]; shaderBuffer[0] = _gl3Header;

@@ -532,51 +533,44 @@

shaderBuffer[1] = _renderMode0; shaderBuffer[2] = _renderTile16; - _compileShader(glRenderer, glRenderer->bgProgram[0], shaderBuffer, 3, vs, log); - _lookupUniforms(glRenderer->bgProgram[0], glRenderer->bgUniforms[0], _uniformsMode0); + _compileShader(glRenderer, &glRenderer->bgShader[0], shaderBuffer, 3, vs, _uniformsMode0, log); shaderBuffer[2] = _renderTile256; - _compileShader(glRenderer, glRenderer->bgProgram[1], shaderBuffer, 3, vs, log); - _lookupUniforms(glRenderer->bgProgram[1], glRenderer->bgUniforms[1], _uniformsMode0); + _compileShader(glRenderer, &glRenderer->bgShader[1], shaderBuffer, 3, vs, _uniformsMode0, log); shaderBuffer[1] = _renderMode2; shaderBuffer[2] = _fetchTileOverflow; - _compileShader(glRenderer, glRenderer->bgProgram[2], shaderBuffer, 3, vs, log); - _lookupUniforms(glRenderer->bgProgram[2], glRenderer->bgUniforms[2], _uniformsMode2); + _compileShader(glRenderer, &glRenderer->bgShader[2], shaderBuffer, 3, vs, _uniformsMode2, log); shaderBuffer[2] = _fetchTileNoOverflow; - _compileShader(glRenderer, glRenderer->bgProgram[3], shaderBuffer, 3, vs, log); - _lookupUniforms(glRenderer->bgProgram[3], glRenderer->bgUniforms[3], _uniformsMode2); + _compileShader(glRenderer, &glRenderer->bgShader[3], shaderBuffer, 3, vs, _uniformsMode2, log); shaderBuffer[1] = _renderObj; shaderBuffer[2] = _renderTile16; - _compileShader(glRenderer, glRenderer->objProgram[0], shaderBuffer, 3, vs, log); - _lookupUniforms(glRenderer->objProgram[0], glRenderer->objUniforms[0], _uniformsObj); + _compileShader(glRenderer, &glRenderer->objShader[0], shaderBuffer, 3, vs, _uniformsObj, log); #ifndef BUILD_GLES3 - glBindFragDataLocation(glRenderer->objProgram[0], 2, "window"); + glBindFragDataLocation(glRenderer->objShader[0].program, 2, "window"); #endif shaderBuffer[2] = _renderTile256; - _compileShader(glRenderer, glRenderer->objProgram[1], shaderBuffer, 3, vs, log); - _lookupUniforms(glRenderer->objProgram[1], glRenderer->objUniforms[1], _uniformsObj); + _compileShader(glRenderer, &glRenderer->objShader[1], shaderBuffer, 3, vs, _uniformsObj, log); #ifndef BUILD_GLES3 - glBindFragDataLocation(glRenderer->objProgram[1], 2, "window"); + glBindFragDataLocation(glRenderer->objShader[1].program, 2, "window"); #endif shaderBuffer[1] = _composite; - _compileShader(glRenderer, glRenderer->compositeProgram, shaderBuffer, 2, vs, log); - _lookupUniforms(glRenderer->compositeProgram, glRenderer->compositeUniforms, _uniformsComposite); + _compileShader(glRenderer, &glRenderer->compositeShader, shaderBuffer, 2, vs, _uniformsComposite, log); #ifndef BUILD_GLES3 - glBindFragDataLocation(glRenderer->compositeProgram, 2, "oldColor"); - glBindFragDataLocation(glRenderer->compositeProgram, 3, "oldFlags"); + glBindFragDataLocation(glRenderer->compositeShader.program, 2, "oldColor"); + glBindFragDataLocation(glRenderer->compositeShader.program, 3, "oldFlags"); #endif shaderBuffer[1] = _finalize; - _compileShader(glRenderer, glRenderer->finalizeProgram, shaderBuffer, 2, vs, log); - _lookupUniforms(glRenderer->finalizeProgram, glRenderer->finalizeUniforms, _uniformsFinalize); + _compileShader(glRenderer, &glRenderer->finalizeShader, shaderBuffer, 2, vs, _uniformsFinalize, log); + glBindVertexArray(0); glDeleteShader(vs); GBAVideoGLRendererReset(renderer);

@@ -588,16 +582,6 @@ glDeleteFramebuffers(GBA_GL_FBO_MAX, glRenderer->fbo);

glDeleteTextures(GBA_GL_TEX_MAX, glRenderer->layers); glDeleteTextures(1, &glRenderer->paletteTex); glDeleteTextures(1, &glRenderer->vramTex); - - glDeleteProgram(glRenderer->bgProgram[0]); - glDeleteProgram(glRenderer->bgProgram[1]); - glDeleteProgram(glRenderer->bgProgram[2]); - glDeleteProgram(glRenderer->bgProgram[3]); - glDeleteProgram(glRenderer->bgProgram[4]); - glDeleteProgram(glRenderer->bgProgram[5]); - glDeleteProgram(glRenderer->objProgram[0]); - glDeleteProgram(glRenderer->objProgram[1]); - glDeleteProgram(glRenderer->compositeProgram); } void GBAVideoGLRendererReset(struct GBAVideoRenderer* renderer) {

@@ -1075,11 +1059,12 @@ static void _compositeLayer(struct GBAVideoGLRenderer* renderer, GLuint tex, GLuint flags, int id, int y) {

if ((y & 0x1F) != 0x1F) { return; } - const GLuint* uniforms = renderer->compositeUniforms; + const GLuint* uniforms = renderer->compositeShader.uniforms; glBindFramebuffer(GL_FRAMEBUFFER, renderer->fbo[GBA_GL_FBO_COMPOSITE]); glViewport(0, 0, GBA_VIDEO_HORIZONTAL_PIXELS * renderer->scale, GBA_VIDEO_VERTICAL_PIXELS * renderer->scale); glScissor(0, (y & ~0x1F) * renderer->scale, GBA_VIDEO_HORIZONTAL_PIXELS * renderer->scale, 0x20 * renderer->scale); - glUseProgram(renderer->compositeProgram); + glUseProgram(renderer->compositeShader.program); + glBindVertexArray(renderer->compositeShader.vao); glActiveTexture(GL_TEXTURE0); glBindTexture(GL_TEXTURE_2D, tex); glActiveTexture(GL_TEXTURE0 + 1);

@@ -1102,23 +1087,21 @@ glUniform1i(uniforms[GBA_GL_COMPOSITE_OLDLAYER], 2);

glUniform1i(uniforms[GBA_GL_COMPOSITE_OLDLAYERFLAGS], 3); glUniform1i(uniforms[GBA_GL_COMPOSITE_OLDOLDFLAGS], 4); glUniform1i(uniforms[GBA_GL_COMPOSITE_WINDOW], 5); - glVertexAttribPointer(0, 2, GL_INT, GL_FALSE, 0, _vertices); - glEnableVertexAttribArray(0); glDrawBuffers(4, (GLenum[]) { GL_COLOR_ATTACHMENT0, GL_COLOR_ATTACHMENT1, GL_COLOR_ATTACHMENT2, GL_COLOR_ATTACHMENT3 }); glDrawArrays(GL_TRIANGLE_FAN, 0, 4); glDrawBuffers(1, (GLenum[]) { GL_COLOR_ATTACHMENT0 }); - glBindFramebuffer(GL_FRAMEBUFFER, 0); } void _finalizeLayers(struct GBAVideoGLRenderer* renderer, int y) { if ((y & 0x1F) != 0x1F) { return; } - const GLuint* uniforms = renderer->finalizeUniforms; + const GLuint* uniforms = renderer->finalizeShader.uniforms; glBindFramebuffer(GL_FRAMEBUFFER, renderer->fbo[GBA_GL_FBO_OUTPUT]); glViewport(0, 0, GBA_VIDEO_HORIZONTAL_PIXELS * renderer->scale, GBA_VIDEO_VERTICAL_PIXELS * renderer->scale); glScissor(0, (y & ~0x1F) * renderer->scale, GBA_VIDEO_HORIZONTAL_PIXELS * renderer->scale, 0x20 * renderer->scale); - glUseProgram(renderer->finalizeProgram); + glUseProgram(renderer->finalizeShader.program); + glBindVertexArray(renderer->finalizeShader.vao); glActiveTexture(GL_TEXTURE0); glBindTexture(GL_TEXTURE_2D, renderer->layers[GBA_GL_TEX_COMPOSITE_COLOR]); glActiveTexture(GL_TEXTURE0 + 1);

@@ -1134,8 +1117,6 @@ glUniform1i(uniforms[GBA_GL_FINALIZE_LAYER], 0);

glUniform1i(uniforms[GBA_GL_FINALIZE_LAYERFLAGS], 1); glUniform1i(uniforms[GBA_GL_FINALIZE_OLDLAYER], 2); glUniform1i(uniforms[GBA_GL_FINALIZE_OLDFLAGS], 3); - glVertexAttribPointer(0, 2, GL_INT, GL_FALSE, 0, _vertices); - glEnableVertexAttribArray(0); glDrawArrays(GL_TRIANGLE_FAN, 0, 4); glBindFramebuffer(GL_FRAMEBUFFER, 0); }

@@ -1167,11 +1148,13 @@ }

enum GBAVideoBlendEffect blendEffect = GBAObjAttributesAGetMode(sprite->a) == OBJ_MODE_SEMITRANSPARENT ? BLEND_ALPHA : renderer->blendEffect; - const GLuint* uniforms = renderer->objUniforms[GBAObjAttributesAGet256Color(sprite->a)]; + const struct GBAVideoGLShader* shader = &renderer->objShader[GBAObjAttributesAGet256Color(sprite->a)]; + const GLuint* uniforms = shader->uniforms; glBindFramebuffer(GL_FRAMEBUFFER, renderer->fbo[GBA_GL_FBO_OBJ]); glViewport(x * renderer->scale, spriteY * renderer->scale, totalWidth * renderer->scale, totalHeight * renderer->scale); glScissor(x * renderer->scale, y * renderer->scale, totalWidth * renderer->scale, renderer->scale); - glUseProgram(renderer->objProgram[GBAObjAttributesAGet256Color(sprite->a)]); + glUseProgram(shader->program); + glBindVertexArray(shader->vao); glActiveTexture(GL_TEXTURE0); glBindTexture(GL_TEXTURE_2D, renderer->vramTex); glActiveTexture(GL_TEXTURE0 + 1);

@@ -1198,8 +1181,6 @@ } else {

glUniformMatrix2fv(uniforms[GBA_GL_OBJ_TRANSFORM], 1, GL_FALSE, (GLfloat[]) { 1.f, 0, 0, 1.f }); } glUniform4i(uniforms[GBA_GL_OBJ_DIMS], width, height, totalWidth, totalHeight); - glVertexAttribPointer(0, 2, GL_INT, GL_FALSE, 0, _vertices); - glEnableVertexAttribArray(0); if (GBAObjAttributesAGetMode(sprite->a) == OBJ_MODE_OBJWIN) { int window = ~renderer->objwin & 0xFF; glUniform3f(uniforms[GBA_GL_OBJ_OBJWIN], 1, (window & 0xF) / 32.f, (window >> 4) / 32.f);

@@ -1220,11 +1201,14 @@ yBase += inY & 0x100;

} else if (background->size == 3) { yBase += (inY & 0x100) << 1; } - const GLuint* uniforms = renderer->bgUniforms[background->multipalette ? 1 : 0]; + + const struct GBAVideoGLShader* shader = &renderer->bgShader[background->multipalette ? 1 : 0]; + const GLuint* uniforms = shader->uniforms; glBindFramebuffer(GL_FRAMEBUFFER, background->fbo); glViewport(0, 0, GBA_VIDEO_HORIZONTAL_PIXELS * renderer->scale, GBA_VIDEO_VERTICAL_PIXELS * renderer->scale); glScissor(0, y * renderer->scale, GBA_VIDEO_HORIZONTAL_PIXELS * renderer->scale, renderer->scale); - glUseProgram(renderer->bgProgram[background->multipalette ? 1 : 0]); + glUseProgram(shader->program); + glBindVertexArray(shader->vao); glActiveTexture(GL_TEXTURE0); glBindTexture(GL_TEXTURE_2D, renderer->vramTex); glActiveTexture(GL_TEXTURE0 + 1);

@@ -1240,8 +1224,6 @@ glUniform2i(uniforms[GBA_GL_BG_OFFSET], background->x, yBase - y);

glUniform4i(uniforms[GBA_GL_BG_INFLAGS], (background->priority << 3) + (background->index << 1) + 1, background->target1 | (background->target2 * 2) | (renderer->blendEffect * 4), renderer->blendEffect == BLEND_ALPHA ? renderer->blda : renderer->bldy, renderer->bldb); - glVertexAttribPointer(0, 2, GL_INT, GL_FALSE, 0, _vertices); - glEnableVertexAttribArray(0); glDrawBuffers(2, (GLenum[]) { GL_COLOR_ATTACHMENT0, GL_COLOR_ATTACHMENT1 }); glDrawArrays(GL_TRIANGLE_FAN, 0, 4); glDrawBuffers(1, (GLenum[]) { GL_COLOR_ATTACHMENT0 });

@@ -1250,11 +1232,13 @@ _compositeLayer(renderer, background->tex, background->flags, background->index, y);

} void GBAVideoGLRendererDrawBackgroundMode2(struct GBAVideoGLRenderer* renderer, struct GBAVideoGLBackground* background, int y) { - const GLuint* uniforms = renderer->bgUniforms[background->overflow ? 2 : 3]; + const struct GBAVideoGLShader* shader = &renderer->bgShader[background->overflow ? 2 : 3]; + const GLuint* uniforms = shader->uniforms; glBindFramebuffer(GL_FRAMEBUFFER, background->fbo); glViewport(0, 0, GBA_VIDEO_HORIZONTAL_PIXELS * renderer->scale, GBA_VIDEO_VERTICAL_PIXELS * renderer->scale); glScissor(0, y * renderer->scale, GBA_VIDEO_HORIZONTAL_PIXELS * renderer->scale, renderer->scale); - glUseProgram(renderer->bgProgram[background->overflow ? 2 : 3]); + glUseProgram(shader->program); + glBindVertexArray(shader->vao); glActiveTexture(GL_TEXTURE0); glBindTexture(GL_TEXTURE_2D, renderer->vramTex); glActiveTexture(GL_TEXTURE0 + 1);

@@ -1296,8 +1280,6 @@ background->affine[0].dx, background->affine[0].dy,

background->affine[0].dx, background->affine[0].dy, }); } - glVertexAttribPointer(0, 2, GL_INT, GL_FALSE, 0, _vertices); - glEnableVertexAttribArray(0); glDrawBuffers(2, (GLenum[]) { GL_COLOR_ATTACHMENT0, GL_COLOR_ATTACHMENT1 }); glDrawArrays(GL_TRIANGLE_FAN, 0, 4); glDrawBuffers(1, (GLenum[]) { GL_COLOR_ATTACHMENT0 });
M src/platform/opengl/gles2.csrc/platform/opengl/gles2.c

@@ -84,6 +84,10 @@ glBindTexture(GL_TEXTURE_2D, context->tex);

glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_WRAP_S, GL_CLAMP_TO_EDGE); glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_WRAP_T, GL_CLAMP_TO_EDGE); + glGenBuffers(1, &context->vbo); + glBindBuffer(GL_ARRAY_BUFFER, context->vbo); + glBufferData(GL_ARRAY_BUFFER, sizeof(_vertices), _vertices, GL_STATIC_DRAW); + glClearColor(0.f, 0.f, 0.f, 1.f); struct mGLES2Uniform* uniforms = malloc(sizeof(struct mGLES2Uniform) * 4);

@@ -159,6 +163,7 @@

static void mGLES2ContextDeinit(struct VideoBackend* v) { struct mGLES2Context* context = (struct mGLES2Context*) v; glDeleteTextures(1, &context->tex); + glDeleteBuffers(1, &context->vbo); mGLES2ShaderDeinit(&context->initialShader); mGLES2ShaderDeinit(&context->finalShader); free(context->initialShader.uniforms);

@@ -239,8 +244,7 @@ glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MAG_FILTER, shader->filter ? GL_LINEAR : GL_NEAREST);

glUseProgram(shader->program); glUniform1i(shader->texLocation, 0); glUniform2f(shader->texSizeLocation, context->d.width - padW, context->d.height - padH); - glVertexAttribPointer(shader->positionLocation, 2, GL_FLOAT, GL_FALSE, 0, _vertices); - glEnableVertexAttribArray(shader->positionLocation); + glBindVertexArray(shader->vao); size_t u; for (u = 0; u < shader->nUniforms; ++u) { struct mGLES2Uniform* uniform = &shader->uniforms[u];

@@ -420,6 +424,13 @@ size_t i;

for (i = 0; i < shader->nUniforms; ++i) { shader->uniforms[i].location = glGetUniformLocation(shader->program, shader->uniforms[i].name); } + + glGenVertexArrays(1, &shader->vao); + glBindVertexArray(shader->vao); + glVertexAttribPointer(shader->positionLocation, 2, GL_FLOAT, GL_FALSE, 0, NULL); + glEnableVertexAttribArray(shader->positionLocation); + glBindVertexArray(0); + glBindFramebuffer(GL_FRAMEBUFFER, 0); }

@@ -428,6 +439,7 @@ glDeleteTextures(1, &shader->tex);

glDeleteShader(shader->fragmentShader); glDeleteProgram(shader->program); glDeleteFramebuffers(1, &shader->fbo); + glDeleteVertexArrays(1, &shader->vao); } void mGLES2ShaderAttach(struct mGLES2Context* context, struct mGLES2Shader* shaders, size_t nShaders) {

@@ -443,7 +455,11 @@ size_t i;

for (i = 0; i < nShaders; ++i) { glBindFramebuffer(GL_FRAMEBUFFER, context->shaders[i].fbo); glClear(GL_COLOR_BUFFER_BIT); + + glBindVertexArray(context->shaders[i].vao); + glBindBuffer(GL_ARRAY_BUFFER, context->vbo); } + glBindVertexArray(0); glBindFramebuffer(GL_FRAMEBUFFER, 0); }
M src/platform/opengl/gles2.hsrc/platform/opengl/gles2.h

@@ -62,6 +62,7 @@ bool filter;

bool blend; GLuint tex; GLuint fbo; + GLuint vao; GLuint fragmentShader; GLuint vertexShader; GLuint program;

@@ -77,8 +78,7 @@ struct mGLES2Context {

struct VideoBackend d; GLuint tex; - GLuint texLocation; - GLuint positionLocation; + GLuint vbo; struct mGLES2Shader initialShader; struct mGLES2Shader finalShader;
M src/platform/qt/DisplayGL.cppsrc/platform/qt/DisplayGL.cpp

@@ -227,7 +227,7 @@

QStringList extensions = QString(reinterpret_cast<const char*>(glGetString(GL_EXTENSIONS))).split(' '); #ifdef BUILD_GLES2 - if (extensions.contains("GL_ARB_framebuffer_object") && majorVersion >= 2) { + if ((majorVersion == 2 && extensions.contains("GL_ARB_framebuffer_object")) || majorVersion > 2) { gl2Backend = static_cast<mGLES2Context*>(malloc(sizeof(mGLES2Context))); mGLES2ContextCreate(gl2Backend); m_backend = &gl2Backend->d;

@@ -500,8 +500,8 @@ void PainterGL::clearShaders() {

if (!supportsShaders()) { return; } - if (!m_active) { #ifdef BUILD_GLES2 + if (!m_active) { m_gl->makeCurrent(m_surface); #if defined(_WIN32) && defined(USE_EPOXY) epoxy_handle_external_wglMakeCurrent();