215 lines
6.8 KiB
C++
215 lines
6.8 KiB
C++
#include <glad/glad.h>
|
|
#include <GLFW/glfw3.h>
|
|
#include <iostream>
|
|
#include <stb_image.h>
|
|
#include <glm/glm.hpp>
|
|
#include <glm/gtc/matrix_transform.hpp>
|
|
#include <glm/gtc/type_ptr.hpp>
|
|
#include "Shader.h"
|
|
#include "Camera.h"
|
|
#include "Model.h"
|
|
|
|
#define TEXTURES_DIR "../../../../textures/"
|
|
#define MODELS_DIR "../../../../models/"
|
|
#define SHADERS_DIR "../src/shaders/"
|
|
|
|
using namespace std;
|
|
typedef unsigned int uint;
|
|
|
|
// Global Constants
|
|
// ...
|
|
// Global Variables
|
|
GLFWwindow* window;
|
|
int WINDOW_WIDTH = 800;
|
|
int WINDOW_HEIGHT = 600;
|
|
Camera myCamera(glm::vec3(0.0f, 0.0f, 3.0f));
|
|
float deltaTime = 0.0f;
|
|
float lastFrame = 0.0f;
|
|
float lastX = 400;
|
|
float lastY = 300;
|
|
bool firstmouse = true;
|
|
glm::vec3 lightPos(1.2f, 1.0f, 2.0f);
|
|
glm::vec3 lightColor(1.0f, 1.0f, 1.0f);
|
|
|
|
uint8_t init(void);
|
|
void framebuffersize_callback(GLFWwindow* window, int width, int height);
|
|
void mouse_callback(GLFWwindow* window, double xpos, double ypos);
|
|
void scroll_callback(GLFWwindow* window, double xoffset, double yoffset);
|
|
void proccessInput(GLFWwindow* window);
|
|
unsigned int load_texture(const char* path, bool flip = true);
|
|
|
|
int main(int argc, char** argv)
|
|
{
|
|
if (init() != 0)
|
|
return -1;
|
|
|
|
Shader lightingShader(SHADERS_DIR "glmlShader.vert", SHADERS_DIR "glmlShader.frag");
|
|
|
|
stbi_set_flip_vertically_on_load(1);
|
|
glml::Model backpack(MODELS_DIR "backpack/backpack.obj");
|
|
|
|
glEnable(GL_DEPTH_TEST);
|
|
/* ------------------ MAIN loop ------------------ */
|
|
while (!glfwWindowShouldClose(window)) {
|
|
float currentFrame = glfwGetTime();
|
|
deltaTime = currentFrame - lastFrame; // cas jak dlouho trval posledni frame
|
|
lastFrame = currentFrame; // cas kdy zacal tento frame
|
|
// input ...
|
|
proccessInput(window);
|
|
|
|
// rendering commands here ...
|
|
glClearColor(0.0f, 0.0f, 0.0f, 1.0f);
|
|
glClear(GL_COLOR_BUFFER_BIT | GL_DEPTH_BUFFER_BIT);
|
|
|
|
lightingShader.Use();
|
|
// lightingShader.setVec3("light.position", lightPos);
|
|
|
|
glm::mat4 view = myCamera.getViewMatrix();
|
|
glm::mat4 projection(1.0f);
|
|
projection = glm::perspective(glm::radians(myCamera.FOV), (float)WINDOW_WIDTH / WINDOW_HEIGHT, 0.1f, 100.0f);
|
|
glm::mat4 model(1.0f);
|
|
glm::mat3 normalMatrix = glm::transpose(glm::inverse(model));
|
|
|
|
lightingShader.setMat4("view", view);
|
|
lightingShader.setMat4("projection", projection);
|
|
lightingShader.setMat4("model", model);
|
|
lightingShader.setMat3("normalMatrix", normalMatrix);
|
|
|
|
glm::vec3 lightColor = glm::vec3(1.0f);
|
|
glm::vec3 lightPos = glm::vec3(-1.13f, 2.0f, 2.0f);
|
|
|
|
lightingShader.setVec3("pointLights[0].position", lightPos);
|
|
// lightingShader.setVec3("spotLight.direction", myCamera.Front);
|
|
lightingShader.setVec3("pointLights[0].ambient_intensity", glm::vec3(0.1f));
|
|
lightingShader.setVec3("pointLights[0].diffuse_intensity", lightColor * glm::vec3(0.5f));
|
|
lightingShader.setVec3("pointLights[0].specular_intensity", lightColor * glm::vec3(1.0f));
|
|
lightingShader.setFloat("pointLights[0].constant", 1.0f);
|
|
lightingShader.setFloat("pointLights[0].linear", 0.07f);
|
|
lightingShader.setFloat("pointLights[0].quadratic", 0.032f);
|
|
// lightingShader.setFloat("spotLight.cutOff", glm::cos(glm::radians(12.5f)));
|
|
// lightingShader.setFloat("spotLight.outerCutOff", glm::cos(glm::radians(17.5f)));
|
|
|
|
lightingShader.setVec3("viewPos", myCamera.Position);
|
|
lightingShader.setFloat("material.shininess", 32.0f);
|
|
|
|
backpack.Draw(lightingShader);
|
|
|
|
// check and calls events and swap the buffers
|
|
glfwSwapBuffers(window);
|
|
glfwPollEvents();
|
|
}
|
|
|
|
glfwTerminate();
|
|
|
|
return 0;
|
|
}
|
|
|
|
uint8_t init(void) {
|
|
// init of glfw window
|
|
glfwInit();
|
|
glfwWindowHint(GLFW_CONTEXT_VERSION_MAJOR, 3);
|
|
glfwWindowHint(GLFW_CONTEXT_VERSION_MINOR, 3);
|
|
glfwWindowHint(GLFW_OPENGL_PROFILE, GLFW_OPENGL_CORE_PROFILE);
|
|
window = glfwCreateWindow(WINDOW_WIDTH, WINDOW_HEIGHT, "6. Multiple Lights", NULL, NULL);
|
|
if (window == NULL) {
|
|
cerr << "Failed to create glfw window" << endl;
|
|
glfwTerminate();
|
|
return 1;
|
|
}
|
|
glfwMakeContextCurrent(window);
|
|
glfwSetInputMode(window, GLFW_CURSOR, GLFW_CURSOR_DISABLED);
|
|
|
|
// init of GLAD
|
|
if (!gladLoadGLLoader((GLADloadproc)glfwGetProcAddress)) {
|
|
cerr << "Failed to initialize GLAD" << endl;
|
|
}
|
|
|
|
glfwSetFramebufferSizeCallback(window, framebuffersize_callback);
|
|
glfwSetCursorPosCallback(window, mouse_callback);
|
|
glfwSetScrollCallback(window, scroll_callback);
|
|
return 0;
|
|
}
|
|
void framebuffersize_callback(GLFWwindow* window, int width, int height)
|
|
{
|
|
glViewport(0, 0, width, height);
|
|
WINDOW_HEIGHT = height;
|
|
WINDOW_WIDTH = width;
|
|
}
|
|
void proccessInput(GLFWwindow* window)
|
|
{
|
|
if (glfwGetKey(window, GLFW_KEY_ESCAPE) == GLFW_PRESS)
|
|
glfwSetWindowShouldClose(window, true);
|
|
if (glfwGetKey(window, GLFW_KEY_F1) == GLFW_PRESS)
|
|
glPolygonMode(GL_FRONT_AND_BACK, GL_FILL);
|
|
if (glfwGetKey(window, GLFW_KEY_F2) == GLFW_PRESS)
|
|
glPolygonMode(GL_FRONT_AND_BACK, GL_LINE);
|
|
/* -------------------- Movement -------------------- */
|
|
if (glfwGetKey(window, GLFW_KEY_W) == GLFW_PRESS)
|
|
myCamera.ProccessKeyboard(CAM_FORWARD, deltaTime);
|
|
if (glfwGetKey(window, GLFW_KEY_S) == GLFW_PRESS)
|
|
myCamera.ProccessKeyboard(CAM_BACKWARD, deltaTime);
|
|
if (glfwGetKey(window, GLFW_KEY_D) == GLFW_PRESS)
|
|
myCamera.ProccessKeyboard(CAM_RIGHT, deltaTime);
|
|
if (glfwGetKey(window, GLFW_KEY_A) == GLFW_PRESS)
|
|
myCamera.ProccessKeyboard(CAM_LEFT, deltaTime);
|
|
if (glfwGetKey(window, GLFW_KEY_LEFT_SHIFT) == GLFW_PRESS)
|
|
myCamera.ProccessKeyboard(CAM_DOWN, deltaTime);
|
|
if (glfwGetKey(window, GLFW_KEY_SPACE) == GLFW_PRESS)
|
|
myCamera.ProccessKeyboard(CAM_UP, deltaTime);
|
|
|
|
}
|
|
void mouse_callback(GLFWwindow* window, double xpos, double ypos)
|
|
{
|
|
if (firstmouse) {
|
|
lastX = xpos;
|
|
lastY = ypos;
|
|
firstmouse = false;
|
|
}
|
|
|
|
float xoffset = xpos - lastX;
|
|
float yoffset = lastY - ypos;
|
|
lastX = xpos;
|
|
lastY = ypos;
|
|
|
|
myCamera.ProccessMouse(xoffset, yoffset);
|
|
}
|
|
void scroll_callback(GLFWwindow* window, double xoffset, double yoffset)
|
|
{
|
|
myCamera.ProccessScroll(yoffset);
|
|
}
|
|
unsigned int load_texture(const char* path, bool flip)
|
|
{
|
|
unsigned int texture = 0;
|
|
int width, height, nrChannels, format;
|
|
stbi_set_flip_vertically_on_load(flip);
|
|
unsigned char* data = stbi_load(path, &width, &height, &nrChannels, 0); // load image to the array of bytes (char = 1 byte)
|
|
|
|
switch (nrChannels)
|
|
{
|
|
case 4: format = GL_RGBA; break;
|
|
case 3: format = GL_RGB; break;
|
|
case 2: format = GL_RED; break;
|
|
default: format = GL_RGB; break;
|
|
}
|
|
|
|
if (data) // data != NULL
|
|
{
|
|
glGenTextures(1, &texture);
|
|
glBindTexture(GL_TEXTURE_2D, texture);
|
|
|
|
glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_WRAP_S, GL_REPEAT);
|
|
glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_WRAP_T, GL_REPEAT);
|
|
glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MIN_FILTER, GL_LINEAR_MIPMAP_LINEAR);
|
|
glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MAG_FILTER, GL_LINEAR);
|
|
|
|
glTexImage2D(GL_TEXTURE_2D, 0, GL_RGB, width, height, 0, format, GL_UNSIGNED_BYTE, data); // generates texture
|
|
glGenerateMipmap(GL_TEXTURE_2D);
|
|
}
|
|
else {
|
|
cerr << "Could not load texture '" << path << "'\n";
|
|
}
|
|
stbi_image_free(data);
|
|
|
|
return texture;
|
|
}
|