You can not select more than 25 topics Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.
OpenGLTemplate/Models/main.cpp

157 lines
5.7 KiB

#include <GL/glew.h>
#include <GLFW/glfw3.h>
#include "utils.h"
#include <algorithm>
#include <vector>
#include <glm/glm.hpp>
#include <glm/gtc/type_ptr.hpp>
#include <glm/gtc/matrix_transform.hpp>
#include <array>
#include <stack>
#define numVAOs 1
#define numVBOs 2
GLuint renderingProgram;
GLuint vao[numVAOs];
GLuint vbo[numVBOs];
glm::vec3 camera;
GLuint mvLoc,projLoc;
int width, height;
float aspect;
glm::mat4 mMat, pMat, vMat, mvMat;
std::stack<glm::mat4>transforms;
void setupVertices(void) { // 36 vertices, 12 triangles, makes 2x2x2 cube placed at origin
float cubePositions[108] = {
-1.0f, 1.0f, -1.0f, -1.0f, -1.0f, -1.0f, 1.0f, -1.0f, -1.0f,
1.0f, -1.0f, -1.0f, 1.0f, 1.0f, -1.0f, -1.0f, 1.0f, -1.0f,
1.0f, -1.0f, -1.0f, 1.0f, -1.0f, 1.0f, 1.0f, 1.0f, -1.0f,
1.0f, -1.0f, 1.0f, 1.0f, 1.0f, 1.0f, 1.0f, 1.0f, -1.0f,
1.0f, -1.0f, 1.0f, -1.0f, -1.0f, 1.0f, 1.0f, 1.0f, 1.0f,
-1.0f, -1.0f, 1.0f, -1.0f, 1.0f, 1.0f, 1.0f, 1.0f, 1.0f,
-1.0f, -1.0f, 1.0f, -1.0f, -1.0f, -1.0f, -1.0f, 1.0f, 1.0f,
-1.0f, -1.0f, -1.0f, -1.0f, 1.0f, -1.0f, -1.0f, 1.0f, 1.0f,
-1.0f, -1.0f, 1.0f, 1.0f, -1.0f, 1.0f, 1.0f, -1.0f, -1.0f,
1.0f, -1.0f, -1.0f, -1.0f, -1.0f, -1.0f, -1.0f, -1.0f, 1.0f,
-1.0f, 1.0f, -1.0f, 1.0f, 1.0f, -1.0f, 1.0f, 1.0f, 1.0f,
1.0f, 1.0f, 1.0f, -1.0f, 1.0f, 1.0f, -1.0f, 1.0f, -1.0f
};
float pyramidPositions[54]={
-1.0f, -1.0f, 1.0f, 1.0f, - 1.0f, 1.0f, 0.0f, 1.0f, 0.0f,
1.0f, -1.0f, 1.0f, 1.0f, -1.0f, -1.0f, 0.0f, 1.0f, 0.0f,
1.0f, -1.0f, -1.0f, -1.0f, -1.0f, -1.0f, 0.0f, 1.0f, 0.0f,
-1.0f, -1.0f, - 1.0f, -1.0f, -1.0f, 1.0f, 0.0f, 1.0f, 0.0f,
-1.0f, -1.0f, - 1.0f, 1.0f, - 1.0f, 1.0f, -1.0f, -1.0f, 1.0f,
1.0f, -1.0f, 1.0f, -1.0f, -1.0f, -1.0f, 1.0f, -1.0f, -1.0f
};
glGenVertexArrays(1, vao);
glBindVertexArray(vao[0]);
glGenBuffers(numVBOs, vbo);
glBindBuffer(GL_ARRAY_BUFFER, vbo[0]);
glBufferData(GL_ARRAY_BUFFER, sizeof(cubePositions), cubePositions, GL_STATIC_DRAW);
glBindBuffer(GL_ARRAY_BUFFER, vbo[1]);
glBufferData(GL_ARRAY_BUFFER, sizeof(pyramidPositions), pyramidPositions, GL_STATIC_DRAW);
}
void init(GLFWwindow* window) {
renderingProgram=utils::createShaderProgram("vertShader.glsl","fragShader.glsl");
camera={0.0f,0.0f,-12.0f};
setupVertices();
}
double lastTime=0;
void DrawCube(){
glUniformMatrix4fv(mvLoc,1,GL_FALSE,glm::value_ptr(mMat));
glUniformMatrix4fv(projLoc,1,GL_FALSE,glm::value_ptr(pMat));
glBindBuffer(GL_ARRAY_BUFFER,vbo[0]);
glVertexAttribPointer(0,3,GL_FLOAT,GL_FALSE,0,0);
glDrawArrays(GL_TRIANGLES,0,36);
}
void DrawSquarePyramid(){
glUniformMatrix4fv(mvLoc,1,GL_FALSE,glm::value_ptr(mMat));
glUniformMatrix4fv(projLoc,1,GL_FALSE,glm::value_ptr(pMat));
glBindBuffer(GL_ARRAY_BUFFER,vbo[1]);
glVertexAttribPointer(0,3,GL_FLOAT,GL_FALSE,0,0);
glDrawArrays(GL_TRIANGLES,0,18);
}
void display(GLFWwindow* window, double currentTime) {
double elapsedTime=currentTime-lastTime;
lastTime=currentTime;
glClear(GL_DEPTH_BUFFER_BIT);
glClearColor(0,0,0.2,1);
glClear(GL_COLOR_BUFFER_BIT);
glUseProgram(renderingProgram);
glEnable(GL_DEPTH_TEST);
glDepthFunc(GL_LEQUAL);
glEnableVertexAttribArray(0);
mvLoc=glGetUniformLocation(renderingProgram,"mv_matrix");
projLoc=glGetUniformLocation(renderingProgram,"proj_matrix");
glfwGetFramebufferSize(window,&width,&height);
aspect=(float)width/(float)height;
pMat=glm::perspective(utils::degToRad(60),aspect,0.1f,1000.f);
vMat=glm::translate(glm::mat4(1.0f),glm::vec3{camera.x,camera.y,camera.z});
transforms.push(vMat);
mMat=glm::translate(transforms.top(),{0.f,0.f,0.f});
transforms.push(mMat);
mMat=glm::rotate(mMat,float(utils::degToRad(90)*currentTime),{0.f,1.f,0.f});
mMat=glm::rotate(mMat,float(utils::degToRad(12)),{0.f,0.f,1.f});
DrawSquarePyramid();
mMat=glm::translate(transforms.top(),{0.f,0.f,0.f});
mMat=glm::rotate(mMat,float(utils::degToRad(90)*currentTime),{0.f,1.f,0.f});
mMat=glm::rotate(mMat,float(utils::degToRad(192)),{0.f,0.f,1.f});
mMat=glm::translate(mMat,{0.f,2.f,0.f});
mMat=glm::rotate(mMat,float(utils::degToRad(270)),{0.f,1.f,0.f});
DrawSquarePyramid();
mMat=glm::translate(transforms.top(),{sin(currentTime*0.5)*6,sin(currentTime*0.5)*0.8-1,cos(currentTime*0.5)*6});
transforms.push(mMat);
mMat=glm::rotate(mMat,float(utils::degToRad(24)-28),{0,0,1});
mMat=glm::rotate(mMat,float(utils::degToRad(24)*currentTime+28),{0,1,0});
DrawCube();
mMat=glm::rotate(transforms.top(),utils::degToRad(90),{1,0,0});
mMat=glm::translate(mMat,{sin(currentTime*3)*3,0,cos(currentTime*3)*3});
mMat=glm::scale(mMat,{0.3,0.3,0.3});
mMat=glm::rotate(mMat,float(-utils::degToRad(220)*currentTime+4),{0,1,0});
DrawCube();
mMat=glm::rotate(transforms.top(),utils::degToRad(90),{1,1,0});
mMat=glm::translate(mMat,{sin(currentTime*3)*3,0,cos(currentTime*3)*3});
mMat=glm::scale(mMat,{0.3,0.3,0.3});
mMat=glm::rotate(mMat,float(utils::degToRad(120)*currentTime),{0,1,0});
DrawCube();
}
int main(void) {
if (!glfwInit()) { exit(EXIT_FAILURE); }
glfwWindowHint(GLFW_CONTEXT_VERSION_MAJOR, 4);
glfwWindowHint(GLFW_CONTEXT_VERSION_MINOR, 3);
GLFWwindow* window = glfwCreateWindow(1920, 1080, "Hello Cubes!", NULL, NULL);
glfwMakeContextCurrent(window);
if (glewInit() != GLEW_OK) { exit(EXIT_FAILURE); }
glfwSwapInterval(1);
init(window);
while (!glfwWindowShouldClose(window)) {
display(window,glfwGetTime());
glfwSwapBuffers(window);
glfwPollEvents();
}
glfwDestroyWindow(window);
glfwTerminate();
exit(EXIT_SUCCESS);
}