Clean up some types here and there

This commit is contained in:
Peder Bergebakken Sundt 2019-03-15 16:34:17 +01:00
parent e00637d46d
commit 88376587e5
8 changed files with 153 additions and 144 deletions

View File

@ -1,23 +1,26 @@
#include <chrono>
#include <GLFW/glfw3.h>
#include <glad/glad.h>
#include <SFML/Audio/SoundBuffer.hpp>
#include <utilities/shader.hpp>
#include <glm/vec3.hpp>
#include <iostream>
#include <utilities/timeutils.h>
#include <utilities/mesh.h>
#include <utilities/shapes.h>
#include <utilities/glutils.h>
#include <utilities/glfont.h>
#include <utilities/imageLoader.hpp>
#include <SFML/Audio/Sound.hpp>
#include <glm/gtc/matrix_transform.hpp>
#include <glm/gtc/type_ptr.hpp>
#include <string>
#include "gamelogic.h" #include "gamelogic.h"
#include "sceneGraph.hpp" #include "sceneGraph.hpp"
#include <GLFW/glfw3.h>
#include <SFML/Audio/Sound.hpp>
#include <SFML/Audio/SoundBuffer.hpp>
#include <chrono>
#include <glad/glad.h>
#include <glm/gtc/matrix_transform.hpp>
#include <glm/gtc/type_ptr.hpp>
#include <glm/vec3.hpp>
#include <iostream>
#include <string>
#include <utilities/glfont.h>
#include <utilities/glutils.h>
#include <utilities/imageLoader.hpp>
#include <utilities/mesh.h>
#include <utilities/shader.hpp>
#include <utilities/shapes.h>
#include <utilities/timeutils.h>
using glm::vec3;
using glm::mat4;
typedef unsigned int uint;
enum KeyFrameAction { enum KeyFrameAction {
BOTTOM, TOP BOTTOM, TOP
@ -28,8 +31,8 @@ enum KeyFrameAction {
double padPositionX = 0; double padPositionX = 0;
double padPositionY = 0; double padPositionY = 0;
unsigned int currentKeyFrame = 0; uint currentKeyFrame = 0;
unsigned int previousKeyFrame = 0; uint previousKeyFrame = 0;
SceneNode* rootNode; SceneNode* rootNode;
SceneNode* boxNode; SceneNode* boxNode;
@ -43,15 +46,15 @@ SceneNode* lightNode[3];
double ballRadius = 3.0f; double ballRadius = 3.0f;
// These are heap allocated, because they should not be initialised at the start of the program // These are heap allocated, because they should not be initialised at the start of the program
sf::Sound* sound;
sf::SoundBuffer* buffer; sf::SoundBuffer* buffer;
Gloom::Shader* shader; Gloom::Shader* shader;
sf::Sound* sound;
const glm::vec3 boxDimensions(180, 90, 50); const vec3 boxDimensions(180, 90, 50);
const glm::vec3 padDimensions(30, 3, 40); const vec3 padDimensions(30, 3, 40);
glm::vec3 ballPosition(0, ballRadius + padDimensions.y, boxDimensions.z / 2); vec3 ballPosition(0, ballRadius + padDimensions.y, boxDimensions.z / 2);
glm::vec3 ballDirection(1, 1, 0.02f); vec3 ballDirection(1, 1, 0.02f);
const float BallVerticalTravelDistance = boxDimensions.y - 2.0 * ballRadius - padDimensions.y; const float BallVerticalTravelDistance = boxDimensions.y - 2.0 * ballRadius - padDimensions.y;
@ -114,18 +117,18 @@ void initGame(GLFWwindow* window, CommandLineOptions gameOptions) {
Mesh pad = generateBox(padDimensions.x, padDimensions.y, padDimensions.z, false); Mesh pad = generateBox(padDimensions.x, padDimensions.y, padDimensions.z, false);
Mesh sphere = generateSphere(1.0, 40, 40); Mesh sphere = generateSphere(1.0, 40, 40);
unsigned int ballVAO = generateBuffer(sphere); uint ballVAO = generateBuffer(sphere);
unsigned int boxVAO = generateBuffer(box, true); uint boxVAO = generateBuffer(box, true);
unsigned int padVAO = generateBuffer(pad); uint padVAO = generateBuffer(pad);
// textures // textures
t_charmap = loadPNGFile("../res/textures/charmap.png"); t_charmap = loadPNGFile("../res/textures/charmap.png");
t_cobble_diff = loadPNGFile("../res/textures/cobble_diff.png"); t_cobble_diff = loadPNGFile("../res/textures/cobble_diff.png");
t_cobble_normal = loadPNGFile("../res/textures/cobble_normal.png"); t_cobble_normal = loadPNGFile("../res/textures/cobble_normal.png");
unsigned int t_charmapID = generateTexture(t_charmap); uint t_charmapID = generateTexture(t_charmap);
unsigned int t_cobble_diffID = generateTexture(t_cobble_diff); uint t_cobble_diffID = generateTexture(t_cobble_diff);
unsigned int t_cobble_normalID = generateTexture(t_cobble_normal); uint t_cobble_normalID = generateTexture(t_cobble_normal);
rootNode = createSceneNode(); rootNode = createSceneNode();
boxNode = createSceneNode(NORMAL_TEXTURED_GEOMETRY); boxNode = createSceneNode(NORMAL_TEXTURED_GEOMETRY);
@ -172,8 +175,8 @@ void initGame(GLFWwindow* window, CommandLineOptions gameOptions) {
// hud // hud
Mesh hello_world = generateTextGeometryBuffer("Skjer'a bagera?", 1.3, 2); Mesh hello_world = generateTextGeometryBuffer("Skjer'a bagera?", 1.3, 2);
textNode->position = glm::vec3(-1.0, 0.0, 0.0); textNode->position = vec3(-1.0, 0.0, 0.0);
textNode->rotation = glm::vec3(0.0, 0.0, 0.0); textNode->rotation = vec3(0.0, 0.0, 0.0);
textNode->vertexArrayObjectID = generateBuffer(hello_world); textNode->vertexArrayObjectID = generateBuffer(hello_world);
textNode->VAOIndexCount = hello_world.indices.size(); textNode->VAOIndexCount = hello_world.indices.size();
textNode->diffuseTextureID = t_charmapID; textNode->diffuseTextureID = t_charmapID;
@ -186,37 +189,37 @@ void initGame(GLFWwindow* window, CommandLineOptions gameOptions) {
std::cout << "Ready. Click to start!" << std::endl; std::cout << "Ready. Click to start!" << std::endl;
} }
void updateNodeTransformations(SceneNode* node, glm::mat4 transformationThusFar, glm::mat4 V, glm::mat4 P) { void updateNodeTransformations(SceneNode* node, mat4 transformationThusFar, mat4 V, mat4 P) {
glm::mat4 transformationMatrix(1.0); mat4 transformationMatrix(1.0);
switch(node->nodeType) { switch(node->nodeType) {
case HUD: case HUD:
// We orthographic now, bitches! // We orthographic now, bitches!
// set orthographic VP // set orthographic VP
V = glm::mat4(1.0); V = mat4(1.0);
P = glm::ortho(-float(windowWidth) / float(windowHeight), float(windowWidth) / float(windowHeight), -1.0f, 1.0f);//, -10.0f, 120.0f); P = glm::ortho(-float(windowWidth) / float(windowHeight), float(windowWidth) / float(windowHeight), -1.0f, 1.0f);//, -10.0f, 120.0f);
break; break;
case NORMAL_TEXTURED_GEOMETRY: case NORMAL_TEXTURED_GEOMETRY:
case TEXTURED_GEOMETRY: case TEXTURED_GEOMETRY:
case GEOMETRY: case GEOMETRY:
transformationMatrix = transformationMatrix =
glm::translate(glm::mat4(1.0), node->position) glm::translate(mat4(1.0), node->position)
* glm::translate(glm::mat4(1.0), node->referencePoint) * glm::translate(mat4(1.0), node->referencePoint)
* glm::rotate(glm::mat4(1.0), node->rotation.z, glm::vec3(0,0,1)) * glm::rotate(mat4(1.0), node->rotation.z, vec3(0,0,1))
* glm::rotate(glm::mat4(1.0), node->rotation.y, glm::vec3(0,1,0)) * glm::rotate(mat4(1.0), node->rotation.y, vec3(0,1,0))
* glm::rotate(glm::mat4(1.0), node->rotation.x, glm::vec3(1,0,0)) * glm::rotate(mat4(1.0), node->rotation.x, vec3(1,0,0))
* glm::translate(glm::mat4(1.0), -node->referencePoint) * glm::translate(mat4(1.0), -node->referencePoint)
* glm::scale(glm::mat4(1.0), node->scale); * glm::scale(mat4(1.0), node->scale);
break; break;
case POINT_LIGHT: case POINT_LIGHT:
case SPOT_LIGHT: case SPOT_LIGHT:
transformationMatrix = transformationMatrix =
glm::translate(glm::mat4(1.0), node->position); glm::translate(mat4(1.0), node->position);
break; break;
} }
glm::mat4 M = transformationThusFar * transformationMatrix; mat4 M = transformationThusFar * transformationMatrix;
glm::mat4 MV = V*M; mat4 MV = V*M;
node->MV = MV; node->MV = MV;
node->MVP = P*MV; node->MVP = P*MV;
@ -228,7 +231,7 @@ void updateNodeTransformations(SceneNode* node, glm::mat4 transformationThusFar,
if (node->targeted_by != nullptr) { if (node->targeted_by != nullptr) {
assert(node->targeted_by->nodeType == SPOT_LIGHT); assert(node->targeted_by->nodeType == SPOT_LIGHT);
node->targeted_by->rotation = glm::vec3(MV*glm::vec4(node->position, 1.0)); node->targeted_by->rotation = vec3(MV*glm::vec4(node->position, 1.0));
//std::cout << node->targeted_by->rotation[0] //std::cout << node->targeted_by->rotation[0]
// << " " << node->targeted_by->rotation[1] // << " " << node->targeted_by->rotation[1]
@ -239,7 +242,6 @@ void updateNodeTransformations(SceneNode* node, glm::mat4 transformationThusFar,
void updateFrame(GLFWwindow* window) { void updateFrame(GLFWwindow* window) {
glfwSetInputMode(window, GLFW_CURSOR, GLFW_CURSOR_DISABLED); glfwSetInputMode(window, GLFW_CURSOR, GLFW_CURSOR_DISABLED);
double timeDelta = getTimeDeltaSeconds(); double timeDelta = getTimeDeltaSeconds();
if(!hasStarted) { if(!hasStarted) {
@ -271,7 +273,7 @@ void updateFrame(GLFWwindow* window) {
ballRadius = 999999; ballRadius = 999999;
} }
} else { } else {
for (unsigned int i = currentKeyFrame; i < keyFrameTimeStamps.size(); i++) { for (uint i = currentKeyFrame; i < keyFrameTimeStamps.size(); i++) {
if (totalElapsedTime < keyFrameTimeStamps.at(i)) { if (totalElapsedTime < keyFrameTimeStamps.at(i)) {
continue; continue;
} }
@ -365,14 +367,16 @@ void updateFrame(GLFWwindow* window) {
} }
} }
glm::mat4 projection = glm::perspective(glm::radians(90.0f), float(windowWidth) / float(windowHeight), 0.1f, mat4 projection = glm::perspective(glm::radians(90.0f), float(windowWidth) / float(windowHeight), 0.1f,
120.f); 120.f);
glm::mat4 cameraTransform = glm::translate(glm::mat4(1), glm::vec3(0, 0, 0)) // hardcoded camera position...
* glm::rotate(glm::mat4(1.0), 0.2f, glm::vec3(1, 0, 0)) mat4 cameraTransform
* glm::rotate(glm::mat4(1.0), float(M_PI), glm::vec3(0, 1, 0)); = glm::translate(mat4(1), vec3(0, 0, 0))
* glm::rotate(mat4(1.0), 0.2f, vec3(1, 0, 0))
* glm::rotate(mat4(1.0), float(M_PI), vec3(0, 1, 0));
updateNodeTransformations(rootNode, glm::mat4(1.0), cameraTransform, projection); updateNodeTransformations(rootNode, mat4(1.0), cameraTransform, projection);
boxNode->position = {-boxDimensions.x / 2, -boxDimensions.y / 2 - 15, boxDimensions.z - 10}; boxNode->position = {-boxDimensions.x / 2, -boxDimensions.y / 2 - 15, boxDimensions.z - 10};
padNode->position = {-boxDimensions.x / 2 + (1 - padPositionX) * (boxDimensions.x - padDimensions.x), padNode->position = {-boxDimensions.x / 2 + (1 - padPositionX) * (boxDimensions.x - padDimensions.x),

View File

@ -1,8 +1,8 @@
#pragma once #pragma once
#include <GLFW/glfw3.h>
#include <utilities/window.hpp> #include <utilities/window.hpp>
void initGame(GLFWwindow* window, CommandLineOptions options); void initGame(GLFWwindow* window, CommandLineOptions options);
void updateFrame(GLFWwindow* window); void updateFrame(GLFWwindow* window);
void renderFrame(GLFWwindow* window); void renderFrame(GLFWwindow* window);

View File

@ -1,26 +1,22 @@
#pragma once #pragma once
#include <glm/glm.hpp> #include <chrono>
#include <glm/mat4x4.hpp>
#include <glm/gtc/type_ptr.hpp>
#include <stack>
#include <vector>
#include <cstdio> #include <cstdio>
#include <stdbool.h>
#include <cstdlib> #include <cstdlib>
#include <ctime> #include <ctime>
#include <chrono>
#include <fstream> #include <fstream>
#include <glm/glm.hpp>
#include <glm/gtc/type_ptr.hpp>
#include <glm/mat4x4.hpp>
#include <stack>
#include <stdbool.h>
#include <utilities/shader.hpp>
#include <vector>
enum SceneNodeType { enum SceneNodeType {
GEOMETRY, POINT_LIGHT, SPOT_LIGHT, HUD, TEXTURED_GEOMETRY, NORMAL_TEXTURED_GEOMETRY GEOMETRY, POINT_LIGHT, SPOT_LIGHT, HUD, TEXTURED_GEOMETRY, NORMAL_TEXTURED_GEOMETRY
}; };
// In case you haven't got much experience with C or C++, let me explain this "typedef" you see below.
// The point of a typedef is that you it, as its name implies, allows you to define arbitrary data types based upon existing ones. For instance, "typedef float typeWhichMightBeAFloat;" allows you to define a variable such as this one: "typeWhichMightBeAFloat variableName = 5.0;". The C/C++ compiler translates this type into a float.
// What is the point of using it here? A smrt person, while designing the C language, thought it would be a good idea for various reasons to force you to explicitly state that you are using a data structure datatype (struct). So, when defining a variable, you'd have to type "struct SceneNode node = ..." in the case of a SceneNode. Which can get in the way of readability.
// If we just use typedef to define a new type called "SceneNode", which really is the type "struct SceneNode", we can omit the "struct" part when creating an instance of SceneNode.
struct SceneNode { struct SceneNode {
SceneNode() { SceneNode() {
position = glm::vec3(0, 0, 0); position = glm::vec3(0, 0, 0);
@ -41,8 +37,6 @@ struct SceneNode {
nodeType = type; nodeType = type;
} }
// A list of all children that belong to this node.
// For instance, in case of the scene graph of a human body shown in the assignment text, the "Upper Torso" node would contain the "Left Arm", "Right Arm", "Head" and "Lower Torso" nodes in its list of children.
std::vector<SceneNode*> children; std::vector<SceneNode*> children;
// The node's position and rotation relative to its parent // The node's position and rotation relative to its parent
@ -82,6 +76,3 @@ SceneNode* createSceneNode();
SceneNode* createSceneNode(SceneNodeType type); SceneNode* createSceneNode(SceneNodeType type);
void addChild(SceneNode* parent, SceneNode* child); void addChild(SceneNode* parent, SceneNode* child);
void printNode(SceneNode* node); void printNode(SceneNode* node);
// For more details, see SceneGraph.cpp.

View File

@ -1,7 +1,12 @@
#include <vector>
#include <glad/glad.h> #include <glad/glad.h>
#include <program.hpp> #include <program.hpp>
#include "glutils.h" #include "glutils.h"
using std::vector;
using glm::vec3;
using glm::vec2;
unsigned int generateBuffer(Mesh &mesh, bool isNormalMapped) { unsigned int generateBuffer(Mesh &mesh, bool isNormalMapped) {
unsigned int vaoID; unsigned int vaoID;
glGenVertexArrays(1, &vaoID); glGenVertexArrays(1, &vaoID);
@ -10,14 +15,14 @@ unsigned int generateBuffer(Mesh &mesh, bool isNormalMapped) {
unsigned int vertexBufferID; unsigned int vertexBufferID;
glGenBuffers(1, &vertexBufferID); glGenBuffers(1, &vertexBufferID);
glBindBuffer(GL_ARRAY_BUFFER, vertexBufferID); glBindBuffer(GL_ARRAY_BUFFER, vertexBufferID);
glBufferData(GL_ARRAY_BUFFER, mesh.vertices.size() * sizeof(glm::vec3), mesh.vertices.data(), GL_STATIC_DRAW); glBufferData(GL_ARRAY_BUFFER, mesh.vertices.size() * sizeof(vec3), mesh.vertices.data(), GL_STATIC_DRAW);
glVertexAttribPointer(0, 3, GL_FLOAT, GL_FALSE, 3 * sizeof(float), 0); glVertexAttribPointer(0, 3, GL_FLOAT, GL_FALSE, 3 * sizeof(float), 0);
glEnableVertexAttribArray(0); glEnableVertexAttribArray(0);
unsigned int normalBufferID; unsigned int normalBufferID;
glGenBuffers(1, &normalBufferID); glGenBuffers(1, &normalBufferID);
glBindBuffer(GL_ARRAY_BUFFER, normalBufferID); glBindBuffer(GL_ARRAY_BUFFER, normalBufferID);
glBufferData(GL_ARRAY_BUFFER, mesh.normals.size() * sizeof(glm::vec3), mesh.normals.data(), GL_STATIC_DRAW); glBufferData(GL_ARRAY_BUFFER, mesh.normals.size() * sizeof(vec3), mesh.normals.data(), GL_STATIC_DRAW);
glVertexAttribPointer(1, 3, GL_FLOAT, GL_TRUE, 3 * sizeof(float), 0); glVertexAttribPointer(1, 3, GL_FLOAT, GL_TRUE, 3 * sizeof(float), 0);
glEnableVertexAttribArray(1); glEnableVertexAttribArray(1);
@ -31,7 +36,7 @@ unsigned int generateBuffer(Mesh &mesh, bool isNormalMapped) {
unsigned int textureBufferID; unsigned int textureBufferID;
glGenBuffers(1, &textureBufferID); glGenBuffers(1, &textureBufferID);
glBindBuffer(GL_ARRAY_BUFFER, textureBufferID); glBindBuffer(GL_ARRAY_BUFFER, textureBufferID);
glBufferData(GL_ARRAY_BUFFER, mesh.textureCoordinates.size() * sizeof(glm::vec2), mesh.textureCoordinates.data(), GL_STATIC_DRAW); glBufferData(GL_ARRAY_BUFFER, mesh.textureCoordinates.size() * sizeof(vec2), mesh.textureCoordinates.data(), GL_STATIC_DRAW);
glVertexAttribPointer(2, 2, GL_FLOAT, GL_FALSE, 2 * sizeof(float), 0); glVertexAttribPointer(2, 2, GL_FLOAT, GL_FALSE, 2 * sizeof(float), 0);
glEnableVertexAttribArray(2); glEnableVertexAttribArray(2);
@ -41,26 +46,26 @@ unsigned int generateBuffer(Mesh &mesh, bool isNormalMapped) {
} }
void addTangents(unsigned int vaoID, Mesh& mesh) { void addTangents(unsigned int vaoID, Mesh& mesh) {
glm::vec3 tangents[mesh.vertices.size()]; vector<vec3> tangents(mesh.vertices.size());
glm::vec3 bitangents[mesh.vertices.size()]; vector<vec3> bitangents(mesh.vertices.size());
for (unsigned int i = 0; i < mesh.indices.size(); i+=3) { for (unsigned int i = 0; i < mesh.indices.size(); i+=3) {
const glm::vec3& pos1 = mesh.vertices[mesh.indices[i+0]]; const vec3& pos1 = mesh.vertices[mesh.indices[i+0]];
const glm::vec3& pos2 = mesh.vertices[mesh.indices[i+1]]; const vec3& pos2 = mesh.vertices[mesh.indices[i+1]];
const glm::vec3& pos3 = mesh.vertices[mesh.indices[i+2]]; const vec3& pos3 = mesh.vertices[mesh.indices[i+2]];
const glm::vec2& uv1 = mesh.textureCoordinates[mesh.indices[i+0]]; const vec2& uv1 = mesh.textureCoordinates[mesh.indices[i+0]];
const glm::vec2& uv2 = mesh.textureCoordinates[mesh.indices[i+1]]; const vec2& uv2 = mesh.textureCoordinates[mesh.indices[i+1]];
const glm::vec2& uv3 = mesh.textureCoordinates[mesh.indices[i+2]]; const vec2& uv3 = mesh.textureCoordinates[mesh.indices[i+2]];
glm::vec3 edge1 = pos2 - pos1; vec3 edge1 = pos2 - pos1;
glm::vec3 edge2 = pos3 - pos1; vec3 edge2 = pos3 - pos1;
glm::vec2 deltaUV1 = uv2 - uv1; vec2 deltaUV1 = uv2 - uv1;
glm::vec2 deltaUV2 = uv3 - uv1; vec2 deltaUV2 = uv3 - uv1;
float f = 1.0f / (deltaUV1.x * deltaUV2.y - deltaUV2.x * deltaUV1.y); float f = 1.0f / (deltaUV1.x * deltaUV2.y - deltaUV2.x * deltaUV1.y);
glm::vec3 tangent, bitangent; vec3 tangent, bitangent;
tangent.x = f * (deltaUV2.y * edge1.x - deltaUV1.y * edge2.x); tangent.x = f * (deltaUV2.y * edge1.x - deltaUV1.y * edge2.x);
tangent.y = f * (deltaUV2.y * edge1.y - deltaUV1.y * edge2.y); tangent.y = f * (deltaUV2.y * edge1.y - deltaUV1.y * edge2.y);
tangent.z = f * (deltaUV2.y * edge1.z - deltaUV1.y * edge2.z); tangent.z = f * (deltaUV2.y * edge1.z - deltaUV1.y * edge2.z);
@ -86,14 +91,14 @@ void addTangents(unsigned int vaoID, Mesh& mesh) {
unsigned int tangentBufferID; unsigned int tangentBufferID;
glGenBuffers(1, &tangentBufferID); glGenBuffers(1, &tangentBufferID);
glBindBuffer(GL_ARRAY_BUFFER, tangentBufferID); glBindBuffer(GL_ARRAY_BUFFER, tangentBufferID);
glBufferData(GL_ARRAY_BUFFER, mesh.vertices.size() * sizeof(glm::vec3), tangents, GL_STATIC_DRAW); glBufferData(GL_ARRAY_BUFFER, mesh.vertices.size() * sizeof(vec3), tangents.data(), GL_STATIC_DRAW);
glVertexAttribPointer(3, 3, GL_FLOAT, GL_FALSE, 3 * sizeof(float), 0); glVertexAttribPointer(3, 3, GL_FLOAT, GL_FALSE, 3 * sizeof(float), 0);
glEnableVertexAttribArray(3); glEnableVertexAttribArray(3);
unsigned int bitangentBufferID; unsigned int bitangentBufferID;
glGenBuffers(1, &bitangentBufferID); glGenBuffers(1, &bitangentBufferID);
glBindBuffer(GL_ARRAY_BUFFER, bitangentBufferID); glBindBuffer(GL_ARRAY_BUFFER, bitangentBufferID);
glBufferData(GL_ARRAY_BUFFER, mesh.vertices.size() * sizeof(glm::vec3), bitangents, GL_STATIC_DRAW); glBufferData(GL_ARRAY_BUFFER, mesh.vertices.size() * sizeof(vec3), bitangents.data(), GL_STATIC_DRAW);
glVertexAttribPointer(4, 3, GL_FLOAT, GL_FALSE, 3 * sizeof(float), 0); glVertexAttribPointer(4, 3, GL_FLOAT, GL_FALSE, 3 * sizeof(float), 0);
glEnableVertexAttribArray(4); glEnableVertexAttribArray(4);
} }

View File

@ -1,41 +1,44 @@
#include "imageLoader.hpp" #include "imageLoader.hpp"
#include <iostream> #include <glm/vec2.hpp>
#include <glm/gtc/noise.hpp>
// Original source: https://raw.githubusercontent.com/lvandeve/lodepng/master/examples/example_decode.cpp #include <iostream>
PNGImage loadPNGFile(std::string fileName)
{ using glm::vec2;
std::vector<unsigned char> png; using std::vector;
std::vector<unsigned char> pixels; //the raw pixels
unsigned int width, height; // Original source: https://raw.githubusercontent.com/lvandeve/lodepng/master/examples/example_decode.cpp
PNGImage loadPNGFile(std::string fileName) {
//load and decode vector<unsigned char> png;
unsigned error = lodepng::load_file(png, fileName); vector<unsigned char> pixels; //the raw pixels
if(!error) error = lodepng::decode(pixels, width, height, png); unsigned int width, height;
//if there's an error, display it //load and decode
if(error) std::cout << "decoder error " << error << ": " << lodepng_error_text(error) << std::endl; unsigned error = lodepng::load_file(png, fileName);
if(!error) error = lodepng::decode(pixels, width, height, png);
//the pixels are now in the vector "image", 4 bytes per pixel, ordered RGBARGBA..., use it as texture, draw it, ...
//if there's an error, display it
// Unfortunately, images usually have their origin at the top left. if(error) std::cout << "decoder error " << error << ": " << lodepng_error_text(error) << std::endl;
// OpenGL instead defines the origin to be on the _bottom_ left instead, so
// here's the world's most inefficient way to flip the image vertically. //the pixels are now in the vector "image", 4 bytes per pixel, ordered RGBARGBA..., use it as texture, draw it, ...
// You're welcome :) // Unfortunately, images usually have their origin at the top left.
// OpenGL instead defines the origin to be on the _bottom_ left instead, so
unsigned int widthBytes = 4 * width; // here's the world's most inefficient way to flip the image vertically.
for(unsigned int row = 0; row < (height / 2); row++) { // You're welcome :)
for(unsigned int col = 0; col < widthBytes; col++) {
std::swap(pixels[row * widthBytes + col], pixels[(height - 1 - row) * widthBytes + col]); unsigned int widthBytes = 4 * width;
}
} for(unsigned int row = 0; row < (height / 2); row++) {
for(unsigned int col = 0; col < widthBytes; col++) {
PNGImage image; std::swap(pixels[row * widthBytes + col], pixels[(height - 1 - row) * widthBytes + col]);
image.width = width; }
image.height = height; }
image.pixels = pixels;
PNGImage image;
return image; image.width = width;
image.height = height;
} image.pixels = pixels;
return image;
}

View File

@ -4,9 +4,11 @@
#include <vector> #include <vector>
#include <string> #include <string>
typedef unsigned int uint;
typedef struct PNGImage { typedef struct PNGImage {
unsigned int width, height; unsigned int width, height;
std::vector<unsigned char> pixels; std::vector<unsigned char> pixels; // RGBA
} PNGImage; } PNGImage;
PNGImage loadPNGFile(std::string fileName); PNGImage loadPNGFile(std::string fileName);

View File

@ -35,8 +35,7 @@ namespace Gloom
{ {
// Load GLSL Shader from source // Load GLSL Shader from source
std::ifstream fd(filename.c_str()); std::ifstream fd(filename.c_str());
if (fd.fail()) if (fd.fail()) {
{
fprintf(stderr, fprintf(stderr,
"Something went wrong when attaching the Shader file at \"%s\".\n" "Something went wrong when attaching the Shader file at \"%s\".\n"
"The file may not exist or is currently inaccessible.\n", "The file may not exist or is currently inaccessible.\n",

View File

@ -1,12 +1,17 @@
#include <iostream> #include <iostream>
#include "shapes.h" #include "shapes.h"
typedef uint uint;
using glm::vec3;
using glm::vec2;
using std::vector;
Mesh generateBox(float width, float height, float depth, bool flipFaces) { Mesh generateBox(float width, float height, float depth, bool flipFaces) {
// Hardcoded. Sue me. // Hardcoded. Sue me.
// Edit: well, that backfired.. // Edit: well, that backfired..
std::vector<glm::vec3> vertices = { vector<vec3> vertices = {
{0, 0, 0}, {0, 0, 0},
{0, 0, depth}, {0, 0, depth},
{0, height, depth}, {0, height, depth},
@ -60,7 +65,7 @@ Mesh generateBox(float width, float height, float depth, bool flipFaces) {
// But for some strange reason the faces are rendered inverted. // But for some strange reason the faces are rendered inverted.
// So to make the assignment work this is the best I can do. // So to make the assignment work this is the best I can do.
std::vector<glm::vec3> normals = { vector<vec3> normals = {
{1.0, 0.0, 0.0}, {1.0, 0.0, 0.0},
{1.0, 0.0, 0.0}, {1.0, 0.0, 0.0},
{1.0, 0.0, 0.0}, {1.0, 0.0, 0.0},
@ -114,7 +119,7 @@ Mesh generateBox(float width, float height, float depth, bool flipFaces) {
float texScaleFactorY = width / depth; float texScaleFactorY = width / depth;
float texScaleFactorZ = width / height; float texScaleFactorZ = width / height;
std::vector<glm::vec2> textureCoordinates = { vector<vec2> textureCoordinates = {
{0, 0}, {0, 0},
{texScaleFactorX, 0}, {texScaleFactorX, 0},
{texScaleFactorX, 1}, {texScaleFactorX, 1},
@ -166,7 +171,7 @@ Mesh generateBox(float width, float height, float depth, bool flipFaces) {
}; };
std::vector<unsigned int> indices = { vector<uint> indices = {
0, 1, 2, 0, 1, 2,
3, 4, 5, 3, 4, 5,
6, 7, 8, 6, 7, 8,
@ -183,7 +188,7 @@ Mesh generateBox(float width, float height, float depth, bool flipFaces) {
if(flipFaces) { if(flipFaces) {
for(int i = 0; i < 36; i += 3) { for(int i = 0; i < 36; i += 3) {
unsigned int temp = indices[i + 1]; uint temp = indices[i + 1];
indices[i + 1] = indices[i + 2]; indices[i + 1] = indices[i + 2];
indices[i + 2] = temp; indices[i + 2] = temp;
@ -203,11 +208,11 @@ Mesh generateBox(float width, float height, float depth, bool flipFaces) {
} }
Mesh generateSphere(float sphereRadius, int slices, int layers) { Mesh generateSphere(float sphereRadius, int slices, int layers) {
const unsigned int triangleCount = slices * layers * 2; const uint triangleCount = slices * layers * 2;
std::vector<glm::vec3> vertices; vector<vec3> vertices;
std::vector<glm::vec3> normals; vector<vec3> normals;
std::vector<unsigned int> indices; vector<uint> indices;
vertices.reserve(3 * triangleCount); vertices.reserve(3 * triangleCount);
normals.reserve(3 * triangleCount); normals.reserve(3 * triangleCount);
@ -218,7 +223,7 @@ Mesh generateSphere(float sphereRadius, int slices, int layers) {
const float degreesPerLayer = 180.0 / (float) layers; const float degreesPerLayer = 180.0 / (float) layers;
const float degreesPerSlice = 360.0 / (float) slices; const float degreesPerSlice = 360.0 / (float) slices;
unsigned int i = 0; uint i = 0;
// Constructing the sphere one layer at a time // Constructing the sphere one layer at a time
for (int layer = 0; layer < layers; layer++) { for (int layer = 0; layer < layers; layer++) {