[Bf-blender-cvs] [035ee375ac3] microfacet_hair: Use functions in `bsdf_microfacet.h`
Weizhen Huang
noreply at git.blender.org
Mon Jan 23 11:58:44 CET 2023
Commit: 035ee375ac32ebfb761bfe35a89a7443ec95e9df
Author: Weizhen Huang
Date: Mon Jan 23 11:58:15 2023 +0100
Branches: microfacet_hair
https://developer.blender.org/rB035ee375ac32ebfb761bfe35a89a7443ec95e9df
Use functions in `bsdf_microfacet.h`
===================================================================
M intern/cycles/kernel/closure/bsdf_hair_microfacet.h
===================================================================
diff --git a/intern/cycles/kernel/closure/bsdf_hair_microfacet.h b/intern/cycles/kernel/closure/bsdf_hair_microfacet.h
index d8e79739ffb..7fb803903cd 100644
--- a/intern/cycles/kernel/closure/bsdf_hair_microfacet.h
+++ b/intern/cycles/kernel/closure/bsdf_hair_microfacet.h
@@ -249,49 +249,6 @@ ccl_device_inline bool microfacet_visible(const float3 wi,
return microfacet_visible(wi, m, h) && microfacet_visible(wo, m, h);
}
-/* Smith's separable shadowing/masking term. */
-ccl_device_inline float smith_g1(
- const bool beckmann, const float roughness, const float3 v, const float3 m, const float3 h)
-{
- /* Assume consistent orientation (can't see the back of the microfacet from the front and vice
- * versa). */
- float cos_vm = dot(v, m);
- if (dot(v, h) <= 0.0f || cos_vm <= 0.0f) {
- return 0.0f;
- }
-
- return beckmann ? bsdf_G1<MicrofacetType::BECKMANN>(sqr(roughness), cos_vm) :
- 2.0f / (1.0f + sqrtf(1.0f + sqr(roughness) * (1.0f / sqr(cos_vm) - 1.0f)));
-}
-
-/* Geometry term. */
-ccl_device_inline float G(const bool beckmann,
- const float roughness,
- const float3 wi,
- const float3 wo,
- const float3 m,
- const float3 h)
-{
- return smith_g1(beckmann, roughness, wi, m, h) * smith_g1(beckmann, roughness, wo, m, h);
-}
-
-/* Normal Distribution Function. */
-ccl_device float D(const bool beckmann, const float roughness, const float3 m, const float3 h)
-{
- const float cos_theta = dot(h, m);
-
- const float roughness2 = sqr(roughness);
- const float cos_theta2 = sqr(cos_theta);
-
- const float result = beckmann ?
- expf((1.0f - 1.0f / cos_theta2) / roughness2) /
- (M_PI_F * roughness2 * sqr(cos_theta2)) :
- roughness2 / (M_PI_F * sqr(1.0f + (roughness2 - 1.0f) * cos_theta2));
-
- /* Prevent potential numerical issues in other stages of the model. */
- return (result * cos_theta > 1e-20f) ? result : 0.0f;
-}
-
/* Compute fresnel reflection. Also return the dot product of the refracted ray and the normal as
* `cos_theta_t`, as it is used when computing the direction of the refracted ray. */
ccl_device float fresnel(float cos_theta_i, float eta, ccl_private float *cos_theta_t)
@@ -345,12 +302,11 @@ ccl_device float3 bsdf_microfacet_hair_eval_r(ccl_private const ShaderClosure *s
ccl_private MicrofacetHairBSDF *bsdf = (ccl_private MicrofacetHairBSDF *)sc;
const float tilt = -bsdf->tilt;
const float roughness = bsdf->roughness;
+ const float roughness2 = sqr(roughness);
const float eta = bsdf->eta;
- const bool beckmann = (bsdf->distribution_type == NODE_MICROFACET_HAIR_BECKMANN);
- float3 R = zero_float3();
if (bsdf->extra->R <= 0.0f) {
- return R;
+ return zero_float3();
}
/* Get elliptical cross section characteristic. Assuming major axis is 1. */
@@ -366,14 +322,14 @@ ccl_device float3 bsdf_microfacet_hair_eval_r(ccl_private const ShaderClosure *s
const float tan_tilt = tanf(tilt);
float phi_m_max1 = acosf(fmaxf(-tan_tilt * tan_theta(wi), 0.0f)) + phi_i;
if (isnan_safe(phi_m_max1)) {
- return R;
+ return zero_float3();
}
float phi_m_min1 = -phi_m_max1 + 2.0f * phi_i;
/* dot(wo, wmi) > 0 */
float phi_m_max2 = acosf(fmaxf(-tan_tilt * tan_theta(wo), 0.0f)) + phi_o;
if (isnan_safe(phi_m_max2)) {
- return R;
+ return zero_float3();
}
float phi_m_min2 = -phi_m_max2 + 2.0f * phi_o;
@@ -392,7 +348,7 @@ ccl_device float3 bsdf_microfacet_hair_eval_r(ccl_private const ShaderClosure *s
const float phi_m_min = fmaxf(phi_m_min1, phi_m_min2) + 1e-3f;
const float phi_m_max = fminf(phi_m_max1, phi_m_max2) - 1e-3f;
if (phi_m_min > phi_m_max) {
- return R;
+ return zero_float3();
}
const float gamma_m_min = to_gamma(phi_m_min, b);
@@ -418,8 +374,8 @@ ccl_device float3 bsdf_microfacet_hair_eval_r(ccl_private const ShaderClosure *s
if (microfacet_visible(wi, wo, make_float3(wm.x, 0.0f, wm.z), wh)) {
const float weight = (i == 0 || i == intervals) ? 0.5f : (i % 2 + 1);
- integral += weight * D(beckmann, roughness, wm, wh) *
- G(beckmann, roughness, wi, wo, wm, wh) * arc_length(e2, gamma_m);
+ integral += weight * bsdf_D<m_type>(roughness2, dot(wm, wh)) *
+ bsdf_G<m_type>(roughness2, dot(wi, wm), dot(wo, wm)) * arc_length(e2, gamma_m);
}
}
@@ -440,8 +396,8 @@ ccl_device float3 bsdf_microfacet_hair_eval_tt_trt(KernelGlobals kg,
ccl_private MicrofacetHairBSDF *bsdf = (ccl_private MicrofacetHairBSDF *)sc;
const float tilt = -bsdf->tilt;
const float roughness = bsdf->roughness;
+ const float roughness2 = sqr(roughness);
const float eta = bsdf->eta;
- const bool beckmann = (bsdf->distribution_type == NODE_MICROFACET_HAIR_BECKMANN);
if (bsdf->extra->TT <= 0.0f && bsdf->extra->TRT <= 0.0f) {
return zero_float3();
@@ -494,13 +450,13 @@ ccl_device float3 bsdf_microfacet_hair_eval_tt_trt(KernelGlobals kg,
lcg_step_float(&rng_quadrature));
const float3 wh1 = sample_wh<m_type>(kg, roughness, wi, wmi, sample1);
- const float dot_wi_wh1 = dot(wi, wh1);
- if (!(dot_wi_wh1 > 0)) {
+ const float cos_hi1 = dot(wi, wh1);
+ if (!(cos_hi1 > 0)) {
continue;
}
float cos_theta_t1;
- const float T1 = 1.0f - fresnel(dot_wi_wh1, eta, &cos_theta_t1);
+ const float T1 = 1.0f - fresnel(cos_hi1, eta, &cos_theta_t1);
/* Refraction at the first interface. */
const float3 wt = -refract_angle(wi, wh1, cos_theta_t1, inv_eta);
@@ -509,7 +465,10 @@ ccl_device float3 bsdf_microfacet_hair_eval_tt_trt(KernelGlobals kg,
const float3 wmt = sphg_dir(-tilt, gamma_mt, b);
const float3 wmt_ = sphg_dir(0.0f, gamma_mt, b);
- const float G1 = G(beckmann, roughness, wi, -wt, wmi, wh1);
+ const float cos_mi1 = dot(wi, wmi);
+ const float cos_mo1 = dot(-wt, wmi);
+ const float cos_mi2 = dot(-wt, wmt);
+ const float G1 = bsdf_G<m_type>(roughness2, cos_mi1, cos_mo1);
if (G1 == 0.0f || !microfacet_visible(wi, -wt, wmi_, wh1)) {
continue;
}
@@ -524,25 +483,22 @@ ccl_device float3 bsdf_microfacet_hair_eval_tt_trt(KernelGlobals kg,
/* TT */
if (bsdf->extra->TT > 0.0f) {
- /* Total internal reflection otherwise. */
- if (dot(wo, wt) >= inv_eta - 1e-5f) {
-
- /* Microfacet visiblity from macronormal. */
+ if (dot(wo, wt) >= inv_eta - 1e-5f) { /* Total internal reflection otherwise. */
float3 wh2 = -wt + inv_eta * wo;
- if (dot(wmt, wh2) >= 0.0f) {
-
- const float rcp_norm_wh2 = 1.0f / len(wh2);
- wh2 *= rcp_norm_wh2;
+ const float rcp_norm_wh2 = 1.0f / len(wh2);
+ wh2 *= rcp_norm_wh2;
+ const float cos_mh2 = dot(wmt, wh2);
+ if (cos_mh2 >= 0.0f) { /* Microfacet visiblity from macronormal. */
+ const float cos_hi2 = dot(-wt, wh2);
+ const float cos_ho2 = dot(-wo, wh2);
+ const float cos_mo2 = dot(-wo, wmt);
- const float dot_wt_wh2 = dot(-wt, wh2);
+ const float T2 = 1.0f - fresnel_dielectric_cos(cos_hi2, inv_eta);
+ const float D2 = bsdf_D<m_type>(roughness2, cos_mh2);
+ const float G2 = bsdf_G<m_type>(roughness2, cos_mi2, cos_mo2);
- const float T2 = 1.0f - fresnel_dielectric_cos(dot_wt_wh2, inv_eta);
- const float D2 = D(beckmann, roughness, wh2, wmt) *
- G(beckmann, roughness, -wt, -wo, wmt, wh2);
-
- const float3 result = T1 * T2 * D2 * A_t * dot_wt_wh2 * dot(wo, wh2) *
- sqr(rcp_norm_wh2) / dot(wt, wmi) * weight *
- smith_g1(beckmann, roughness, -wt, wmi, wh1) * dot(wi, wmi);
+ const float3 result = weight * T1 * T2 * D2 * G2 * A_t / cos_mo1 * cos_mi1 * cos_hi2 *
+ cos_ho2 * sqr(rcp_norm_wh2) * bsdf_G1<m_type>(roughness2, cos_mo1);
if (isfinite_safe(result)) {
S_tt += bsdf->extra->TT * result * arc_length(e2, gamma_mt);
@@ -556,24 +512,21 @@ ccl_device float3 bsdf_microfacet_hair_eval_tt_trt(KernelGlobals kg,
/* sample wh2 */
const float2 sample2 = make_float2(lcg_step_float(&rng_quadrature),
lcg_step_float(&rng_quadrature));
-
const float3 wh2 = sample_wh<m_type>(kg, roughness, -wt, wmt, sample2);
-
- const float cos_th2 = dot(-wt, wh2);
- if (!(cos_th2 > 0)) {
+ const float cos_hi2 = dot(-wt, wh2);
+ if (!(cos_hi2 > 0)) {
continue;
}
+ const float R2 = fresnel_dielectric_cos(cos_hi2, inv_eta);
- const float R2 = fresnel_dielectric_cos(cos_th2, inv_eta);
const float3 wtr = -reflect(wt, wh2);
-
- const float G2 = G(beckmann, roughness, -wt, -wtr, wmt, wh2);
- if (G2 == 0.0f || !microfacet_visible(-wt, -wtr, wmt_, wh2)) {
+ if (dot(-wtr, wo) < inv_eta - 1e-5f) {
+ /* Total internal reflection. */
continue;
}
-
- /* Total internal reflection. */
- if (dot(-wtr, wo) < inv_eta - 1e-5f) {
+ const float cos_mo2 = dot(-wtr, wmt);
+ const float G2 = bsdf_G<m_type>(roughness2, cos_mi2, cos_mo2);
+ if (G2 == 0.0f || !microfacet_visible(-wt, -wtr, wmt_, wh2)) {
continue;
}
@@ -582,31 +535,29 @@ ccl_device float3 bsdf_microfacet_hair_eval_tt_trt(KernelGlobals kg,
const float3 wmtr = sphg_dir(-tilt, gamma_mtr, b);
const float3 wmtr_ = sphg_dir(0.0f, gamma_mtr, b);
+ const float G3 = bsdf_G<m_type>(roughness2, dot(wtr, wmtr), dot(-wo, wmtr));
float3 wh3 = wtr + inv_eta * wo;
- const float G3 = G(beckmann, roughness, wtr, -wo, wmtr, wh3);
- if (dot(wmtr, wh3) < 0.0f || G3 == 0.0f || !microfacet_visible(wtr, -wo, wmtr_, wh3)) {
- continue;
- }
-
const float rcp_norm_wh3 = 1.0f / len(wh3);
wh3 *= rcp_norm_wh3;
+ const float cos_mh3 = dot(wmtr, wh3);
+ if (cos_mh3 < 0.0f || G3 == 0.0f || !microfacet_visible(wtr, -wo, wmtr_, wh3)) {
+ continue;
+
@@ Diff output truncated at 10240 characters. @@
More information about the Bf-blender-cvs
mailing list