@@ -110,45 +110,12 @@ struct BeckmannCommon<T,false NBL_PARTIAL_REQ_BOT(concepts::FloatingPointScalar<
110110 return numbers::inv_pi<scalar_type> * nom / denom;
111111 }
112112
113- template<class Query NBL_FUNC_REQUIRES (beckmann_concepts::DG1Query<Query>)
114- static scalar_type DG1 (NBL_CONST_REF_ARG (Query) query)
115- {
116- return query.getNdf () / (scalar_type (1.0 ) + query.getLambdaV ());
117- }
118-
119113 scalar_type C2 (scalar_type NdotX2)
120114 {
121115 assert (NdotX2 >= scalar_type (0.0 ));
122116 return NdotX2 / (a2 * (scalar_type (1.0 ) - NdotX2));
123117 }
124118
125- static scalar_type Lambda (scalar_type c2)
126- {
127- scalar_type c = sqrt<scalar_type>(c2);
128- scalar_type nom = scalar_type (1.0 ) - scalar_type (1.259 ) * c + scalar_type (0.396 ) * c2;
129- scalar_type denom = scalar_type (2.181 ) * c2 + scalar_type (3.535 ) * c;
130- return hlsl::mix<scalar_type>(scalar_type (0.0 ), nom / denom, c < scalar_type (1.6 ));
131- }
132-
133- scalar_type LambdaC2 (scalar_type NdotX2)
134- {
135- return Lambda (C2 (NdotX2));
136- }
137-
138- template<class Query NBL_FUNC_REQUIRES (beckmann_concepts::G2overG1Query<Query>)
139- static scalar_type correlated (NBL_CONST_REF_ARG (Query) query)
140- {
141- return scalar_type (1.0 ) / (scalar_type (1.0 ) + query.getLambdaV () + query.getLambdaL ());
142- }
143-
144- template<class Query, class MicrofacetCache NBL_FUNC_REQUIRES (beckmann_concepts::G2overG1Query<Query> && ReadableIsotropicMicrofacetCache<MicrofacetCache>)
145- static scalar_type G2_over_G1 (NBL_CONST_REF_ARG (Query) query, NBL_CONST_REF_ARG (MicrofacetCache) cache)
146- {
147- scalar_type onePlusLambda_V = scalar_type (1.0 ) + query.getLambdaV ();
148- scalar_type lambda_L = query.getLambdaL ();
149- return onePlusLambda_V * hlsl::mix (scalar_type (1.0 )/(onePlusLambda_V + lambda_L), bxdf::beta<scalar_type>(onePlusLambda_V, scalar_type (1.0 ) + lambda_L), cache.isTransmission ());
150- }
151-
152119 scalar_type a2;
153120};
154121
@@ -169,46 +136,11 @@ struct BeckmannCommon<T,true NBL_PARTIAL_REQ_BOT(concepts::FloatingPointScalar<T
169136 return numbers::inv_pi<scalar_type> * nom / denom;
170137 }
171138
172- template<class Query NBL_FUNC_REQUIRES (beckmann_concepts::DG1Query<Query>)
173- static scalar_type DG1 (NBL_CONST_REF_ARG (Query) query)
174- {
175- BeckmannCommon<T,false > beckmann;
176- scalar_type dg = beckmann.DG1 (query);
177- return dg;
178- }
179-
180139 scalar_type C2 (scalar_type TdotX2, scalar_type BdotX2, scalar_type NdotX2)
181140 {
182141 return NdotX2 / (TdotX2 * ax2 + BdotX2 * ay2);
183142 }
184143
185- static scalar_type Lambda (scalar_type c2)
186- {
187- scalar_type c = sqrt<scalar_type>(c2);
188- scalar_type nom = scalar_type (1.0 ) - scalar_type (1.259 ) * c + scalar_type (0.396 ) * c2;
189- scalar_type denom = scalar_type (2.181 ) * c2 + scalar_type (3.535 ) * c;
190- return hlsl::mix<scalar_type>(scalar_type (0.0 ), nom / denom, c < scalar_type (1.6 ));
191- }
192-
193- scalar_type LambdaC2 (scalar_type TdotX2, scalar_type BdotX2, scalar_type NdotX2)
194- {
195- return Lambda (C2 (TdotX2, BdotX2, NdotX2));
196- }
197-
198- template<class Query NBL_FUNC_REQUIRES (beckmann_concepts::G2overG1Query<Query>)
199- static scalar_type correlated (NBL_CONST_REF_ARG (Query) query)
200- {
201- return scalar_type (1.0 ) / (scalar_type (1.0 ) + query.getLambdaV () + query.getLambdaL ());
202- }
203-
204- template<class Query, class MicrofacetCache NBL_FUNC_REQUIRES (beckmann_concepts::G2overG1Query<Query> && AnisotropicMicrofacetCache<MicrofacetCache>)
205- static scalar_type G2_over_G1 (NBL_CONST_REF_ARG (Query) query, NBL_CONST_REF_ARG (MicrofacetCache) cache)
206- {
207- scalar_type onePlusLambda_V = scalar_type (1.0 ) + query.getLambdaV ();
208- scalar_type lambda_L = query.getLambdaL ();
209- return onePlusLambda_V * hlsl::mix (scalar_type (1.0 )/(onePlusLambda_V + lambda_L), bxdf::beta<scalar_type>(onePlusLambda_V, scalar_type (1.0 ) + lambda_L), cache.isTransmission ());
210- }
211-
212144 scalar_type ax2;
213145 scalar_type ay2;
214146 scalar_type a2;
@@ -299,7 +231,7 @@ template<typename T, bool _IsAnisotropic, MicrofacetTransformTypes reflect_refra
299231struct Beckmann
300232{
301233 NDF_CONSTEXPR_DECLS (_IsAnisotropic,reflect_refract);
302- NDF_TYPE_ALIASES (SINGLE_ARG (Beckmann<T,IsAnisotropic,SupportedPaths>), SINGLE_ARG (impl::BeckmannCommon<T,IsAnisotropic>), impl::SBeckmannDG1Query<scalar_type>, impl::SBeckmannG2overG1Query<scalar_type>, DualMeasureQuantQuery<scalar_type>);
234+ NDF_TYPE_ALIASES (NDF_SINGLE_ARG (Beckmann<T,IsAnisotropic,SupportedPaths>), NDF_SINGLE_ARG (impl::BeckmannCommon<T,IsAnisotropic>), impl::SBeckmannDG1Query<scalar_type>, impl::SBeckmannG2overG1Query<scalar_type>, DualMeasureQuantQuery<scalar_type>);
303235
304236 template<typename C=bool_constant<!IsAnisotropic> >
305237 static enable_if_t<C::value && !IsAnisotropic, this_t> create (scalar_type A)
@@ -322,11 +254,19 @@ struct Beckmann
322254 return retval;
323255 }
324256
257+ static scalar_type Lambda (scalar_type c2)
258+ {
259+ scalar_type c = sqrt<scalar_type>(c2);
260+ scalar_type nom = scalar_type (1.0 ) - scalar_type (1.259 ) * c + scalar_type (0.396 ) * c2;
261+ scalar_type denom = scalar_type (2.181 ) * c2 + scalar_type (3.535 ) * c;
262+ return hlsl::mix<scalar_type>(scalar_type (0.0 ), nom / denom, c < scalar_type (1.6 ));
263+ }
264+
325265 template<class MicrofacetCache NBL_FUNC_REQUIRES (RequiredMicrofacetCache<MicrofacetCache>)
326266 quant_query_type createQuantQuery (NBL_CONST_REF_ARG (MicrofacetCache) cache, scalar_type orientedEta)
327267 {
328268 quant_query_type quant_query; // only has members for refraction
329- if (SupportsTransmission)
269+ NBL_IF_CONSTEXPR (SupportsTransmission)
330270 {
331271 quant_query.VdotHLdotH = cache.getVdotHLdotH ();
332272 quant_query.VdotH_etaLdotH = cache.getVdotH () + orientedEta * cache.getLdotH ();
@@ -338,31 +278,31 @@ struct Beckmann
338278 {
339279 dg1_query_type dg1_query;
340280 dg1_query.ndf = __ndf_base.template D<MicrofacetCache>(cache);
341- dg1_query.lambda_V = __ndf_base.LambdaC2 (interaction.getNdotV2 ());
281+ dg1_query.lambda_V = Lambda ( __ndf_base.C2 (interaction.getNdotV2 () ));
342282 return dg1_query;
343283 }
344284 template<class LS, class Interaction, typename C=bool_constant<!IsAnisotropic> NBL_FUNC_REQUIRES (LightSample<LS> && RequiredInteraction<Interaction>)
345285 enable_if_t<C::value && !IsAnisotropic, g2g1_query_type> createG2G1Query (NBL_CONST_REF_ARG (LS) _sample, NBL_CONST_REF_ARG (Interaction) interaction)
346286 {
347287 g2g1_query_type g2_query;
348- g2_query.lambda_L = __ndf_base.LambdaC2 (_sample.getNdotL2 ());
349- g2_query.lambda_V = __ndf_base.LambdaC2 (interaction.getNdotV2 ());
288+ g2_query.lambda_L = Lambda ( __ndf_base.C2 (_sample.getNdotL2 () ));
289+ g2_query.lambda_V = Lambda ( __ndf_base.C2 (interaction.getNdotV2 () ));
350290 return g2_query;
351291 }
352292 template<class Interaction, class MicrofacetCache, typename C=bool_constant<IsAnisotropic> NBL_FUNC_REQUIRES (RequiredInteraction<Interaction> && RequiredMicrofacetCache<MicrofacetCache>)
353293 enable_if_t<C::value && IsAnisotropic, dg1_query_type> createDG1Query (NBL_CONST_REF_ARG (Interaction) interaction, NBL_CONST_REF_ARG (MicrofacetCache) cache)
354294 {
355295 dg1_query_type dg1_query;
356296 dg1_query.ndf = __ndf_base.template D<MicrofacetCache>(cache);
357- dg1_query.lambda_V = __ndf_base.LambdaC2 (interaction.getTdotV2 (), interaction.getBdotV2 (), interaction.getNdotV2 ());
297+ dg1_query.lambda_V = Lambda ( __ndf_base.C2 (interaction.getTdotV2 (), interaction.getBdotV2 (), interaction.getNdotV2 () ));
358298 return dg1_query;
359299 }
360300 template<class LS, class Interaction, typename C=bool_constant<IsAnisotropic> NBL_FUNC_REQUIRES (LightSample<LS> && RequiredInteraction<Interaction>)
361301 enable_if_t<C::value && IsAnisotropic, g2g1_query_type> createG2G1Query (NBL_CONST_REF_ARG (LS) _sample, NBL_CONST_REF_ARG (Interaction) interaction)
362302 {
363303 g2g1_query_type g2_query;
364- g2_query.lambda_L = __ndf_base.LambdaC2 (_sample.getTdotL2 (), _sample.getBdotL2 (), _sample.getNdotL2 ());
365- g2_query.lambda_V = __ndf_base.LambdaC2 (interaction.getTdotV2 (), interaction.getBdotV2 (), interaction.getNdotV2 ());
304+ g2_query.lambda_L = Lambda ( __ndf_base.C2 (_sample.getTdotL2 (), _sample.getBdotL2 (), _sample.getNdotL2 () ));
305+ g2_query.lambda_V = Lambda ( __ndf_base.C2 (interaction.getTdotV2 (), interaction.getBdotV2 (), interaction.getNdotV2 () ));
366306 return g2_query;
367307 }
368308
@@ -371,42 +311,32 @@ struct Beckmann
371311 return __generate_base.__call (localV, u);
372312 }
373313
374- template<class LS, class Interaction, class MicrofacetCache, typename C=bool_constant<!SupportsTransmission> NBL_FUNC_REQUIRES (LightSample<LS> && RequiredInteraction<Interaction> && RequiredMicrofacetCache<MicrofacetCache>)
375- enable_if_t<C::value && !SupportsTransmission, quant_type> D (NBL_CONST_REF_ARG (quant_query_type) quant_query, NBL_CONST_REF_ARG (LS) _sample, NBL_CONST_REF_ARG (Interaction) interaction, NBL_CONST_REF_ARG (MicrofacetCache) cache)
376- {
377- scalar_type d = __ndf_base.template D<MicrofacetCache>(cache);
378- return createDualMeasureQuantity<T>(d, interaction.getNdotV (BxDFClampMode::BCM_MAX), _sample.getNdotL (BxDFClampMode::BCM_MAX));
379- }
380- template<class LS, class Interaction, class MicrofacetCache, typename C=bool_constant<SupportsTransmission> NBL_FUNC_REQUIRES (LightSample<LS> && RequiredInteraction<Interaction> && RequiredMicrofacetCache<MicrofacetCache>)
381- enable_if_t<C::value && SupportsTransmission, quant_type> D (NBL_CONST_REF_ARG (quant_query_type) quant_query, NBL_CONST_REF_ARG (LS) _sample, NBL_CONST_REF_ARG (Interaction) interaction, NBL_CONST_REF_ARG (MicrofacetCache) cache)
314+ template<class LS, class Interaction, class MicrofacetCache NBL_FUNC_REQUIRES (LightSample<LS> && RequiredInteraction<Interaction> && RequiredMicrofacetCache<MicrofacetCache>)
315+ quant_type D (NBL_CONST_REF_ARG (quant_query_type) quant_query, NBL_CONST_REF_ARG (LS) _sample, NBL_CONST_REF_ARG (Interaction) interaction, NBL_CONST_REF_ARG (MicrofacetCache) cache)
382316 {
383317 scalar_type d = __ndf_base.template D<MicrofacetCache>(cache);
384- return createDualMeasureQuantity<T, reflect_refract>(d, interaction.getNdotV (BxDFClampMode::BCM_ABS), _sample.getNdotL (BxDFClampMode::BCM_ABS), quant_query. getVdotHLdotH (), quant_query. getVdotH_etaLdotH () );
318+ return createDualMeasureQuantity<T, reflect_refract, quant_query_type >(d, interaction.getNdotV (BxDFClampMode::BCM_ABS), _sample.getNdotL (BxDFClampMode::BCM_ABS), quant_query);
385319 }
386320
387- template<class LS, class Interaction, typename C=bool_constant<!SupportsTransmission> NBL_FUNC_REQUIRES (LightSample<LS> && RequiredInteraction<Interaction>)
388- enable_if_t<C::value && !SupportsTransmission, quant_type> DG1 (NBL_CONST_REF_ARG (dg1_query_type) query, NBL_CONST_REF_ARG (quant_query_type) quant_query, NBL_CONST_REF_ARG (LS) _sample, NBL_CONST_REF_ARG (Interaction) interaction)
389- {
390- scalar_type dg1 = base_type::template DG1<dg1_query_type>(query);
391- return createDualMeasureQuantity<T>(dg1, interaction.getNdotV (BxDFClampMode::BCM_MAX), _sample.getNdotL (BxDFClampMode::BCM_MAX));
392- }
393- template<class LS, class Interaction, typename C=bool_constant<SupportsTransmission> NBL_FUNC_REQUIRES (LightSample<LS> && RequiredInteraction<Interaction>)
394- enable_if_t<C::value && SupportsTransmission, quant_type> DG1 (NBL_CONST_REF_ARG (dg1_query_type) query, NBL_CONST_REF_ARG (quant_query_type) quant_query, NBL_CONST_REF_ARG (LS) _sample, NBL_CONST_REF_ARG (Interaction) interaction)
321+ template<class LS, class Interaction NBL_FUNC_REQUIRES (LightSample<LS> && RequiredInteraction<Interaction>)
322+ quant_type DG1 (NBL_CONST_REF_ARG (dg1_query_type) query, NBL_CONST_REF_ARG (quant_query_type) quant_query, NBL_CONST_REF_ARG (LS) _sample, NBL_CONST_REF_ARG (Interaction) interaction)
395323 {
396- scalar_type dg1 = base_type::template DG1<dg1_query_type>( query);
397- return createDualMeasureQuantity<T, reflect_refract>(dg1, interaction.getNdotV (BxDFClampMode::BCM_ABS), _sample.getNdotL (BxDFClampMode::BCM_ABS), quant_query. getVdotHLdotH (), quant_query. getVdotH_etaLdotH () );
324+ scalar_type dg1 = query. getNdf () / ( scalar_type ( 1.0 ) + query. getLambdaV () );
325+ return createDualMeasureQuantity<T, reflect_refract, quant_query_type >(dg1, interaction.getNdotV (BxDFClampMode::BCM_ABS), _sample.getNdotL (BxDFClampMode::BCM_ABS), quant_query);
398326 }
399327
400328 template<class LS, class Interaction NBL_FUNC_REQUIRES (LightSample<LS> && RequiredInteraction<Interaction>)
401329 scalar_type correlated (NBL_CONST_REF_ARG (g2g1_query_type) query, NBL_CONST_REF_ARG (LS) _sample, NBL_CONST_REF_ARG (Interaction) interaction)
402330 {
403- return base_type::template correlated<g2g1_query_type>( query);
331+ return scalar_type ( 1.0 ) / ( scalar_type ( 1.0 ) + query. getLambdaV () + query. getLambdaL () );
404332 }
405333
406334 template<class LS, class Interaction, class MicrofacetCache NBL_FUNC_REQUIRES (LightSample<LS> && RequiredInteraction<Interaction> && RequiredMicrofacetCache<MicrofacetCache>)
407335 scalar_type G2_over_G1 (NBL_CONST_REF_ARG (g2g1_query_type) query, NBL_CONST_REF_ARG (LS) _sample, NBL_CONST_REF_ARG (Interaction) interaction, NBL_CONST_REF_ARG (MicrofacetCache) cache)
408336 {
409- return base_type::template G2_over_G1<g2g1_query_type, MicrofacetCache>(query, cache);
337+ scalar_type onePlusLambda_V = scalar_type (1.0 ) + query.getLambdaV ();
338+ scalar_type lambda_L = query.getLambdaL ();
339+ return onePlusLambda_V * hlsl::mix (scalar_type (1.0 )/(onePlusLambda_V + lambda_L), bxdf::beta<scalar_type>(onePlusLambda_V, scalar_type (1.0 ) + lambda_L), cache.isTransmission ());
410340 }
411341
412342 base_type __ndf_base;
0 commit comments