@@ -340,13 +340,9 @@ class MaterialCompilerTest final : public application_templates::MonoDeviceAppli
340340 }
341341
342342 // dielectric
343+ const auto dielectricH = forest->_new <CFrontendIR::CMul>();
343344 {
344- const auto layerH = forest->_new <CFrontendIR::CLayer>();
345- auto * layer = forest->deref (layerH);
346- layer->debugInfo = forest->_new <CNodePool::CDebugInfo>(" Glass" );
347-
348- const auto mulH = forest->_new <CFrontendIR::CMul>();
349- auto * mul = forest->deref (mulH);
345+ auto * mul = forest->deref (dielectricH);
350346 // do fresnel first
351347 const auto fresnelH = forest->createNamedFresnel (" ThF4" );
352348 auto * fresnel = forest->deref (fresnelH);
@@ -361,12 +357,60 @@ class MaterialCompilerTest final : public application_templates::MonoDeviceAppli
361357 ct->orientedRealEta = fresnel->orientedRealEta ;
362358 mul->lhs = ctH;
363359 }
364-
360+ }
361+ {
362+ const auto layerH = forest->_new <CFrontendIR::CLayer>();
363+ auto * layer = forest->deref (layerH);
364+ layer->debugInfo = forest->_new <CNodePool::CDebugInfo>(" Glass" );
365+
365366 // use same BxDF for all parts of a layer
366- layer->brdfTop = mulH;
367- layer->btdf = mulH;
368- layer->brdfBottom = mulH;
367+ layer->brdfTop = dielectricH;
368+ layer->btdf = dielectricH;
369+ layer->brdfBottom = dielectricH;
370+
371+ ASSERT_VALUE (forest->addMaterial (layerH,logger),true ," Dielectric" );
372+ }
373+
374+ // thindielectric
375+ {
376+ const auto layerH = forest->_new <CFrontendIR::CLayer>();
377+ auto * layer = forest->deref (layerH);
378+ layer->debugInfo = forest->_new <CNodePool::CDebugInfo>(" Single Pane" );
379+
380+ // do fresnel first for all to have the same one
381+ const auto fresnelH = forest->createNamedFresnel (" ThF4" );
382+ const auto * fresnel = forest->deref (fresnelH);
383+
384+ auto makeIsotropicDielectric = [&](const float roughness, const auto weightNode)->CFrontendIR ::TypedHandle<CFrontendIR::IExprNode>
385+ {
386+ const auto mulH = forest->_new <CFrontendIR::CMul>();
387+ auto * mul = forest->deref (mulH);
388+ const auto ctH = forest->_new <CFrontendIR::CCookTorrance>();
389+ {
390+ auto * ct = forest->deref (ctH);
391+ ct->ndParams .getRougness ()[0 ].scale = ct->ndParams .getRougness ()[1 ].scale = roughness;
392+ // ignored for BRDFs, needed for BTDFs
393+ ct->orientedRealEta = fresnel->orientedRealEta ;
394+ }
395+ mul->lhs = ctH;
396+ mul->rhs = weightNode;
397+ return mulH;
398+ };
399+
400+ const auto thinInfiniteScatterH = forest->_new <CFrontendIR::CThinInfiniteScatterCorrection>();
401+ {
402+ auto * thinInfiniteScatter = forest->deref (thinInfiniteScatterH);
403+ thinInfiniteScatter->reflectance = fresnelH;
404+ thinInfiniteScatter->transmittance = fresnelH;
405+ // without extinction
406+ }
369407
408+ // and now the most implausible material of all!
409+ // smoother on the topside and rough on the underside with a weird intermediate part
410+ layer->brdfTop = makeIsotropicDielectric (0 .01f ,fresnelH);
411+ layer->btdf = makeIsotropicDielectric (0 .1f ,thinInfiniteScatterH);
412+ layer->brdfBottom = makeIsotropicDielectric (0 .2f ,fresnelH);
413+
370414 {
371415 auto * imagEta = forest->deref (fresnel->orientedImagEta );
372416 imagEta->getParam (0 )->scale = std::numeric_limits<float >::min ();
@@ -377,27 +421,78 @@ class MaterialCompilerTest final : public application_templates::MonoDeviceAppli
377421 imagEta->getParam (i)->scale = 0 .f ;
378422 }
379423
380- ASSERT_VALUE (forest->addMaterial (layerH,logger),true ," Dielectric " );
424+ ASSERT_VALUE (forest->addMaterial (layerH,logger),true ," ThinDielectric " );
381425 }
382426
383- // thindielectric
427+ // plastics with IOR 1.5
384428 {
385- //
386- }
429+ // make the node everyone shares
430+ const auto fresnelH = forest->_new <CFrontendIR::CFresnel>();
431+ {
432+ auto * fresnel = forest->deref (fresnelH);
433+ spectral_var_t ::SCreationParams<1 > params = {};
434+ params.knots .params [0 ].scale = 1 .5f ;
435+ fresnel->orientedRealEta = forest->_new <CFrontendIR::CSpectralVariable>(std::move (params));
436+ }
387437
388- // rough plastic
389- {
390- //
391- }
438+ // rough plastic
439+ {
440+ const auto rootH = forest->_new <CFrontendIR::CLayer>();
441+ auto * topLayer = forest->deref (rootH);
442+ topLayer->debugInfo = forest->_new <CNodePool::CDebugInfo>(" Rough Plastic" );
392443
393- // coated diffuse transmitter (twosided roughplastic)
394- {
395- //
396- }
444+ topLayer->brdfTop = dielectricH;
445+ // the delta layering should optimize out nicely due to the sampling property
446+ const auto transH = forest->_new <CFrontendIR::CMul>();
447+ {
448+ auto * mul = forest->deref (transH);
449+ mul->lhs = forest->_new <CFrontendIR::CDeltaTransmission>();
450+ mul->rhs = fresnelH;
451+ }
452+ topLayer->btdf = transH;
397453
398- // same thing but with subsurface beer scattering
399- {
400- //
454+ const auto diffuseH = forest->_new <CFrontendIR::CLayer>();
455+ auto * midLayer = forest->deref (diffuseH);
456+ {
457+ const auto mulH = forest->_new <CFrontendIR::CMul>();
458+ {
459+ auto * mul = forest->deref (mulH);
460+ {
461+ const auto orenNayarH = forest->_new <CFrontendIR::COrenNayar>();
462+ auto * orenNayar = forest->deref (orenNayarH);
463+ orenNayar->ndParams .getRougness ()[0 ].scale = orenNayar->ndParams .getRougness ()[1 ].scale = 0 .2f ;
464+ mul->lhs = orenNayarH;
465+ }
466+ {
467+ spectral_var_t ::SCreationParams<3 > params = {};
468+ params.getSemantics () = spectral_var_t ::Semantics::Fixed3_SRGB;
469+ params.knots .params [0 ].scale = 0 .9f ;
470+ params.knots .params [1 ].scale = 0 .6f ;
471+ params.knots .params [2 ].scale = 0 .01f ;
472+ const auto albedoH = forest->_new <CFrontendIR::CSpectralVariable>(std::move (params));
473+ forest->deref (albedoH)->debugInfo = forest->_new <CNodePool::CDebugInfo>(" Albedo" );
474+ mul->rhs = albedoH;
475+ }
476+ }
477+ midLayer->brdfTop = mulH;
478+ // no transmission in the mid-layer, the backend needs to decompose into separate front/back materials
479+ midLayer->brdfBottom = mulH;
480+ midLayer->coated = rootH;
481+ }
482+ topLayer->coated = diffuseH;
483+
484+ ASSERT_VALUE (forest->addMaterial (rootH,logger),true ," Twosided Rough Plastic" );
485+ }
486+
487+ // coated diffuse transmitter
488+ {
489+ //
490+ }
491+
492+ // same thing but with subsurface beer scattering
493+ {
494+ //
495+ }
401496 }
402497
403498 smart_refctd_ptr<IFile> file;
0 commit comments