#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(
{
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);
}
if(!init())
return -1;
+ initTri();
itime = SDL_GetTicks();
--- /dev/null
+#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);
+}