Browse Source

maybe this is an interesting direction?

fix/style
Martin Dørum 3 years ago
parent
commit
ccec9eb54c

+ 3
- 0
libcygnet/CMakeLists.txt View File

@@ -1,5 +1,8 @@
add_library(libcygnet SHARED
src/shaders/basic.cc
src/Context.cc
src/Program.cc
src/Renderer.cc
src/Window.cc)
target_include_directories(libcygnet
PUBLIC "include"

+ 64
- 0
libcygnet/include/cygnet/Program.h View File

@@ -0,0 +1,64 @@
#pragma once

#include <stdint.h>
#include <stdexcept>

#include "util.h"

namespace Cygnet {

struct GlCompileError: public std::exception {
GlCompileError(std::string message): message(std::move(message)) {}
const char *what() const noexcept override { return message.c_str(); }
std::string message;
};

class GlShader {
public:
enum class Type {
VERTEX,
FRAGMENT,
};

GlShader(Type type, const char *source);
~GlShader();

GlID id() const { return id_; }

private:
GlID id_;
};

class GlVxShader: public GlShader {
public:
explicit GlVxShader(const char *source): GlShader(Type::VERTEX, source) {}
};

class GlFrShader: public GlShader {
public:
explicit GlFrShader(const char *source): GlShader(Type::FRAGMENT, source) {}
};

class GlProgram {
public:
template <typename... T>
GlProgram(const T &... shaders): GlProgram() { (addShader(shaders), ...); link(); }
GlProgram();
~GlProgram();

void use();
GlID id() const { return id_; }

protected:

GlLoc attribLoc(const char *name);
GlLoc uniformLoc(const char *name);

private:
void addShader(const GlShader &shader);
void link();

GlID id_;
};

}

+ 21
- 0
libcygnet/include/cygnet/Renderer.h View File

@@ -0,0 +1,21 @@
#pragma once

#include <memory>

namespace Cygnet {

struct RendererState;

class Renderer {
public:
Renderer();
~Renderer();

void clear();
void draw();

private:
std::unique_ptr<RendererState> state_;
};

}

+ 11
- 0
libcygnet/include/cygnet/shaders.h View File

@@ -0,0 +1,11 @@
#pragma once

namespace Cygnet::Shaders {

extern const char *texturedQuadVx;
extern const char *texturedFr;

extern const char *coloredQuadVx;
extern const char *coloredFr;

}

+ 5
- 8
libcygnet/include/cygnet/util.h View File

@@ -6,22 +6,19 @@

namespace Cygnet {

using GlID = uint32_t;
using GlLoc = int32_t;

struct SDLError: public std::exception {
SDLError(std::string msg): message(std::move(msg)) {}
const char *what() const noexcept override { return message.c_str(); }
std::string message;

const char *what() const noexcept override {
return message.c_str();
}
};

struct GLError: public std::exception {
GLError(std::string msg): message(std::move(msg)) {}
const char *what() const noexcept override { return message.c_str(); }
std::string message;

const char *what() const noexcept override {
return message.c_str();
}
};

inline const char *glErrorString(int err) {

+ 100
- 0
libcygnet/src/Program.cc View File

@@ -0,0 +1,100 @@
#include "Program.h"

#include <SDL_opengles2.h>
#include <iostream>

#include "util.h"

namespace Cygnet {

GlShader::GlShader(Type type, const char *source) {
switch (type) {
case Type::VERTEX:
id_ = glCreateShader(GL_VERTEX_SHADER);
glCheck();
std::cerr << "Cygnet: Compiling vertex shader...\n";
break;

case Type::FRAGMENT:
id_ = glCreateShader(GL_FRAGMENT_SHADER);
glCheck();
std::cerr << "Cygnet: Compiling fragment shader...\n";
break;
}

glShaderSource(id_, 1, &source, NULL);
glCheck();
glCompileShader(id_);
glCheck();

char log[4096];
GLsizei length = 0;
glGetShaderInfoLog(id_, sizeof(log), &length, log);
glCheck();
if (length != 0) {
std::cerr << "Cygnet: Shader compile info (" << length << "):\n" << log << '\n';
}

GLint status = 0;
glGetShaderiv(id_, GL_COMPILE_STATUS, &status);
glCheck();
if (status == GL_FALSE) {
throw GlCompileError("GL shader compilation failed.");
}
}

GlShader::~GlShader() {
glDeleteShader(id_);
glCheck();
}

GlProgram::GlProgram() {
id_ = glCreateProgram();
glCheck();
}

GlProgram::~GlProgram() {
glDeleteProgram(id_);
glCheck();
}

void GlProgram::use() {
glUseProgram(id_);
glCheck();
}

void GlProgram::addShader(const GlShader &shader) {
glAttachShader(id_, shader.id());
glCheck();
}

GlLoc GlProgram::attribLoc(const char *name) {
return glGetAttribLocation(id_, name);
}

GlLoc GlProgram::uniformLoc(const char *name) {
return glGetUniformLocation(id_, name);
}

void GlProgram::link() {
std::cout << "Cygnet: Linking...\n";
glLinkProgram(id_);
glCheck();

char log[4096];
GLsizei length = 0;
glGetProgramInfoLog(id_, sizeof(log), &length, log);
glCheck();
if (length != 0) {
std::cerr << "Cygnet: Program link info:\n" << log << '\n';
}

GLint status = 0;
glGetProgramiv(id_, GL_LINK_STATUS, &status);
glCheck();
if (status == GL_FALSE) {
throw GlCompileError("GL program link failed.");
}
}

}

+ 38
- 0
libcygnet/src/Renderer.cc View File

@@ -0,0 +1,38 @@
#include "Renderer.h"

#include "shaders.h"
#include "Program.h"
#include "util.h"

namespace Cygnet {

struct TexturedQuad: public GlProgram {
using GlProgram::GlProgram;

GlLoc position = attribLoc("position");
GlLoc texCoord = attribLoc("texCoord");
GlLoc tex = uniformLoc("tex");
};

struct ColoredQuad: public GlProgram {
using GlProgram::GlProgram;

GlLoc position = attribLoc("position");
GlLoc color = uniformLoc("color");
};

struct RendererState {
GlVxShader texturedQuadVx{Shaders::texturedQuadVx};
GlFrShader texturedFr{Shaders::texturedFr};
GlVxShader coloredQuadVx{Shaders::texturedQuadVx};
GlFrShader coloredFr{Shaders::texturedFr};

TexturedQuad texturedQuad{texturedQuadVx, texturedFr};
ColoredQuad coloredQuad{coloredQuadVx, coloredFr};
};

Renderer::Renderer(): state_(std::make_unique<RendererState>()) {}

Renderer::~Renderer() = default;

}

+ 1
- 2
libcygnet/src/Window.cc View File

@@ -31,8 +31,7 @@ Window::Window(const char *name, int w, int h):
onResize(w, h);
}

Window::~Window() {
}
Window::~Window() = default;

void Window::makeCurrent() {
SDL_GL_MakeCurrent(state_->window, state_->glctx);

+ 43
- 0
libcygnet/src/shaders/basic.cc View File

@@ -0,0 +1,43 @@
#include "shaders.h"

namespace Cygnet::Shaders {

const char *texturedQuadVx = R"glsl(
uniform mat3 transform;
attribute vec2 position;
attribute vec2 texCoord;
varying vec2 v_texCoord;
void main() {
vec3 pos = transform * vec3(position, 0);
gl_Position = vec4(pos.x, pos.y, 0, 1);
v_texCoord = texCoord;
}
)glsl";

const char *texturedFr = R"glsl(
precision mediump float;
varying vec2 v_texCoord;
uniform sampler2D tex;
void main() {
gl_FragColor = texture2D(tex, v_texCoord);
}
)glsl";

const char *coloredQuadVx = R"glsl(
uniform mat3 transform;
attribute vec2 position;
void main() {
vec3 pos = transform * vec3(position, 0);
gl_Position = vec4(pos.x, pos.y, 0, 1);
}
)glsl";

const char *coloredFr = R"glsl(
precision mediump float;
uniform vec4 color;
void main() {
gl_FragColor = color;
}
)glsl";

}

+ 2
- 0
src/cygnet-test.cc View File

@@ -1,11 +1,13 @@
#include <cygnet/Context.h>
#include <cygnet/Window.h>
#include <cygnet/Renderer.h>

#include <SDL.h>

int main() {
Cygnet::Context ctx;
Cygnet::Window win("Cygnet Test", 640, 480);
Cygnet::Renderer rnd;

while (true) {
SDL_Event evt;

Loading…
Cancel
Save