void CCreateField::RenderQuad(const Vec3f & p1, const Vec3f & p2, const Vec3f & p3, const Vec3f & p4, int rec, Vec3f norm, RenderMaterial & mat) { if(rec < 3) { rec++; Vec3f v[5] = { p1 + (p3 - p1) * 0.5f, p1 + (p4 - p1) * 0.5f, p2 + (p3 - p2) * 0.5f, p4 + (p3 - p4) * 0.5f, p1 + (p2 - p1) * 0.5f, }; float patchsize = 0.005f; v[0].x += glm::sin(glm::radians((v[0].x - eSrc.x) * patchsize + fwrap)) * 5; v[0].y += glm::sin(glm::radians((v[0].y - eSrc.y) * patchsize + fwrap)) * 5; v[0].z += glm::sin(glm::radians((v[0].z - eSrc.z) * patchsize + fwrap)) * 5; v[1].x += glm::sin(glm::radians((v[1].x - eSrc.x) * patchsize + fwrap)) * 5; v[1].y += glm::sin(glm::radians((v[1].y - eSrc.y) * patchsize + fwrap)) * 5; v[1].z += glm::sin(glm::radians((v[1].z - eSrc.z) * patchsize + fwrap)) * 5; v[2].x += glm::sin(glm::radians((v[2].x - eSrc.x) * patchsize + fwrap)) * 5; v[2].y += glm::sin(glm::radians((v[2].y - eSrc.y) * patchsize + fwrap)) * 5; v[2].z += glm::sin(glm::radians((v[2].z - eSrc.z) * patchsize + fwrap)) * 5; v[3].x += glm::sin(glm::radians((v[3].x - eSrc.x) * patchsize + fwrap)) * 5; v[3].y += glm::sin(glm::radians((v[3].y - eSrc.y) * patchsize + fwrap)) * 5; v[3].z += glm::sin(glm::radians((v[3].z - eSrc.z) * patchsize + fwrap)) * 5; v[4].x += glm::sin(glm::radians((v[4].x - eSrc.x) * patchsize + fwrap)) * 5; v[4].y += glm::sin(glm::radians((v[4].y - eSrc.y) * patchsize + fwrap)) * 5; v[4].z += glm::sin(glm::radians((v[4].z - eSrc.z) * patchsize + fwrap)) * 5; RenderQuad(p1, v[4], v[0], v[1], rec, norm, mat); RenderQuad(v[4], p2, v[2], v[0], rec, norm, mat); RenderQuad(v[0], v[2], p3, v[3], rec, norm, mat); RenderQuad(v[1], v[0], v[3], p4, rec, norm, mat); } else if(rec == 3) { float zab = glm::sin(glm::radians(ft)); TexturedQuad q; q.v[0].uv.x = 0 + zab; q.v[0].uv.y = 0 + zab; q.v[1].uv.x = 1 + zab; q.v[1].uv.y = 0 + zab; q.v[2].uv.x = 1 + zab; q.v[2].uv.y = 1 + zab; q.v[3].uv.x = 0 + zab; q.v[3].uv.y = 1 + zab; q.v[1].color = q.v[2].color = Color3f(falpha * .3f + Random::getf(0.f, .025f), 0.f, falpha * .5f + Random::getf(0.f, .025f)).toRGB(); q.v[0].color = q.v[3].color = Color3f(falpha * .3f + Random::getf(0.f, .025f), 0.f, falpha * .5f + Random::getf(0.f, .025f)).toRGB(); q.v[0].p = p1; q.v[1].p = p2; q.v[2].p = p3; q.v[3].p = p4; drawQuadRTP(mat, q); } }
void DrawScene() { BeginScene(1); ImageToScreen(pimage_bg,0,0); RenderQuad(pimage_box,0,0,0,0,70,185,1,1,0,maskbox); RenderQuad(pimage_box,0,0,0,0,70,5,1,1,0,maskbox); DrawImage(pimage_icon[0],0,0,0,0,-20,-37,128,128); DrawImage(pimage_icon[1],0,0,0,0,-20,143,128,128); ImageToScreen(pimage_text,0,0); EndScene(); }
void DrawScene() { BeginScene(1); RenderQuad(p_logo,0,0,0,0,(480-p_logo->w)/2,(272-p_logo->h)/2,1,1,0,MAKE_RGBA_8888(255,255,255,40)); mParticleSys->Render(); EndScene(); }
void RenderThread::RenderFrame() { GS_RuntimeInfo runtime_info; m_pEmulator->GetRuntimeInfo(runtime_info); glBindFramebuffer(GL_FRAMEBUFFER, 0); switch (runtime_info.screen_height) { case GS_RESOLUTION_GG_HEIGHT: glBindTexture(GL_TEXTURE_2D, m_GBTexture[0]); break; case GS_RESOLUTION_SMS_HEIGHT: glBindTexture(GL_TEXTURE_2D, m_GBTexture[1]); break; case GS_RESOLUTION_SMS_HEIGHT_EXTENDED: glBindTexture(GL_TEXTURE_2D, m_GBTexture[2]); break; } glTexSubImage2D(GL_TEXTURE_2D, 0, 0, 0, runtime_info.screen_width, runtime_info.screen_height, GL_RGBA, GL_UNSIGNED_BYTE, (GLvoid*) m_pFrameBuffer); if (m_bFiltering) { glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MAG_FILTER, GL_LINEAR); glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MIN_FILTER, GL_LINEAR); } else { glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MAG_FILTER, GL_NEAREST); glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MIN_FILTER, GL_NEAREST); } RenderQuad(m_iWidth, m_iHeight, false); }
void RenderLine2D(Shader *sh, Primitive prim, const float3 &v1, const float3 &v2, float thickness) { auto v = (v2 - v1) / 2; auto len = length(v); auto vnorm = v / len; auto trans = translation(v1 + v) * rotationZ(vnorm.xy()) * float4x4(float4(len, thickness / 2, 1, 1)); RenderQuad(sh, prim, true, trans); }
void PezRender(GLuint windowFbo) { glBindFramebuffer(GL_FRAMEBUFFER, OffscreenFbo); glClearColor(0, 0, 0, 0); glClear(GL_COLOR_BUFFER_BIT); RenderBuddha(); glBindFramebuffer(GL_FRAMEBUFFER, windowFbo); glClearColor(1, 1, 1, 1); glClear(GL_COLOR_BUFFER_BIT); RenderQuad(); }
void RenderThread::RenderMixFrames() { glBindFramebuffer(GL_FRAMEBUFFER, m_AccumulationFramebuffer); glBindTexture(GL_TEXTURE_2D, m_GBTexture); glTexSubImage2D(GL_TEXTURE_2D, 0, 0, 0, GAMEBOY_WIDTH, GAMEBOY_HEIGHT, GL_RGBA, GL_UNSIGNED_BYTE, (GLvoid*) m_pFrameBuffer); float alpha = kMixFrameAlpha; if (m_bFirstFrame) { m_bFirstFrame = false; alpha = 1.0f; } static bool round_error = false; float round_color = 1.0f - (round_error ? 0.03f : 0.0f); round_error = !round_error; glEnable(GL_BLEND); glColor4f(round_color, round_color, round_color, alpha); glBlendFunc(GL_SRC_ALPHA, GL_ONE_MINUS_SRC_ALPHA); RenderQuad(GAMEBOY_WIDTH, GAMEBOY_HEIGHT, false); glColor4f(1.0f, 1.0f, 1.0f, 1.0f); glDisable(GL_BLEND); glBindFramebuffer(GL_FRAMEBUFFER, 0); glBindTexture(GL_TEXTURE_2D, m_AccumulationTexture); if (m_bFiltering) { glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MAG_FILTER, GL_LINEAR); glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MIN_FILTER, GL_LINEAR); } else { glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MAG_FILTER, GL_NEAREST); glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MIN_FILTER, GL_NEAREST); } RenderQuad(m_iWidth, m_iHeight, true); }
void TileLayer::Render(float x, float y, float w, float h) { IRenderer& rRenderer = Renderer::Instance(); // Do alpha blending? if ( m_pPrivData->bAlphaBlending ) rRenderer.SetAlphaBlending(true); // Set rendering color rRenderer.SetColor(m_pPrivData->color); // Do we rotate? if ( m_pPrivData->rotAngle != 0 ) { float xTileCenterOffset = (w/2.0f); float yTileCenterOffset = (h/2.0f); rRenderer.PushMatrix(); rRenderer.Translate(x+xTileCenterOffset, y+yTileCenterOffset); rRenderer.Rotate(m_pPrivData->rotAngle); RenderQuad(m_pPrivData->texId, -xTileCenterOffset, -yTileCenterOffset, w, h); rRenderer.PopMatrix(); } else { // Render texture onto a quad RenderQuad(m_pPrivData->texId, x, y, w, h); } // Restore color rRenderer.SetColor(Color3F::White()); // Restore alpha blending state if ( m_pPrivData->bAlphaBlending ) rRenderer.SetAlphaBlending(false); }
void RenderLine3D(Shader *sh, const float3 &v1, const float3 &v2, const float3 &/*campos*/, float thickness) { glDisable(GL_CULL_FACE); // An exception in 3d mode. // FIXME: need to rotate the line also to make it face the camera. //auto camvec = normalize(campos - (v1 + v2) / 2); auto v = v2 - v1; auto vq = quatfromtwovectors(normalize(v), float3_x); //auto sq = quatfromtwovectors(camvec, float3_z); auto trans = translation((v1 + v2) / 2) * float3x3to4x4(rotation(vq)) * // FIXME: cheaper? float4x4(float4(length(v) / 2, thickness, 1, 1)); RenderQuad(sh, PRIM_FAN, true, trans); glEnable(GL_CULL_FACE); }
static void DrawFps() { glPushMatrix(); glLoadIdentity(); SetOrthographicProjection(); glColor3f(0.0f, 0.0f, 0.0f); RenderQuad(25, 6, 50, 12); glColor3f(1.0f, 1.0f, 1.0f); RenderBitmapString(5, 10, GLUT_BITMAP_TIMES_ROMAN_10, FpsString); glPopMatrix(); RestorePerspectiveProjection(); }
void RenderScene() { glClear(GL_COLOR_BUFFER_BIT); //glColor3f(0.0f, 0.0f, 1.0f); glPushMatrix(); /*glEnableClientState(GL_VERTEX_ARRAY); glVertexPointer(3, GL_FLOAT, 0, cube); glDrawElements(GL_QUADS, 24, GL_UNSIGNED_BYTE, index); glDisableClientState(GL_VERTEX_ARRAY);*/ RenderQuad(); glPopMatrix(); glutSwapBuffers(); }
VOID Render() { SetupMatrix() ; g_ModelViewCamera->OnFrameMove(); g_pd3dDevice->GetRenderTarget(0, &g_pOldRenderTarget) ; g_pd3dDevice->SetRenderTarget(0, g_pRenderSurface) ; g_pd3dDevice->Clear( 0, NULL, D3DCLEAR_TARGET | D3DCLEAR_ZBUFFER, 0xff0000ff, 1.0f, 0 ); // Begin the scene if( SUCCEEDED( g_pd3dDevice->BeginScene() ) ) { // Without this line, the teapot won't show up, what's the inner stuff of SetTexture? g_pd3dDevice->SetTexture(0, NULL) ; // Disable lighting, since we didn't specify color for vertex g_pd3dDevice->SetRenderState( D3DRS_LIGHTING , FALSE ); g_pd3dDevice->SetRenderState(D3DRS_FILLMODE, D3DFILL_WIREFRAME) ; g_pTeapotMesh->DrawSubset(0) ; // End the scene g_pd3dDevice->EndScene(); } g_pd3dDevice->SetRenderTarget(0, g_pOldRenderTarget) ; g_pd3dDevice->Clear( 0, NULL, D3DCLEAR_TARGET | D3DCLEAR_ZBUFFER, 0xff00ff00, 1.0f, 0 ); // Begin the scene if( SUCCEEDED( g_pd3dDevice->BeginScene() ) ) { g_pd3dDevice->SetRenderState(D3DRS_FILLMODE, D3DFILL_SOLID) ; // Render texture RenderQuad() ; // End the scene g_pd3dDevice->EndScene(); } // Present the back-buffer contents to the display g_pd3dDevice->Present( NULL, NULL, NULL, NULL ); }
void RenderThread::RenderFrame() { glBindFramebuffer(GL_FRAMEBUFFER, 0); glBindTexture(GL_TEXTURE_2D, m_GBTexture); glTexSubImage2D(GL_TEXTURE_2D, 0, 0, 0, GAMEBOY_WIDTH, GAMEBOY_HEIGHT, GL_RGBA, GL_UNSIGNED_BYTE, (GLvoid*) m_pFrameBuffer); if (m_bFiltering) { glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MAG_FILTER, GL_LINEAR); glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MIN_FILTER, GL_LINEAR); } else { glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MAG_FILTER, GL_NEAREST); glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MIN_FILTER, GL_NEAREST); } RenderQuad(m_iWidth, m_iHeight, false); }
VOID Render() { SetupMatrix() ; g_pd3dDevice->Clear( 0, NULL, D3DCLEAR_TARGET | D3DCLEAR_ZBUFFER, 0xff000000, 1.0f, 0 ); // Begin the scene if( SUCCEEDED( g_pd3dDevice->BeginScene() ) ) { RenderQuad() ; // End the scene g_pd3dDevice->EndScene(); } // Present the back-buffer contents to the display g_pd3dDevice->Present( NULL, NULL, NULL, NULL ); }
void CMaterialWave::Render(SMaterialRenderData* Data) { GLint tex0 = GetScreenTexture(); glUseProgram(CShader::GetShader(ST_WAVE)->GetProgram()); glActiveTexture(GL_TEXTURE0); glBindTexture(GL_TEXTURE_2D, tex0); glUniform1i(CShader::GetShader(ST_WAVE)->GetUnivormLocation(SUL_TEXTURE0), 0); glActiveTexture(GL_TEXTURE1); glBindTexture(GL_TEXTURE_2D, m_gTexture); glUniform1i(CShader::GetShader(ST_WAVE)->GetUnivormLocation(SUL_TEXTURE1), 1); // glUniform1fv(CShader::GetShader(ST_WAVE)->GetUnivormLocation(SUL_FLOATV), 5, Data->Params); // glUniformMatrix4fv(CShader::GetShader(ST_WAVE)->GetUnivormLocation(SUL_TEXTURE1), 1, GL_FALSE, invertTemp.m); RenderQuad(); }
void IMaterial::RenderFrameBuffer() { glBindTexture(GL_TEXTURE_2D, m_gMainTexFrameBuffer); glCopyTexImage2D(GL_TEXTURE_2D, 0, GL_RGBA, 0, 0, 640, 960, 0); glBindFramebuffer(GL_FRAMEBUFFER, Globals::GetDefaultFramebuffer()); glClearColor(0.0f, 0.0f, 1.0f, 1.0f); glClear(GL_COLOR_BUFFER_BIT | GL_DEPTH_BUFFER_BIT); glUseProgram(CShader::GetShader(ST_FRAME)->GetProgram()); glActiveTexture(GL_TEXTURE0); glBindTexture(GL_TEXTURE_2D, m_gMainTexFrameBuffer); glUniform1i(CShader::GetShader(ST_FRAME)->GetUnivormLocation(SUL_TEXTURE0), 0); RenderQuad(); glBindFramebuffer(GL_FRAMEBUFFER, m_gFB); glClear(GL_COLOR_BUFFER_BIT | GL_DEPTH_BUFFER_BIT); }
void CAsteroid::Render() { int frame = (int) (4.5f * -m_fTemperatureTime / m_fTempTime) + 4; m_pImage->SetFrame(frame); if ( m_fInvincibleTime > 0.0f ) { SDL_Rect target; target = m_pExplosionParticle->GetSize(); target.w += target.w; target.h += target.h; target.x = (int)GetX() - (target.w / 2); target.y = (int)GetY() - (target.h / 2); RenderQuad( target, m_pExplosionParticle, 0, 1 ); } else { CBaseObject::Render(); } }
void OpenGLRenderer::RenderPrimitive(PrimitiveType primitive) { switch (primitive) { case AbstractRenderer::Point: RenderPoint(); break; case AbstractRenderer::Line: RenderLine(); break; case AbstractRenderer::Triangle: RenderTriangle(); break; case AbstractRenderer::Quad: RenderQuad(); break; default: break; } }
VOID Render(float timeDelta) { SetupMatrix() ; UpdateTextureCoordinates(timeDelta) ; // Clear the back-buffer to a RED color g_pd3dDevice->Clear( 0, NULL, D3DCLEAR_TARGET | D3DCLEAR_ZBUFFER, 0xff568800, 1.0f, 0 ); // Begin the scene if( SUCCEEDED( g_pd3dDevice->BeginScene() ) ) { RenderQuad() ; // End the scene g_pd3dDevice->EndScene(); } // Present the back-buffer contents to the display g_pd3dDevice->Present( NULL, NULL, NULL, NULL ); }
// The MAIN function, from here we start our application and run our Game loop int main() { // Init GLFW glfwInit(); glfwWindowHint(GLFW_CONTEXT_VERSION_MAJOR, 4); glfwWindowHint(GLFW_CONTEXT_VERSION_MINOR, 1); glfwWindowHint(GLFW_OPENGL_PROFILE, GLFW_OPENGL_CORE_PROFILE); glfwWindowHint(GLFW_OPENGL_FORWARD_COMPAT, GL_TRUE); glfwWindowHint(GLFW_RESIZABLE, GL_FALSE); GLFWwindow* window = glfwCreateWindow(SCR_WIDTH, SCR_HEIGHT, "LearnOpenGL", nullptr, nullptr); // Windowed glfwMakeContextCurrent(window); // Set the required callback functions glfwSetKeyCallback(window, key_callback); glfwSetCursorPosCallback(window, mouse_callback); glfwSetScrollCallback(window, scroll_callback); // Options glfwSetInputMode(window, GLFW_CURSOR, GLFW_CURSOR_DISABLED); // Initialize GLEW to setup the OpenGL Function pointers glewExperimental = GL_TRUE; glewInit(); // Define the viewport dimensions int width, height; glfwGetFramebufferSize(window, &width, &height); glViewport(0, 0, width, height); // Setup some OpenGL options glEnable(GL_DEPTH_TEST); // Setup and compile our shaders Shader shader("bloom.vs", "bloom.frag"); Shader shaderLight("bloom.vs", "light_box.frag"); Shader shaderBlur("blur.vs", "blur.frag"); Shader shaderBloomFinal("bloom_final.vs", "bloom_final.frag"); // Set samplers shaderBloomFinal.Use(); glUniform1i(glGetUniformLocation(shaderBloomFinal.Program, "scene"), 0); glUniform1i(glGetUniformLocation(shaderBloomFinal.Program, "bloomBlur"), 1); // Light sources // - Positions std::vector<glm::vec3> lightPositions; lightPositions.push_back(glm::vec3(0.0f, 0.5f, 1.5f)); // back light lightPositions.push_back(glm::vec3(-4.0f, 0.5f, -3.0f)); lightPositions.push_back(glm::vec3(3.0f, 0.5f, 1.0f)); lightPositions.push_back(glm::vec3(-.8f, 2.4f, -1.0f)); // - Colors std::vector<glm::vec3> lightColors; lightColors.push_back(glm::vec3(5.0f, 5.0f, 5.0f)); lightColors.push_back(glm::vec3(5.5f, 0.0f, 0.0f)); lightColors.push_back(glm::vec3(0.0f, 0.0f, 15.0f)); lightColors.push_back(glm::vec3(0.0f, 1.5f, 0.0f)); // Load textures GLuint woodTexture = loadTexture(FileSystem::getPath("resources/textures/wood.png").c_str()); GLuint containerTexture = loadTexture(FileSystem::getPath("resources/textures/container2.png").c_str()); // Set up floating point framebuffer to render scene to GLuint hdrFBO; glGenFramebuffers(1, &hdrFBO); glBindFramebuffer(GL_FRAMEBUFFER, hdrFBO); // - Create 2 floating point color buffers (1 for normal rendering, other for brightness treshold values) GLuint colorBuffers[2]; glGenTextures(2, colorBuffers); for (GLuint i = 0; i < 2; i++) { glBindTexture(GL_TEXTURE_2D, colorBuffers[i]); glTexImage2D(GL_TEXTURE_2D, 0, GL_RGB16F, SCR_WIDTH, SCR_HEIGHT, 0, GL_RGB, 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_WRAP_S, GL_CLAMP_TO_EDGE); // We clamp to the edge as the blur filter would otherwise sample repeated texture values! glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_WRAP_T, GL_CLAMP_TO_EDGE); // attach texture to framebuffer glFramebufferTexture2D(GL_FRAMEBUFFER, GL_COLOR_ATTACHMENT0 + i, GL_TEXTURE_2D, colorBuffers[i], 0); } // - Create and attach depth buffer (renderbuffer) GLuint rboDepth; glGenRenderbuffers(1, &rboDepth); glBindRenderbuffer(GL_RENDERBUFFER, rboDepth); glRenderbufferStorage(GL_RENDERBUFFER, GL_DEPTH_COMPONENT, SCR_WIDTH, SCR_HEIGHT); glFramebufferRenderbuffer(GL_FRAMEBUFFER, GL_DEPTH_ATTACHMENT, GL_RENDERBUFFER, rboDepth); // - Tell OpenGL which color attachments we'll use (of this framebuffer) for rendering GLuint attachments[2] = { GL_COLOR_ATTACHMENT0, GL_COLOR_ATTACHMENT1 }; glDrawBuffers(2, attachments); // - Finally check if framebuffer is complete if (glCheckFramebufferStatus(GL_FRAMEBUFFER) != GL_FRAMEBUFFER_COMPLETE) std::cout << "Framebuffer not complete!" << std::endl; glBindFramebuffer(GL_FRAMEBUFFER, 0); // Ping pong framebuffer for blurring GLuint pingpongFBO[2]; GLuint pingpongColorbuffers[2]; glGenFramebuffers(2, pingpongFBO); glGenTextures(2, pingpongColorbuffers); for (GLuint i = 0; i < 2; i++) { glBindFramebuffer(GL_FRAMEBUFFER, pingpongFBO[i]); glBindTexture(GL_TEXTURE_2D, pingpongColorbuffers[i]); glTexImage2D(GL_TEXTURE_2D, 0, GL_RGB16F, SCR_WIDTH, SCR_HEIGHT, 0, GL_RGB, 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_WRAP_S, GL_CLAMP_TO_EDGE); // We clamp to the edge as the blur filter would otherwise sample repeated texture values! glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_WRAP_T, GL_CLAMP_TO_EDGE); glFramebufferTexture2D(GL_FRAMEBUFFER, GL_COLOR_ATTACHMENT0, GL_TEXTURE_2D, pingpongColorbuffers[i], 0); // Also check if framebuffers are complete (no need for depth buffer) if (glCheckFramebufferStatus(GL_FRAMEBUFFER) != GL_FRAMEBUFFER_COMPLETE) std::cout << "Framebuffer not complete!" << std::endl; } glClearColor(0.0f, 0.0f, 0.0f, 1.0f); // Game loop while (!glfwWindowShouldClose(window)) { // Set frame time GLfloat currentFrame = glfwGetTime(); deltaTime = currentFrame - lastFrame; lastFrame = currentFrame; // Check and call events glfwPollEvents(); Do_Movement(); // 1. Render scene into floating point framebuffer glBindFramebuffer(GL_FRAMEBUFFER, hdrFBO); glClear(GL_COLOR_BUFFER_BIT | GL_DEPTH_BUFFER_BIT); glm::mat4 projection = glm::perspective(camera.Zoom, (GLfloat)SCR_WIDTH / (GLfloat)SCR_HEIGHT, 0.1f, 100.0f); glm::mat4 view = camera.GetViewMatrix(); glm::mat4 model; shader.Use(); glUniformMatrix4fv(glGetUniformLocation(shader.Program, "projection"), 1, GL_FALSE, glm::value_ptr(projection)); glUniformMatrix4fv(glGetUniformLocation(shader.Program, "view"), 1, GL_FALSE, glm::value_ptr(view)); glActiveTexture(GL_TEXTURE0); glBindTexture(GL_TEXTURE_2D, woodTexture); // - set lighting uniforms for (GLuint i = 0; i < lightPositions.size(); i++) { glUniform3fv(glGetUniformLocation(shader.Program, ("lights[" + std::to_string(i) + "].Position").c_str()), 1, &lightPositions[i][0]); glUniform3fv(glGetUniformLocation(shader.Program, ("lights[" + std::to_string(i) + "].Color").c_str()), 1, &lightColors[i][0]); } glUniform3fv(glGetUniformLocation(shader.Program, "viewPos"), 1, &camera.Position[0]); // - create one large cube that acts as the floor model = glm::mat4(); model = glm::translate(model, glm::vec3(0.0f, -1.0f, 0.0)); model = glm::scale(model, glm::vec3(25.0f, 1.0f, 25.0f)); glUniformMatrix4fv(glGetUniformLocation(shader.Program, "model"), 1, GL_FALSE, glm::value_ptr(model)); RenderCube(); // - then create multiple cubes as the scenery glBindTexture(GL_TEXTURE_2D, containerTexture); model = glm::mat4(); model = glm::translate(model, glm::vec3(0.0f, 1.5f, 0.0)); glUniformMatrix4fv(glGetUniformLocation(shader.Program, "model"), 1, GL_FALSE, glm::value_ptr(model)); RenderCube(); model = glm::mat4(); model = glm::translate(model, glm::vec3(2.0f, 0.0f, 1.0)); glUniformMatrix4fv(glGetUniformLocation(shader.Program, "model"), 1, GL_FALSE, glm::value_ptr(model)); RenderCube(); model = glm::mat4(); model = glm::translate(model, glm::vec3(-1.0f, -1.0f, 2.0)); model = glm::rotate(model, 60.0f, glm::normalize(glm::vec3(1.0, 0.0, 1.0))); model = glm::scale(model, glm::vec3(2.0)); glUniformMatrix4fv(glGetUniformLocation(shader.Program, "model"), 1, GL_FALSE, glm::value_ptr(model)); RenderCube(); model = glm::mat4(); model = glm::translate(model, glm::vec3(0.0f, 2.7f, 4.0)); model = glm::rotate(model, 23.0f, glm::normalize(glm::vec3(1.0, 0.0, 1.0))); model = glm::scale(model, glm::vec3(2.5)); glUniformMatrix4fv(glGetUniformLocation(shader.Program, "model"), 1, GL_FALSE, glm::value_ptr(model)); RenderCube(); model = glm::mat4(); model = glm::translate(model, glm::vec3(-2.0f, 1.0f, -3.0)); model = glm::rotate(model, 124.0f, glm::normalize(glm::vec3(1.0, 0.0, 1.0))); model = glm::scale(model, glm::vec3(2.0)); glUniformMatrix4fv(glGetUniformLocation(shader.Program, "model"), 1, GL_FALSE, glm::value_ptr(model)); RenderCube(); RenderCube(); model = glm::mat4(); model = glm::translate(model, glm::vec3(-3.0f, 0.0f, 0.0)); glUniformMatrix4fv(glGetUniformLocation(shader.Program, "model"), 1, GL_FALSE, glm::value_ptr(model)); RenderCube(); // - finally show all the light sources as bright cubes shaderLight.Use(); glUniformMatrix4fv(glGetUniformLocation(shaderLight.Program, "projection"), 1, GL_FALSE, glm::value_ptr(projection)); glUniformMatrix4fv(glGetUniformLocation(shaderLight.Program, "view"), 1, GL_FALSE, glm::value_ptr(view)); for (GLuint i = 0; i < lightPositions.size(); i++) { model = glm::mat4(); model = glm::translate(model, glm::vec3(lightPositions[i])); model = glm::scale(model, glm::vec3(0.5f)); glUniformMatrix4fv(glGetUniformLocation(shaderLight.Program, "model"), 1, GL_FALSE, glm::value_ptr(model)); glUniform3fv(glGetUniformLocation(shaderLight.Program, "lightColor"), 1, &lightColors[i][0]); RenderCube(); } glBindFramebuffer(GL_FRAMEBUFFER, 0); // 2. Blur bright fragments w/ two-pass Gaussian Blur GLboolean horizontal = true, first_iteration = true; GLuint amount = 10; shaderBlur.Use(); for (GLuint i = 0; i < amount; i++) { glBindFramebuffer(GL_FRAMEBUFFER, pingpongFBO[horizontal]); glUniform1i(glGetUniformLocation(shaderBlur.Program, "horizontal"), horizontal); glBindTexture(GL_TEXTURE_2D, first_iteration ? colorBuffers[1] : pingpongColorbuffers[!horizontal]); // bind texture of other framebuffer (or scene if first iteration) RenderQuad(); horizontal = !horizontal; if (first_iteration) first_iteration = false; } glBindFramebuffer(GL_FRAMEBUFFER, 0); // 2. Now render floating point color buffer to 2D quad and tonemap HDR colors to default framebuffer's (clamped) color range glClear(GL_COLOR_BUFFER_BIT | GL_DEPTH_BUFFER_BIT); shaderBloomFinal.Use(); glActiveTexture(GL_TEXTURE0); glBindTexture(GL_TEXTURE_2D, colorBuffers[0]); //glBindTexture(GL_TEXTURE_2D, pingpongColorbuffers[!horizontal]); glActiveTexture(GL_TEXTURE1); glBindTexture(GL_TEXTURE_2D, pingpongColorbuffers[!horizontal]); glUniform1i(glGetUniformLocation(shaderBloomFinal.Program, "bloom"), bloom); glUniform1f(glGetUniformLocation(shaderBloomFinal.Program, "exposure"), exposure); RenderQuad(); // Swap the buffers glfwSwapBuffers(window); } glfwTerminate(); return 0; }
void CCreateField::RenderSubDivFace(Vec3f * b, Vec3f * t, int b1, int b2, int t1, int t2, RenderMaterial & mat) { Vec3f norm = (b[b1] + b[b2] + t[t1] + t[t2]) * 0.25f - eSrc; norm = glm::normalize(norm); RenderQuad(b[b1], b[b2], t[t1], t[t2], 1, norm, mat); }
// The MAIN function, from here we start our application and run our Game loop int main() { // Init GLFW glfwInit(); glfwWindowHint(GLFW_CONTEXT_VERSION_MAJOR, 3); glfwWindowHint(GLFW_CONTEXT_VERSION_MINOR, 3); glfwWindowHint(GLFW_OPENGL_PROFILE, GLFW_OPENGL_CORE_PROFILE); glfwWindowHint(GLFW_RESIZABLE, GL_FALSE); GLFWwindow* window = glfwCreateWindow(SCR_WIDTH, SCR_HEIGHT, "LearnOpenGL", nullptr, nullptr); // Windowed glfwMakeContextCurrent(window); // Set the required callback functions glfwSetKeyCallback(window, key_callback); glfwSetCursorPosCallback(window, mouse_callback); glfwSetScrollCallback(window, scroll_callback); // Options glfwSetInputMode(window, GLFW_CURSOR, GLFW_CURSOR_DISABLED); // Initialize GLEW to setup the OpenGL Function pointers glewExperimental = GL_TRUE; glewInit(); // Define the viewport dimensions glViewport(0, 0, SCR_WIDTH, SCR_HEIGHT); // Setup some OpenGL options glEnable(GL_DEPTH_TEST); // Setup and compile our shaders Shader shaderGeometryPass("g_buffer.vs", "g_buffer.frag"); Shader shaderLightingPass("deferred_shading.vs", "deferred_shading.frag"); Shader shaderLightBox("deferred_light_box.vs", "deferred_light_box.frag"); // Set samplers shaderLightingPass.Use(); glUniform1i(glGetUniformLocation(shaderLightingPass.Program, "gPosition"), 0); glUniform1i(glGetUniformLocation(shaderLightingPass.Program, "gNormal"), 1); glUniform1i(glGetUniformLocation(shaderLightingPass.Program, "gAlbedoSpec"), 2); // Models Model cyborg(FileSystem::getPath("resources/objects/nanosuit/nanosuit.obj").c_str()); std::vector<glm::vec3> objectPositions; objectPositions.push_back(glm::vec3(-3.0, -3.0, -3.0)); objectPositions.push_back(glm::vec3(0.0, -3.0, -3.0)); objectPositions.push_back(glm::vec3(3.0, -3.0, -3.0)); objectPositions.push_back(glm::vec3(-3.0, -3.0, 0.0)); objectPositions.push_back(glm::vec3(0.0, -3.0, 0.0)); objectPositions.push_back(glm::vec3(3.0, -3.0, 0.0)); objectPositions.push_back(glm::vec3(-3.0, -3.0, 3.0)); objectPositions.push_back(glm::vec3(0.0, -3.0, 3.0)); objectPositions.push_back(glm::vec3(3.0, -3.0, 3.0)); // - Colors const GLuint NR_LIGHTS = 32; std::vector<glm::vec3> lightPositions; std::vector<glm::vec3> lightColors; srand(13); for (GLuint i = 0; i < NR_LIGHTS; i++) { // Calculate slightly random offsets GLfloat xPos = ((rand() % 100) / 100.0) * 6.0 - 3.0; GLfloat yPos = ((rand() % 100) / 100.0) * 6.0 - 4.0; GLfloat zPos = ((rand() % 100) / 100.0) * 6.0 - 3.0; lightPositions.push_back(glm::vec3(xPos, yPos, zPos)); // Also calculate random color GLfloat rColor = ((rand() % 100) / 200.0f) + 0.5; // Between 0.5 and 1.0 GLfloat gColor = ((rand() % 100) / 200.0f) + 0.5; // Between 0.5 and 1.0 GLfloat bColor = ((rand() % 100) / 200.0f) + 0.5; // Between 0.5 and 1.0 lightColors.push_back(glm::vec3(rColor, gColor, bColor)); } // Set up G-Buffer // 3 textures: // 1. Positions (RGB) // 2. Color (RGB) + Specular (A) // 3. Normals (RGB) GLuint gBuffer; glGenFramebuffers(1, &gBuffer); glBindFramebuffer(GL_FRAMEBUFFER, gBuffer); GLuint gPosition, gNormal, gAlbedoSpec; // - Position color buffer glGenTextures(1, &gPosition); glBindTexture(GL_TEXTURE_2D, gPosition); glTexImage2D(GL_TEXTURE_2D, 0, GL_RGB16F, SCR_WIDTH, SCR_HEIGHT, 0, GL_RGB, GL_FLOAT, NULL); glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MIN_FILTER, GL_NEAREST); glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MAG_FILTER, GL_NEAREST); glFramebufferTexture2D(GL_FRAMEBUFFER, GL_COLOR_ATTACHMENT0, GL_TEXTURE_2D, gPosition, 0); // - Normal color buffer glGenTextures(1, &gNormal); glBindTexture(GL_TEXTURE_2D, gNormal); glTexImage2D(GL_TEXTURE_2D, 0, GL_RGB16F, SCR_WIDTH, SCR_HEIGHT, 0, GL_RGB, GL_FLOAT, NULL); glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MIN_FILTER, GL_NEAREST); glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MAG_FILTER, GL_NEAREST); glFramebufferTexture2D(GL_FRAMEBUFFER, GL_COLOR_ATTACHMENT1, GL_TEXTURE_2D, gNormal, 0); // - Color + Specular color buffer glGenTextures(1, &gAlbedoSpec); glBindTexture(GL_TEXTURE_2D, gAlbedoSpec); glTexImage2D(GL_TEXTURE_2D, 0, GL_RGBA, SCR_WIDTH, SCR_HEIGHT, 0, GL_RGBA, GL_UNSIGNED_BYTE, NULL); glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MIN_FILTER, GL_NEAREST); glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MAG_FILTER, GL_NEAREST); glFramebufferTexture2D(GL_FRAMEBUFFER, GL_COLOR_ATTACHMENT2, GL_TEXTURE_2D, gAlbedoSpec, 0); // - Tell OpenGL which color attachments we'll use (of this framebuffer) for rendering GLuint attachments[3] = { GL_COLOR_ATTACHMENT0, GL_COLOR_ATTACHMENT1, GL_COLOR_ATTACHMENT2 }; glDrawBuffers(3, attachments); // - Create and attach depth buffer (renderbuffer) GLuint rboDepth; glGenRenderbuffers(1, &rboDepth); glBindRenderbuffer(GL_RENDERBUFFER, rboDepth); glRenderbufferStorage(GL_RENDERBUFFER, GL_DEPTH_COMPONENT, SCR_WIDTH, SCR_HEIGHT); glFramebufferRenderbuffer(GL_FRAMEBUFFER, GL_DEPTH_ATTACHMENT, GL_RENDERBUFFER, rboDepth); // - Finally check if framebuffer is complete if (glCheckFramebufferStatus(GL_FRAMEBUFFER) != GL_FRAMEBUFFER_COMPLETE) std::cout << "Framebuffer not complete!" << std::endl; glBindFramebuffer(GL_FRAMEBUFFER, 0); glClearColor(0.0f, 0.0f, 0.0f, 0.0f); // Game loop while (!glfwWindowShouldClose(window)) { // Set frame time GLfloat currentFrame = glfwGetTime(); deltaTime = currentFrame - lastFrame; lastFrame = currentFrame; // Check and call events glfwPollEvents(); Do_Movement(); glPolygonMode(GL_FRONT_AND_BACK, wireframe ? GL_LINE : GL_FILL); // 1. Geometry Pass: render scene's geometry/color data into gbuffer glBindFramebuffer(GL_FRAMEBUFFER, gBuffer); glClear(GL_COLOR_BUFFER_BIT | GL_DEPTH_BUFFER_BIT); glm::mat4 projection = glm::perspective(camera.Zoom, (GLfloat)SCR_WIDTH / (GLfloat)SCR_HEIGHT, 0.1f, 100.0f); glm::mat4 view = camera.GetViewMatrix(); glm::mat4 model; shaderGeometryPass.Use(); glUniformMatrix4fv(glGetUniformLocation(shaderGeometryPass.Program, "projection"), 1, GL_FALSE, glm::value_ptr(projection)); glUniformMatrix4fv(glGetUniformLocation(shaderGeometryPass.Program, "view"), 1, GL_FALSE, glm::value_ptr(view)); for (GLuint i = 0; i < objectPositions.size(); i++) { model = glm::mat4(); model = glm::translate(model, objectPositions[i]); model = glm::scale(model, glm::vec3(0.25f)); glUniformMatrix4fv(glGetUniformLocation(shaderGeometryPass.Program, "model"), 1, GL_FALSE, glm::value_ptr(model)); cyborg.Draw(shaderGeometryPass); } glBindFramebuffer(GL_FRAMEBUFFER, 0); glPolygonMode(GL_FRONT_AND_BACK, GL_FILL); // 2. Lighting Pass: calculate lighting by iterating over a screen filled quad pixel-by-pixel using the gbuffer's content. glClear(GL_COLOR_BUFFER_BIT | GL_DEPTH_BUFFER_BIT); shaderLightingPass.Use(); glActiveTexture(GL_TEXTURE0); glBindTexture(GL_TEXTURE_2D, gPosition); glActiveTexture(GL_TEXTURE1); glBindTexture(GL_TEXTURE_2D, gNormal); glActiveTexture(GL_TEXTURE2); glBindTexture(GL_TEXTURE_2D, gAlbedoSpec); // Also send light relevant uniforms for (GLuint i = 0; i < lightPositions.size(); i++) { glUniform3fv(glGetUniformLocation(shaderLightingPass.Program, ("lights[" + std::to_string(i) + "].Position").c_str()), 1, &lightPositions[i][0]); glUniform3fv(glGetUniformLocation(shaderLightingPass.Program, ("lights[" + std::to_string(i) + "].Color").c_str()), 1, &lightColors[i][0]); // Update attenuation parameters and calculate radius const GLfloat constant = 1.0; // Note that we don't send this to the shader, we assume it is always 1.0 (in our case) const GLfloat linear = 0.7; const GLfloat quadratic = 1.8; glUniform1f(glGetUniformLocation(shaderLightingPass.Program, ("lights[" + std::to_string(i) + "].Linear").c_str()), linear); glUniform1f(glGetUniformLocation(shaderLightingPass.Program, ("lights[" + std::to_string(i) + "].Quadratic").c_str()), quadratic); // Then calculate radius of light volume/sphere const GLfloat lightThreshold = 5.0; // 5 / 256 const GLfloat maxBrightness = std::fmaxf(std::fmaxf(lightColors[i].r, lightColors[i].g), lightColors[i].b); GLfloat radius = (-linear + static_cast<float>(std::sqrt(linear * linear - 4 * quadratic * (constant - (256.0 / lightThreshold) * maxBrightness)))) / (2 * quadratic); glUniform1f(glGetUniformLocation(shaderLightingPass.Program, ("lights[" + std::to_string(i) + "].Radius").c_str()), radius); } glUniform3fv(glGetUniformLocation(shaderLightingPass.Program, "viewPos"), 1, &camera.Position[0]); glUniform1i(glGetUniformLocation(shaderLightingPass.Program, "draw_mode"), draw_mode); RenderQuad(); // 2.5. Copy content of geometry's depth buffer to default framebuffer's depth buffer glBindFramebuffer(GL_READ_FRAMEBUFFER, gBuffer); glBindFramebuffer(GL_DRAW_FRAMEBUFFER, 0); // Write to default framebuffer // blit to default framebuffer. Note that this may or may not work as the internal formats of both the FBO and default framebuffer have to match. // the internal formats are implementation defined. This works on all of my systems, but if it doesn't on yours you'll likely have to write to the // depth buffer in another stage (or somehow see to match the default framebuffer's internal format with the FBO's internal format). glBlitFramebuffer(0, 0, SCR_WIDTH, SCR_HEIGHT, 0, 0, SCR_WIDTH, SCR_HEIGHT, GL_DEPTH_BUFFER_BIT, GL_NEAREST); glBindFramebuffer(GL_FRAMEBUFFER, 0); // 3. Render lights on top of scene, by blitting shaderLightBox.Use(); glUniformMatrix4fv(glGetUniformLocation(shaderLightBox.Program, "projection"), 1, GL_FALSE, glm::value_ptr(projection)); glUniformMatrix4fv(glGetUniformLocation(shaderLightBox.Program, "view"), 1, GL_FALSE, glm::value_ptr(view)); for (GLuint i = 0; i < lightPositions.size(); i++) { model = glm::mat4(); model = glm::translate(model, lightPositions[i]); model = glm::scale(model, glm::vec3(0.25f)); glUniformMatrix4fv(glGetUniformLocation(shaderLightBox.Program, "model"), 1, GL_FALSE, glm::value_ptr(model)); glUniform3fv(glGetUniformLocation(shaderLightBox.Program, "lightColor"), 1, &lightColors[i][0]); RenderCube(); } // Swap the buffers glfwSwapBuffers(window); } glfwTerminate(); return 0; }
void Render(void) { RenderToTextures(); RenderQuad(); }
// The MAIN function, from here we start our application and run our Game loop int main() { // Init GLFW glfwInit(); glfwWindowHint(GLFW_CONTEXT_VERSION_MAJOR, 3); glfwWindowHint(GLFW_CONTEXT_VERSION_MINOR, 3); glfwWindowHint(GLFW_OPENGL_PROFILE, GLFW_OPENGL_CORE_PROFILE); glfwWindowHint(GLFW_RESIZABLE, GL_FALSE); GLFWwindow* window = glfwCreateWindow(SCR_WIDTH, SCR_HEIGHT, "LearnOpenGL", nullptr, nullptr); // Windowed glfwMakeContextCurrent(window); // Set the required callback functions glfwSetKeyCallback(window, key_callback); glfwSetCursorPosCallback(window, mouse_callback); glfwSetScrollCallback(window, scroll_callback); // Options glfwSetInputMode(window, GLFW_CURSOR, GLFW_CURSOR_DISABLED); // Initialize GLEW to setup the OpenGL Function pointers glewExperimental = GL_TRUE; glewInit(); // Define the viewport dimensions glViewport(0, 0, SCR_WIDTH, SCR_HEIGHT); // Setup some OpenGL options glEnable(GL_DEPTH_TEST); // Setup and compile our shaders Shader shader("resources/normal_map/normal_mapping.vs", "resources/normal_map/normal_mapping.frag"); // Load textures GLuint diffuseMap = loadTexture("resources/normal_map/brickwall.jpg"); GLuint normalMap = loadTexture("resources/normal_map/brickwall_normal.jpg"); // Set texture units shader.Use(); glUniform1i(glGetUniformLocation(shader.Program, "diffuseMap"), 0); glUniform1i(glGetUniformLocation(shader.Program, "normalMap"), 1); // Light position glm::vec3 lightPos(0.5f, 1.0f, 0.3f); // Game loop while (!glfwWindowShouldClose(window)) { // Set frame time GLfloat currentFrame = glfwGetTime(); deltaTime = currentFrame - lastFrame; lastFrame = currentFrame; // Check and call events glfwPollEvents(); Do_Movement(); // Clear the colorbuffer glClearColor(0.1f, 0.1f, 0.1f, 1.0f); glClear(GL_COLOR_BUFFER_BIT | GL_DEPTH_BUFFER_BIT); // Configure view/projection matrices shader.Use(); glm::mat4 view = camera.GetViewMatrix(); glm::mat4 projection = glm::perspective(camera.Zoom, (float)SCR_WIDTH / (float)SCR_HEIGHT, 0.1f, 100.0f); glUniformMatrix4fv(glGetUniformLocation(shader.Program, "view"), 1, GL_FALSE, glm::value_ptr(view)); glUniformMatrix4fv(glGetUniformLocation(shader.Program, "projection"), 1, GL_FALSE, glm::value_ptr(projection)); // Render normal-mapped quad glm::mat4 model; model = glm::rotate(model, (GLfloat)glfwGetTime() * -0.1f, glm::normalize(glm::vec3(1.0, 0.0, 1.0))); // Rotates the quad to show normal mapping works in all directions glUniformMatrix4fv(glGetUniformLocation(shader.Program, "model"), 1, GL_FALSE, glm::value_ptr(model)); glUniform3fv(glGetUniformLocation(shader.Program, "lightPos"), 1, &lightPos[0]); glUniform3fv(glGetUniformLocation(shader.Program, "viewPos"), 1, &camera.Position[0]); glActiveTexture(GL_TEXTURE0); glBindTexture(GL_TEXTURE_2D, diffuseMap); glActiveTexture(GL_TEXTURE1); glBindTexture(GL_TEXTURE_2D, normalMap); RenderQuad(); // render light source (simply re-renders a smaller plane at the light's position for debugging/visualization) model = glm::mat4(); model = glm::translate(model, lightPos); model = glm::scale(model, glm::vec3(0.1f)); glUniformMatrix4fv(glGetUniformLocation(shader.Program, "model"), 1, GL_FALSE, glm::value_ptr(model)); RenderQuad(); // Swap the buffers glfwSwapBuffers(window); } glfwTerminate(); return 0; }
void SCRenderer::RenderBlock(RSArea* area, int LOD, int i, bool renderTexture){ AreaBlock* block = area->GetAreaBlockByID(LOD, i); uint32_t sideSize = block->sideSize; for (size_t x=0 ; x < sideSize-1 ; x ++){ for (size_t y=0 ; y < sideSize-1 ; y ++){ MapVertex* currentVertex = &block->vertice[x+y*sideSize]; MapVertex* rightVertex = &block->vertice[(x+1)+y*sideSize]; MapVertex* bottomRightVertex = &block->vertice[(x+1)+(y+1)*sideSize]; MapVertex* bottomVertex = &block->vertice[x+(y+1)*sideSize]; RenderQuad(currentVertex,rightVertex, bottomRightVertex, bottomVertex,area,renderTexture); } } //Inter-block right side if ( i % 18 != 17){ AreaBlock* currentBlock = area->GetAreaBlockByID(LOD, i); AreaBlock* rightBlock = area->GetAreaBlockByID(LOD, i+1); for (int y=0 ; y < sideSize-1 ; y ++){ MapVertex* currentVertex = currentBlock->GetVertice(currentBlock->sideSize-1, y); MapVertex* rightVertex = rightBlock->GetVertice(0, y); MapVertex* bottomRightVertex = rightBlock->GetVertice(0, y+1); MapVertex* bottomVertex = currentBlock->GetVertice(currentBlock->sideSize-1, y+1); RenderQuad(currentVertex,rightVertex, bottomRightVertex, bottomVertex,area,renderTexture); } } //Inter-block bottom side if ( i / 18 != 17){ AreaBlock* currentBlock = area->GetAreaBlockByID(LOD, i); AreaBlock* bottomBlock = area->GetAreaBlockByID(LOD, i+BLOCK_PER_MAP_SIDE); for (int x=0 ; x < sideSize-1 ; x++){ MapVertex* currentVertex = currentBlock->GetVertice(x,currentBlock->sideSize-1); MapVertex* rightVertex = currentBlock->GetVertice(x+1,currentBlock->sideSize-1); MapVertex* bottomRightVertex = bottomBlock->GetVertice(x+1,0); MapVertex* bottomVertex = bottomBlock->GetVertice(x,0); RenderQuad(currentVertex,rightVertex, bottomRightVertex, bottomVertex,area,renderTexture); } } //Inter bottom-right quad if ( i % 18 != 17 && i / 18 != 17){ AreaBlock* currentBlock = area->GetAreaBlockByID(LOD, i); AreaBlock* rightBlock = area->GetAreaBlockByID(LOD, i+1); AreaBlock* rightBottonBlock = area->GetAreaBlockByID(LOD, i+1+BLOCK_PER_MAP_SIDE); AreaBlock* bottomBlock = area->GetAreaBlockByID(LOD, i+BLOCK_PER_MAP_SIDE); MapVertex* currentVertex = currentBlock->GetVertice(currentBlock->sideSize-1,currentBlock->sideSize-1); MapVertex* rightVertex = rightBlock->GetVertice(0,currentBlock->sideSize-1); MapVertex* bottomRightVertex = rightBottonBlock->GetVertice(0,0); MapVertex* bottomVertex = bottomBlock->GetVertice(currentBlock->sideSize-1,0); RenderQuad(currentVertex,rightVertex, bottomRightVertex, bottomVertex,area,renderTexture); } }
// The MAIN function, from here we start our application and run our Game loop int main() { // Init GLFW glfwInit(); glfwWindowHint(GLFW_CONTEXT_VERSION_MAJOR, 3); glfwWindowHint(GLFW_CONTEXT_VERSION_MINOR, 3); glfwWindowHint(GLFW_OPENGL_PROFILE, GLFW_OPENGL_CORE_PROFILE); glfwWindowHint(GLFW_RESIZABLE, GL_FALSE); GLFWwindow* window = glfwCreateWindow(SCR_WIDTH, SCR_HEIGHT, "LearnOpenGL", nullptr, nullptr); // Windowed glfwMakeContextCurrent(window); // Set the required callback functions glfwSetKeyCallback(window, key_callback); glfwSetCursorPosCallback(window, mouse_callback); glfwSetScrollCallback(window, scroll_callback); // Options glfwSetInputMode(window, GLFW_CURSOR, GLFW_CURSOR_DISABLED); // Initialize GLEW to setup the OpenGL Function pointers glewExperimental = GL_TRUE; glewInit(); // Define the viewport dimensions glViewport(0, 0, SCR_WIDTH, SCR_HEIGHT); // Setup some OpenGL options glEnable(GL_DEPTH_TEST); // Setup and compile our shaders ////Shader shader("shadow_mapping.vs", "shadow_mapping.frag"); Shader simpleDepthShader("shadow_mapping_depth.vs", "shadow_mapping_depth.frag"); Shader shaderGeometryPass("g_buffer.vs", "g_buffer.frag"); Shader shaderLightingPass("deferred_shading.vs", "deferred_shading.frag"); // Set texture samples ////shader.Use(); ////glUniform1i(glGetUniformLocation(shader.Program, "diffuseTexture"), 0); ////glUniform1i(glGetUniformLocation(shader.Program, "shadowMap"), 1); // Set samplers shaderLightingPass.Use(); glUniform1i(glGetUniformLocation(shaderLightingPass.Program, "gPosition"), 0); glUniform1i(glGetUniformLocation(shaderLightingPass.Program, "gNormal"), 1); glUniform1i(glGetUniformLocation(shaderLightingPass.Program, "gAlbedoSpec"), 2); glUniform1i(glGetUniformLocation(shaderLightingPass.Program, "gDepthViewer"), 3); glUniform1i(glGetUniformLocation(shaderLightingPass.Program, "gShadowMap"), 4); shaderGeometryPass.Use(); glUniform1i(glGetUniformLocation(shaderGeometryPass.Program, "texture_diffuse1"), 0); glUniform1i(glGetUniformLocation(shaderGeometryPass.Program, "texture_specular1"), 1); GLfloat planeVertices[] = { // Positions // Normals // Texture Coords 25.0f, -0.5f, 25.0f, 0.0f, 1.0f, 0.0f, 25.0f, 0.0f, -25.0f, -0.5f, -25.0f, 0.0f, 1.0f, 0.0f, 0.0f, 25.0f, -25.0f, -0.5f, 25.0f, 0.0f, 1.0f, 0.0f, 0.0f, 0.0f, 25.0f, -0.5f, 25.0f, 0.0f, 1.0f, 0.0f, 25.0f, 0.0f, 25.0f, -0.5f, -25.0f, 0.0f, 1.0f, 0.0f, 25.0f, 25.0f, -25.0f, -0.5f, -25.0f, 0.0f, 1.0f, 0.0f, 0.0f, 25.0f }; // Setup plane VAO GLuint planeVBO; glGenVertexArrays(1, &planeVAO); glGenBuffers(1, &planeVBO); glBindVertexArray(planeVAO); glBindBuffer(GL_ARRAY_BUFFER, planeVBO); glBufferData(GL_ARRAY_BUFFER, sizeof(planeVertices), &planeVertices, GL_STATIC_DRAW); glEnableVertexAttribArray(0); glVertexAttribPointer(0, 3, GL_FLOAT, GL_FALSE, 8 * sizeof(GLfloat), (GLvoid*)0); glEnableVertexAttribArray(1); glVertexAttribPointer(1, 3, GL_FLOAT, GL_FALSE, 8 * sizeof(GLfloat), (GLvoid*)(3 * sizeof(GLfloat))); glEnableVertexAttribArray(2); glVertexAttribPointer(2, 2, GL_FLOAT, GL_FALSE, 8 * sizeof(GLfloat), (GLvoid*)(6 * sizeof(GLfloat))); glBindVertexArray(0); // Light source glm::vec3 lightPos(-2.0f, 4.0f, -1.0f); // Load textures woodTexture = loadTexture(FileSystem::getPath("resources/textures/wood.png").c_str()); // Configure depth map FBO const GLuint SHADOW_WIDTH = 1024, SHADOW_HEIGHT = 1024; GLuint depthMapFBO; glGenFramebuffers(1, &depthMapFBO); // - Create depth texture GLuint gShadowMap; glGenTextures(1, &gShadowMap); glBindTexture(GL_TEXTURE_2D, gShadowMap); glTexImage2D(GL_TEXTURE_2D, 0, GL_DEPTH_COMPONENT, SHADOW_WIDTH, SHADOW_HEIGHT, 0, GL_DEPTH_COMPONENT, GL_FLOAT, NULL); glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MIN_FILTER, GL_NEAREST); glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MAG_FILTER, GL_NEAREST); glBindFramebuffer(GL_FRAMEBUFFER, depthMapFBO); glFramebufferTexture2D(GL_FRAMEBUFFER, GL_DEPTH_ATTACHMENT, GL_TEXTURE_2D, gShadowMap, 0); glDrawBuffer(GL_NONE); glReadBuffer(GL_NONE); glBindFramebuffer(GL_FRAMEBUFFER, 0); // Set up G-Buffer // 3 textures: // 1. Positions (RGB) // 2. Color (RGB) + Specular (A) // 3. Normals (RGB) //// 4. gDepthViewer (DEPTH) GLuint gBuffer; glGenFramebuffers(1, &gBuffer); glBindFramebuffer(GL_FRAMEBUFFER, gBuffer); GLuint gPosition, gNormal, gAlbedoSpec, gDepthViewer; // - Position color buffer glGenTextures(1, &gPosition); glBindTexture(GL_TEXTURE_2D, gPosition); glTexImage2D(GL_TEXTURE_2D, 0, GL_RGB16F, SCR_WIDTH, SCR_HEIGHT, 0, GL_RGB, GL_FLOAT, NULL); glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MIN_FILTER, GL_NEAREST); glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MAG_FILTER, GL_NEAREST); glFramebufferTexture2D(GL_FRAMEBUFFER, GL_COLOR_ATTACHMENT0, GL_TEXTURE_2D, gPosition, 0); // - Normal color buffer glGenTextures(1, &gNormal); glBindTexture(GL_TEXTURE_2D, gNormal); glTexImage2D(GL_TEXTURE_2D, 0, GL_RGB, SCR_WIDTH, SCR_HEIGHT, 0, GL_RGB, GL_FLOAT, NULL); glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MIN_FILTER, GL_NEAREST); glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MAG_FILTER, GL_NEAREST); glFramebufferTexture2D(GL_FRAMEBUFFER, GL_COLOR_ATTACHMENT1, GL_TEXTURE_2D, gNormal, 0); // - Color + Specular color buffer glGenTextures(1, &gAlbedoSpec); glBindTexture(GL_TEXTURE_2D, gAlbedoSpec); glTexImage2D(GL_TEXTURE_2D, 0, GL_RGBA, SCR_WIDTH, SCR_HEIGHT, 0, GL_RGBA, GL_FLOAT, NULL); glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MIN_FILTER, GL_NEAREST); glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MAG_FILTER, GL_NEAREST); glFramebufferTexture2D(GL_FRAMEBUFFER, GL_COLOR_ATTACHMENT2, GL_TEXTURE_2D, gAlbedoSpec, 0); // - Depth Map from viewer buffer glGenTextures(1, &gDepthViewer); glBindTexture(GL_TEXTURE_2D, gDepthViewer); glTexImage2D(GL_TEXTURE_2D, 0, GL_RGBA, SCR_WIDTH, SCR_HEIGHT, 0, GL_RGBA, GL_FLOAT, NULL); glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MIN_FILTER, GL_NEAREST); glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MAG_FILTER, GL_NEAREST); glFramebufferTexture2D(GL_FRAMEBUFFER, GL_COLOR_ATTACHMENT3, GL_TEXTURE_2D, gDepthViewer, 0); // - Tell OpenGL which color attachments we'll use (of this framebuffer) for rendering GLuint attachments[4] = { GL_COLOR_ATTACHMENT0, GL_COLOR_ATTACHMENT1, GL_COLOR_ATTACHMENT2, GL_COLOR_ATTACHMENT3 }; //////check! glDrawBuffers(4, attachments); glClearColor(0.1f, 0.1f, 0.1f, 1.0f); // Game loop while (!glfwWindowShouldClose(window)) { // Set frame time GLfloat currentFrame = glfwGetTime(); deltaTime = currentFrame - lastFrame; lastFrame = currentFrame; // Check and call events glfwPollEvents(); Do_Movement(); // Change light position over time lightPos.z = cos(glfwGetTime()) * 2.0f; // 1. Render depth of scene to texture (from light's perspective) // - Get light projection/view matrix. glm::mat4 lightProjection, lightView; glm::mat4 lightSpaceMatrix; GLfloat near_plane = 1.0f, far_plane = 9.5f; //lightProjection = glm::ortho(-10.0f, 10.0f, -10.0f, 10.0f, near_plane, far_plane); lightProjection = glm::perspective(65.0f, (GLfloat)SHADOW_WIDTH / (GLfloat)SHADOW_HEIGHT, near_plane, far_plane); // Note that if you use a perspective projection matrix you'll have to change the light position as the current light position isn't enough to reflect the whole scene. lightView = glm::lookAt(lightPos, glm::vec3(0.0f), glm::vec3(1.0)); lightSpaceMatrix = lightProjection * lightView; // - now render scene from light's point of view simpleDepthShader.Use(); glUniformMatrix4fv(glGetUniformLocation(simpleDepthShader.Program, "lightSpaceMatrix"), 1, GL_FALSE, glm::value_ptr(lightSpaceMatrix)); glViewport(0, 0, SHADOW_WIDTH, SHADOW_HEIGHT); glBindFramebuffer(GL_FRAMEBUFFER, depthMapFBO); glClear(GL_DEPTH_BUFFER_BIT); RenderScene(simpleDepthShader); glBindFramebuffer(GL_FRAMEBUFFER, 0); /* // 2. Render scene as normal glViewport(0, 0, SCR_WIDTH, SCR_HEIGHT); glClear(GL_COLOR_BUFFER_BIT | GL_DEPTH_BUFFER_BIT); shader.Use(); glm::mat4 projection = glm::perspective(camera.Zoom, (float)SCR_WIDTH / (float)SCR_HEIGHT, 0.1f, 100.0f); glm::mat4 view = camera.GetViewMatrix(); glUniformMatrix4fv(glGetUniformLocation(shader.Program, "projection"), 1, GL_FALSE, glm::value_ptr(projection)); glUniformMatrix4fv(glGetUniformLocation(shader.Program, "view"), 1, GL_FALSE, glm::value_ptr(view)); // Set light uniforms glUniform3fv(glGetUniformLocation(shader.Program, "lightPos"), 1, &lightPos[0]); glUniform3fv(glGetUniformLocation(shader.Program, "viewPos"), 1, &camera.Position[0]); glUniformMatrix4fv(glGetUniformLocation(shader.Program, "lightSpaceMatrix"), 1, GL_FALSE, glm::value_ptr(lightSpaceMatrix)); // Enable/Disable shadows by pressing 'SPACE' glUniform1i(glGetUniformLocation(shader.Program, "shadows"), shadows); glActiveTexture(GL_TEXTURE0); glBindTexture(GL_TEXTURE_2D, woodTexture); glActiveTexture(GL_TEXTURE1); glBindTexture(GL_TEXTURE_2D, depthMap); RenderScene(shader); */ glBindFramebuffer(GL_FRAMEBUFFER, gBuffer); glClear(GL_COLOR_BUFFER_BIT | GL_DEPTH_BUFFER_BIT); shaderGeometryPass.Use(); glm::mat4 projection = glm::perspective(camera.Zoom, (float)SCR_WIDTH / (float)SCR_HEIGHT, 0.1f, 100.0f); glm::mat4 view = camera.GetViewMatrix(); glUniformMatrix4fv(glGetUniformLocation(shaderGeometryPass.Program, "projection"), 1, GL_FALSE, glm::value_ptr(projection)); glUniformMatrix4fv(glGetUniformLocation(shaderGeometryPass.Program, "view"), 1, GL_FALSE, glm::value_ptr(view)); glUniformMatrix4fv(glGetUniformLocation(shaderGeometryPass.Program, "lightSpaceMatrix"), 1, GL_FALSE, glm::value_ptr(lightSpaceMatrix)); glActiveTexture(GL_TEXTURE0); glBindTexture(GL_TEXTURE_2D, woodTexture); RenderScene(shaderGeometryPass); glBindFramebuffer(GL_FRAMEBUFFER, 0); glClear(GL_COLOR_BUFFER_BIT | GL_DEPTH_BUFFER_BIT); shaderLightingPass.Use(); glActiveTexture(GL_TEXTURE0); glBindTexture(GL_TEXTURE_2D, gPosition); glActiveTexture(GL_TEXTURE1); glBindTexture(GL_TEXTURE_2D, gNormal); glActiveTexture(GL_TEXTURE2); glBindTexture(GL_TEXTURE_2D, gAlbedoSpec); glActiveTexture(GL_TEXTURE3); glBindTexture(GL_TEXTURE_2D, gDepthViewer); glActiveTexture(GL_TEXTURE4); glBindTexture(GL_TEXTURE_2D, gShadowMap); // Also send light relevant uniforms glUniform3fv(glGetUniformLocation(shaderLightingPass.Program, "lightPos"), 1, &lightPos[0]); glUniform3fv(glGetUniformLocation(shaderLightingPass.Program, "viewPos"), 1, &camera.Position[0]); glUniform1i(glGetUniformLocation(shaderLightingPass.Program, "draw_mode"), draw_mode); RenderQuad(); // Swap the buffers glfwSwapBuffers(window); } glfwTerminate(); return 0; }
// The MAIN function, from here we start our application and run our Game loop int main() { // Init GLFW glfwInit(); glfwWindowHint(GLFW_CONTEXT_VERSION_MAJOR, 3); glfwWindowHint(GLFW_CONTEXT_VERSION_MINOR, 3); glfwWindowHint(GLFW_OPENGL_PROFILE, GLFW_OPENGL_CORE_PROFILE); glfwWindowHint(GLFW_RESIZABLE, GL_FALSE); GLFWwindow* window = glfwCreateWindow(SCR_WIDTH, SCR_HEIGHT, "LearnOpenGL", nullptr, nullptr); // Windowed glfwMakeContextCurrent(window); // Set the required callback functions glfwSetKeyCallback(window, key_callback); glfwSetCursorPosCallback(window, mouse_callback); glfwSetScrollCallback(window, scroll_callback); // Options glfwSetInputMode(window, GLFW_CURSOR, GLFW_CURSOR_DISABLED); // Initialize GLEW to setup the OpenGL Function pointers glewExperimental = GL_TRUE; glewInit(); glGetError(); // Define the viewport dimensions glViewport(0, 0, SCR_WIDTH, SCR_HEIGHT); // Setup some OpenGL options glEnable(GL_DEPTH_TEST); // Setup and compile our shaders Shader shaderGeometryPass("ssao_geometry.vs", "ssao_geometry.frag"); Shader shaderLightingPass("ssao.vs", "ssao_lighting.frag"); Shader shaderSSAO("ssao.vs", "ssao.frag"); Shader shaderSSAOBlur("ssao.vs", "ssao_blur.frag"); // Set samplers shaderLightingPass.Use(); glUniform1i(glGetUniformLocation(shaderLightingPass.Program, "gPositionDepth"), 0); glUniform1i(glGetUniformLocation(shaderLightingPass.Program, "gNormal"), 1); glUniform1i(glGetUniformLocation(shaderLightingPass.Program, "gAlbedo"), 2); glUniform1i(glGetUniformLocation(shaderLightingPass.Program, "ssao"), 3); shaderSSAO.Use(); glUniform1i(glGetUniformLocation(shaderSSAO.Program, "gPositionDepth"), 0); glUniform1i(glGetUniformLocation(shaderSSAO.Program, "gNormal"), 1); glUniform1i(glGetUniformLocation(shaderSSAO.Program, "texNoise"), 2); // Objects Model nanosuit(FileSystem::getPath("resources/objects/nanosuit/nanosuit.obj").c_str()); // Lights glm::vec3 lightPos = glm::vec3(2.0, 4.0, -2.0); glm::vec3 lightColor = glm::vec3(0.2, 0.2, 0.7); // Set up G-Buffer // 3 textures: // 1. Positions + depth (RGBA) // 2. Color (RGB) // 3. Normals (RGB) GLuint gBuffer; glGenFramebuffers(1, &gBuffer); glBindFramebuffer(GL_FRAMEBUFFER, gBuffer); GLuint gPositionDepth, gNormal, gAlbedo; // - Position + linear depth color buffer glGenTextures(1, &gPositionDepth); glBindTexture(GL_TEXTURE_2D, gPositionDepth); glTexImage2D(GL_TEXTURE_2D, 0, GL_RGBA16F, SCR_WIDTH, SCR_HEIGHT, 0, GL_RGB, GL_FLOAT, NULL); glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MIN_FILTER, GL_NEAREST); glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MAG_FILTER, GL_NEAREST); glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_WRAP_S, GL_CLAMP_TO_EDGE); glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_WRAP_T, GL_CLAMP_TO_EDGE); glFramebufferTexture2D(GL_FRAMEBUFFER, GL_COLOR_ATTACHMENT0, GL_TEXTURE_2D, gPositionDepth, 0); // - Normal color buffer glGenTextures(1, &gNormal); glBindTexture(GL_TEXTURE_2D, gNormal); glTexImage2D(GL_TEXTURE_2D, 0, GL_RGB, SCR_WIDTH, SCR_HEIGHT, 0, GL_RGB, GL_FLOAT, NULL); glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MIN_FILTER, GL_NEAREST); glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MAG_FILTER, GL_NEAREST); glFramebufferTexture2D(GL_FRAMEBUFFER, GL_COLOR_ATTACHMENT1, GL_TEXTURE_2D, gNormal, 0); // - Albedo color buffer glGenTextures(1, &gAlbedo); glBindTexture(GL_TEXTURE_2D, gAlbedo); glTexImage2D(GL_TEXTURE_2D, 0, GL_RGB, SCR_WIDTH, SCR_HEIGHT, 0, GL_RGBA, GL_FLOAT, NULL); glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MIN_FILTER, GL_NEAREST); glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MAG_FILTER, GL_NEAREST); glFramebufferTexture2D(GL_FRAMEBUFFER, GL_COLOR_ATTACHMENT2, GL_TEXTURE_2D, gAlbedo, 0); // - Tell OpenGL which color attachments we'll use (of this framebuffer) for rendering GLuint attachments[3] = { GL_COLOR_ATTACHMENT0, GL_COLOR_ATTACHMENT1, GL_COLOR_ATTACHMENT2 }; glDrawBuffers(3, attachments); // - Create and attach depth buffer (renderbuffer) GLuint rboDepth; glGenRenderbuffers(1, &rboDepth); glBindRenderbuffer(GL_RENDERBUFFER, rboDepth); glRenderbufferStorage(GL_RENDERBUFFER, GL_DEPTH_COMPONENT, SCR_WIDTH, SCR_HEIGHT); glFramebufferRenderbuffer(GL_FRAMEBUFFER, GL_DEPTH_ATTACHMENT, GL_RENDERBUFFER, rboDepth); // - Finally check if framebuffer is complete if (glCheckFramebufferStatus(GL_FRAMEBUFFER) != GL_FRAMEBUFFER_COMPLETE) std::cout << "GBuffer Framebuffer not complete!" << std::endl; // Also create framebuffer to hold SSAO processing stage GLuint ssaoFBO, ssaoBlurFBO; glGenFramebuffers(1, &ssaoFBO); glGenFramebuffers(1, &ssaoBlurFBO); glBindFramebuffer(GL_FRAMEBUFFER, ssaoFBO); GLuint ssaoColorBuffer, ssaoColorBufferBlur; // - SSAO color buffer glGenTextures(1, &ssaoColorBuffer); glBindTexture(GL_TEXTURE_2D, ssaoColorBuffer); glTexImage2D(GL_TEXTURE_2D, 0, GL_RED, SCR_WIDTH, SCR_HEIGHT, 0, GL_RGB, GL_FLOAT, NULL); glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MIN_FILTER, GL_NEAREST); glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MAG_FILTER, GL_NEAREST); glFramebufferTexture2D(GL_FRAMEBUFFER, GL_COLOR_ATTACHMENT0, GL_TEXTURE_2D, ssaoColorBuffer, 0); if (glCheckFramebufferStatus(GL_FRAMEBUFFER) != GL_FRAMEBUFFER_COMPLETE) std::cout << "SSAO Framebuffer not complete!" << std::endl; // - and blur stage glBindFramebuffer(GL_FRAMEBUFFER, ssaoBlurFBO); glGenTextures(1, &ssaoColorBufferBlur); glBindTexture(GL_TEXTURE_2D, ssaoColorBufferBlur); glTexImage2D(GL_TEXTURE_2D, 0, GL_RED, SCR_WIDTH, SCR_HEIGHT, 0, GL_RGB, GL_FLOAT, NULL); glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MIN_FILTER, GL_NEAREST); glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MAG_FILTER, GL_NEAREST); glFramebufferTexture2D(GL_FRAMEBUFFER, GL_COLOR_ATTACHMENT0, GL_TEXTURE_2D, ssaoColorBufferBlur, 0); if (glCheckFramebufferStatus(GL_FRAMEBUFFER) != GL_FRAMEBUFFER_COMPLETE) std::cout << "SSAO Blur Framebuffer not complete!" << std::endl; glBindFramebuffer(GL_FRAMEBUFFER, 0); // Sample kernel std::uniform_real_distribution<GLfloat> randomFloats(0.0, 1.0); // generates random floats between 0.0 and 1.0 std::default_random_engine generator; std::vector<glm::vec3> ssaoKernel; for (GLuint i = 0; i < 64; ++i) { glm::vec3 sample(randomFloats(generator) * 2.0 - 1.0, randomFloats(generator) * 2.0 - 1.0, randomFloats(generator)); sample = glm::normalize(sample); sample *= randomFloats(generator); GLfloat scale = GLfloat(i) / 64.0; // Scale samples s.t. they're more aligned to center of kernel scale = lerp(0.1f, 1.0f, scale * scale); sample *= scale; ssaoKernel.push_back(sample); } // Noise texture std::vector<glm::vec3> ssaoNoise; for (GLuint i = 0; i < 16; i++) { glm::vec3 noise(randomFloats(generator) * 2.0 - 1.0, randomFloats(generator) * 2.0 - 1.0, 0.0f); // rotate around z-axis (in tangent space) ssaoNoise.push_back(noise); } GLuint noiseTexture; glGenTextures(1, &noiseTexture); glBindTexture(GL_TEXTURE_2D, noiseTexture); glTexImage2D(GL_TEXTURE_2D, 0, GL_RGB16F, 4, 4, 0, GL_RGB, GL_FLOAT, &ssaoNoise[0]); glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MIN_FILTER, GL_NEAREST); glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MAG_FILTER, GL_NEAREST); glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_WRAP_S, GL_REPEAT); glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_WRAP_T, GL_REPEAT); glClearColor(0.0f, 0.0f, 0.0f, 1.0f); // Game loop while (!glfwWindowShouldClose(window)) { // Set frame time GLfloat currentFrame = glfwGetTime(); deltaTime = currentFrame - lastFrame; lastFrame = currentFrame; // Check and call events glfwPollEvents(); Do_Movement(); // 1. Geometry Pass: render scene's geometry/color data into gbuffer glBindFramebuffer(GL_FRAMEBUFFER, gBuffer); glClear(GL_COLOR_BUFFER_BIT | GL_DEPTH_BUFFER_BIT); glm::mat4 projection = glm::perspective(camera.Zoom, (GLfloat)SCR_WIDTH / (GLfloat)SCR_HEIGHT, 0.1f, 50.0f); glm::mat4 view = camera.GetViewMatrix(); glm::mat4 model; shaderGeometryPass.Use(); glUniformMatrix4fv(glGetUniformLocation(shaderGeometryPass.Program, "projection"), 1, GL_FALSE, glm::value_ptr(projection)); glUniformMatrix4fv(glGetUniformLocation(shaderGeometryPass.Program, "view"), 1, GL_FALSE, glm::value_ptr(view)); // Floor cube model = glm::translate(model, glm::vec3(0.0, -1.0f, 0.0f)); model = glm::scale(model, glm::vec3(20.0f, 1.0f, 20.0f)); glUniformMatrix4fv(glGetUniformLocation(shaderGeometryPass.Program, "model"), 1, GL_FALSE, glm::value_ptr(model)); RenderCube(); // Nanosuit model on the floor model = glm::mat4(); model = glm::translate(model, glm::vec3(0.0f, 0.0f, 5.0)); model = glm::rotate(model, -90.0f, glm::vec3(1.0, 0.0, 0.0)); model = glm::scale(model, glm::vec3(0.5f)); glUniformMatrix4fv(glGetUniformLocation(shaderGeometryPass.Program, "model"), 1, GL_FALSE, glm::value_ptr(model)); nanosuit.Draw(shaderGeometryPass); glBindFramebuffer(GL_FRAMEBUFFER, 0); // 2. Create SSAO texture glBindFramebuffer(GL_FRAMEBUFFER, ssaoFBO); glClear(GL_COLOR_BUFFER_BIT); shaderSSAO.Use(); glActiveTexture(GL_TEXTURE0); glBindTexture(GL_TEXTURE_2D, gPositionDepth); glActiveTexture(GL_TEXTURE1); glBindTexture(GL_TEXTURE_2D, gNormal); glActiveTexture(GL_TEXTURE2); glBindTexture(GL_TEXTURE_2D, noiseTexture); // Send kernel + rotation for (GLuint i = 0; i < 64; ++i) glUniform3fv(glGetUniformLocation(shaderSSAO.Program, ("samples[" + std::to_string(i) + "]").c_str()), 1, &ssaoKernel[i][0]); glUniformMatrix4fv(glGetUniformLocation(shaderSSAO.Program, "projection"), 1, GL_FALSE, glm::value_ptr(projection)); RenderQuad(); glBindFramebuffer(GL_FRAMEBUFFER, 0); // 3. Blur SSAO texture to remove noise glBindFramebuffer(GL_FRAMEBUFFER, ssaoBlurFBO); glClear(GL_COLOR_BUFFER_BIT); shaderSSAOBlur.Use(); glActiveTexture(GL_TEXTURE0); glBindTexture(GL_TEXTURE_2D, ssaoColorBuffer); RenderQuad(); glBindFramebuffer(GL_FRAMEBUFFER, 0); // 4. Lighting Pass: traditional deferred Blinn-Phong lighting now with added screen-space ambient occlusion glClear(GL_COLOR_BUFFER_BIT | GL_DEPTH_BUFFER_BIT); shaderLightingPass.Use(); glActiveTexture(GL_TEXTURE0); glBindTexture(GL_TEXTURE_2D, gPositionDepth); glActiveTexture(GL_TEXTURE1); glBindTexture(GL_TEXTURE_2D, gNormal); glActiveTexture(GL_TEXTURE2); glBindTexture(GL_TEXTURE_2D, gAlbedo); glActiveTexture(GL_TEXTURE3); // Add extra SSAO texture to lighting pass glBindTexture(GL_TEXTURE_2D, ssaoColorBufferBlur); // Also send light relevant uniforms glm::vec3 lightPosView = glm::vec3(camera.GetViewMatrix() * glm::vec4(lightPos, 1.0)); glUniform3fv(glGetUniformLocation(shaderLightingPass.Program, "light.Position"), 1, &lightPosView[0]); glUniform3fv(glGetUniformLocation(shaderLightingPass.Program, "light.Color"), 1, &lightColor[0]); // Update attenuation parameters const GLfloat constant = 1.0; // Note that we don't send this to the shader, we assume it is always 1.0 (in our case) const GLfloat linear = 0.09; const GLfloat quadratic = 0.032; glUniform1f(glGetUniformLocation(shaderLightingPass.Program, "light.Linear"), linear); glUniform1f(glGetUniformLocation(shaderLightingPass.Program, "light.Quadratic"), quadratic); glUniform1i(glGetUniformLocation(shaderLightingPass.Program, "draw_mode"), draw_mode); RenderQuad(); // Swap the buffers glfwSwapBuffers(window); } glfwTerminate(); return 0; }