diff --git a/CMakeLists.txt b/CMakeLists.txt index ccb978b..9f5b8ab 100644 --- a/CMakeLists.txt +++ b/CMakeLists.txt @@ -1,7 +1,7 @@ cmake_minimum_required(VERSION 3.2) project(glTest) -set(CMAKE_CXX_FLAGS "${CMAKE_CXX_FLAGS} -std=c++11 -O3 -g") +set(CMAKE_CXX_FLAGS "${CMAKE_CXX_FLAGS} -std=c++11 -O0 -g") set(CMAKE_BUILD_TYPE DEBUG) set(CMAKE_RUNTIME_OUTPUT_DIRECTORY ${CMAKE_SOURCE_DIR}/bin) set(CMAKE_MODULE_PATH ${CMAKE_MODULE_PATH} "${CMAKE_SOURCE_DIR}/cmake/Modules/") diff --git a/src/Camera.cpp b/src/Camera.cpp index 7ae40d0..5c5ac35 100644 --- a/src/Camera.cpp +++ b/src/Camera.cpp @@ -1,10 +1,22 @@ #include "Camera.h" -#include +#include "OGL.h" +#include Camera::Camera() { - glm::vec3 eye(0.0f, 0.0f, 4.0f), at(0.0f, 0.0f, 0.0f), up(0.0f, 1.0f, 0.0f); - _view = glm::lookAt(eye, at, up); - _projection = glm::perspective(45.0f, 1.0f, 2.0f, -2.0f); + _viewDistance = 4.0f; + _eye = glm::vec3(0.0f, 0.0f, _viewDistance); + _at = glm::vec3(0.0f, 0.0f, 0.0f); + _up = glm::vec3(0.0f, 1.0f, 0.0f); + _view = glm::lookAt(_eye, _at, _up); + _projection = glm::perspective(45.0f, 1.0f, -2.0f, 2.0f); +} + +void Camera::init() { + ShaderProgram* sp = OGL::instance()->getCurShaderProgram(); + GLint view = glGetUniformLocation(*sp, "mView"); + glUniformMatrix4fv(view, 1, GL_FALSE, glm::value_ptr(_view)); + GLint projection = glGetUniformLocation(*sp, "mProjection"); + glUniformMatrix4fv(projection, 1, GL_FALSE, glm::value_ptr(_projection)); } Camera *Camera::instance() { @@ -12,9 +24,33 @@ Camera *Camera::instance() { return &camera; } -void Camera::storeUniformVars() const { -// GLint view = glGetUniformLocation(program, "mView"); -// glUniformMatrix4fv(view, 1, GL_FALSE, glm::value_ptr(mView)); -// GLint projection = glGetUniformLocation(program, "mProjection"); -// glUniformMatrix4fv(projection, 1, GL_FALSE, glm::value_ptr(mProjection)); +void Camera::updateView() { + _view = glm::lookAt(_eye, _at, _up); + ShaderProgram* sp = OGL::instance()->getCurShaderProgram(); + GLint view = glGetUniformLocation(*sp, "mView"); + glUniformMatrix4fv(view, 1, GL_FALSE, glm::value_ptr(_view)); +} + +void Camera::turnLeft(float angle) { + _up = glm::rotateY(_up, angle); + _eye = glm::rotateY(_eye, angle); + updateView(); +} + +void Camera::turnRight(float angle) { + _up = glm::rotateY(_up, -angle); + _eye = glm::rotateY(_eye, -angle); + updateView(); +} + +void Camera::turnUp(float angle) { + _up = glm::rotateX(_up, angle); + _eye = glm::rotateX(_eye, angle); + updateView(); +} + +void Camera::turnDown(float angle) { + _up = glm::rotateX(_up, -angle); + _eye = glm::rotateX(_eye, -angle); + updateView(); } diff --git a/src/Camera.h b/src/Camera.h index 2117476..4f6eae2 100644 --- a/src/Camera.h +++ b/src/Camera.h @@ -6,6 +6,8 @@ class Camera { private: + float _viewDistance; + glm::vec3 _eye, _at, _up; glm::mat4 _view; glm::mat4 _projection; @@ -13,10 +15,15 @@ private: Camera(); Camera(const Camera&) = delete; void operator=(const Camera&) = delete; - void storeUniformVars() const; + void updateView(); public: static Camera* instance(); + void init(); + void turnLeft(float angle); + void turnRight(float angle); + void turnUp(float angle); + void turnDown(float angle); }; diff --git a/src/GLApp.cpp b/src/GLApp.cpp deleted file mode 100644 index 2d6bd55..0000000 --- a/src/GLApp.cpp +++ /dev/null @@ -1,57 +0,0 @@ -#include -#include "GLApp.h" -#include - -bool wiredFlag = false; -void keyCallback(GLFWwindow* window, int key, int scancode, int action, int mods) -{ - if (key == GLFW_KEY_M && action == GLFW_PRESS) { - glPolygonMode(GL_FRONT_AND_BACK, wiredFlag ? GL_FILL : GL_LINE); - wiredFlag = !wiredFlag; - } -} - -GLApp::GLApp() { - -} - -GLApp *GLApp::instance() { - static GLApp app; - return &app; -} - -void GLApp::updateFpsCounter() const { - static double previous_seconds = glfwGetTime (); - static int frame_count; - double current_seconds = glfwGetTime (); - double elapsed_seconds = current_seconds - previous_seconds; - if (elapsed_seconds > 0.25) { - previous_seconds = current_seconds; - double fps = (double)frame_count / elapsed_seconds; - char tmp[128]; - sprintf (tmp, "opengl @ fps: %.2f", fps); - glfwSetWindowTitle (_window, tmp); - frame_count = 0; - } - frame_count++; -} - -void GLApp::init() { - glfwInit(); - glfwWindowHint(GLFW_CONTEXT_VERSION_MAJOR, 3); - glfwWindowHint(GLFW_CONTEXT_VERSION_MINOR, 3); - glfwWindowHint(GLFW_OPENGL_PROFILE, GLFW_OPENGL_CORE_PROFILE); - glfwWindowHint(GLFW_OPENGL_FORWARD_COMPAT, GL_TRUE); - glfwWindowHint(GLFW_RESIZABLE, GL_FALSE); - glfwWindowHint (GLFW_SAMPLES, 4); - - _window = glfwCreateWindow(1024, 1024, "OpenGL", nullptr, nullptr); // Windowed - glfwMakeContextCurrent(_window); - glfwSetKeyCallback(_window, keyCallback); - - glewExperimental = GL_TRUE; - GLenum err = glewInit(); - if(err != GLEW_OK) { - std::cout << "GLEW error: " << err << ": " << glewGetErrorString(err) << std::endl; - } -} diff --git a/src/GLApp.h b/src/GLApp.h deleted file mode 100644 index bbc44c6..0000000 --- a/src/GLApp.h +++ /dev/null @@ -1,22 +0,0 @@ -#ifndef GLTEST_GLAPP_H -#define GLTEST_GLAPP_H - -#include - -class GLApp { -private: - GLFWwindow* _window; - -private: - GLApp(); - GLApp(const GLApp&) = delete; - void operator=(const GLApp&) = delete; - void updateFpsCounter() const; - -public: - static GLApp* instance(); - void init(); -}; - - -#endif //GLTEST_GLAPP_H diff --git a/src/GLObjects/GLObject.cpp b/src/GLObjects/GLObject.cpp index a95d7fb..b725734 100644 --- a/src/GLObjects/GLObject.cpp +++ b/src/GLObjects/GLObject.cpp @@ -40,6 +40,7 @@ void GLObject::create() { } void GLObject::rotate(glm::vec3 angles) { + // FIXME: Change transformation code GLint world = glGetUniformLocation(*_sp, "mWorld"); _worldMatrix = glm::rotate(_worldMatrix, angles.x, glm::vec3(1.0f, 0.0f, 0.0f)); _worldMatrix = glm::rotate(_worldMatrix, angles.y, glm::vec3(0.0f, 1.0f, 0.0f)); @@ -48,6 +49,7 @@ void GLObject::rotate(glm::vec3 angles) { } void GLObject::scale(glm::vec3 scaleFactor) { + // FIXME: Change transformation code GLint world = glGetUniformLocation(*_sp, "mWorld"); _worldMatrix = glm::scale(_worldMatrix, scaleFactor); glUniformMatrix4fv(world, 1, GL_FALSE, glm::value_ptr(_worldMatrix)); @@ -58,7 +60,8 @@ void GLObject::translate(glm::vec3 point) { } void GLObject::draw() { - _worldMatrix = glm::mat4(); + GLint world = glGetUniformLocation(*_sp, "mWorld"); + glUniformMatrix4fv(world, 1, GL_FALSE, glm::value_ptr(_worldMatrix)); glBindVertexArray(_vao); glBindBuffer(GL_ELEMENT_ARRAY_BUFFER, _indexVbo); glDrawElements(GL_TRIANGLES, _trianglesCount, GL_UNSIGNED_INT, nullptr); diff --git a/src/GLObjects/GLObject.h b/src/GLObjects/GLObject.h index 4797718..c8dc888 100644 --- a/src/GLObjects/GLObject.h +++ b/src/GLObjects/GLObject.h @@ -26,7 +26,7 @@ public: void scale(glm::vec3 scaleFactor) override final; void translate(glm::vec3 point) override final; void draw() override final; - void update(); + void update() override final; protected: virtual std::tuple generateVertices() const = 0; diff --git a/src/GLObjects/IGLObject.h b/src/GLObjects/IGLObject.h index ba999bc..954ca62 100644 --- a/src/GLObjects/IGLObject.h +++ b/src/GLObjects/IGLObject.h @@ -9,6 +9,7 @@ struct IGLObject { virtual void scale(glm::vec3 scaleFactor) = 0; virtual void translate(glm::vec3 point) = 0; virtual void draw() = 0; + virtual void update() = 0; }; #endif //GLTEST_IGLOBJECT_H diff --git a/src/GLObjects/SpectralMesh.h b/src/GLObjects/SpectralMesh.h index cff0770..3bcb207 100644 --- a/src/GLObjects/SpectralMesh.h +++ b/src/GLObjects/SpectralMesh.h @@ -13,7 +13,7 @@ private: public: SpectralMesh(ShaderProgram* shader, std::size_t size); - ~SpectralMesh(); + virtual ~SpectralMesh(); void addLine(float* line); private: diff --git a/src/GLObjects/WaveMesh.cpp b/src/GLObjects/WaveMesh.cpp index 46265fc..8d5bac4 100644 --- a/src/GLObjects/WaveMesh.cpp +++ b/src/GLObjects/WaveMesh.cpp @@ -13,3 +13,7 @@ void WaveMesh::setShift(float shift) { WaveMesh::WaveMesh(ShaderProgram *shader, std::size_t size): Mesh(shader, size), _shift(0) { } + +WaveMesh::~WaveMesh() { + +} diff --git a/src/GLObjects/WaveMesh.h b/src/GLObjects/WaveMesh.h index 11e9dda..fe68c5f 100644 --- a/src/GLObjects/WaveMesh.h +++ b/src/GLObjects/WaveMesh.h @@ -9,6 +9,7 @@ private: public: WaveMesh(ShaderProgram* shader, std::size_t size); + virtual ~WaveMesh(); void setShift(float shift); private: diff --git a/src/OGL.cpp b/src/OGL.cpp new file mode 100644 index 0000000..1df73c3 --- /dev/null +++ b/src/OGL.cpp @@ -0,0 +1,112 @@ +#include "OGL.h" +#include "Camera.h" + +#include +#include + +bool wiredFlag = false; +void keyCallback(GLFWwindow* window, int key, int scancode, int action, int mods) +{ + const float turnStep = 0.1f; // in radians + + if (key == GLFW_KEY_M && action == GLFW_PRESS) { + glPolygonMode(GL_FRONT_AND_BACK, wiredFlag ? GL_FILL : GL_LINE); + wiredFlag = !wiredFlag; + } + + if(action == GLFW_PRESS || action == GLFW_REPEAT) { + switch (key) { + case GLFW_KEY_LEFT: + Camera::instance()->turnLeft(turnStep); + break; + case GLFW_KEY_RIGHT: + Camera::instance()->turnRight(turnStep); + break; + case GLFW_KEY_UP: + Camera::instance()->turnUp(turnStep); + break; + case GLFW_KEY_DOWN: + Camera::instance()->turnDown(turnStep); + break; + } + } +} + +OGL::OGL() { + +} + +OGL::~OGL() { + glfwTerminate(); +} + +OGL *OGL::instance() { + static OGL app; + return &app; +} + +void OGL::updateFpsCounter() const { + static double previous_seconds = glfwGetTime (); + static int frame_count; + double current_seconds = glfwGetTime (); + double elapsed_seconds = current_seconds - previous_seconds; + if (elapsed_seconds > 0.25) { + previous_seconds = current_seconds; + double fps = (double)frame_count / elapsed_seconds; + char tmp[128]; + sprintf (tmp, "opengl @ fps: %.2f", fps); + glfwSetWindowTitle (_window, tmp); + frame_count = 0; + } + frame_count++; +} + +void OGL::init() { + glfwInit(); + glfwWindowHint(GLFW_CONTEXT_VERSION_MAJOR, 3); + glfwWindowHint(GLFW_CONTEXT_VERSION_MINOR, 3); + glfwWindowHint(GLFW_OPENGL_PROFILE, GLFW_OPENGL_CORE_PROFILE); + glfwWindowHint(GLFW_OPENGL_FORWARD_COMPAT, GL_TRUE); + glfwWindowHint(GLFW_RESIZABLE, GL_FALSE); + glfwWindowHint (GLFW_SAMPLES, 4); + + _window = glfwCreateWindow(1024, 1024, "OpenGL", nullptr, nullptr); // Windowed + glfwMakeContextCurrent(_window); + glfwSetKeyCallback(_window, keyCallback); + + glewExperimental = GL_TRUE; + GLenum err = glewInit(); + if(err != GLEW_OK) { + std::string errMsg = std::string("GLEW init error: ") + (char*)glewGetErrorString(err); + throw new std::runtime_error(errMsg); + } +} + +void OGL::run() { + while(!glfwWindowShouldClose(_window)) { + updateFpsCounter(); + glClear (GL_COLOR_BUFFER_BIT | GL_DEPTH_BUFFER_BIT); + + for(IGLObject* obj: _glObjects) { + //obj->scale(glm::vec3(1.0f, 1.0f, 1.0f)); + obj->update(); + obj->draw(); + } + + glfwPollEvents(); + glfwSwapBuffers(_window); + } +} + +void OGL::addObject(IGLObject *object) { + _glObjects.push_back(object); +} + +ShaderProgram *OGL::getCurShaderProgram() { + return _curShaderProgram; +} + +void OGL::setCurShaderProgram(ShaderProgram *sp) { + _curShaderProgram = sp; + _curShaderProgram->use(); +} diff --git a/src/OGL.h b/src/OGL.h new file mode 100644 index 0000000..0121735 --- /dev/null +++ b/src/OGL.h @@ -0,0 +1,33 @@ +#ifndef GLTEST_GLAPP_H +#define GLTEST_GLAPP_H + +#include "GLObjects/IGLObject.h" +#include "Shaders/ShaderProgram.h" + +#include +#include + +class OGL { +private: + GLFWwindow* _window; + std::list _glObjects; + ShaderProgram* _curShaderProgram; + +private: + OGL(); + ~OGL(); + OGL(const OGL &) = delete; + void operator=(const OGL &) = delete; + void updateFpsCounter() const; + +public: + static OGL * instance(); + void init(); + void run(); + void addObject(IGLObject* object); + ShaderProgram* getCurShaderProgram(); + void setCurShaderProgram(ShaderProgram* sp); +}; + + +#endif //GLTEST_GLAPP_H diff --git a/src/main.cpp b/src/main.cpp index bf92764..a53fb69 100644 --- a/src/main.cpp +++ b/src/main.cpp @@ -2,76 +2,24 @@ #include "GLObjects/WaveMesh.h" #include "Audio/AudioPlayer.h" #include "GLObjects/SpectralMesh.h" - -#include -#include -#include +#include "OGL.h" +#include "Camera.h" #include #include #include -glm::vec3 eye(0.0f, 0.0f, 4.0f), at(0.0f, 0.0f, 0.0f), up(0.0f, 1.0f, 0.0f); -glm::mat4 mView = glm::lookAt(eye, at, up); -glm::mat4 mProjection = glm::perspective(45.0f, 1.0f, -2.0f, 2.0f); //glm::perspective(45.0f, 1.0f, 2.0f, -2.0f); -bool wired = false; - -void key_callback(GLFWwindow* window, int key, int scancode, int action, int mods) -{ - if (key == GLFW_KEY_M && action == GLFW_PRESS) { - glPolygonMode(GL_FRONT_AND_BACK, wired ? GL_FILL : GL_LINE); - wired = !wired; - } -} - -void _update_fps_counter (GLFWwindow* window) { - static double previous_seconds = glfwGetTime (); - static int frame_count; - double current_seconds = glfwGetTime (); - double elapsed_seconds = current_seconds - previous_seconds; - if (elapsed_seconds > 0.25) { - previous_seconds = current_seconds; - double fps = (double)frame_count / elapsed_seconds; - char tmp[128]; - sprintf (tmp, "opengl @ fps: %.2f", fps); - glfwSetWindowTitle (window, tmp); - frame_count = 0; - } - frame_count++; -} - int main() { - glfwInit(); - glfwWindowHint(GLFW_CONTEXT_VERSION_MAJOR, 3); - glfwWindowHint(GLFW_CONTEXT_VERSION_MINOR, 3); - glfwWindowHint(GLFW_OPENGL_PROFILE, GLFW_OPENGL_CORE_PROFILE); - glfwWindowHint(GLFW_OPENGL_FORWARD_COMPAT, GL_TRUE); - glfwWindowHint(GLFW_RESIZABLE, GL_FALSE); - glfwWindowHint (GLFW_SAMPLES, 4); - - GLFWwindow* window = glfwCreateWindow(1024, 1024, "OpenGL", nullptr, nullptr); // Windowed - glfwMakeContextCurrent(window); - glfwSetKeyCallback(window, key_callback); - - glewExperimental = GL_TRUE; - GLenum err = glewInit(); - if(err != GLEW_OK) { - std::cout << "GLEW error: " << err << ": " << glewGetErrorString(err) << std::endl; - } + OGL::instance()->init(); ShaderProgram program("../shaders/vertex.glsl", "../shaders/fragment.glsl"); - program.use(); - -// WaveMesh mesh(&program, 128); -// mesh.create(); + OGL::instance()->setCurShaderProgram(&program); SpectralMesh mesh(&program, 256); mesh.create(); + OGL::instance()->addObject(&mesh); - GLint view = glGetUniformLocation(program, "mView"); - glUniformMatrix4fv(view, 1, GL_FALSE, glm::value_ptr(mView)); - GLint projection = glGetUniformLocation(program, "mProjection"); - glUniformMatrix4fv(projection, 1, GL_FALSE, glm::value_ptr(mProjection)); + Camera::instance()->init(); // glPolygonMode(GL_FRONT_AND_BACK, GL_LINE); glDepthFunc(GL_LEQUAL); @@ -83,39 +31,5 @@ int main() { }); player.play(); - float azimuth = 0.0f, elevation = 0.0f, scale = 1.0f; - - while(!glfwWindowShouldClose(window)) { - _update_fps_counter (window); - glClear (GL_COLOR_BUFFER_BIT | GL_DEPTH_BUFFER_BIT); - - if(glfwGetKey(window, GLFW_KEY_LEFT) == GLFW_PRESS) { - azimuth -= 0.05f; - } else if(glfwGetKey(window, GLFW_KEY_RIGHT) == GLFW_PRESS) { - azimuth += 0.05f; - } else if(glfwGetKey(window, GLFW_KEY_UP) == GLFW_PRESS) { - elevation -= 0.05f; - } else if(glfwGetKey(window, GLFW_KEY_DOWN) == GLFW_PRESS) { - elevation += 0.05f; - } else if(glfwGetKey(window, GLFW_KEY_KP_ADD) == GLFW_PRESS) { - scale += 0.05f; - } else if(glfwGetKey(window, GLFW_KEY_KP_SUBTRACT) == GLFW_PRESS) { - scale -= 0.05f; - } - -// double time = glfwGetTime(); -// float shift = (float)fmod(time, 2*3.1415926); -// mesh.setShift(shift*2); - mesh.update(); - - - mesh.scale(glm::vec3(scale, scale, scale)); - mesh.rotate(glm::vec3(elevation, azimuth, 0)); - mesh.draw(); - - glfwPollEvents(); - glfwSwapBuffers(window); - } - - glfwTerminate(); + OGL::instance()->run(); } \ No newline at end of file