Skip to content

Instantly share code, notes, and snippets.

@TheOpenDevProject
Last active August 16, 2023 12:09
Show Gist options
  • Save TheOpenDevProject/1662fa2bfd8ef087d94ad4ed27746120 to your computer and use it in GitHub Desktop.
Save TheOpenDevProject/1662fa2bfd8ef087d94ad4ed27746120 to your computer and use it in GitHub Desktop.
#include "display.h"
#include <iostream>
#include <string>
#include "glmathtoolkit.h"
Display::Display()
{
}
void Display::createWindow(int width, int height, std::__cxx11::string windowTitle, int openGLMinVersion, int openGLMaxVersion, bool resizeable)
{
glfwInit();
//glfw settings
glfwWindowHint(GLFW_CONTEXT_VERSION_MAJOR, openGLMaxVersion);
glfwWindowHint(GLFW_CONTEXT_VERSION_MINOR, openGLMinVersion);
glfwWindowHint(GLFW_OPENGL_PROFILE, GLFW_OPENGL_CORE_PROFILE);
glfwWindowHint(GLFW_RESIZABLE, resizeable);
//TODO: Replace with smart pointer typedef
this->window.reset(glfwCreateWindow(width, height, windowTitle.c_str(), NULL, NULL));
glfwMakeContextCurrent(this->window.get());
//Check if we have a pointer to the window
if (this->window == nullptr)
{
std::cout << "Failed to create GLFW window" << std::endl;
glfwTerminate();
}
//Load OpenGL via GLAD
if (!gladLoadGLLoader((GLADloadproc)glfwGetProcAddress))
{
std::cout << "Failed to initialize OpenGL context" << std::endl;
}
//Setup the OpenGL Viewport
glViewport(0, 0, width, height);
}
void Display::updateWindow()
{
glClearColor(clearR, clearG, clearB, clearA);
glClear(GL_COLOR_BUFFER_BIT);
glfwSwapBuffers(this->window.get());
}
void Display::pollEvents() const
{
glfwPollEvents();
}
bool Display::isClosing() const
{
return glfwWindowShouldClose(this->window.get());
}
void Display::close() const
{
glfwTerminate();
}
void Display::setClearColor(float r, float g, float b)
{
this->clearR = GLMathToolkit::convertFromRGB(r);
this->clearG = GLMathToolkit::convertFromRGB(g);
this->clearB = GLMathToolkit::convertFromRGB(b);
this->clearA = GLMathToolkit::convertFromRGB(r);
}
Display::~Display()
{
std::cout << "Display Closing" << std::endl;
}
#ifndef DISPLAY_H
#define DISPLAY_H
#include <glad/glad.h>
#include <GLFW/glfw3.h>
#include <functional>
#include <memory>
#include <iostream>
struct glfwDeleter
{
void operator()(GLFWwindow *wnd)
{
std::cout << "Destroying GLFW Window Context" << std::endl;
glfwDestroyWindow(wnd);
}
};
class Display
{
public:
Display();
void createWindow(int width, int height, std::string windowTitle, int openGLMinVersion, int openGLMaxVersion, bool resizeable);
void setClearColor(float r, float g, float b);
void updateWindow();
void pollEvents() const;
bool isClosing() const;
void close() const;
~Display();
private:
std::unique_ptr<GLFWwindow, glfwDeleter> window;
float clearR = 1.0f, clearG = 1.0f, clearB = 1.0f, clearA = 1.0f;
};
#endif // DISPLAY_H
#include <iostream>
#include "display.h"
#include "shader.h"
#include "mesh.h"
int main()
{
Display d;
//GL Clear color in RGB
d.setClearColor(100, 255, 255);
//Last step in fake game engine
d.createWindow(800, 800, "Goood", 3, 3, GL_FALSE);
//Development shader
Shader xShader("../untitled/basicshader");
Vertex verticies[] = {Vertex(glm::vec3(-0.5, -0.5, 0)),
Vertex(glm::vec3(0, 0.5, 0)),
Vertex(glm::vec3(0.5, -0.5, 0))};
Mesh foo(verticies,sizeof(verticies) / sizeof(verticies[0]));
while (!d.isClosing())
{
d.pollEvents();
auto err = glGetError();
if(err != GL_NO_ERROR){
std::cout << err;
}
xShader.bindShader();
foo.draw();
d.updateWindow();
}
d.close();
return 0;
}
#include "mesh.h"
Mesh::Mesh(Vertex *verticies, unsigned int numVerticies)
{
m_drawCount = numVerticies;
glGenVertexArrays(1, &m_vertexArrayObject);
glBindVertexArray(m_vertexArrayObject);
glGenBuffers(NUM_BUFFERS, m_vertexArrayBuffers);
glBindBuffer(GL_ARRAY_BUFFER, m_vertexArrayBuffers[POSITION_VB]);
glBufferData(GL_ARRAY_BUFFER, (numVerticies * sizeof(verticies[0])) , verticies, GL_STATIC_DRAW); //use Sub zero as that gives us the size of each Vertex (X,Y,Z)
glEnableVertexAttribArray(0);
glVertexAttribPointer(0, 3, GL_FLOAT, GL_FALSE, 0, 0);
glBindVertexArray(0);
}
Mesh::~Mesh()
{
glDeleteVertexArrays(1, &m_vertexArrayObject);
}
void Mesh::draw()
{
glBindVertexArray(m_vertexArrayObject);
glDrawArrays(GL_TRIANGLES, 0, m_drawCount);
glBindVertexArray(0);
}
#ifndef MESH_H
#define MESH_H
#include <glad/glad.h>
#include <glm/glm.hpp>
class Vertex{
public:
Vertex(const glm::vec3& pos){this->pos = pos;}
private:
protected:
glm::vec3 pos;
};
class Mesh
{
public:
Mesh(Vertex *verticies, unsigned int numVerticies);
~Mesh();
void draw();
private:
Mesh(const Mesh &other) = delete;
void operator=(const Mesh &other) = delete;
enum
{
POSITION_VB,
NUM_BUFFERS
};
GLuint m_vertexArrayObject;
GLuint m_vertexArrayBuffers[NUM_BUFFERS];
unsigned int m_drawCount;
};
#endif // MESH_H
#include "shader.h"
#include <fstream>
#include <iostream>
Shader::Shader(const std::__cxx11::string &fileName)
{
m_program = glCreateProgram();
m_shaders[0] = ShaderTools::createShader(ShaderTools::loadFromFile(fileName + ".vs"), GL_VERTEX_SHADER);
m_shaders[1] = ShaderTools::createShader(ShaderTools::loadFromFile(fileName + ".fs"), GL_FRAGMENT_SHADER);
for (unsigned int i = 0; i < NUM_SHADERS; i++)
{
glAttachShader(m_program, m_shaders[i]);
}
glBindAttribLocation(m_program, 0, "position");
glLinkProgram(m_program);
ShaderTools::checkShaderCompileError(m_program, GL_LINK_STATUS, true, "Error Shader Program Failed to link");
glValidateProgram(m_program);
ShaderTools::checkShaderCompileError(m_program, GL_VALIDATE_STATUS, true, "Error: Program failed to validate");
}
Shader::~Shader()
{
for (unsigned int i = 0; i < NUM_SHADERS; i++)
{
glDetachShader(m_program, m_shaders[i]);
glDeleteShader(m_shaders[i]);
}
glDeleteProgram(m_program);
}
void Shader::bindShader()
{
glUseProgram(m_program);
}
GLuint ShaderTools::createShader(const std::string &programSource, GLenum shaderType)
{
GLuint shader = glCreateShader(shaderType);
if (shader == 0)
{
std::cerr << "Error Shader Creation failed" << std::endl;
}
const GLchar *shaderSourceStrings[1];
GLint shaderSourceStringLengths[1];
shaderSourceStrings[0] = programSource.c_str();
shaderSourceStringLengths[0] = programSource.length();
glShaderSource(shader, 1, shaderSourceStrings, shaderSourceStringLengths);
glCompileShader(shader);
ShaderTools::checkShaderCompileError(shader, GL_COMPILE_STATUS, false, "Error, Program failed to compile. Could not create shader");
return shader;
}
std::string ShaderTools::loadFromFile(const std::string &fileName)
{
std::ifstream file;
file.open((fileName).c_str());
std::string output;
std::string line;
if (file.is_open())
{
while (file.good())
{
getline(file, line);
output.append(line + "\n");
}
}
else
{
std::cerr << "Unable to load shader " << fileName << std::endl;
}
return output;
}
void ShaderTools::checkShaderCompileError(GLuint shaderIndex, GLuint flag, bool isProgram, std::string &&errorMessage)
{
GLint success = 0; //Always assume it failed
GLchar error[1024] = {0};
if (isProgram)
{
glGetProgramiv(shaderIndex, flag, &success);
}
else
{
glGetShaderiv(shaderIndex, flag, &success);
if (success == GL_FALSE)
{
if (isProgram)
{
glGetProgramInfoLog(shaderIndex, sizeof(error), NULL, error);
}
else
{
glGetShaderInfoLog(shaderIndex, sizeof(error), NULL, error);
}
std::cerr << errorMessage << " " << error << " " << std::endl;
}
}
}
#ifndef SHADER_H
#define SHADER_H
#include <string>
#include <glad/glad.h>
//The lessons I was following abused the hell out of static which is silly because C++ has free functions and namespaces and static is not fre
namespace ShaderTools
{
std::string loadFromFile(const std::string &fileName);
void checkShaderCompileError(GLuint shaderIndex, GLuint flag, bool isProgram, std::string &&errorMessage);
GLuint createShader(const std::string &programSource, GLenum shaderType);
}
class Shader
{
public:
Shader(const std::string &fileName);
~Shader();
void bindShader();
private:
//Helper Methods (This might be bad to make static, when building engine after learning consider a propper loader pattern).
static const unsigned int NUM_SHADERS = 2;
Shader(const Shader &other) = delete;
void operator=(const Shader &other) = delete;
GLuint m_program;
GLuint m_shaders[NUM_SHADERS];
};
#endif // SHADER_H
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment