Fix T51956: color noise with principled sss, radius 0 and branched path.
[blender-staging.git] / intern / cycles / kernel / closure / bsdf.h
1 /*
2  * Copyright 2011-2013 Blender Foundation
3  *
4  * Licensed under the Apache License, Version 2.0 (the "License");
5  * you may not use this file except in compliance with the License.
6  * You may obtain a copy of the License at
7  *
8  * http://www.apache.org/licenses/LICENSE-2.0
9  *
10  * Unless required by applicable law or agreed to in writing, software
11  * distributed under the License is distributed on an "AS IS" BASIS,
12  * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13  * See the License for the specific language governing permissions and
14  * limitations under the License.
15  */
16
17 #include "kernel/closure/bsdf_ashikhmin_velvet.h"
18 #include "kernel/closure/bsdf_diffuse.h"
19 #include "kernel/closure/bsdf_oren_nayar.h"
20 #include "kernel/closure/bsdf_phong_ramp.h"
21 #include "kernel/closure/bsdf_diffuse_ramp.h"
22 #include "kernel/closure/bsdf_microfacet.h"
23 #include "kernel/closure/bsdf_microfacet_multi.h"
24 #include "kernel/closure/bsdf_reflection.h"
25 #include "kernel/closure/bsdf_refraction.h"
26 #include "kernel/closure/bsdf_transparent.h"
27 #include "kernel/closure/bsdf_ashikhmin_shirley.h"
28 #include "kernel/closure/bsdf_toon.h"
29 #include "kernel/closure/bsdf_hair.h"
30 #include "kernel/closure/bsdf_principled_diffuse.h"
31 #include "kernel/closure/bsdf_principled_sheen.h"
32 #ifdef __SUBSURFACE__
33 #  include "kernel/closure/bssrdf.h"
34 #endif
35 #ifdef __VOLUME__
36 #  include "kernel/closure/volume.h"
37 #endif
38
39 CCL_NAMESPACE_BEGIN
40
41 ccl_device_forceinline int bsdf_sample(KernelGlobals *kg,
42                                        ShaderData *sd,
43                                        const ShaderClosure *sc,
44                                        float randu,
45                                        float randv,
46                                        float3 *eval,
47                                        float3 *omega_in,
48                                        differential3 *domega_in,
49                                        float *pdf)
50 {
51         int label;
52
53         switch(sc->type) {
54                 case CLOSURE_BSDF_DIFFUSE_ID:
55                 case CLOSURE_BSDF_BSSRDF_ID:
56                         label = bsdf_diffuse_sample(sc, sd->Ng, sd->I, sd->dI.dx, sd->dI.dy, randu, randv,
57                                 eval, omega_in, &domega_in->dx, &domega_in->dy, pdf);
58                         break;
59 #ifdef __SVM__
60                 case CLOSURE_BSDF_OREN_NAYAR_ID:
61                         label = bsdf_oren_nayar_sample(sc, sd->Ng, sd->I, sd->dI.dx, sd->dI.dy, randu, randv,
62                                 eval, omega_in, &domega_in->dx, &domega_in->dy, pdf);
63                         break;
64 #ifdef __OSL__
65                 case CLOSURE_BSDF_PHONG_RAMP_ID:
66                         label = bsdf_phong_ramp_sample(sc, sd->Ng, sd->I, sd->dI.dx, sd->dI.dy, randu, randv,
67                                 eval, omega_in, &domega_in->dx, &domega_in->dy, pdf);
68                         break;
69                 case CLOSURE_BSDF_DIFFUSE_RAMP_ID:
70                         label = bsdf_diffuse_ramp_sample(sc, sd->Ng, sd->I, sd->dI.dx, sd->dI.dy, randu, randv,
71                                 eval, omega_in, &domega_in->dx, &domega_in->dy, pdf);
72                         break;
73 #endif
74                 case CLOSURE_BSDF_TRANSLUCENT_ID:
75                         label = bsdf_translucent_sample(sc, sd->Ng, sd->I, sd->dI.dx, sd->dI.dy, randu, randv,
76                                 eval, omega_in, &domega_in->dx, &domega_in->dy, pdf);
77                         break;
78                 case CLOSURE_BSDF_REFLECTION_ID:
79                         label = bsdf_reflection_sample(sc, sd->Ng, sd->I, sd->dI.dx, sd->dI.dy, randu, randv,
80                                 eval, omega_in, &domega_in->dx, &domega_in->dy, pdf);
81                         break;
82                 case CLOSURE_BSDF_REFRACTION_ID:
83                         label = bsdf_refraction_sample(sc, sd->Ng, sd->I, sd->dI.dx, sd->dI.dy, randu, randv,
84                                 eval, omega_in, &domega_in->dx, &domega_in->dy, pdf);
85                         break;
86                 case CLOSURE_BSDF_TRANSPARENT_ID:
87                         label = bsdf_transparent_sample(sc, sd->Ng, sd->I, sd->dI.dx, sd->dI.dy, randu, randv,
88                                 eval, omega_in, &domega_in->dx, &domega_in->dy, pdf);
89                         break;
90                 case CLOSURE_BSDF_MICROFACET_GGX_ID:
91                 case CLOSURE_BSDF_MICROFACET_GGX_FRESNEL_ID:
92                 case CLOSURE_BSDF_MICROFACET_GGX_CLEARCOAT_ID:
93                 case CLOSURE_BSDF_MICROFACET_GGX_ANISO_ID:
94                 case CLOSURE_BSDF_MICROFACET_GGX_ANISO_FRESNEL_ID:
95                 case CLOSURE_BSDF_MICROFACET_GGX_REFRACTION_ID:
96                         label = bsdf_microfacet_ggx_sample(kg, sc, sd->Ng, sd->I, sd->dI.dx, sd->dI.dy, randu, randv,
97                                 eval, omega_in, &domega_in->dx, &domega_in->dy, pdf);
98                         break;
99                 case CLOSURE_BSDF_MICROFACET_MULTI_GGX_ID:
100                 case CLOSURE_BSDF_MICROFACET_MULTI_GGX_FRESNEL_ID:
101                         label = bsdf_microfacet_multi_ggx_sample(kg, sc, sd->Ng, sd->I, sd->dI.dx, sd->dI.dy, randu, randv,
102                                 eval, omega_in,  &domega_in->dx, &domega_in->dy, pdf, &sd->lcg_state);
103                         break;
104                 case CLOSURE_BSDF_MICROFACET_MULTI_GGX_GLASS_ID:
105                 case CLOSURE_BSDF_MICROFACET_MULTI_GGX_GLASS_FRESNEL_ID:
106                         label = bsdf_microfacet_multi_ggx_glass_sample(kg, sc, sd->Ng, sd->I, sd->dI.dx, sd->dI.dy, randu, randv,
107                                 eval, omega_in,  &domega_in->dx, &domega_in->dy, pdf, &sd->lcg_state);
108                         break;
109                 case CLOSURE_BSDF_MICROFACET_BECKMANN_ID:
110                 case CLOSURE_BSDF_MICROFACET_BECKMANN_ANISO_ID:
111                 case CLOSURE_BSDF_MICROFACET_BECKMANN_REFRACTION_ID:
112                         label = bsdf_microfacet_beckmann_sample(kg, sc, sd->Ng, sd->I, sd->dI.dx, sd->dI.dy, randu, randv,
113                                 eval, omega_in, &domega_in->dx, &domega_in->dy, pdf);
114                         break;
115                 case CLOSURE_BSDF_ASHIKHMIN_SHIRLEY_ID:
116                 case CLOSURE_BSDF_ASHIKHMIN_SHIRLEY_ANISO_ID:
117                         label = bsdf_ashikhmin_shirley_sample(sc, sd->Ng, sd->I, sd->dI.dx, sd->dI.dy, randu, randv,
118                                 eval, omega_in, &domega_in->dx, &domega_in->dy, pdf);
119                         break;
120                 case CLOSURE_BSDF_ASHIKHMIN_VELVET_ID:
121                         label = bsdf_ashikhmin_velvet_sample(sc, sd->Ng, sd->I, sd->dI.dx, sd->dI.dy, randu, randv,
122                                 eval, omega_in, &domega_in->dx, &domega_in->dy, pdf);
123                         break;
124                 case CLOSURE_BSDF_DIFFUSE_TOON_ID:
125                         label = bsdf_diffuse_toon_sample(sc, sd->Ng, sd->I, sd->dI.dx, sd->dI.dy, randu, randv,
126                                 eval, omega_in, &domega_in->dx, &domega_in->dy, pdf);
127                         break;
128                 case CLOSURE_BSDF_GLOSSY_TOON_ID:
129                         label = bsdf_glossy_toon_sample(sc, sd->Ng, sd->I, sd->dI.dx, sd->dI.dy, randu, randv,
130                                 eval, omega_in, &domega_in->dx, &domega_in->dy, pdf);
131                         break;
132                 case CLOSURE_BSDF_HAIR_REFLECTION_ID:
133                         label = bsdf_hair_reflection_sample(sc, sd->Ng, sd->I, sd->dI.dx, sd->dI.dy, randu, randv,
134                                 eval, omega_in, &domega_in->dx, &domega_in->dy, pdf);
135                         break;
136                 case CLOSURE_BSDF_HAIR_TRANSMISSION_ID:
137                         label = bsdf_hair_transmission_sample(sc, sd->Ng, sd->I, sd->dI.dx, sd->dI.dy, randu, randv,
138                                 eval, omega_in, &domega_in->dx, &domega_in->dy, pdf);
139                         break;
140 #ifdef __PRINCIPLED__
141                 case CLOSURE_BSDF_PRINCIPLED_DIFFUSE_ID:
142                 case CLOSURE_BSDF_BSSRDF_PRINCIPLED_ID:
143                         label = bsdf_principled_diffuse_sample(sc, sd->Ng, sd->I, sd->dI.dx, sd->dI.dy, randu, randv,
144                                 eval, omega_in, &domega_in->dx, &domega_in->dy, pdf);
145                         break;
146                 case CLOSURE_BSDF_PRINCIPLED_SHEEN_ID:
147                         label = bsdf_principled_sheen_sample(sc, sd->Ng, sd->I, sd->dI.dx, sd->dI.dy, randu, randv,
148                                 eval, omega_in, &domega_in->dx, &domega_in->dy, pdf);
149                         break;
150 #endif  /* __PRINCIPLED__ */
151 #endif
152 #ifdef __VOLUME__
153                 case CLOSURE_VOLUME_HENYEY_GREENSTEIN_ID:
154                         label = volume_henyey_greenstein_sample(sc, sd->I, sd->dI.dx, sd->dI.dy, randu, randv, eval, omega_in, &domega_in->dx, &domega_in->dy, pdf);
155                         break;
156 #endif
157                 default:
158                         label = LABEL_NONE;
159                         break;
160         }
161
162         return label;
163 }
164
165 #ifndef __KERNEL_CUDA__
166 ccl_device
167 #else
168 ccl_device_forceinline
169 #endif
170 float3 bsdf_eval(KernelGlobals *kg,
171                  ShaderData *sd,
172                  const ShaderClosure *sc,
173                  const float3 omega_in,
174                  float *pdf)
175 {
176         float3 eval;
177
178         if(dot(sd->Ng, omega_in) >= 0.0f) {
179                 switch(sc->type) {
180                         case CLOSURE_BSDF_DIFFUSE_ID:
181                         case CLOSURE_BSDF_BSSRDF_ID:
182                                 eval = bsdf_diffuse_eval_reflect(sc, sd->I, omega_in, pdf);
183                                 break;
184 #ifdef __SVM__
185                         case CLOSURE_BSDF_OREN_NAYAR_ID:
186                                 eval = bsdf_oren_nayar_eval_reflect(sc, sd->I, omega_in, pdf);
187                                 break;
188 #ifdef __OSL__
189                         case CLOSURE_BSDF_PHONG_RAMP_ID:
190                                 eval = bsdf_phong_ramp_eval_reflect(sc, sd->I, omega_in, pdf);
191                                 break;
192                         case CLOSURE_BSDF_DIFFUSE_RAMP_ID:
193                                 eval = bsdf_diffuse_ramp_eval_reflect(sc, sd->I, omega_in, pdf);
194                                 break;
195 #endif
196                         case CLOSURE_BSDF_TRANSLUCENT_ID:
197                                 eval = bsdf_translucent_eval_reflect(sc, sd->I, omega_in, pdf);
198                                 break;
199                         case CLOSURE_BSDF_REFLECTION_ID:
200                                 eval = bsdf_reflection_eval_reflect(sc, sd->I, omega_in, pdf);
201                                 break;
202                         case CLOSURE_BSDF_REFRACTION_ID:
203                                 eval = bsdf_refraction_eval_reflect(sc, sd->I, omega_in, pdf);
204                                 break;
205                         case CLOSURE_BSDF_TRANSPARENT_ID:
206                                 eval = bsdf_transparent_eval_reflect(sc, sd->I, omega_in, pdf);
207                                 break;
208                         case CLOSURE_BSDF_MICROFACET_GGX_ID:
209                         case CLOSURE_BSDF_MICROFACET_GGX_FRESNEL_ID:
210                         case CLOSURE_BSDF_MICROFACET_GGX_CLEARCOAT_ID:
211                         case CLOSURE_BSDF_MICROFACET_GGX_ANISO_ID:
212                         case CLOSURE_BSDF_MICROFACET_GGX_ANISO_FRESNEL_ID:
213                         case CLOSURE_BSDF_MICROFACET_GGX_REFRACTION_ID:
214                                 eval = bsdf_microfacet_ggx_eval_reflect(sc, sd->I, omega_in, pdf);
215                                 break;
216                         case CLOSURE_BSDF_MICROFACET_MULTI_GGX_ID:
217                         case CLOSURE_BSDF_MICROFACET_MULTI_GGX_FRESNEL_ID:
218                                 eval = bsdf_microfacet_multi_ggx_eval_reflect(sc, sd->I, omega_in, pdf, &sd->lcg_state);
219                                 break;
220                         case CLOSURE_BSDF_MICROFACET_MULTI_GGX_GLASS_ID:
221                         case CLOSURE_BSDF_MICROFACET_MULTI_GGX_GLASS_FRESNEL_ID:
222                                 eval = bsdf_microfacet_multi_ggx_glass_eval_reflect(sc, sd->I, omega_in, pdf, &sd->lcg_state);
223                                 break;
224                         case CLOSURE_BSDF_MICROFACET_BECKMANN_ID:
225                         case CLOSURE_BSDF_MICROFACET_BECKMANN_ANISO_ID:
226                         case CLOSURE_BSDF_MICROFACET_BECKMANN_REFRACTION_ID:
227                                 eval = bsdf_microfacet_beckmann_eval_reflect(sc, sd->I, omega_in, pdf);
228                                 break;
229                         case CLOSURE_BSDF_ASHIKHMIN_SHIRLEY_ID:
230                         case CLOSURE_BSDF_ASHIKHMIN_SHIRLEY_ANISO_ID:
231                                 eval = bsdf_ashikhmin_shirley_eval_reflect(sc, sd->I, omega_in, pdf);
232                                 break;
233                         case CLOSURE_BSDF_ASHIKHMIN_VELVET_ID:
234                                 eval = bsdf_ashikhmin_velvet_eval_reflect(sc, sd->I, omega_in, pdf);
235                                 break;
236                         case CLOSURE_BSDF_DIFFUSE_TOON_ID:
237                                 eval = bsdf_diffuse_toon_eval_reflect(sc, sd->I, omega_in, pdf);
238                                 break;
239                         case CLOSURE_BSDF_GLOSSY_TOON_ID:
240                                 eval = bsdf_glossy_toon_eval_reflect(sc, sd->I, omega_in, pdf);
241                                 break;
242                         case CLOSURE_BSDF_HAIR_REFLECTION_ID:
243                                 eval = bsdf_hair_reflection_eval_reflect(sc, sd->I, omega_in, pdf);
244                                 break;
245                         case CLOSURE_BSDF_HAIR_TRANSMISSION_ID:
246                                 eval = bsdf_hair_transmission_eval_reflect(sc, sd->I, omega_in, pdf);
247                                 break;
248 #ifdef __PRINCIPLED__
249                         case CLOSURE_BSDF_PRINCIPLED_DIFFUSE_ID:
250                         case CLOSURE_BSDF_BSSRDF_PRINCIPLED_ID:
251                                 eval = bsdf_principled_diffuse_eval_reflect(sc, sd->I, omega_in, pdf);
252                                 break;
253                         case CLOSURE_BSDF_PRINCIPLED_SHEEN_ID:
254                                 eval = bsdf_principled_sheen_eval_reflect(sc, sd->I, omega_in, pdf);
255                                 break;
256 #endif  /* __PRINCIPLED__ */
257 #endif
258 #ifdef __VOLUME__
259                         case CLOSURE_VOLUME_HENYEY_GREENSTEIN_ID:
260                                 eval = volume_henyey_greenstein_eval_phase(sc, sd->I, omega_in, pdf);
261                                 break;
262 #endif
263                         default:
264                                 eval = make_float3(0.0f, 0.0f, 0.0f);
265                                 break;
266                 }
267         }
268         else {
269                 switch(sc->type) {
270                         case CLOSURE_BSDF_DIFFUSE_ID:
271                         case CLOSURE_BSDF_BSSRDF_ID:
272                                 eval = bsdf_diffuse_eval_transmit(sc, sd->I, omega_in, pdf);
273                                 break;
274 #ifdef __SVM__
275                         case CLOSURE_BSDF_OREN_NAYAR_ID:
276                                 eval = bsdf_oren_nayar_eval_transmit(sc, sd->I, omega_in, pdf);
277                                 break;
278                         case CLOSURE_BSDF_TRANSLUCENT_ID:
279                                 eval = bsdf_translucent_eval_transmit(sc, sd->I, omega_in, pdf);
280                                 break;
281                         case CLOSURE_BSDF_REFLECTION_ID:
282                                 eval = bsdf_reflection_eval_transmit(sc, sd->I, omega_in, pdf);
283                                 break;
284                         case CLOSURE_BSDF_REFRACTION_ID:
285                                 eval = bsdf_refraction_eval_transmit(sc, sd->I, omega_in, pdf);
286                                 break;
287                         case CLOSURE_BSDF_TRANSPARENT_ID:
288                                 eval = bsdf_transparent_eval_transmit(sc, sd->I, omega_in, pdf);
289                                 break;
290                         case CLOSURE_BSDF_MICROFACET_GGX_ID:
291                         case CLOSURE_BSDF_MICROFACET_GGX_FRESNEL_ID:
292                         case CLOSURE_BSDF_MICROFACET_GGX_CLEARCOAT_ID:
293                         case CLOSURE_BSDF_MICROFACET_GGX_ANISO_ID:
294                         case CLOSURE_BSDF_MICROFACET_GGX_ANISO_FRESNEL_ID:
295                         case CLOSURE_BSDF_MICROFACET_GGX_REFRACTION_ID:
296                                 eval = bsdf_microfacet_ggx_eval_transmit(sc, sd->I, omega_in, pdf);
297                                 break;
298                         case CLOSURE_BSDF_MICROFACET_MULTI_GGX_ID:
299                         case CLOSURE_BSDF_MICROFACET_MULTI_GGX_FRESNEL_ID:
300                                 eval = bsdf_microfacet_multi_ggx_eval_transmit(sc, sd->I, omega_in, pdf, &sd->lcg_state);
301                                 break;
302                         case CLOSURE_BSDF_MICROFACET_MULTI_GGX_GLASS_ID:
303                         case CLOSURE_BSDF_MICROFACET_MULTI_GGX_GLASS_FRESNEL_ID:
304                                 eval = bsdf_microfacet_multi_ggx_glass_eval_transmit(sc, sd->I, omega_in, pdf, &sd->lcg_state);
305                                 break;
306                         case CLOSURE_BSDF_MICROFACET_BECKMANN_ID:
307                         case CLOSURE_BSDF_MICROFACET_BECKMANN_ANISO_ID:
308                         case CLOSURE_BSDF_MICROFACET_BECKMANN_REFRACTION_ID:
309                                 eval = bsdf_microfacet_beckmann_eval_transmit(sc, sd->I, omega_in, pdf);
310                                 break;
311                         case CLOSURE_BSDF_ASHIKHMIN_SHIRLEY_ID:
312                         case CLOSURE_BSDF_ASHIKHMIN_SHIRLEY_ANISO_ID:
313                                 eval = bsdf_ashikhmin_shirley_eval_transmit(sc, sd->I, omega_in, pdf);
314                                 break;
315                         case CLOSURE_BSDF_ASHIKHMIN_VELVET_ID:
316                                 eval = bsdf_ashikhmin_velvet_eval_transmit(sc, sd->I, omega_in, pdf);
317                                 break;
318                         case CLOSURE_BSDF_DIFFUSE_TOON_ID:
319                                 eval = bsdf_diffuse_toon_eval_transmit(sc, sd->I, omega_in, pdf);
320                                 break;
321                         case CLOSURE_BSDF_GLOSSY_TOON_ID:
322                                 eval = bsdf_glossy_toon_eval_transmit(sc, sd->I, omega_in, pdf);
323                                 break;
324                         case CLOSURE_BSDF_HAIR_REFLECTION_ID:
325                                 eval = bsdf_hair_reflection_eval_transmit(sc, sd->I, omega_in, pdf);
326                                 break;
327                         case CLOSURE_BSDF_HAIR_TRANSMISSION_ID:
328                                 eval = bsdf_hair_transmission_eval_transmit(sc, sd->I, omega_in, pdf);
329                                 break;
330 #ifdef __PRINCIPLED__
331                         case CLOSURE_BSDF_PRINCIPLED_DIFFUSE_ID:
332                         case CLOSURE_BSDF_BSSRDF_PRINCIPLED_ID:
333                                 eval = bsdf_principled_diffuse_eval_transmit(sc, sd->I, omega_in, pdf);
334                                 break;
335                         case CLOSURE_BSDF_PRINCIPLED_SHEEN_ID:
336                                 eval = bsdf_principled_sheen_eval_transmit(sc, sd->I, omega_in, pdf);
337                                 break;
338 #endif  /* __PRINCIPLED__ */
339 #endif
340 #ifdef __VOLUME__
341                         case CLOSURE_VOLUME_HENYEY_GREENSTEIN_ID:
342                                 eval = volume_henyey_greenstein_eval_phase(sc, sd->I, omega_in, pdf);
343                                 break;
344 #endif
345                         default:
346                                 eval = make_float3(0.0f, 0.0f, 0.0f);
347                                 break;
348                 }
349         }
350
351         return eval;
352 }
353
354 ccl_device void bsdf_blur(KernelGlobals *kg, ShaderClosure *sc, float roughness)
355 {
356         /* ToDo: do we want to blur volume closures? */
357 #ifdef __SVM__
358         switch(sc->type) {
359                 case CLOSURE_BSDF_MICROFACET_MULTI_GGX_ID:
360                 case CLOSURE_BSDF_MICROFACET_MULTI_GGX_FRESNEL_ID:
361                 case CLOSURE_BSDF_MICROFACET_MULTI_GGX_GLASS_ID:
362                 case CLOSURE_BSDF_MICROFACET_MULTI_GGX_GLASS_FRESNEL_ID:
363                         bsdf_microfacet_multi_ggx_blur(sc, roughness);
364                         break;
365                 case CLOSURE_BSDF_MICROFACET_GGX_ID:
366                 case CLOSURE_BSDF_MICROFACET_GGX_FRESNEL_ID:
367                 case CLOSURE_BSDF_MICROFACET_GGX_CLEARCOAT_ID:
368                 case CLOSURE_BSDF_MICROFACET_GGX_ANISO_ID:
369                 case CLOSURE_BSDF_MICROFACET_GGX_ANISO_FRESNEL_ID:
370                 case CLOSURE_BSDF_MICROFACET_GGX_REFRACTION_ID:
371                         bsdf_microfacet_ggx_blur(sc, roughness);
372                         break;
373                 case CLOSURE_BSDF_MICROFACET_BECKMANN_ID:
374                 case CLOSURE_BSDF_MICROFACET_BECKMANN_ANISO_ID:
375                 case CLOSURE_BSDF_MICROFACET_BECKMANN_REFRACTION_ID:
376                         bsdf_microfacet_beckmann_blur(sc, roughness);
377                         break;
378                 case CLOSURE_BSDF_ASHIKHMIN_SHIRLEY_ID:
379                 case CLOSURE_BSDF_ASHIKHMIN_SHIRLEY_ANISO_ID:
380                         bsdf_ashikhmin_shirley_blur(sc, roughness);
381                         break;
382                 default:
383                         break;
384         }
385 #endif
386 }
387
388 ccl_device bool bsdf_merge(ShaderClosure *a, ShaderClosure *b)
389 {
390 #ifdef __SVM__
391         switch(a->type) {
392                 case CLOSURE_BSDF_TRANSPARENT_ID:
393                         return true;
394                 case CLOSURE_BSDF_DIFFUSE_ID:
395                 case CLOSURE_BSDF_BSSRDF_ID:
396                 case CLOSURE_BSDF_TRANSLUCENT_ID:
397                         return bsdf_diffuse_merge(a, b);
398                 case CLOSURE_BSDF_OREN_NAYAR_ID:
399                         return bsdf_oren_nayar_merge(a, b);
400                 case CLOSURE_BSDF_REFLECTION_ID:
401                 case CLOSURE_BSDF_REFRACTION_ID:
402                 case CLOSURE_BSDF_MICROFACET_GGX_ID:
403                 case CLOSURE_BSDF_MICROFACET_GGX_FRESNEL_ID:
404                 case CLOSURE_BSDF_MICROFACET_GGX_CLEARCOAT_ID:
405                 case CLOSURE_BSDF_MICROFACET_GGX_ANISO_ID:
406                 case CLOSURE_BSDF_MICROFACET_GGX_ANISO_FRESNEL_ID:
407                 case CLOSURE_BSDF_MICROFACET_GGX_REFRACTION_ID:
408                 case CLOSURE_BSDF_MICROFACET_MULTI_GGX_ID:
409                 case CLOSURE_BSDF_MICROFACET_MULTI_GGX_FRESNEL_ID:
410                 case CLOSURE_BSDF_MICROFACET_MULTI_GGX_GLASS_ID:
411                 case CLOSURE_BSDF_MICROFACET_MULTI_GGX_GLASS_FRESNEL_ID:
412                 case CLOSURE_BSDF_MICROFACET_BECKMANN_ID:
413                 case CLOSURE_BSDF_MICROFACET_BECKMANN_ANISO_ID:
414                 case CLOSURE_BSDF_MICROFACET_BECKMANN_REFRACTION_ID:
415                 case CLOSURE_BSDF_ASHIKHMIN_SHIRLEY_ID:
416                 case CLOSURE_BSDF_ASHIKHMIN_SHIRLEY_ANISO_ID:
417                         return bsdf_microfacet_merge(a, b);
418                 case CLOSURE_BSDF_ASHIKHMIN_VELVET_ID:
419                         return bsdf_ashikhmin_velvet_merge(a, b);
420                 case CLOSURE_BSDF_DIFFUSE_TOON_ID:
421                 case CLOSURE_BSDF_GLOSSY_TOON_ID:
422                         return bsdf_toon_merge(a, b);
423                 case CLOSURE_BSDF_HAIR_REFLECTION_ID:
424                 case CLOSURE_BSDF_HAIR_TRANSMISSION_ID:
425                         return bsdf_hair_merge(a, b);
426 #ifdef __PRINCIPLED__
427                 case CLOSURE_BSDF_PRINCIPLED_DIFFUSE_ID:
428                 case CLOSURE_BSDF_BSSRDF_PRINCIPLED_ID:
429                         return bsdf_principled_diffuse_merge(a, b);
430 #endif
431 #ifdef __VOLUME__
432                 case CLOSURE_VOLUME_HENYEY_GREENSTEIN_ID:
433                         return volume_henyey_greenstein_merge(a, b);
434 #endif
435                 default:
436                         return false;
437         }
438 #else
439         return false;
440 #endif
441 }
442
443 /* Classifies a closure as diffuse-like or specular-like.
444  * This is needed for the denoising feature pass generation,
445  * which are written on the first bounce where more than 25%
446  * of the sampling weight belongs to diffuse-line closures. */
447 ccl_device_inline bool bsdf_is_specular_like(ShaderClosure *sc)
448 {
449         if(CLOSURE_IS_BSDF_TRANSPARENT(sc->type)) {
450                 return true;
451         }
452
453         if(CLOSURE_IS_BSDF_MICROFACET(sc->type)) {
454                 MicrofacetBsdf *bsdf = (MicrofacetBsdf*) sc;
455                 return (bsdf->alpha_x*bsdf->alpha_y <= 0.075f*0.075f);
456         }
457
458         return false;
459 }
460
461 CCL_NAMESPACE_END
462