// commented, dpl 10 august 2005 void Anisotropic::Sample_f(const Vector &wo, Vector *wi, float u1, float u2, float *pdf) const { // Sample from first quadrant and remap to hemisphere to sample \wh float phi, costheta; if (u1 < .25f) { sampleFirstQuadrant(4.f * u1, u2, &phi, &costheta); } else if (u1 < .5f) { u1 = 4.f * (.5f - u1); sampleFirstQuadrant(u1, u2, &phi, &costheta); phi = M_PI - phi; } else if (u1 < .75f) { u1 = 4.f * (u1 - .5f); sampleFirstQuadrant(u1, u2, &phi, &costheta); phi += M_PI; } else { u1 = 4.f * (1.f - u1); sampleFirstQuadrant(u1, u2, &phi, &costheta); phi = 2.f * M_PI - phi; } float sintheta = sqrtf(max(0.f, 1.f - costheta*costheta)); Vector H = SphericalDirection(sintheta, costheta, phi); if (Dot(wo, H) < 0.f) H = -H; // Compute incident direction by reflecting about $\wh$ *wi = -wo + 2.f * Dot(wo, H) * H; // Compute PDF for \wi from Anisotropic distribution float anisotropic_pdf = D(H) / (4.f * Dot(wo, H)); *pdf = anisotropic_pdf; }
//复制自PBRT void Anisotropic::Sample_f(const Vector3f &wo, Vector3f *wi, Float u1, Float u2, Float *pdf) const { Float phi, costheta; if (u1 < .25f) { sampleFirstQuadrant(4.f * u1, u2, &phi, &costheta); } else if (u1 < .5f) { u1 = 4.f * (.5f - u1); sampleFirstQuadrant(u1, u2, &phi, &costheta); phi = Pi - phi; } else if (u1 < .75f) { u1 = 4.f * (u1 - .5f); sampleFirstQuadrant(u1, u2, &phi, &costheta); phi += Pi; } else { u1 = 4.f * (1.f - u1); sampleFirstQuadrant(u1, u2, &phi, &costheta); phi = 2.f * Pi - phi; } Float sintheta = sqrtf(std::max(0.f, 1.f - costheta * costheta)); Vector3f wh = SphericalDirection(sintheta, costheta, phi); if (!SameHemisphere(wo, wh)) wh = -wh; // Compute incident direction by reflecting about $\wh$ *wi = -wo + 2.f * Dot(wo, wh) * wh; // Compute PDF for $\wi$ from anisotropic distribution Float costhetah = AbsCosTheta(wh); Float ds = 1.f - costhetah * costhetah; Float anisotropic_pdf = 0.f; if (ds > 0.f && Dot(wo, wh) > 0.f) { Float e = (ex * wh.x * wh.x + ey * wh.y * wh.y) / ds; Float d = sqrtf((ex + 1.f) * (ey + 1.f)) * InvTwoPi * powf(costhetah, e); anisotropic_pdf = d / (4.f * Dot(wo, wh)); } *pdf = anisotropic_pdf; }