239 lines
6.7 KiB
C++
239 lines
6.7 KiB
C++
#include <algorithm>
|
|
#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));
|
|
}
|