Pull shader code into main #1

Merged
YourWishes merged 4 commits from shader into main 2026-03-22 15:46:37 +00:00
9 changed files with 184 additions and 61 deletions
Showing only changes of commit 5ac21db997 - Show all commits

View File

@@ -29,6 +29,7 @@ target_compile_definitions(${DUSK_LIBRARY_TARGET_NAME} PUBLIC
DUSK_SDL2
DUSK_OPENGL
DUSK_LINUX
DUSK_OPENGL_LEGACY
DUSK_DISPLAY_SIZE_DYNAMIC
DUSK_DISPLAY_WIDTH_DEFAULT=640
DUSK_DISPLAY_HEIGHT_DEFAULT=480

View File

@@ -23,7 +23,7 @@ errorret_t shaderBind(shader_t *shader) {
errorret_t shaderSetMatrix(
shader_t *shader,
const char_t *name,
const mat4 matrix
mat4 matrix
) {
assertNotNull(shader, "Shader cannot be null");
assertStrLenMin(name, 1, "Uniform name cannot be empty");

View File

@@ -54,7 +54,7 @@ errorret_t shaderBind(shader_t *shader);
errorret_t shaderSetMatrix(
shader_t *shader,
const char_t *name,
const mat4 matrix
mat4 matrix
);
/**

View File

@@ -8,8 +8,6 @@
#include "displaygl.h"
errorret_t displayOpenGLInit(void) {
glDisable(GL_CULL_FACE);
// glDisable(GL_LIGHTING);// PSP defaults this on?
// glShadeModel(GL_SMOOTH); // Fixes color on PSP?
@@ -26,10 +24,5 @@ errorret_t displayOpenGLInit(void) {
glPixelStorei(GL_UNPACK_ALIGNMENT, 1);
errorChain(errorGLCheck());
// glEnableClientState(GL_COLOR_ARRAY);// To confirm: every frame on PSP?
// glEnableClientState(GL_TEXTURE_COORD_ARRAY);
// glEnableClientState(GL_VERTEX_ARRAY);
// errorChain(errorGLCheck());
errorOk();
}

View File

@@ -8,6 +8,7 @@
#include "display/mesh/mesh.h"
#include "assert/assertgl.h"
#include "error/errorgl.h"
#include "display/shader/shadergl.h"
errorret_t meshInitGL(
meshgl_t *mesh,
@@ -25,6 +26,10 @@ errorret_t meshInitGL(
#ifdef DUSK_OPENGL_LEGACY
// Nothing needed.
glEnableClientState(GL_COLOR_ARRAY);
glEnableClientState(GL_TEXTURE_COORD_ARRAY);
glEnableClientState(GL_VERTEX_ARRAY);
errorChain(errorGLCheck());
#else
// Generate Vertex Buffer Object
glGenBuffers(1, &mesh->vboId);
@@ -143,6 +148,11 @@ errorret_t meshDrawGL(
(const GLvoid*)&mesh->vertices[offset].pos
);
// Shader may have model matrix here
#ifdef DUSK_OPENGL_LEGACY
errorChain(shaderLegacyMatrixUpdate());
#endif
glDrawArrays(mesh->primitiveType, offset, count);
errorChain(errorGLCheck());
#else

View File

@@ -7,7 +7,13 @@
#include "shadergl.h"
#include "util/memory.h"
#include "util/string.h"
#include "assert/assertgl.h"
#include "display/shader/shaderunlit.h"
#ifdef DUSK_OPENGL_LEGACY
shaderlegacygl_t SHADER_LEGACY = { 0 };
#endif
errorret_t shaderInitGL(shadergl_t *shader, const shaderdefinitiongl_t *def) {
assertNotNull(shader, "Shader cannot be null");
@@ -15,7 +21,11 @@ errorret_t shaderInitGL(shadergl_t *shader, const shaderdefinitiongl_t *def) {
memoryZero(shader, sizeof(shadergl_t));
#ifdef DUSK_OPENGL_LEGACY
// No initialization needed for legacy shader
glm_mat4_identity(shader->view);
glm_mat4_identity(shader->proj);
glm_mat4_identity(shader->model);
SHADER_LEGACY.boundShader = NULL;
errorOk();
#else
// Create vertex shader
@@ -139,12 +149,16 @@ errorret_t shaderParamGetLocationGL(
assertStrLenMin(name, 1, "Uniform name cannot be empty");
assertNotNull(location, "Location cannot be null");
shadergl_t *shaderGL = (shadergl_t *)shader;
*location = glGetUniformLocation(shaderGL->shaderProgramId, name);
errorret_t err = errorGLCheck();
if(err.code != ERROR_OK) {
errorChain(err);
}
#ifdef DUSK_OPENGL_LEGACY
assertUnreachable("Cannot get uniform locations on legacy opengl.");
#else
shadergl_t *shaderGL = (shadergl_t *)shader;
*location = glGetUniformLocation(shaderGL->shaderProgramId, name);
errorret_t err = errorGLCheck();
if(err.code != ERROR_OK) {
errorChain(err);
}
#endif
errorOk();
}
@@ -152,27 +166,58 @@ errorret_t shaderParamGetLocationGL(
errorret_t shaderSetMatrixGL(
shadergl_t *shader,
const char_t *name,
const mat4 mat
mat4 mat
) {
assertNotNull(shader, "Shader cannot be null");
assertNotNull(mat, "Matrix data cannot be null");
assertStrLenMin(name, 1, "Uniform name cannot be empty");
GLint location;
errorChain(shaderParamGetLocationGL(shader, name, &location));
#ifdef DUSK_OPENGL_LEGACY
assertTrue(
SHADER_LEGACY.boundShader == shader,
"Shader must be bound to set legacy matrices."
);
if(stringCompare(name, SHADER_UNLIT_PROJECTION) == 0) {
SHADER_LEGACY.dirty |= SHADER_LEGACY_DIRTY_PROJ;
glm_mat4_copy(mat, shader->proj);
glUniformMatrix4fv(location, 1, GL_FALSE, (const GLfloat *)mat);
errorChain(errorGLCheck());
} else if(stringCompare(name, SHADER_UNLIT_VIEW) == 0) {
SHADER_LEGACY.dirty |= SHADER_LEGACY_DIRTY_VIEW;
glm_mat4_copy(mat, shader->view);
} else if(stringCompare(name, SHADER_UNLIT_MODEL) == 0) {
SHADER_LEGACY.dirty |= SHADER_LEGACY_DIRTY_MODEL;
glm_mat4_copy(mat, shader->model);
} else {
assertUnreachable("Cannot use a custom matrix on legacy opengl.");
}
#else
GLint location;
errorChain(shaderParamGetLocationGL(shader, name, &location));
glUniformMatrix4fv(location, 1, GL_FALSE, (const GLfloat *)mat);
errorChain(errorGLCheck());
#endif
errorOk();
}
errorret_t shaderBindGL(shadergl_t *shader) {
assertNotNull(shader, "Shader cannot be null");
glUseProgram(shader->shaderProgramId);
errorChain(errorGLCheck());
#ifdef DUSK_OPENGL_LEGACY
assertNotNull(shader, "Cannot bind a null shader.");
SHADER_LEGACY.boundShader = shader;
SHADER_LEGACY.dirty = (
SHADER_LEGACY_DIRTY_MODEL |
SHADER_LEGACY_DIRTY_PROJ |
SHADER_LEGACY_DIRTY_VIEW
);
#else
assertNotNull(shader, "Shader cannot be null");
glUseProgram(shader->shaderProgramId);
errorChain(errorGLCheck());
#endif
errorOk();
}
@@ -180,22 +225,58 @@ errorret_t shaderBindGL(shadergl_t *shader) {
errorret_t shaderDisposeGL(shadergl_t *shader) {
assertNotNull(shader, "Shader cannot be null");
if(shader->shaderProgramId != 0) {
glDeleteProgram(shader->shaderProgramId);
errorChain(errorGLCheck());
}
#ifdef DUSK_OPENGL_LEGACY
SHADER_LEGACY.boundShader = NULL;
#else
if(shader->shaderProgramId != 0) {
glDeleteProgram(shader->shaderProgramId);
}
if(shader->vertexShaderId != 0) {
glDeleteShader(shader->vertexShaderId);
errorChain(errorGLCheck());
}
if(shader->vertexShaderId != 0) {
glDeleteShader(shader->vertexShaderId);
}
if(shader->fragmentShaderId != 0) {
glDeleteShader(shader->fragmentShaderId);
errorChain(errorGLCheck());
}
if(shader->fragmentShaderId != 0) {
glDeleteShader(shader->fragmentShaderId);
}
assertNoGLError("Failed disposing shader");
#endif
assertNoGLError("Failed disposing shader");
memoryZero(shader, sizeof(shadergl_t));
errorOk();
}
#ifdef DUSK_OPENGL_LEGACY
errorret_t shaderLegacyMatrixUpdate() {
assertNotNull(SHADER_LEGACY.boundShader, "No shader is currently bound.");
if((SHADER_LEGACY.dirty & SHADER_LEGACY_DIRTY_PROJ) != 0) {
glMatrixMode(GL_PROJECTION);
errorChain(errorGLCheck());
glLoadIdentity();
errorChain(errorGLCheck());
glMultMatrixf((const GLfloat *)SHADER_LEGACY.boundShader->proj);
errorChain(errorGLCheck());
}
if((SHADER_LEGACY.dirty & SHADER_LEGACY_DIRTY_VIEW) != 0) {
glMatrixMode(GL_MODELVIEW);
errorChain(errorGLCheck());
glLoadIdentity();
errorChain(errorGLCheck());
glMultMatrixf((const GLfloat *)SHADER_LEGACY.boundShader->view);
errorChain(errorGLCheck());
}
if((SHADER_LEGACY.dirty & SHADER_LEGACY_DIRTY_MODEL) != 0) {
glMatrixMode(GL_MODELVIEW);
errorChain(errorGLCheck());
glMultMatrixf((const GLfloat *)SHADER_LEGACY.boundShader->model);
errorChain(errorGLCheck());
}
SHADER_LEGACY.dirty = 0;
errorOk();
}
#endif

View File

@@ -16,6 +16,12 @@ typedef struct {
GLuint vertexShaderId;
GLuint fragmentShaderId;
#endif
#if DUSK_OPENGL_LEGACY
mat4 view;
mat4 proj;
mat4 model;
#endif
} shadergl_t;
typedef struct {
@@ -27,6 +33,19 @@ typedef struct {
#endif
} shaderdefinitiongl_t;
#if DUSK_OPENGL_LEGACY
typedef struct {
shadergl_t *boundShader;
uint_fast8_t dirty;
} shaderlegacygl_t;
extern shaderlegacygl_t SHADER_LEGACY;
#define SHADER_LEGACY_DIRTY_PROJ (1 << 0)
#define SHADER_LEGACY_DIRTY_VIEW (1 << 1)
#define SHADER_LEGACY_DIRTY_MODEL (1 << 2)
#endif
/**
* Initializes a shader.
*
@@ -69,7 +88,7 @@ errorret_t shaderParamGetLocationGL(
errorret_t shaderSetMatrixGL(
shadergl_t *shader,
const char_t *name,
const mat4 matrix
mat4 matrix
);
/**
@@ -78,3 +97,13 @@ errorret_t shaderSetMatrixGL(
* @param shader The shader to dispose.
*/
errorret_t shaderDisposeGL(shadergl_t *shader);
#ifdef DUSK_OPENGL_LEGACY
/**
* During mesh rendering, this is requesting the legacy system to push all
* shaders necessary to render the currently bound shader's matrices.
*
* @return Any error state.
*/
errorret_t shaderLegacyMatrixUpdate();
#endif

View File

@@ -7,21 +7,25 @@
#include "display/shader/shaderunlit.h"
shaderdefinition_t SHADER_UNLIT_DEFINITION = {
.vert =
"#version 330 core\n"
"layout(location = 0) in vec3 aPos;\n"
"uniform mat4 u_Proj;\n"
"uniform mat4 u_View;\n"
"uniform mat4 u_Model;\n"
"void main() {\n"
" gl_Position = u_Proj * u_View * u_Model * vec4(aPos, 1.0);\n"
"}\n",
#ifdef DUSK_OPENGL_LEGACY
shaderdefinition_t SHADER_UNLIT_DEFINITION = { 0 };
#else
shaderdefinition_t SHADER_UNLIT_DEFINITION = {
.vert =
"#version 330 core\n"
"layout(location = 0) in vec3 aPos;\n"
"uniform mat4 u_Proj;\n"
"uniform mat4 u_View;\n"
"uniform mat4 u_Model;\n"
"void main() {\n"
" gl_Position = u_Proj * u_View * u_Model * vec4(aPos, 1.0);\n"
"}\n",
.frag =
"#version 330 core\n"
"out vec4 FragColor;\n"
"void main() {\n"
" FragColor = vec4(1.0, 0.0, 0.0, 1.0);\n"
"}\n"
};
.frag =
"#version 330 core\n"
"out vec4 FragColor;\n"
"void main() {\n"
" FragColor = vec4(1.0, 0.0, 0.0, 1.0);\n"
"}\n"
};
#endif

View File

@@ -24,8 +24,13 @@ errorret_t displaySDL2Init(void) {
// SDL_GL_SetAttribute(SDL_GL_DEPTH_SIZE, 24);
// SDL_GL_SetAttribute(SDL_GL_STENCIL_SIZE, 8);
SDL_GL_SetAttribute(SDL_GL_CONTEXT_MAJOR_VERSION, 3);
SDL_GL_SetAttribute(SDL_GL_CONTEXT_MINOR_VERSION, 3);
#ifdef DUSK_OPENGL_LEGACY
SDL_GL_SetAttribute(SDL_GL_CONTEXT_PROFILE_MASK, SDL_GL_CONTEXT_PROFILE_COMPATIBILITY);
#else
SDL_GL_SetAttribute(SDL_GL_CONTEXT_PROFILE_MASK, SDL_GL_CONTEXT_PROFILE_CORE);
SDL_GL_SetAttribute(SDL_GL_CONTEXT_MAJOR_VERSION, 3);
SDL_GL_SetAttribute(SDL_GL_CONTEXT_MINOR_VERSION, 3);
#endif
// Create window with OpenGL flag.
DISPLAY.window = SDL_CreateWindow(