diff --git a/mybox.cpp b/mybox.cpp index 8cc8790..bb9466c 100644 --- a/mybox.cpp +++ b/mybox.cpp @@ -1,29 +1,55 @@ + #include #include #include #include +#include #include "src/standard_ints.h" #include "src/lgl_callbacks.h" #include "src/lgl_shader_tools.h" +#define SHADER_CNT 3 + +char *shader_list[SHADER_CNT] = { + "vertex.vert", + "fragment.frag", + "fragment2.frag" +}; + +struct shader_storage { + u32 type; + bool compiled; + bool freed; + u32 h; +}; + +struct shader_storage shader_set[SHADER_CNT] = { + {GL_VERTEX_SHADER}, + {GL_FRAGMENT_SHADER}, + {GL_FRAGMENT_SHADER} +}; + +void helper_capabilitiesCheck() { + i32 numAttrs; + glGetIntegerv(GL_MAX_VERTEX_ATTRIBS, &numAttrs); + std::cout << "Maximum number of vertex attributes for this hardware: " + << numAttrs << std::endl; +} + int main(void) { + std::cout << "Hello Shaders." << std::endl; - std::cout << "Hello World." << std::endl; - - // Setup GLFW context glfwInit(); - // Establish 4.2 GL requirement glfwWindowHint(GLFW_CONTEXT_VERSION_MAJOR, 4); glfwWindowHint(GLFW_CONTEXT_VERSION_MINOR, 2); glfwWindowHint(GLFW_OPENGL_PROFILE, GLFW_OPENGL_CORE_PROFILE); - // Build the winodw - GLFWwindow *window = glfwCreateWindow(960, 400, - "Hello MyBox", NULL, NULL); + GLFWwindow *window = glfwCreateWindow(960, 400, + "Hello Shader", NULL, NULL); glfwSetWindowPos(window, 140, 1000); if (window == NULL) { @@ -33,99 +59,69 @@ int main(void) { } glfwMakeContextCurrent(window); - // Set the resize callback; glfwSetFramebufferSizeCallback(window, framebuffer_size_callback); - // Setup the glad loader if (!gladLoadGLLoader((GLADloadproc)glfwGetProcAddress)) { std::cout << "Failed to initalize GLAD." << std::endl; + glfwTerminate(); return -1; } + helper_capabilitiesCheck(); + /* ====================================================================== */ /* ====================================================================== */ /* ====================================================================== */ i32 success; - char infoLog[512]; + char debug_msg[512]; + GLchar *shdr_source; - // Create the vertex shader - GLchar *shdr_src_vertex; - readshader("vertex.vert", &shdr_src_vertex); - u32 vertexShader = glCreateShader(GL_VERTEX_SHADER); - glShaderSource(vertexShader, 1, &shdr_src_vertex, NULL); - glCompileShader(vertexShader); - glGetShaderiv(vertexShader, GL_COMPILE_STATUS, &success); - freeshader(shdr_src_vertex); - - if (!success) { - glGetShaderInfoLog(vertexShader, 512, NULL, infoLog); - std::cout << "ERROR SHADER::VERTEX::Compilation Failed\n" << - infoLog << std::endl; - return -1; + for (u32 i = 0; i < SHADER_CNT; i++) { + shader_set[i].h = glCreateShader(shader_set[i].type); + readshader(shader_list[i], &shdr_source); + glShaderSource(shader_set[i].h, 1, &shdr_source, NULL); + glCompileShader(shader_set[i].h); + glGetShaderiv(shader_set[i].h, GL_COMPILE_STATUS, &success); + freeshader(shdr_source); + if (!success) { + glGetShaderInfoLog(shader_set[i].h, 512, NULL, debug_msg); + std::cerr << "ERROR SHADER::Compilation Failed for shader: \n\t" << + shader_list[i] << std::endl; + return -1; + } else { + shader_set[i].compiled = true; + } } - // Create the fragment shader - GLchar *shdr_src_fragment; - readshader("fragment.frag", &shdr_src_fragment); - u32 fragmentShader[2] = { - glCreateShader(GL_FRAGMENT_SHADER), - glCreateShader(GL_FRAGMENT_SHADER) - }; - glShaderSource(fragmentShader[0], 1, &shdr_src_fragment, NULL); - glCompileShader(fragmentShader[0]); - glGetShaderiv(fragmentShader[0], GL_COMPILE_STATUS, &success); - freeshader(shdr_src_fragment); - if (!success) { - glGetShaderInfoLog(fragmentShader[0], 512, NULL, infoLog); - std::cout << "ERROR SHADER::FRAGMENT::Compilation Failed\n" << - infoLog << std::endl; - return -1; + // Next, generate the shader programs + u32 shaderProgram[2]; + for (u32 i = 0; i < 2; i++) { + shaderProgram[i] = glCreateProgram(); + glAttachShader(shaderProgram[i], shader_set[0].h); + } + glAttachShader(shaderProgram[0], shader_set[1].h); + glAttachShader(shaderProgram[1], shader_set[2].h); + for (u32 i = 0; i < 2; i++) { + glLinkProgram(shaderProgram[i]); + glGetProgramiv(shaderProgram[i], GL_LINK_STATUS, &success); + if (!success) { + glGetProgramInfoLog(shaderProgram[i], 512, NULL, debug_msg); + std::cout << "ERROR SHADER::Linking Failed\n" << + debug_msg << std::endl; + return -1; + } } - readshader("fragment2.frag", &shdr_src_fragment); - glShaderSource(fragmentShader[1], 1, &shdr_src_fragment, NULL); - glCompileShader(fragmentShader[1]); - glGetShaderiv(fragmentShader[1], GL_COMPILE_STATUS, &success); - freeshader(shdr_src_fragment); - if (!success) { - glGetShaderInfoLog(fragmentShader[1], 512, NULL, infoLog); - std::cout << "ERROR SHADER::FRAGMENT::Compilation Failed\n" << - infoLog << std::endl; - return -1; + for (u32 i = 0; i < SHADER_CNT; i++) { + if (shader_set[i].compiled && !shader_set[i].freed) { + glDeleteShader(shader_set[i].h); + shader_set[i].freed = true; + } } - // Create the shader program - u32 shaderProgram[2] = {glCreateProgram(), glCreateProgram()}; - glAttachShader(shaderProgram[0], vertexShader); - glAttachShader(shaderProgram[1], vertexShader); - glAttachShader(shaderProgram[0], fragmentShader[0]); - glAttachShader(shaderProgram[1], fragmentShader[1]); - - glLinkProgram(shaderProgram[0]); - glGetProgramiv(shaderProgram[0], GL_LINK_STATUS, &success); - if (!success) { - glGetProgramInfoLog(shaderProgram[0], 512, NULL, infoLog); - std::cout << "ERROR SHADER::PROGRAM::Linking Failed\n" << - infoLog << std::endl; - return -1; - } - glLinkProgram(shaderProgram[1]); - glGetProgramiv(shaderProgram[1], GL_LINK_STATUS, &success); - if (!success) { - glGetProgramInfoLog(shaderProgram[1], 512, NULL, infoLog); - std::cout << "ERROR SHADER::PROGRAM::Linking Failed\n" << - infoLog << std::endl; - return -1; - } - - // Free the old shader bits - glDeleteShader(vertexShader); - glDeleteShader(fragmentShader[0]); - glDeleteShader(fragmentShader[1]); - /* ====================================================================== */ /* ====================================================================== */ - + /* ====================================================================== */ // Define the vertex shader dat. f32 vertices_1[] = { -0.9f, -0.66f, 0.0f, @@ -133,82 +129,61 @@ int main(void) { -0.50f, +0.66f, 0.0f }; f32 vertices_2[sizeof(vertices_1)/sizeof(f32)]; - for (u32 i = 0; i < sizeof(vertices_1)/sizeof(f32); i++) { - if (i % 3 == 0) { - vertices_2[i] = -1*vertices_1[i]; - } else { - vertices_2[i] = vertices_1[i]; - } + memcpy(vertices_2, vertices_1, sizeof(vertices_1)); + for (u32 i = 0; i < sizeof(vertices_1)/sizeof(f32); i+=3) { + vertices_2[i] *= -1; } + + f32 *vert_ptr[2]; + vert_ptr[0] = vertices_1; + vert_ptr[1] = vertices_2; + u32 indicies[] { 0, 1, 2, // t1 }; - u32 VAO[2]; // Vertex Array Object refernce number - glGenVertexArrays(2, VAO); // ask the GPU for a reference for one buffer - u32 VBO[2]; // Vertex Buffer Object refernce number - glGenBuffers(2, VBO); // ask the GPU for a reference for one buffer - u32 EBO; // - glGenBuffers(1, &EBO); // ask the gpu for a reference for one buffer - - // Bind VAO, meaning we - glBindVertexArray(VAO[0]); - // Tell the GPU subsequent calls to modify buffers apply to this buffer, - // namely, the VBO buffer. - glBindBuffer(GL_ARRAY_BUFFER, VBO[0]); - glBufferData(GL_ARRAY_BUFFER, sizeof(vertices_1), vertices_1, GL_STATIC_DRAW); - glVertexAttribPointer(0, 3, GL_FLOAT, GL_FALSE, 3*sizeof(f32), (void *)0); - glBindBuffer(GL_ELEMENT_ARRAY_BUFFER, EBO); - glBufferData(GL_ELEMENT_ARRAY_BUFFER, sizeof(indicies), indicies, GL_STATIC_DRAW); - // For the current Generic Vertex Attirbute Array object (VAO), indicate - // what index we should be starting in for subsequent draw calls. - glEnableVertexAttribArray(0); - glBindVertexArray(VAO[1]); - glBindBuffer(GL_ARRAY_BUFFER, VBO[1]); - glBufferData(GL_ARRAY_BUFFER, sizeof(vertices_2), vertices_2, GL_STATIC_DRAW); - glVertexAttribPointer(0, 3, GL_FLOAT, GL_FALSE, 3*sizeof(f32), (void *)0); - glBindBuffer(GL_ELEMENT_ARRAY_BUFFER, EBO); - glBufferData(GL_ELEMENT_ARRAY_BUFFER, sizeof(indicies), indicies, GL_STATIC_DRAW); + u32 VAOs[2]; + glGenVertexArrays(2, VAOs); + u32 VBOs[2]; + glGenBuffers(2, VBOs); + u32 EBO; + glGenBuffers(1, &EBO); - // For the VAO array (theoretically, but we have an array of 1), start - // at the 0th element of the VAO array. - glEnableVertexAttribArray(0); + for (u32 i = 0; i < 2; i++) { + glBindVertexArray(VAOs[i]); + glBindBuffer(GL_ARRAY_BUFFER, VBOs[i]); + glBufferData(GL_ARRAY_BUFFER, sizeof(vertices_1), vert_ptr[i], GL_STATIC_DRAW); + glVertexAttribPointer(0, 3, GL_FLOAT, GL_FALSE, 3*sizeof(f32), (void *)0); + glBindBuffer(GL_ELEMENT_ARRAY_BUFFER, EBO); + glBufferData(GL_ELEMENT_ARRAY_BUFFER, sizeof(indicies), indicies, GL_STATIC_DRAW); - // Setup the indexing into the VBO data. The EBO is the indirection buffer - // that tells the GPU where to look into it's known GL_ARRAY_BUFFER object - // for data. + glEnableVertexAttribArray(0); + } glPolygonMode(GL_FRONT_AND_BACK, GL_FILL); - // ?? - glBindVertexArray(0); // i.e., UNBIND the vertex array. - - while(!glfwWindowShouldClose(window)) { processInput(window); - - // Do some rendering + glClearColor(0.0f, 0.1f, 0.3f, 1.0f); glClear(GL_COLOR_BUFFER_BIT); + + for (u32 i = 0; i < 2; i++) { + glUseProgram(shaderProgram[i]); + glBindVertexArray(VAOs[i]); + glDrawArrays(GL_TRIANGLES, 0, 3); + } - glUseProgram(shaderProgram[0]); - glBindVertexArray(VAO[0]); - glDrawArrays(GL_TRIANGLES, 0, 3); - glUseProgram(shaderProgram[1]); - glBindVertexArray(VAO[1]); - glDrawArrays(GL_TRIANGLES, 0, 3); - //glDrawElements(GL_TRIANGLES, 3, GL_UNSIGNED_INT, 0); - - // Finish up glfwSwapBuffers(window); glfwPollEvents(); } - glDeleteVertexArrays(2, VAO); - glDeleteBuffers(2, VBO); - glDeleteBuffers(1, &EBO); - glDeleteProgram(shaderProgram[0]); - glDeleteProgram(shaderProgram[1]); + glDeleteVertexArrays(2, VAOs); + glDeleteBuffers(2, VBOs); + glDeleteTextures(1, &EBO); + for (u32 i = 0; i < 2; i++) { + glDeleteProgram(shaderProgram[i]); + } i32 xpos, ypos; glfwGetWindowPos(window, &xpos, &ypos); @@ -217,4 +192,5 @@ int main(void) { glfwTerminate(); return 0; + } \ No newline at end of file diff --git a/mybox_1.cpp b/mybox_1.cpp new file mode 100644 index 0000000..8cc8790 --- /dev/null +++ b/mybox_1.cpp @@ -0,0 +1,220 @@ + + +#include +#include +#include +#include + +#include "src/standard_ints.h" +#include "src/lgl_callbacks.h" +#include "src/lgl_shader_tools.h" + +int main(void) { + + std::cout << "Hello World." << std::endl; + + // Setup GLFW context + glfwInit(); + + // Establish 4.2 GL requirement + glfwWindowHint(GLFW_CONTEXT_VERSION_MAJOR, 4); + glfwWindowHint(GLFW_CONTEXT_VERSION_MINOR, 2); + glfwWindowHint(GLFW_OPENGL_PROFILE, GLFW_OPENGL_CORE_PROFILE); + + // Build the winodw + GLFWwindow *window = glfwCreateWindow(960, 400, + "Hello MyBox", NULL, NULL); + glfwSetWindowPos(window, 140, 1000); + + if (window == NULL) { + std::cout << "Failed to create GLFW window." << std::endl; + glfwTerminate(); + return -1; + } + + glfwMakeContextCurrent(window); + // Set the resize callback; + glfwSetFramebufferSizeCallback(window, framebuffer_size_callback); + + // Setup the glad loader + if (!gladLoadGLLoader((GLADloadproc)glfwGetProcAddress)) { + std::cout << "Failed to initalize GLAD." << std::endl; + return -1; + } + + /* ====================================================================== */ + /* ====================================================================== */ + /* ====================================================================== */ + i32 success; + char infoLog[512]; + + // Create the vertex shader + GLchar *shdr_src_vertex; + readshader("vertex.vert", &shdr_src_vertex); + u32 vertexShader = glCreateShader(GL_VERTEX_SHADER); + glShaderSource(vertexShader, 1, &shdr_src_vertex, NULL); + glCompileShader(vertexShader); + glGetShaderiv(vertexShader, GL_COMPILE_STATUS, &success); + freeshader(shdr_src_vertex); + + if (!success) { + glGetShaderInfoLog(vertexShader, 512, NULL, infoLog); + std::cout << "ERROR SHADER::VERTEX::Compilation Failed\n" << + infoLog << std::endl; + return -1; + } + + // Create the fragment shader + GLchar *shdr_src_fragment; + readshader("fragment.frag", &shdr_src_fragment); + u32 fragmentShader[2] = { + glCreateShader(GL_FRAGMENT_SHADER), + glCreateShader(GL_FRAGMENT_SHADER) + }; + glShaderSource(fragmentShader[0], 1, &shdr_src_fragment, NULL); + glCompileShader(fragmentShader[0]); + glGetShaderiv(fragmentShader[0], GL_COMPILE_STATUS, &success); + freeshader(shdr_src_fragment); + if (!success) { + glGetShaderInfoLog(fragmentShader[0], 512, NULL, infoLog); + std::cout << "ERROR SHADER::FRAGMENT::Compilation Failed\n" << + infoLog << std::endl; + return -1; + } + + readshader("fragment2.frag", &shdr_src_fragment); + glShaderSource(fragmentShader[1], 1, &shdr_src_fragment, NULL); + glCompileShader(fragmentShader[1]); + glGetShaderiv(fragmentShader[1], GL_COMPILE_STATUS, &success); + freeshader(shdr_src_fragment); + if (!success) { + glGetShaderInfoLog(fragmentShader[1], 512, NULL, infoLog); + std::cout << "ERROR SHADER::FRAGMENT::Compilation Failed\n" << + infoLog << std::endl; + return -1; + } + + // Create the shader program + u32 shaderProgram[2] = {glCreateProgram(), glCreateProgram()}; + glAttachShader(shaderProgram[0], vertexShader); + glAttachShader(shaderProgram[1], vertexShader); + glAttachShader(shaderProgram[0], fragmentShader[0]); + glAttachShader(shaderProgram[1], fragmentShader[1]); + + glLinkProgram(shaderProgram[0]); + glGetProgramiv(shaderProgram[0], GL_LINK_STATUS, &success); + if (!success) { + glGetProgramInfoLog(shaderProgram[0], 512, NULL, infoLog); + std::cout << "ERROR SHADER::PROGRAM::Linking Failed\n" << + infoLog << std::endl; + return -1; + } + glLinkProgram(shaderProgram[1]); + glGetProgramiv(shaderProgram[1], GL_LINK_STATUS, &success); + if (!success) { + glGetProgramInfoLog(shaderProgram[1], 512, NULL, infoLog); + std::cout << "ERROR SHADER::PROGRAM::Linking Failed\n" << + infoLog << std::endl; + return -1; + } + + // Free the old shader bits + glDeleteShader(vertexShader); + glDeleteShader(fragmentShader[0]); + glDeleteShader(fragmentShader[1]); + + /* ====================================================================== */ + /* ====================================================================== */ + + // Define the vertex shader dat. + f32 vertices_1[] = { + -0.9f, -0.66f, 0.0f, + -0.1f, -0.66f, 0.0f, + -0.50f, +0.66f, 0.0f + }; + f32 vertices_2[sizeof(vertices_1)/sizeof(f32)]; + for (u32 i = 0; i < sizeof(vertices_1)/sizeof(f32); i++) { + if (i % 3 == 0) { + vertices_2[i] = -1*vertices_1[i]; + } else { + vertices_2[i] = vertices_1[i]; + } + } + u32 indicies[] { + 0, 1, 2, // t1 + }; + u32 VAO[2]; // Vertex Array Object refernce number + glGenVertexArrays(2, VAO); // ask the GPU for a reference for one buffer + u32 VBO[2]; // Vertex Buffer Object refernce number + glGenBuffers(2, VBO); // ask the GPU for a reference for one buffer + u32 EBO; // + glGenBuffers(1, &EBO); // ask the gpu for a reference for one buffer + + // Bind VAO, meaning we + glBindVertexArray(VAO[0]); + // Tell the GPU subsequent calls to modify buffers apply to this buffer, + // namely, the VBO buffer. + glBindBuffer(GL_ARRAY_BUFFER, VBO[0]); + glBufferData(GL_ARRAY_BUFFER, sizeof(vertices_1), vertices_1, GL_STATIC_DRAW); + glVertexAttribPointer(0, 3, GL_FLOAT, GL_FALSE, 3*sizeof(f32), (void *)0); + glBindBuffer(GL_ELEMENT_ARRAY_BUFFER, EBO); + glBufferData(GL_ELEMENT_ARRAY_BUFFER, sizeof(indicies), indicies, GL_STATIC_DRAW); + // For the current Generic Vertex Attirbute Array object (VAO), indicate + // what index we should be starting in for subsequent draw calls. + glEnableVertexAttribArray(0); + + glBindVertexArray(VAO[1]); + glBindBuffer(GL_ARRAY_BUFFER, VBO[1]); + glBufferData(GL_ARRAY_BUFFER, sizeof(vertices_2), vertices_2, GL_STATIC_DRAW); + glVertexAttribPointer(0, 3, GL_FLOAT, GL_FALSE, 3*sizeof(f32), (void *)0); + glBindBuffer(GL_ELEMENT_ARRAY_BUFFER, EBO); + glBufferData(GL_ELEMENT_ARRAY_BUFFER, sizeof(indicies), indicies, GL_STATIC_DRAW); + + // For the VAO array (theoretically, but we have an array of 1), start + // at the 0th element of the VAO array. + glEnableVertexAttribArray(0); + + // Setup the indexing into the VBO data. The EBO is the indirection buffer + // that tells the GPU where to look into it's known GL_ARRAY_BUFFER object + // for data. + + glPolygonMode(GL_FRONT_AND_BACK, GL_FILL); + // ?? + + glBindVertexArray(0); // i.e., UNBIND the vertex array. + + + while(!glfwWindowShouldClose(window)) { + processInput(window); + + // Do some rendering + glClearColor(0.0f, 0.1f, 0.3f, 1.0f); + glClear(GL_COLOR_BUFFER_BIT); + + glUseProgram(shaderProgram[0]); + glBindVertexArray(VAO[0]); + glDrawArrays(GL_TRIANGLES, 0, 3); + glUseProgram(shaderProgram[1]); + glBindVertexArray(VAO[1]); + glDrawArrays(GL_TRIANGLES, 0, 3); + //glDrawElements(GL_TRIANGLES, 3, GL_UNSIGNED_INT, 0); + + // Finish up + glfwSwapBuffers(window); + glfwPollEvents(); + } + + glDeleteVertexArrays(2, VAO); + glDeleteBuffers(2, VBO); + glDeleteBuffers(1, &EBO); + glDeleteProgram(shaderProgram[0]); + glDeleteProgram(shaderProgram[1]); + + i32 xpos, ypos; + glfwGetWindowPos(window, &xpos, &ypos); + std::cout << "Closed window at pos`ition\n (X,Y) = " + << xpos << ", " << ypos << "\n" << std::endl; + + glfwTerminate(); + return 0; +} \ No newline at end of file