implemented basic modern opengl rendering. Currently just rendering a tri to the...
authormatthew <matthew@owens.tech>
Sat, 18 Aug 2018 16:19:25 +0000 (17:19 +0100)
committermatthew <matthew@owens.tech>
Sat, 18 Aug 2018 16:19:25 +0000 (17:19 +0100)
gl/err.c [new file with mode: 0644]
gl/main.c
gl/shaderLoader.c [new file with mode: 0644]
gl/shaderLoader.h [new file with mode: 0644]
gl/shaders/tri/tri.frag [new file with mode: 0644]
gl/shaders/tri/tri.vert [new file with mode: 0644]

diff --git a/gl/err.c b/gl/err.c
new file mode 100644 (file)
index 0000000..4945b60
--- /dev/null
+++ b/gl/err.c
@@ -0,0 +1,18 @@
+#include "err.h"
+#include <stdio.h>
+#include "point.h"
+
+void err_output(const char *message)
+{
+       fprintf(stderr, message);
+       fflush(stderr);
+}
+
+void err_enable_logging(const char* logpath)
+{
+       err_output("logging not yet implemented");
+}
+
+void err_clear()
+{
+}
index 7d2c057..507cf58 100644 (file)
--- a/gl/main.c
+++ b/gl/main.c
@@ -2,12 +2,69 @@
 #include <stdbool.h>
 #include <SDL2/SDL.h>
 #include <GL/glew.h>
+#include "shaderLoader.h"
+#include "err.h"
 
 static SDL_Window *window = NULL;
 static SDL_GLContext *context = NULL;
 static int screen_width = 1280;
 static int screen_height = 720;
 
+static float vertices[] = {
+       -0.5f, -0.5f, 0.0f,
+       0.5f, -0.5f, 0.0f,
+       0.0f, 0.5f, 0.0f
+};
+
+static unsigned int vbo, vao;
+static unsigned int vertShader, fragShader, shaderProgram;
+static GLchar *vertSrc = NULL;
+static GLchar *fragSrc = NULL;
+
+static void initTri()
+{
+       glGenBuffers(1, &vbo);
+       glBindBuffer(GL_ARRAY_BUFFER, vbo);
+       glBufferData(GL_ARRAY_BUFFER, sizeof(vertices), vertices, GL_STATIC_DRAW);
+
+       glGenVertexArrays(1, &vao);
+       glBindVertexArray(vao);
+
+       vertShader = glCreateShader(GL_VERTEX_SHADER);
+       vertSrc = shader_load_src("tri", VERTEX);
+       shader_compile(vertShader, vertSrc, "triangle vertex");
+
+       fragShader = glCreateShader(GL_FRAGMENT_SHADER);
+       fragSrc = shader_load_src("tri", FRAGMENT);
+       shader_compile(fragShader, fragSrc, "triangle fragment");
+
+       shaderProgram = glCreateProgram();
+       glAttachShader(shaderProgram, vertShader);
+       glAttachShader(shaderProgram, fragShader);
+       glLinkProgram(shaderProgram);
+
+       /*
+        * The glVertexAttribPointer call is rather complex, so I will document it
+        * here.
+        * The 1st paramater specifies the vertex attrib to configure. We want to
+        * configure the position attribute, as specified with:
+        * layout (location = 0) in tri.vert.
+        * The 2nd paramater specifies the size of the attribute to configure.
+        * We are using a vec3 value in the shader which is composed of 3 values.
+        * The 3rd specifies the data type of the paramater.
+        * The 4th specifies if the value should be normalised.
+        * The 5th specifies the size of the stride and the 6th is the offset.
+        */
+       glVertexAttribPointer(0, 3, GL_FLOAT, GL_FALSE, 3*sizeof(float), (void*)0);
+       glEnableVertexAttribArray(0); // param is the location of the attrib to enable.
+
+       // cleaning up
+       glDeleteShader(vertShader);
+       glDeleteShader(fragShader);
+       shader_free_src(vertSrc);
+       shader_free_src(fragSrc);
+}
+
 static bool init()
 {
        if (SDL_Init(
@@ -51,6 +108,10 @@ static void render()
 {
        glClearColor(0.2, 0.3, 0.3, 1.0);
        glClear(GL_COLOR_BUFFER_BIT);
+
+       glUseProgram(shaderProgram);
+       glBindVertexArray(vao);
+       glDrawArrays(GL_TRIANGLES, 0, 3);
        SDL_GL_SwapWindow(window);
 }
 
@@ -63,6 +124,7 @@ int main()
        if(!init())
                return -1;
 
+       initTri();
        itime = SDL_GetTicks();
 
 
diff --git a/gl/shaderLoader.c b/gl/shaderLoader.c
new file mode 100644 (file)
index 0000000..9bccfaf
--- /dev/null
@@ -0,0 +1,75 @@
+#include "shaderLoader.h"
+#include "fileRead.h"
+#include <stdlib.h>
+#include <stdio.h>
+#include <string.h>
+#include "err.h"
+
+static char *fileEnds[] = {
+       ".vert",
+       ".frag",
+       ".comp",
+       ".tesc",
+       ".tese"
+};
+static char *dirPath = "gl/shaders/";
+
+char *shader_load_src(const char *name, enum ShaderType type)
+{
+       GLchar *src = NULL;
+
+       int nSize = strlen(name);
+       int eSize = strlen(fileEnds[type]);
+       int dSize = strlen(dirPath);
+
+       int tSize = dSize + (2*nSize) + eSize + 2;
+
+       // constructing the final path string
+       char *path = malloc(tSize);
+       printf("sizes: dSize=%d nSize=%d, eSize=%d\n", dSize, nSize, eSize);
+       printf("total allocated %d\n", tSize);
+
+       strcpy(path, dirPath);
+       strcat(path, name);
+       strcat(path, "/");
+       strcat(path, name);
+       strcat(path, fileEnds[type]);
+
+       // debug output
+       printf("path length is %ld\n", strlen(path));
+       printf("loading shader from file '%s'\n\n", path);
+       src = readFile(path);
+       free(path);
+       return src;
+}
+
+void shader_compile(unsigned int shader, const GLchar *shaderSrc, const char *description)
+{
+       int success;
+       char log[512];
+       char out[512];
+
+       strcpy(out, "failed to compile shader: ");
+       strcat(out, description);
+
+       if(shaderSrc){
+               glShaderSource(shader, 1, &shaderSrc, NULL);
+               glCompileShader(shader);
+               glGetShaderiv(shader, GL_COMPILE_STATUS, &success);
+
+               if(!success){
+                       glGetShaderInfoLog(shader, 512, NULL, log);
+                       strcat(out, "!\n");
+                       strcat(out, log);
+                       err_output(out);
+               }
+       } else {
+               strcat(out, " source is NULL!\n");
+               err_output(out);
+       }
+}
+
+void shader_free_src(GLchar *src)
+{
+       free(src);
+}
diff --git a/gl/shaderLoader.h b/gl/shaderLoader.h
new file mode 100644 (file)
index 0000000..572f5d6
--- /dev/null
@@ -0,0 +1,18 @@
+#ifndef SHADER_LOADER
+#define SHADER_LOADER
+#include <GL/glew.h>
+
+enum ShaderType
+{
+       VERTEX = 0,
+       FRAGMENT,
+       GEOMETRY,
+       COMPUTE,
+       TESSCONTROL,
+       TESSEVAL
+};
+
+char *shader_load_src(const char *name, enum ShaderType type);
+void shader_compile(unsigned int shader, const GLchar *shaderSrc, const char *description);
+void shader_free_src(GLchar *src);
+#endif//SHADER_LOADER
diff --git a/gl/shaders/tri/tri.frag b/gl/shaders/tri/tri.frag
new file mode 100644 (file)
index 0000000..b162430
--- /dev/null
@@ -0,0 +1,7 @@
+#version 330 core
+out vec4 fragColor;
+
+void main()
+{
+       fragColor = vec4(1.0f, 0.5f, 0.2f, 1.0f);
+}
diff --git a/gl/shaders/tri/tri.vert b/gl/shaders/tri/tri.vert
new file mode 100644 (file)
index 0000000..0e6b9fc
--- /dev/null
@@ -0,0 +1,7 @@
+#version 330 core
+layout (location = 0) in vec3 aPos;
+
+void main()
+{
+       gl_Position = vec4(aPos.x, aPos.y, aPos.z, 1.0);
+}