diff --git a/assets/scenes/sponza.json b/assets/scenes/sponza.json index cb1c74b..1dd5b62 100644 --- a/assets/scenes/sponza.json +++ b/assets/scenes/sponza.json @@ -1,5 +1,5 @@ { - "sceneID": "Sponza", + "sceneID": "sponza", "skybox": {"id": "barcelona", "hdr": true, "resolution": 512 diff --git a/assets/shaders/ComputeShaders/clusterShader.comp b/assets/shaders/ComputeShaders/clusterShader.comp index fec91b1..d9dd7ff 100644 --- a/assets/shaders/ComputeShaders/clusterShader.comp +++ b/assets/shaders/ComputeShaders/clusterShader.comp @@ -11,8 +11,16 @@ layout (std430, binding = 1) buffer clusterAABB{ }; layout (std430, binding = 2) buffer screenToView{ mat4 inverseProjection; - uvec4 tileSizes; - uvec2 screenDimensions; + uint tileSizeX; + uint tileSizeY; + uint tileSizeZ; + uint padding1; + vec2 tileSizePx; + vec2 viewPxSize; + float scale; + float bias; + uint padding2; + uint padding3; }; //Shared between all clusters @@ -29,14 +37,14 @@ void main(){ const vec3 eyePos = vec3(0.0); //Per Tile variables - uint tileSizePx = tileSizes[3]; uint tileIndex = gl_WorkGroupID.x + gl_WorkGroupID.y * gl_NumWorkGroups.x + gl_WorkGroupID.z * (gl_NumWorkGroups.x * gl_NumWorkGroups.y); - //Calculating the min and max point in screen space - vec4 maxPoint_sS = vec4(vec2(gl_WorkGroupID.x + 1, gl_WorkGroupID.y + 1) * tileSizePx, -1.0, 1.0); // Top Right - vec4 minPoint_sS = vec4(gl_WorkGroupID.xy * tileSizePx, -1.0, 1.0); // Bottom left + // Calculating the min and max point in screen space + // tileSizePx is 1/x so we have to divide again to get a y*x + vec4 maxPoint_sS = vec4(vec2(gl_WorkGroupID.x + 1, gl_WorkGroupID.y + 1) / tileSizePx, -1.0, 1.0); // Top Right + vec4 minPoint_sS = vec4(gl_WorkGroupID.xy / tileSizePx, -1.0, 1.0); // Bottom left //Pass min and max to view space vec3 maxPoint_vS = screen2View(maxPoint_sS).xyz; @@ -89,7 +97,7 @@ vec4 clipToView(vec4 clip){ vec4 screen2View(vec4 screen){ //Convert to NDC - vec2 texCoord = screen.xy / screenDimensions.xy; + vec2 texCoord = screen.xy * viewPxSize.xy; //Convert to clipSpace // vec4 clip = vec4(vec2(texCoord.x, 1.0 - texCoord.y)* 2.0 - 1.0, screen.z, screen.w); diff --git a/assets/shaders/PBRClusteredShader.frag b/assets/shaders/PBRClusteredShader.frag index 2f2d22a..f254ff7 100644 --- a/assets/shaders/PBRClusteredShader.frag +++ b/assets/shaders/PBRClusteredShader.frag @@ -14,7 +14,6 @@ in VS_OUT{ vec3 T; vec3 B; vec3 N; - mat3 TBN; } fs_in; //Dir light uniform @@ -61,10 +60,16 @@ struct LightGrid{ }; layout (std430, binding = 2) buffer screenToView{ mat4 inverseProjection; - uvec4 tileSizes; - uvec2 screenDimensions; + uint tileSizeX; + uint tileSizeY; + uint tileSizeZ; + uint padding1; + vec2 tileSizePx; + vec2 viewPxSize; float scale; float bias; + uint padding2; + uint padding3; }; layout (std430, binding = 3) buffer lightSSBO{ PointLight pointLight[]; @@ -158,10 +163,10 @@ void main(){ //Locating which cluster you are a part of uint zTile = uint(max(log2(linearDepth(gl_FragCoord.z)) * scale + bias, 0.0)); - uvec3 tiles = uvec3( uvec2( gl_FragCoord.xy / tileSizes[3] ), zTile); + uvec3 tiles = uvec3( uvec2( gl_FragCoord.xy * tileSizePx ), zTile); uint tileIndex = tiles.x + - tileSizes.x * tiles.y + - (tileSizes.x * tileSizes.y) * tiles.z; + tileSizeX * tiles.y + + (tileSizeX * tileSizeY) * tiles.z; //Solving outgoing reflectance of fragment vec3 radianceOut = vec3(0.0); @@ -210,7 +215,7 @@ void main(){ radianceOut += emissive; if(slices){ - FragColor = vec4(colors[uint(mod(zTile, 8.0))], 1.0); + FragColor = vec4(colors[uint(mod(float(zTile), 8.0))], 1.0); } else{ FragColor = vec4(radianceOut, 1.0); @@ -319,7 +324,7 @@ float calcPointLightShadows(samplerCube depthMap, vec3 fragToLight, float viewDi float currentDepth = (length(fragToLight) - bias); for(int i = 0; i < samples; ++i){ - float closestDepth = texture(depthMap, fragToLight + sampleOffsetDirections[i], diskRadius).r; + float closestDepth = texture(depthMap, fragToLight + (sampleOffsetDirections[i] * diskRadius)).r; closestDepth *= far_plane; if(currentDepth > closestDepth){ shadow += fraction; diff --git a/assets/shaders/PBRClusteredShader.vert b/assets/shaders/PBRClusteredShader.vert index e1bab12..d4bea4c 100644 --- a/assets/shaders/PBRClusteredShader.vert +++ b/assets/shaders/PBRClusteredShader.vert @@ -19,7 +19,6 @@ out VS_OUT{ vec3 T; vec3 B; vec3 N; - mat3 TBN; } vs_out; uniform mat4 MVP; diff --git a/assets/shaders/screenShader.frag b/assets/shaders/screenShader.frag index b4b3383..e07c89f 100644 --- a/assets/shaders/screenShader.frag +++ b/assets/shaders/screenShader.frag @@ -5,7 +5,6 @@ in vec2 TexCoords; uniform sampler2D screenTexture; uniform sampler2D bloomBlur; -uniform int offset; uniform float exposure; void main(){ diff --git a/include/cubeMap.h b/include/cubeMap.h index 0fa0091..324d4da 100644 --- a/include/cubeMap.h +++ b/include/cubeMap.h @@ -41,7 +41,7 @@ struct CubeMap : public Texture{ //Static constants used in all cubemaps static Cube cubeMapCube; - static const glm::mat4 captureViews[18]; + static const glm::mat4 captureViews[6]; static const unsigned int numSidesInCube; static const glm::mat4 captureProjection; static const std::string fileHandleForFaces[6]; //Order from Opengl cubemap enums diff --git a/include/gpuData.h b/include/gpuData.h index 08a7a6e..709c62c 100644 --- a/include/gpuData.h +++ b/include/gpuData.h @@ -1,5 +1,5 @@ #ifndef GPUDATA_H -#define GPUTDATA_H +#define GPUDATA_H /* AUTHOR : Angel Ortiz (angelo12 AT vt DOT edu) @@ -19,11 +19,16 @@ struct VolumeTileAABB{ struct ScreenToView{ glm::mat4 inverseProjectionMat; - unsigned int tileSizes[4]; - unsigned int screenWidth; - unsigned int screenHeight; + unsigned int tileSizeX; + unsigned int tileSizeY; + unsigned int tileSizeZ; + unsigned int padding1; + glm::vec2 tilePixelSize; + glm::vec2 viewPixelSize; float sliceScalingFactor; float sliceBiasFactor; + unsigned int padding2; + unsigned int padding3; }screen2View; #endif \ No newline at end of file diff --git a/include/renderManager.h b/include/renderManager.h index d5f8ee7..7ef318b 100644 --- a/include/renderManager.h +++ b/include/renderManager.h @@ -42,7 +42,7 @@ class RenderManager{ //optimizations. In the future, (the magical land where all projects are complete) I plan on //heavily optimizing this part of the program along the lines of the 2014 talk, "beyond porting" //But in the mean-time it uses pretty basic an naive openGL. - void render(const unsigned int start); + void render(); private: //Internal initialization functions bool initFBOs(); @@ -53,7 +53,7 @@ class RenderManager{ bool preProcess(); //Functions used to break up the main render function into more manageable parts. - void postProcess(const unsigned int start); + void postProcess(); //Todo:: shaders should belong to a material not the rendermanager Shader depthPrePassShader, PBRClusteredShader, skyboxShader, diff --git a/src/cubeMap.cpp b/src/cubeMap.cpp index b438367..e89eff5 100644 --- a/src/cubeMap.cpp +++ b/src/cubeMap.cpp @@ -12,7 +12,7 @@ DATE : 2018-09-24 //Initializing all static variables at compile time const glm::mat4 CubeMap::captureProjection = glm::perspective(glm::radians(90.0f), 1.0f, 0.1f, 10.0f); -const glm::mat4 CubeMap::captureViews[18] = { +const glm::mat4 CubeMap::captureViews[6] = { glm::lookAt(glm::vec3(0.0f, 0.0f, 0.0f), glm::vec3(1.0f, 0.0f, 0.0f), glm::vec3(0.0f, -1.0f, 0.0f)), glm::lookAt(glm::vec3(0.0f, 0.0f, 0.0f), glm::vec3(-1.0f, 0.0f, 0.0f), glm::vec3(0.0f, -1.0f, 0.0f)), glm::lookAt(glm::vec3(0.0f, 0.0f, 0.0f), glm::vec3(0.0f, 1.0f, 0.0f), glm::vec3(0.0f, 0.0f, 1.0f)), @@ -82,7 +82,6 @@ void CubeMap::generateCubeMap(const int width, const int height, CubeMapType cub glTexParameteri(GL_TEXTURE_CUBE_MAP, GL_TEXTURE_WRAP_S, GL_CLAMP_TO_EDGE); glTexParameteri(GL_TEXTURE_CUBE_MAP, GL_TEXTURE_WRAP_T, GL_CLAMP_TO_EDGE); glTexParameteri(GL_TEXTURE_CUBE_MAP, GL_TEXTURE_WRAP_R, GL_CLAMP_TO_EDGE); - glTexParameteri(GL_TEXTURE_CUBE_MAP, GL_TEXTURE_COMPARE_MODE, GL_COMPARE_REF_TO_TEXTURE); glTexParameteri(GL_TEXTURE_CUBE_MAP, GL_TEXTURE_MIN_FILTER, GL_LINEAR); glTexParameteri(GL_TEXTURE_CUBE_MAP, GL_TEXTURE_MAG_FILTER, GL_LINEAR); break; @@ -168,7 +167,9 @@ void CubeMap::preFilterCubeMap(const unsigned int environmentMap, glBindRenderbuffer(GL_RENDERBUFFER, captureRBO); glRenderbufferStorage(GL_RENDERBUFFER, GL_DEPTH_COMPONENT24, mipWidth, mipHeight); glViewport(0, 0, mipWidth, mipHeight); - + + filterShader.setFloat("roughness", mip / (float)(maxMipLevels - 1)); + for(unsigned int i = 0; i < numSidesInCube; ++i){ filterShader.setMat4("view", captureViews[i]); diff --git a/src/engine.cpp b/src/engine.cpp index eeedbc6..41c0095 100644 --- a/src/engine.cpp +++ b/src/engine.cpp @@ -91,7 +91,7 @@ void Engine::run(){ //Update all models, camera and lighting in the current scene gSceneManager.update(deltaT); - gRenderManager.render(start); + gRenderManager.render(); //Obtaining deltaT for any deltaT = SDL_GetTicks() - start; diff --git a/src/mesh.cpp b/src/mesh.cpp index 53928e8..78bcf73 100644 --- a/src/mesh.cpp +++ b/src/mesh.cpp @@ -53,7 +53,7 @@ void Mesh::draw(const Shader &shader, bool textured){ //Mesh Drawing glBindVertexArray(VAO); - glDrawElements(GL_TRIANGLES, (GLsizei)indices.size(), GL_UNSIGNED_INT, 0); + glDrawElements(GL_TRIANGLES, (GLsizei)indices.size(), GL_UNSIGNED_INT, NULL); } //Sending the data to the GPU and formatting it in memory diff --git a/src/model.cpp b/src/model.cpp index 7fed5e1..8f870bb 100644 --- a/src/model.cpp +++ b/src/model.cpp @@ -152,7 +152,8 @@ std::vector Model::processTextures(const aiMaterial *material){ //If this texture has not been added to the atlas yet we load it if (textureAtlas.count(fullTexturePath) == 0){ Texture texture; - bool srgb = false; + // Diffuse is sRGB, the rest aren't + bool srgb = tex == aiTextureType_DIFFUSE; texture.loadTexture(fullTexturePath, srgb); textureAtlas.insert({fullTexturePath, texture}); } diff --git a/src/renderManager.cpp b/src/renderManager.cpp index 032f6d2..e3182a9 100644 --- a/src/renderManager.cpp +++ b/src/renderManager.cpp @@ -55,6 +55,8 @@ bool RenderManager::startUp(DisplayManager &displayManager, SceneManager &sceneM } bool RenderManager::preProcess(){ + glDisable(GL_BLEND); + //Initializing the surface that we use to draw screen-space effects canvas.setup(); @@ -116,6 +118,7 @@ bool RenderManager::preProcess(){ bool RenderManager::initSSBOs(){ //Setting up tile size on both X and Y sizeX = (unsigned int)std::ceilf(DisplayManager::SCREEN_WIDTH / (float)gridSizeX); + sizeY = (unsigned int)std::ceilf(DisplayManager::SCREEN_HEIGHT / (float)gridSizeY); float zFar = sceneCamera->cameraFrustum.farPlane; float zNear = sceneCamera->cameraFrustum.nearPlane; @@ -138,12 +141,13 @@ bool RenderManager::initSSBOs(){ //Setting up contents of buffer screen2View.inverseProjectionMat = glm::inverse(sceneCamera->projectionMatrix); - screen2View.tileSizes[0] = gridSizeX; - screen2View.tileSizes[1] = gridSizeY; - screen2View.tileSizes[2] = gridSizeZ; - screen2View.tileSizes[3] = sizeX; - screen2View.screenWidth = DisplayManager::SCREEN_WIDTH; - screen2View.screenHeight = DisplayManager::SCREEN_HEIGHT; + screen2View.tileSizeX = gridSizeX; + screen2View.tileSizeY = gridSizeY; + screen2View.tileSizeZ = gridSizeZ; + screen2View.tilePixelSize.x = 1.0f / (float)sizeX; + screen2View.tilePixelSize.y = 1.0f / (float)sizeY; + screen2View.viewPixelSize.x = 1.0f / (float)DisplayManager::SCREEN_WIDTH; + screen2View.viewPixelSize.y = 1.0f / (float)DisplayManager::SCREEN_HEIGHT; //Basically reduced a log function into a simple multiplication an addition by pre-calculating these screen2View.sliceScalingFactor = (float)gridSizeZ / std::log2f(zFar / zNear) ; screen2View.sliceBiasFactor = -((float)gridSizeZ * std::log2f(zNear) / std::log2f(zFar / zNear)) ; @@ -324,7 +328,7 @@ Algorithm steps: 5. Shading by reading from the active tiles list :: DONE 6. Post processing and screen space effects :: DONE */ -void RenderManager::render(const unsigned int start){ +void RenderManager::render(){ //Initiating rendering gui ImGui::Begin("Rendering Controls"); ImGui::Text("Application average %.3f ms/frame (%.1f FPS)", 1000.0f / ImGui::GetIO().Framerate, ImGui::GetIO().Framerate); @@ -338,7 +342,8 @@ void RenderManager::render(const unsigned int start){ ImGui::InputFloat3("Camera Pos", (float*)&sceneCamera->position); //Camera controls ImGui::SliderFloat("Movement speed", &sceneCamera->camSpeed, 0.005f, 1.0f); } - //Making sure depth testing is enabled + + glDisable(GL_BLEND); glEnable(GL_DEPTH_TEST); glDepthMask(true); @@ -367,7 +372,7 @@ void RenderManager::render(const unsigned int start){ multiSampledFBO.blitTo(simpleFBO, GL_COLOR_BUFFER_BIT | GL_DEPTH_BUFFER_BIT); //6 -postprocessing, includes bloom, exposure mapping - postProcess(start); + postProcess(); //Rendering gui scope ends here cannot be done later because the whole frame //is reset in the display buffer swap @@ -379,7 +384,7 @@ void RenderManager::render(const unsigned int start){ } -void RenderManager::postProcess(const unsigned int start){ +void RenderManager::postProcess(){ if(ImGui::CollapsingHeader("Post-processing")){ ImGui::SliderInt("Blur", &sceneCamera->blurAmount, 0, 10); ImGui::SliderFloat("Exposure", &sceneCamera->exposure, 0.1f, 5.0f); @@ -406,6 +411,7 @@ void RenderManager::postProcess(const unsigned int start){ //Vertical pass glBindFramebuffer(GL_FRAMEBUFFER, pingPongFBO.frameBufferID); + glDrawBuffer(GL_COLOR_ATTACHMENT0); gaussianBlurShader.setBool("horizontal", false); canvas.draw(simpleFBO.blurHighEnd); } @@ -416,7 +422,6 @@ void RenderManager::postProcess(const unsigned int start){ //Shader setup for postprocessing screenSpaceShader.use(); - screenSpaceShader.setInt("offset", start); screenSpaceShader.setFloat("exposure", sceneCamera->exposure); screenSpaceShader.setInt("screenTexture", 0); screenSpaceShader.setInt("bloomBlur", 1); diff --git a/src/scene.cpp b/src/scene.cpp index a6cbfab..90d6b4e 100644 --- a/src/scene.cpp +++ b/src/scene.cpp @@ -13,7 +13,7 @@ DATE : 2018-09-12 #include "imgui/imgui.h" Scene::Scene(const std::string &sceneName){ - std::string folderPath = "../assets/scenes/"; + std::string folderPath = "../../../assets/scenes/"; std::string fileExtension = ".json"; sceneID = sceneName; @@ -252,7 +252,7 @@ PointLight *Scene::getPointLight(unsigned int index){ //Config file parsing, gets all the important bool Scene::loadContent(){ //Parsing into Json file readable format - std::string folderPath = "../assets/scenes/"; + std::string folderPath = "../../../assets/scenes/"; std::string fileExtension = ".json"; std::string sceneConfigFilePath = folderPath + sceneID + fileExtension; std::ifstream file(sceneConfigFilePath.c_str()); @@ -394,7 +394,7 @@ void Scene::loadSceneModels(const json &sceneConfigJson ){ for (unsigned int i = 0; i < modelCount; ++i){ //get model mesh and material info json currentModel = sceneConfigJson["models"][i]; - modelMesh = currentModel["mesh"]; + modelMesh = currentModel["mesh"].get(); IBL = currentModel["IBL"]; modelName = modelMesh.substr(0, modelMesh.find_last_of('.')); @@ -415,7 +415,7 @@ void Scene::loadSceneModels(const json &sceneConfigJson ){ initParameters.scaling = glm::vec3((float)scaling[0], (float)scaling[1], (float)scaling[2]); //attempts to load model with the initparameters it has read - modelMesh = "../assets/models/" + modelName + "/" + modelMesh; + modelMesh = "../../../assets/models/" + modelName + "/" + modelMesh; if (!FLOAD::checkFileValidity(modelMesh)){ printf("Error! Mesh: %s does not exist.\n", modelMesh.c_str()); } @@ -443,7 +443,7 @@ void Scene::generateEnvironmentMaps(){ brdfLUTTexture.width = res; glGenTextures(1, &brdfLUTTexture.textureID); glBindTexture(GL_TEXTURE_2D, brdfLUTTexture.textureID); - glTexImage2D(GL_TEXTURE_2D, 0, GL_RG16F, res, res, 0, GL_RG, GL_FLOAT, 0); + glTexImage2D(GL_TEXTURE_2D, 0, GL_RG16F, res, res, 0, GL_RG, GL_FLOAT, NULL); glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_WRAP_S, GL_CLAMP_TO_EDGE); glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_WRAP_T, GL_CLAMP_TO_EDGE); glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MIN_FILTER, GL_LINEAR); diff --git a/src/sceneManager.cpp b/src/sceneManager.cpp index 8ddf2d4..83d6836 100644 --- a/src/sceneManager.cpp +++ b/src/sceneManager.cpp @@ -16,7 +16,7 @@ SceneManager::~SceneManager(){} // the scene could not load any model, or there are none defined it quits early. bool SceneManager::startUp(){ // currentSceneID = "pbrTest"; - currentSceneID = "Sponza"; + currentSceneID = "sponza"; if (!loadScene(currentSceneID)){ printf("Could not load default sponza scene. No models succesfully loaded!\n"); return false; diff --git a/src/shader.cpp b/src/shader.cpp index f357fb7..822d491 100644 --- a/src/shader.cpp +++ b/src/shader.cpp @@ -15,7 +15,7 @@ DATE : 2018-09-08 bool Shader::setup(const std::string vertexPath, const std::string fragmentPath, const std::string geometryPath){ //Getting the vertex shader code from the text file at file path bool gShaderOn = geometryPath != ""; - std::string shaderFolderPath = "../assets/shaders/"; + std::string shaderFolderPath = "../../../assets/shaders/"; std::string vertexCode, fragmentCode, geometryCode; std::stringstream vShaderStream, fShaderStream, gShaderStream; @@ -150,7 +150,7 @@ void Shader::setVec3(const std::string &name, const glm::vec3 &vec) const { //Could be simplified? bool ComputeShader::setup(const std::string computePath){ //Getting the compute shader code from the text file at file path - std::string shaderFolderPath = "../assets/shaders/ComputeShaders/"; + std::string shaderFolderPath = "../../../assets/shaders/ComputeShaders/"; std::string computeCode; std::ifstream cShaderFile(shaderFolderPath + computePath); std::stringstream cShaderStream; diff --git a/src/skybox.cpp b/src/skybox.cpp index 2176e20..22e9ebc 100644 --- a/src/skybox.cpp +++ b/src/skybox.cpp @@ -24,7 +24,7 @@ void Skybox::draw(){ //Two setup paths for HDR and non HDR cubemap void Skybox::setup(const std::string &skyboxName, bool isHDR, int res){ - std::string skyBoxFolderPath = "../assets/skyboxes/"; + std::string skyBoxFolderPath = "../../../assets/skyboxes/"; skyBoxFolderPath += skyboxName; std::string skyBoxFilePath = skyBoxFolderPath + "/" + skyboxName + ".hdr"; diff --git a/src/texture.cpp b/src/texture.cpp index 779bda1..6b3aeba 100644 --- a/src/texture.cpp +++ b/src/texture.cpp @@ -274,8 +274,6 @@ unsigned int Texture::genTextureDirectlyOnGPU(const int width, const int height, glTexImage2D(GL_TEXTURE_2D, 0, GL_DEPTH_COMPONENT32F, width, height, 0, GL_DEPTH_COMPONENT, GL_FLOAT, NULL); glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MIN_FILTER, GL_LINEAR); glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MAG_FILTER, GL_LINEAR); - glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_COMPARE_MODE, GL_COMPARE_REF_TO_TEXTURE); - glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_COMPARE_FUNC, GL_LESS); glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_WRAP_S, GL_CLAMP_TO_BORDER); glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_WRAP_T, GL_CLAMP_TO_BORDER); glTexParameterfv(GL_TEXTURE_2D, GL_TEXTURE_BORDER_COLOR, borderColor);