glm::vec3 BlinnMicrofacetBxDF::EvaluateHemisphereScatteredEnergy(const glm::vec3 &wo, int num_samples, const glm::vec2 *samples) const { //TODO glm::vec3 color( 0.f ); for( int i = 0; i < num_samples; ++i ){ float cos_theta( powf( samples[ i ].x, 1.f / ( exponent + 1.f ) ) ); float sin_theta( sqrtf( fmaxf( 0.f, 1.f - cos_theta * cos_theta ) ) ); float phi( samples[ i ].y * TWO_PI ); float cos_phi( cosf( phi ) ); float sin_phi( sinf( phi ) ); glm::vec3 wh( sin_theta * cos_phi, sin_theta * sin_phi, cos_theta ); float woDwh( glm::dot( wo, wh ) ); if( woDwh < 0.f ) wh = -wh; glm::vec3 wi( -wo + 2.f * woDwh * wh ); color += EvaluateScatteredEnergy( wo, wi ); } return color / ( float )num_samples; }
glm::vec3 SpecularReflectionBxDF::SampleAndEvaluateScatteredEnergy(const glm::vec3 &wo, glm::vec3 &wi_ret, float rand1, float rand2, float &pdf_ret) const { // specular reflection wi = delta(w-wo) where w is perfectly reflective direction glm::vec3 N(0,0,1); wi_ret = 2.0f*glm::dot(N,wo)*N - wo; wi_ret = glm::normalize(wi_ret); //pdf_ret = PDF(wo, wi_ret); return EvaluateScatteredEnergy(wo, wi_ret, pdf_ret); }
glm::vec3 BxDF::SampleAndEvaluateScatteredEnergy(const glm::vec3 &wo, glm::vec3 &wi_ret, float rand1, float rand2, float &pdf_ret) const { glm::vec3 tmp = la::UnifSampleDisc(rand1, rand2); tmp.z = sqrtf(std::max(0.f, 1.f - tmp.x*tmp.x - tmp.y*tmp.y)); if (wo.z < 0.f) tmp.z *= -1.f; wi_ret = tmp; pdf_ret = PDF(wo, wi_ret); return EvaluateScatteredEnergy(wo, wi_ret); }
glm::vec3 LambertBxDF::SampleAndEvaluateScatteredEnergy(const glm::vec3 &wo, glm::vec3 &wi_ret, float rand1, float rand2, float &pdf_ret) const { glm::vec3 normal=glm::vec3(0,0,1); float t = 2*PI*rand1; float u = rand2-0.5;//[-0.5,+0.5]*/ float x=u*cos(t); float y=u*sin(t); float z=sqrt(0.25-pow(x,2.0)-pow(y,2.0)); wi_ret=glm::normalize(glm::vec3(x,y,z)); pdf_ret=glm::dot(wi_ret,normal)/PI; return EvaluateScatteredEnergy(wo, wi_ret); }
glm::vec3 BxDF::SampleAndEvaluateScatteredEnergy(const glm::vec3 &wo, glm::vec3 &wi_ret, float rand1, float rand2, float &pdf_ret) const { //TODO rand1 *= TWO_PI; rand2 *= PI * .5f; float x( cosf( rand1 ) * sinf( rand2 ) ); float y( sinf( rand1 ) * sinf( rand2 ) ); float z( cosf( rand2 ) ); wi_ret = glm::vec3( x, y, z ); pdf_ret = PDF( wo, wi_ret ); return EvaluateScatteredEnergy( wo, wi_ret ); }
glm::vec3 BlinnMicrofacetBxDF::SampleAndEvaluateScatteredEnergy(const glm::vec3 &wo, glm::vec3 &wi_ret, float rand1, float rand2, float &pdf_ret) const{ float cos_theta( powf( rand1, 1.f / ( exponent + 1.f ) ) ); float sin_theta( sqrtf( fmaxf( 0.f, 1.f - cos_theta * cos_theta ) ) ); float phi( rand2 * TWO_PI ); float cos_phi( cosf( phi ) ); float sin_phi( sinf( phi ) ); glm::vec3 wh( sin_theta * cos_phi, sin_theta * sin_phi, cos_theta ); float woDwh( glm::dot( wo, wh ) ); if( woDwh < 0.f ) wh = -wh; wi_ret = -wo + 2.f * woDwh * wh; pdf_ret = PDF( wo, wi_ret ); return EvaluateScatteredEnergy( wo, wi_ret ); }
glm::vec3 BxDF::EvaluateHemisphereScatteredEnergy(const glm::vec3 &wo, int num_samples, const glm::vec2* samples) const { //TODO glm::vec3 color( 0.f ); for( int i = 0; i < num_samples; ++i ){ float r( sqrtf( samples[ i ].x ) ); float theta( samples[ i ].y * TWO_PI ); float x( r * cosf( theta ) ); float y( r * sinf( theta ) ); float z( sqrtf( 1.f - samples[ i ].x ) ); glm::vec3 wi( x, y, z ); color += EvaluateScatteredEnergy( wo, wi ); } return color / ( float )num_samples; }