MaterialPtr AmbientOcclusionScene::createAmbientOcclusionMaterial( const QString& diffuse, const QString& aoFactors ) const { MaterialPtr material( new Material ); // Setup the shaders material->setShaders( ":/shaders/ambientocclusion.vert", ":/shaders/ambientocclusion.frag" ); // Create a diffuse texture TexturePtr diffuseTexture( new Texture( Texture::Texture2D ) ); diffuseTexture->create(); diffuseTexture->bind(); diffuseTexture->setImage( QImage( diffuse ) ); // Create the ambient occlusion factors texture TexturePtr aoTexture( new Texture( Texture::Texture2D ) ); aoTexture->create(); aoTexture->bind(); aoTexture->setImage( QImage( aoFactors ) ); #if !defined(Q_OS_MAC) // Create a sampler. This can be shared by both textures SamplerPtr sampler( new Sampler ); sampler->create(); sampler->setWrapMode( Sampler::DirectionS, GL_CLAMP_TO_EDGE ); sampler->setWrapMode( Sampler::DirectionT, GL_CLAMP_TO_EDGE ); sampler->setMinificationFilter( GL_LINEAR ); sampler->setMagnificationFilter( GL_LINEAR ); // We associate the diffuse texture with texture unit 0 and // the ao factors texture with unit 1 material->setTextureUnitConfiguration( 0, diffuseTexture, sampler, "diffuseTexture" ); material->setTextureUnitConfiguration( 1, aoTexture, sampler, "ambientOcclusionTexture" ); #else diffuseTexture->bind(); diffuseTexture->setWrapMode( Texture::DirectionS, GL_CLAMP_TO_EDGE ); diffuseTexture->setWrapMode( Texture::DirectionT, GL_CLAMP_TO_EDGE ); diffuseTexture->setMinificationFilter( GL_LINEAR ); diffuseTexture->setMagnificationFilter( GL_LINEAR ); aoTexture->bind(); aoTexture->setWrapMode( Texture::DirectionS, GL_CLAMP_TO_EDGE ); aoTexture->setWrapMode( Texture::DirectionT, GL_CLAMP_TO_EDGE ); aoTexture->setMinificationFilter( GL_LINEAR ); aoTexture->setMagnificationFilter( GL_LINEAR ); // We associate the diffuse texture with texture unit 0 and // the ao factors texture with unit 1 material->setTextureUnitConfiguration( 0, diffuseTexture, "diffuseTexture" ); material->setTextureUnitConfiguration( 1, aoTexture, "ambientOcclusionTexture" ); #endif return material; }
SSAOScene::SSAOScene(Context * ctx): CameraScene(ctx), cryModel("assets/models/nanosuit/nanosuit.obj") { FramebufferConfiguration cfg(ctx->getWindowWidth(),ctx->getWindowHeight()); TextureConfig posBfrConfig("positionDepth",GL_RGBA16F,GL_RGBA,GL_FLOAT); posBfrConfig.setTextureFilter(GL_NEAREST); posBfrConfig.setWrapMode(GL_CLAMP_TO_EDGE); TextureAttachment posBfr(posBfrConfig,GL_COLOR_ATTACHMENT0); TextureConfig norBfrConfig("normal",GL_RGB16F,GL_RGB,GL_FLOAT); posBfrConfig.setTextureFilter(GL_NEAREST); TextureAttachment norBfr(norBfrConfig,GL_COLOR_ATTACHMENT1); TextureConfig spec_albedoConfig("color",GL_RGBA,GL_RGBA,GL_FLOAT); posBfrConfig.setTextureFilter(GL_NEAREST); TextureAttachment spec_albedoBfr(spec_albedoConfig,GL_COLOR_ATTACHMENT2); cfg.addTexturebuffer(posBfr); cfg.addTexturebuffer(norBfr); cfg.addTexturebuffer(spec_albedoBfr); cfg.addRenderbuffer(RenderbufferAttachment(GL_DEPTH24_STENCIL8,GL_DEPTH_STENCIL_ATTACHMENT)); gBuffer.init(cfg); FramebufferConfiguration aoConfig(ctx->getWindowWidth(),ctx->getWindowHeight()); TextureConfig aoTexture("occlusion",GL_RED,GL_RGB,GL_FLOAT); aoTexture.setTextureFilter(GL_NEAREST); TextureAttachment ssaoBufferAttachment(aoTexture,GL_COLOR_ATTACHMENT0); aoConfig.addTexturebuffer(ssaoBufferAttachment); ssaoBuffer.init(aoConfig); GL_Logger::LogError("Could not configure ssaoBuffer"); //Blur buffer has same properties as ao buffer. FramebufferConfiguration blurConfiguration(ctx->getWindowWidth(),ctx->getWindowHeight()); TextureConfig blurTexture("occlusion",GL_RED,GL_RGB,GL_FLOAT); blurTexture.setTextureFilter(GL_NEAREST); TextureAttachment blurBufferAttachment(blurTexture,GL_COLOR_ATTACHMENT0); blurConfiguration.addTexturebuffer(blurBufferAttachment); ssaoBlurBuffer.init(blurConfiguration); std::uniform_real_distribution<GLfloat> randomFloats(0.0, 1.0); // random floats between 0.0 - 1.0 std::default_random_engine generator; //Set up a noise texture std::vector<glm::vec3> ssaoNoiseVec; for (GLuint i = 0; i < 16; i++) { glm::vec3 noise( randomFloats(generator) * 2.0 - 1.0, randomFloats(generator) * 2.0 - 1.0, 0.0f); ssaoNoiseVec.push_back(noise); } TextureConfig ssaoConfig("ssaoNoise",GL_RGB16F,GL_RGB,GL_FLOAT); ssaoConfig.setWrapMode(GL_REPEAT); ssaoConfig.setTextureFilter(GL_NEAREST); ssaoNoise.init(ssaoConfig,&ssaoNoiseVec[0],4,4); GL_Logger::LogError("Could not configure ssaoNoise"); deferredGBufferProg = createProgram("SSAO GBuffer fill program"); ssaoProgram = createProgram("SSAO creation program"); postProcessProg = createProgram("Display AO map program"); ssaoBlurProgram = createProgram("SSAO blur program"); finalPassProgram = createProgram("Final Pass Program"); geomPlane.transform.setScale(glm::vec3(20.0)); geomPlane.transform.setPosition(glm::vec3(0,-1,0)); cryModel.transform.setScale(glm::vec3(0.5)); cryModel.transform.setPosition(glm::vec3(0,0,3.5)); cryModel.transform.rotate(-M_PI/2, glm::vec3(1.0,0,0)); }