#include #include "MyGlWindow.h" glm::mat4x4 perspective(float fovy, float aspect, float near, float far) { float fovy2 = glm::tan(fovy / 2); glm::mat4x4 pmat{ { 1 / (aspect * fovy2), 0, 0, 0}, { 0, 1 / fovy2, 0, 0}, { 0, 0, -((far + near) / (far - near)), -1}, { 0, 0, -((2 * far * near) / (far - near)), 0} }; return pmat; } // Getting the view matrix glm::mat4x4 lookAt(glm::vec3 campos, glm::vec3 look, glm::vec3 up) { glm::vec3 ZCam(glm::normalize(campos - look)); glm::vec3 XCam(glm::normalize(glm::cross(up, ZCam))); glm::vec3 YCam(glm::normalize(glm::cross(ZCam, XCam))); glm::mat4x4 cam_mat{ {XCam.x, YCam.x, ZCam.x, 0}, {XCam.y, YCam.y, ZCam.y, 0}, {XCam.z, YCam.z, ZCam.z, 0}, {0, 0, 0 ,1} }; glm::mat4x4 norm_mat{ {1, 0, 0, 0}, {0, 1, 0, 0}, {0, 0, 1, 0}, {-campos.x, -campos.y, -campos.z, 1} }; return cam_mat * norm_mat; } MyGlWindow::MyGlWindow(int w, int h) : viewer(glm::vec3(5, 5, 5), glm::vec3(0, 0, 0), glm::vec3(0, 1, 0), 45.0f, (w / (float)h)), _floor(50, 16) { m_width = w; m_height = h; setup(); setupCubeBuffer(); } MyGlWindow::~MyGlWindow() { } void MyGlWindow::setBgColor(float bgColor[3]) { _bgColor[0] = bgColor[0]; _bgColor[1] = bgColor[1]; _bgColor[2] = bgColor[2]; } void MyGlWindow::setup() { _shaderProgram = new ShaderProgram(); _shaderProgram->initFromFiles("simple.vert", "simple.frag"); _static_drawables.emplace_back(new CheckeredFloor(50, 16)); _static_drawables.emplace_back(new WireCube()); _static_drawables.back()->addTranslation(glm::vec4(0, 1.01, 0, 0)); _static_drawables.emplace_back(new WireCube()); _static_drawables.back()->addTranslation(glm::vec4(0, 3.01, 0, 0)); _static_drawables.emplace_back(new WireCube()); _static_drawables.back()->addTranslation(glm::vec4(0, 5.01, 0, 0)); _static_drawables.emplace_back(new WireCube()); _static_drawables.back()->addTranslation(glm::vec4(0, 7.01, 0, 0)); _crane_boom.emplace_back(new WireCube()); _crane_boom.back()->addTranslation(glm::vec4(0, 9.01, 0, 0)); _crane_boom.emplace_back(new WireCube()); _crane_boom.back()->addTranslation(glm::vec4(-2, 9.01, 0, 0)); _crane_boom.emplace_back(new WireCube()); _crane_boom.back()->addTranslation(glm::vec4(2, 9.01, 0, 0)); _crane_boom.emplace_back(new WireCube()); _crane_boom.back()->addTranslation(glm::vec4(4, 9.01, 0, 0)); _crane_boom.emplace_back(new WireCube()); _crane_boom.back()->addTranslation(glm::vec4(6, 9.01, 0, 0)); _crane_boom.push_back(new ColorCube()); _crane_boom.back()->addTranslation(glm::vec4(8, 7.01, 0, 0)); _crane_boom.emplace_back(new WireCube()); _crane_boom.back()->addTranslation(glm::vec4(8, 9.01, 0, 0)); _crane_boom.emplace_back(new LineSegment()); _crane_boom.back()->addTranslation(glm::vec4(8, 8.01, 0, 0)); } void MyGlWindow::setupCubeBuffer() { } void MyGlWindow::setupRectBuffer() { GLuint vbo_cube_vertices; glGenVertexArrays(1, &_vaoHandle); glBindVertexArray(_vaoHandle); vertexAttr* verts = new vertexAttr[6]; verts[0].posX = -0.3f; verts[0].posY = 0.4f; verts[0].posZ = 0; verts[0].r = 1; verts[0].g = 0; verts[0].b = 0; verts[1].posX = -0.3f; verts[1].posY = -0.4f; verts[1].posZ = 0; verts[1].r = 0; verts[1].g = 1; verts[1].b = 0; verts[2].posX = 0.3f; verts[2].posY = -0.4f; verts[2].posZ = 0; verts[2].r = 0; verts[2].g = 0; verts[2].b = 1; verts[3].posX = 0.3f; verts[3].posY = -0.4f; verts[3].posZ = 0; verts[3].r = 0; verts[3].g = 0; verts[3].b = 1; verts[4].posX = 0.3f; verts[4].posY = 0.4f; verts[4].posZ = 0; verts[4].r = 0; verts[4].g = 1; verts[4].b = 0; verts[5].posX = -0.3f; verts[5].posY = 0.4f; verts[5].posZ = 0; verts[5].r = 1; verts[5].g = 0; verts[5].b = 0; glGenBuffers(1, &vbo_cube_vertices); glBindBuffer(GL_ARRAY_BUFFER, vbo_cube_vertices); glBufferData(GL_ARRAY_BUFFER, sizeof(vertexAttr) * 6, verts, GL_STATIC_DRAW); glVertexAttribPointer( 0, //attr number = 0 3, GL_FLOAT, GL_FALSE, sizeof(vertexAttr), (void*)0); glEnableVertexAttribArray(0); //attr number = 0 glVertexAttribPointer( 1, 3, GL_FLOAT, GL_FALSE, sizeof(vertexAttr), (void*)(sizeof(GLfloat) * 3)); glEnableVertexAttribArray(1); glBindVertexArray(0); } void MyGlWindow::setViewFromBox(glm::vec3 &eye, glm::vec3 &look, glm::vec3 &up) { glm::vec4 cube_base_position = { 8, 7.01, 0 , 1.0f}; Model model; cube_base_position.x = 7 - (floatValues["box_horizontal"] * 6); cube_base_position.y = 7 - (floatValues["box_vertical"] * 6); model.glPushMatrix(); model.glTranslate(-8, 2, 0); model.glRotate(floatValues["boom_rotation"], 0, -1, 0); model.glTranslate(8, -2, 0); eye = cube_base_position * model.getMatrix(); } void MyGlWindow::draw() { glClearColor(_bgColor[0], _bgColor[1], _bgColor[2], 1); glClear(GL_COLOR_BUFFER_BIT | GL_DEPTH_BUFFER_BIT); glViewport(0, 0, m_width, m_height); glEnable(GL_DEPTH_TEST); _shaderProgram->use(); glm::vec3 eye(viewer.getViewPoint().x, viewer.getViewPoint().y, viewer.getViewPoint().z); glm::vec3 look(viewer.getViewCenter().x, viewer.getViewCenter().y, viewer.getViewCenter().z); glm::vec3 up(viewer.getUpVector().x, viewer.getUpVector().y, viewer.getUpVector().z); if (view_from_box) setViewFromBox(eye, look, up); glm::mat4 view = lookAt(eye, look, up); //Calculate view matrix from paramters of m_viewer glm::mat4 projection = perspective(45.0f, m_width / m_height, 0.1f, 500.0f); _shaderProgram->addUniform("mvp"); for (ADrawable *drawable : _static_drawables) drawable->draw(_shaderProgram, projection * view); for (ADrawable *drawable : _crane_boom) { glm::vec4 t = drawable->translateToPivot(glm::vec3(0, 9.01, 0)); drawable->addRotation(glm::vec4(0, 1, 0, floatValues["boom_rotation"])); drawable->addTranslation(t); if (drawable->getType() == COLOR_CUBE) drawable->addTranslation(glm::vec4(floatValues["box_horizontal"] * -6.01, floatValues["box_vertical"] * -6.01, 0 ,0)); if (drawable->getType() == LINE_SEGMENT) { drawable->addTranslation(glm::vec4(floatValues["box_horizontal"] * -6.01 , floatValues["box_vertical"] * -4.01, 0, 0)); drawable->addScaling(glm::vec4(0, floatValues["box_vertical"] * 4.01, 0, 0)); } if (!view_from_box || (drawable->getType() != COLOR_CUBE && drawable->getType() != LINE_SEGMENT)) drawable->draw(_shaderProgram, projection * view); if (drawable->getType() == COLOR_CUBE) drawable->removeLastTransformations(1); else if (drawable->getType() == LINE_SEGMENT) drawable->removeLastTransformations(2); drawable->removeLastTransformations(3); } _shaderProgram->disable(); } void MyGlWindow::AddDrawable(ADrawable *d) { _static_drawables.push_back(d); } void MyGlWindow::resize(int w, int h) { m_width = w; m_height = h; viewer.setAspectRatio(w / float(h)); }