Switch: Update GL code to GLES 3, up frame limiter

This commit is contained in:
Vicki Pfau 2018-09-19 13:31:08 -07:00
parent bb6ecd41cb
commit 90c656961e
4 changed files with 59 additions and 42 deletions

View File

@ -48,6 +48,7 @@ set(BUILD_SHARED ON CACHE BOOL "Build a shared library")
set(SKIP_LIBRARY OFF CACHE BOOL "Skip building the library (useful for only building libretro or OpenEmu cores)")
set(BUILD_GL ON CACHE BOOL "Build with OpenGL")
set(BUILD_GLES2 OFF CACHE BOOL "Build with OpenGL|ES 2")
set(BUILD_GLES3 OFF CACHE BOOL "Build with OpenGL|ES 3")
set(USE_EPOXY ON CACHE STRING "Build with libepoxy")
set(DISABLE_DEPS OFF CACHE BOOL "Build without dependencies")
set(DISTBUILD OFF CACHE BOOL "Build distribution packages")
@ -296,7 +297,7 @@ if(DEFINED 3DS)
endif()
if(DEFINED SWITCH)
set(BUILD_GLES2 ON CACHE BOOL "Build with OpenGL|ES 2" FORCE)
set(BUILD_GLES3 ON CACHE BOOL "Build with OpenGL|ES 3" FORCE)
endif()
if(NOT M_CORE_GBA)
@ -438,6 +439,13 @@ endif()
if(NOT BUILD_GLES2)
set(OPENGLES2_LIBRARY "" CACHE PATH "" FORCE)
endif()
if(BUILD_GLES3)
find_path(OPENGLES3_INCLUDE_DIR NAMES GLES3/gl3.h)
find_library(OPENGLES3_LIBRARY NAMES GLESv3 GLESv2)
if(NOT OPENGLES3_INCLUDE_DIR OR NOT OPENGLES3_LIBRARY)
set(BUILD_GLES3 OFF CACHE BOOL "OpenGL|ES 3 not found" FORCE)
endif()
endif()
set(WANT_ZLIB ${USE_ZLIB})
set(WANT_PNG ${USE_PNG})
set(WANT_LIBZIP ${USE_LIBZIP})
@ -878,6 +886,10 @@ if(BUILD_GLES2)
add_definitions(-DBUILD_GLES2)
endif()
if(BUILD_GLES3)
add_definitions(-DBUILD_GLES3)
endif()
if(DISABLE_FRONTENDS)
set(BUILD_SDL OFF)
set(BUILD_QT OFF)
@ -1096,6 +1108,9 @@ else()
if(BUILD_GLES2)
list(APPEND SUMMARY_GL_LIST "OpenGL|ES 2")
endif()
if(BUILD_GLES3)
list(APPEND SUMMARY_GL_LIST "OpenGL|ES 3")
endif()
endif()
if(NOT SUMMARY_GL_LIST)
set(SUMMARY_GL OFF)

View File

@ -8,7 +8,7 @@ set(OS_DEFINES USE_VFS_FILE IOAPI_NO_64)
list(APPEND CORE_VFS_SRC ${CMAKE_SOURCE_DIR}/src/util/vfs/vfs-file.c ${CMAKE_SOURCE_DIR}/src/util/vfs/vfs-dirent.c)
list(APPEND GUI_SRC ${CMAKE_CURRENT_SOURCE_DIR}/gui-font.c)
include_directories(AFTER ${OPENGLES2_INCLUDE_DIR} ${OPENGL_EGL_INCLUDE_DIR})
include_directories(AFTER ${OPENGLES3_INCLUDE_DIR} ${OPENGL_EGL_INCLUDE_DIR})
file(GLOB OS_SRC ${CMAKE_SOURCE_DIR}/src/platform/wii/wii-*.c)
if(${CMAKE_BUILD_TYPE} STREQUAL Debug OR ${CMAKE_BUILD_TYPE} STREQUAL RelWithDebInfo)
@ -34,7 +34,7 @@ endif()
add_executable(${BINARY_NAME}.elf ${GUI_SRC} ${PLATFORM_SRC} main.c)
set_target_properties(${BINARY_NAME}.elf PROPERTIES COMPILE_DEFINITIONS "${OS_DEFINES};${FEATURE_DEFINES};${FUNCTION_DEFINES}")
target_link_libraries(${BINARY_NAME}.elf ${BINARY_NAME} ${M_LIBRARY} ${EGL_LIBRARY} ${OPENGLES2_LIBRARY} ${GLAPI_LIBRARY} ${NOUVEAU_LIBRARY} stdc++ ${OS_LIB})
target_link_libraries(${BINARY_NAME}.elf ${BINARY_NAME} ${M_LIBRARY} ${EGL_LIBRARY} ${OPENGLES3_LIBRARY} ${GLAPI_LIBRARY} ${NOUVEAU_LIBRARY} stdc++ ${OS_LIB})
add_custom_command(OUTPUT control.nacp
COMMAND ${NACPTOOL} --create "${PROJECT_NAME}" "endrift" "${VERSION_STRING}" control.nacp)

View File

@ -9,7 +9,7 @@
#include <mgba-util/string.h>
#include <mgba-util/vfs.h>
#include <GLES2/gl2.h>
#include <GLES3/gl3.h>
#define GLYPH_HEIGHT 24
#define CELL_HEIGHT 32
@ -58,7 +58,7 @@ struct GUIFont {
GLuint font;
GLuint program;
GLuint vbo;
GLuint offsetLocation;
GLuint vao;
GLuint texLocation;
GLuint dimsLocation;
GLuint transformLocation;
@ -166,12 +166,16 @@ struct GUIFont* GUIFontCreate(void) {
font->originLocation = glGetUniformLocation(font->program, "origin");
font->glyphLocation = glGetUniformLocation(font->program, "glyph");
font->cutoffLocation = glGetUniformLocation(font->program, "cutoff");
font->offsetLocation = glGetAttribLocation(font->program, "offset");
GLuint offsetLocation = glGetAttribLocation(font->program, "offset");
glGenBuffers(1, &font->vbo);
glGenVertexArrays(1, &font->vao);
glBindVertexArray(font->vao);
glBindBuffer(GL_ARRAY_BUFFER, font->vbo);
glBufferData(GL_ARRAY_BUFFER, sizeof(_offsets), _offsets, GL_STATIC_DRAW);
glBindBuffer(GL_ARRAY_BUFFER, 0);
glVertexAttribPointer(offsetLocation, 2, GL_FLOAT, GL_FALSE, 0, NULL);
glEnableVertexAttribArray(offsetLocation);
glBindVertexArray(0);
return font;
}
@ -180,6 +184,7 @@ void GUIFontDestroy(struct GUIFont* font) {
glDeleteBuffers(1, &font->vbo);
glDeleteProgram(font->program);
glDeleteTextures(1, &font->font);
glDeleteVertexArrays(1, &font->vao);
free(font);
}
@ -222,9 +227,9 @@ void GUIFontDrawGlyph(const struct GUIFont* font, int x, int y, uint32_t color,
struct GUIFontGlyphMetric metric = defaultFontMetrics[glyph];
glUseProgram(font->program);
glBindVertexArray(font->vao);
glActiveTexture(GL_TEXTURE0);
glBindTexture(GL_TEXTURE_2D, font->font);
glBindBuffer(GL_ARRAY_BUFFER, font->vbo);
glEnable(GL_BLEND);
glBlendFunc(GL_SRC_ALPHA, GL_ONE_MINUS_SRC_ALPHA);
@ -235,9 +240,6 @@ void GUIFontDrawGlyph(const struct GUIFont* font, int x, int y, uint32_t color,
glUniform3f(font->originLocation, x, y - GLYPH_HEIGHT + metric.padding.top * 2, 0);
glUniformMatrix2fv(font->transformLocation, 1, GL_FALSE, (float[4]) {1.0, 0.0, 0.0, 1.0});
glVertexAttribPointer(font->offsetLocation, 2, GL_FLOAT, GL_FALSE, 0, NULL);
glEnableVertexAttribArray(font->offsetLocation);
glUniform1f(font->cutoffLocation, 0.1f);
glUniform4f(font->colorLocation, 0.0, 0.0, 0.0, ((color >> 24) & 0xFF) / 128.0f);
glDrawArrays(GL_TRIANGLE_FAN, 0, 4);
@ -246,8 +248,7 @@ void GUIFontDrawGlyph(const struct GUIFont* font, int x, int y, uint32_t color,
glUniform4f(font->colorLocation, (color & 0xFF) / 255.0f, ((color >> 8) & 0xFF) / 255.0f, ((color >> 16) & 0xFF) / 255.0f, ((color >> 24) & 0xFF) / 255.0f);
glDrawArrays(GL_TRIANGLE_FAN, 0, 4);
glDisableVertexAttribArray(font->offsetLocation);
glBindBuffer(GL_ARRAY_BUFFER, 0);
glBindVertexArray(0);
glUseProgram(0);
}
@ -291,9 +292,9 @@ void GUIFontDrawIcon(const struct GUIFont* font, int x, int y, enum GUIAlignment
}
glUseProgram(font->program);
glBindVertexArray(font->vao);
glActiveTexture(GL_TEXTURE0);
glBindTexture(GL_TEXTURE_2D, font->font);
glBindBuffer(GL_ARRAY_BUFFER, font->vbo);
glEnable(GL_BLEND);
glBlendFunc(GL_SRC_ALPHA, GL_ONE_MINUS_SRC_ALPHA);
@ -304,9 +305,6 @@ void GUIFontDrawIcon(const struct GUIFont* font, int x, int y, enum GUIAlignment
glUniform3f(font->originLocation, x, y, 0);
glUniformMatrix2fv(font->transformLocation, 1, GL_FALSE, (float[4]) {hFlip, 0.0, 0.0, vFlip});
glVertexAttribPointer(font->offsetLocation, 2, GL_FLOAT, GL_FALSE, 0, NULL);
glEnableVertexAttribArray(font->offsetLocation);
glUniform1f(font->cutoffLocation, 0.1f);
glUniform4f(font->colorLocation, 0.0, 0.0, 0.0, ((color >> 24) & 0xFF) / 128.0f);
glDrawArrays(GL_TRIANGLE_FAN, 0, 4);
@ -315,8 +313,7 @@ void GUIFontDrawIcon(const struct GUIFont* font, int x, int y, enum GUIAlignment
glUniform4f(font->colorLocation, (color & 0xFF) / 255.0f, ((color >> 8) & 0xFF) / 255.0f, ((color >> 16) & 0xFF) / 255.0f, ((color >> 24) & 0xFF) / 255.0f);
glDrawArrays(GL_TRIANGLE_FAN, 0, 4);
glDisableVertexAttribArray(font->offsetLocation);
glBindBuffer(GL_ARRAY_BUFFER, 0);
glBindVertexArray(0);
glUseProgram(0);
}
@ -334,9 +331,9 @@ void GUIFontDrawIconSize(const struct GUIFont* font, int x, int y, int w, int h,
}
glUseProgram(font->program);
glBindVertexArray(font->vao);
glActiveTexture(GL_TEXTURE0);
glBindTexture(GL_TEXTURE_2D, font->font);
glBindBuffer(GL_ARRAY_BUFFER, font->vbo);
glEnable(GL_BLEND);
glBlendFunc(GL_SRC_ALPHA, GL_ONE_MINUS_SRC_ALPHA);
@ -347,9 +344,6 @@ void GUIFontDrawIconSize(const struct GUIFont* font, int x, int y, int w, int h,
glUniform3f(font->originLocation, x + w / 2 - metric.width, y + h / 2 - metric.height, 0);
glUniformMatrix2fv(font->transformLocation, 1, GL_FALSE, (float[4]) {w * 0.5f / metric.width, 0.0, 0.0, h * 0.5f / metric.height});
glVertexAttribPointer(font->offsetLocation, 2, GL_FLOAT, GL_FALSE, 0, NULL);
glEnableVertexAttribArray(font->offsetLocation);
glUniform1f(font->cutoffLocation, 0.1f);
glUniform4f(font->colorLocation, 0.0, 0.0, 0.0, ((color >> 24) & 0xFF) / 128.0f);
glDrawArrays(GL_TRIANGLE_FAN, 0, 4);
@ -358,7 +352,6 @@ void GUIFontDrawIconSize(const struct GUIFont* font, int x, int y, int w, int h,
glUniform4f(font->colorLocation, ((color >> 16) & 0xFF) / 255.0f, ((color >> 8) & 0xFF) / 255.0f, (color & 0xFF) / 255.0f, ((color >> 24) & 0xFF) / 255.0f);
glDrawArrays(GL_TRIANGLE_FAN, 0, 4);
glDisableVertexAttribArray(font->offsetLocation);
glBindBuffer(GL_ARRAY_BUFFER, 0);
glBindVertexArray(0);
glUseProgram(0);
}

View File

@ -13,12 +13,13 @@
#include <switch.h>
#include <EGL/egl.h>
#include <GLES2/gl2.h>
#include <GLES3/gl3.h>
#define AUTO_INPUT 0x4E585031
#define SAMPLES 0x400
#define BUFFER_SIZE 0x1000
#define N_BUFFERS 4
#define FRAME_LIMIT 10
TimeType __nx_time_type = TimeType_UserSystemClock;
@ -63,7 +64,7 @@ static const char* const _fragmentShader =
static GLuint program;
static GLuint vbo;
static GLuint offsetLocation;
static GLuint vao;
static GLuint texLocation;
static GLuint dimsLocation;
static GLuint insizeLocation;
@ -106,7 +107,7 @@ static bool initEgl() {
}
EGLint contextAttributeList[] = {
EGL_CONTEXT_CLIENT_VERSION, 2,
EGL_CONTEXT_CLIENT_VERSION, 3,
EGL_NONE
};
s_context = eglCreateContext(s_display, config, EGL_NO_CONTEXT, contextAttributeList);
@ -144,11 +145,11 @@ static void _mapKey(struct mInputMap* map, uint32_t binding, int nativeKey, enum
}
static void _drawStart(void) {
glClear(GL_COLOR_BUFFER_BIT | GL_DEPTH_BUFFER_BIT);
glClear(GL_COLOR_BUFFER_BIT);
}
static void _drawEnd(void) {
if (frameLimiter || (framecount & 3) == 0) {
if (frameLimiter || (framecount % FRAME_LIMIT) == 0) {
eglSwapBuffers(s_display, s_surface);
}
}
@ -199,12 +200,11 @@ static void _gameLoaded(struct mGUIRunner* runner) {
}
static void _drawTex(struct mGUIRunner* runner, unsigned width, unsigned height, bool faded) {
glBindBuffer(GL_ARRAY_BUFFER, vbo);
glEnable(GL_BLEND);
glBlendFunc(GL_SRC_ALPHA, GL_ONE_MINUS_SRC_ALPHA);
glUseProgram(program);
glBindVertexArray(vao);
float aspectX = width / (float) runner->params.width;
float aspectY = height / (float) runner->params.height;
float max;
@ -226,26 +226,25 @@ static void _drawTex(struct mGUIRunner* runner, unsigned width, unsigned height,
glUniform4f(colorLocation, 0.8f, 0.8f, 0.8f, 0.8f);
}
glVertexAttribPointer(offsetLocation, 2, GL_FLOAT, GL_FALSE, 0, NULL);
glEnableVertexAttribArray(offsetLocation);
glDrawArrays(GL_TRIANGLE_FAN, 0, 4);
glDisableVertexAttribArray(offsetLocation);
glBindBuffer(GL_ARRAY_BUFFER, 0);
glBindVertexArray(0);
glUseProgram(0);
}
static void _drawFrame(struct mGUIRunner* runner, bool faded) {
++framecount;
if (!frameLimiter && (framecount % FRAME_LIMIT) != 0) {
return;
}
glActiveTexture(GL_TEXTURE0);
glBindTexture(GL_TEXTURE_2D, tex);
glTexImage2D(GL_TEXTURE_2D, 0, GL_RGBA, 256, 256, 0, GL_RGBA, GL_UNSIGNED_BYTE, frameBuffer);
unsigned width, height;
runner->core->desiredVideoDimensions(runner->core, &width, &height);
glTexSubImage2D(GL_TEXTURE_2D, 0, 0, 0, 256, height, GL_RGBA, GL_UNSIGNED_BYTE, frameBuffer);
_drawTex(runner, width, height, faded);
++framecount;
}
static void _drawScreenshot(struct mGUIRunner* runner, const color_t* pixels, unsigned width, unsigned height, bool faded) {
@ -342,6 +341,7 @@ int main(int argc, char* argv[]) {
glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_WRAP_T, GL_CLAMP_TO_EDGE);
glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MIN_FILTER, GL_LINEAR);
glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MAG_FILTER, GL_NEAREST);
glTexImage2D(GL_TEXTURE_2D, 0, GL_RGBA, 256, 256, 0, GL_RGBA, GL_UNSIGNED_BYTE, NULL);
program = glCreateProgram();
GLuint vertexShader = glCreateShader(GL_VERTEX_SHADER);
@ -386,12 +386,16 @@ int main(int argc, char* argv[]) {
colorLocation = glGetUniformLocation(program, "color");
dimsLocation = glGetUniformLocation(program, "dims");
insizeLocation = glGetUniformLocation(program, "insize");
offsetLocation = glGetAttribLocation(program, "offset");
GLuint offsetLocation = glGetAttribLocation(program, "offset");
glGenBuffers(1, &vbo);
glGenVertexArrays(1, &vao);
glBindVertexArray(vao);
glBindBuffer(GL_ARRAY_BUFFER, vbo);
glBufferData(GL_ARRAY_BUFFER, sizeof(_offsets), _offsets, GL_STATIC_DRAW);
glBindBuffer(GL_ARRAY_BUFFER, 0);
glVertexAttribPointer(offsetLocation, 2, GL_FLOAT, GL_FALSE, 0, NULL);
glEnableVertexAttribArray(offsetLocation);
glBindVertexArray(0);
stream.videoDimensionsChanged = NULL;
stream.postVideoFrame = NULL;
@ -483,6 +487,11 @@ int main(int argc, char* argv[]) {
audoutStartAudioOut();
mGUIRunloop(&runner);
glDeleteTextures(1, &tex);
glDeleteBuffers(1, &vbo);
glDeleteProgram(program);
glDeleteVertexArrays(1, &vao);
psmExit();
audoutExit();
deinitEgl();