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 CCL_NAMESPACE_BEGIN
18 
19 #ifdef __BAKING__
20 
compute_light_pass(KernelGlobals * kg,ShaderData * sd,PathRadiance * L,uint rng_hash,int pass_filter,int sample)21 ccl_device_noinline void compute_light_pass(
22     KernelGlobals *kg, ShaderData *sd, PathRadiance *L, uint rng_hash, int pass_filter, int sample)
23 {
24   kernel_assert(kernel_data.film.use_light_pass);
25 
26   float3 throughput = make_float3(1.0f, 1.0f, 1.0f);
27 
28   /* Emission and indirect shader data memory used by various functions. */
29   ShaderDataTinyStorage emission_sd_storage;
30   ShaderData *emission_sd = AS_SHADER_DATA(&emission_sd_storage);
31   ShaderData indirect_sd;
32 
33   /* Init radiance. */
34   path_radiance_init(kg, L);
35 
36   /* Init path state. */
37   PathState state;
38   path_state_init(kg, emission_sd, &state, rng_hash, sample, NULL);
39 
40   /* Evaluate surface shader. */
41   shader_eval_surface(kg, sd, &state, NULL, state.flag);
42 
43   /* TODO, disable more closures we don't need besides transparent */
44   shader_bsdf_disable_transparency(kg, sd);
45 
46   /* Init ray. */
47   Ray ray;
48   ray.P = sd->P + sd->Ng;
49   ray.D = -sd->Ng;
50   ray.t = FLT_MAX;
51 #  ifdef __CAMERA_MOTION__
52   ray.time = 0.5f;
53 #  endif
54 
55 #  ifdef __BRANCHED_PATH__
56   if (!kernel_data.integrator.branched) {
57     /* regular path tracer */
58 #  endif
59 
60     /* sample ambient occlusion */
61     if (pass_filter & BAKE_FILTER_AO) {
62       kernel_path_ao(kg, sd, emission_sd, L, &state, throughput, shader_bsdf_alpha(kg, sd));
63     }
64 
65     /* sample emission */
66     if ((pass_filter & BAKE_FILTER_EMISSION) && (sd->flag & SD_EMISSION)) {
67       float3 emission = indirect_primitive_emission(kg, sd, 0.0f, state.flag, state.ray_pdf);
68       path_radiance_accum_emission(kg, L, &state, throughput, emission);
69     }
70 
71     bool is_sss_sample = false;
72 
73 #  ifdef __SUBSURFACE__
74     /* sample subsurface scattering */
75     if ((pass_filter & BAKE_FILTER_DIFFUSE) && (sd->flag & SD_BSSRDF)) {
76       /* When mixing BSSRDF and BSDF closures we should skip BSDF lighting
77        * if scattering was successful. */
78       SubsurfaceIndirectRays ss_indirect;
79       kernel_path_subsurface_init_indirect(&ss_indirect);
80       if (kernel_path_subsurface_scatter(
81               kg, sd, emission_sd, L, &state, &ray, &throughput, &ss_indirect)) {
82         while (ss_indirect.num_rays) {
83           kernel_path_subsurface_setup_indirect(kg, &ss_indirect, &state, &ray, L, &throughput);
84           kernel_path_indirect(kg, &indirect_sd, emission_sd, &ray, throughput, &state, L);
85         }
86         is_sss_sample = true;
87       }
88     }
89 #  endif
90 
91     /* sample light and BSDF */
92     if (!is_sss_sample && (pass_filter & (BAKE_FILTER_DIRECT | BAKE_FILTER_INDIRECT))) {
93       kernel_path_surface_connect_light(kg, sd, emission_sd, throughput, &state, L);
94 
95       if (kernel_path_surface_bounce(kg, sd, &throughput, &state, &L->state, &ray)) {
96 #  ifdef __LAMP_MIS__
97         state.ray_t = 0.0f;
98 #  endif
99         /* compute indirect light */
100         kernel_path_indirect(kg, &indirect_sd, emission_sd, &ray, throughput, &state, L);
101 
102         /* sum and reset indirect light pass variables for the next samples */
103         path_radiance_sum_indirect(L);
104         path_radiance_reset_indirect(L);
105       }
106     }
107 #  ifdef __BRANCHED_PATH__
108   }
109   else {
110     /* branched path tracer */
111 
112     /* sample ambient occlusion */
113     if (pass_filter & BAKE_FILTER_AO) {
114       kernel_branched_path_ao(kg, sd, emission_sd, L, &state, throughput);
115     }
116 
117     /* sample emission */
118     if ((pass_filter & BAKE_FILTER_EMISSION) && (sd->flag & SD_EMISSION)) {
119       float3 emission = indirect_primitive_emission(kg, sd, 0.0f, state.flag, state.ray_pdf);
120       path_radiance_accum_emission(kg, L, &state, throughput, emission);
121     }
122 
123 #    ifdef __SUBSURFACE__
124     /* sample subsurface scattering */
125     if ((pass_filter & BAKE_FILTER_DIFFUSE) && (sd->flag & SD_BSSRDF)) {
126       /* When mixing BSSRDF and BSDF closures we should skip BSDF lighting
127        * if scattering was successful. */
128       kernel_branched_path_subsurface_scatter(
129           kg, sd, &indirect_sd, emission_sd, L, &state, &ray, throughput);
130     }
131 #    endif
132 
133     /* sample light and BSDF */
134     if (pass_filter & (BAKE_FILTER_DIRECT | BAKE_FILTER_INDIRECT)) {
135 #    if defined(__EMISSION__)
136       /* direct light */
137       if (kernel_data.integrator.use_direct_light) {
138         int all = kernel_data.integrator.sample_all_lights_direct;
139         kernel_branched_path_surface_connect_light(
140             kg, sd, emission_sd, &state, throughput, 1.0f, L, all);
141       }
142 #    endif
143 
144       /* indirect light */
145       kernel_branched_path_surface_indirect_light(
146           kg, sd, &indirect_sd, emission_sd, throughput, 1.0f, &state, L);
147     }
148   }
149 #  endif
150 }
151 
152 /* this helps with AA but it's not the real solution as it does not AA the geometry
153  *  but it's better than nothing, thus committed */
bake_clamp_mirror_repeat(float u,float max)154 ccl_device_inline float bake_clamp_mirror_repeat(float u, float max)
155 {
156   /* use mirror repeat (like opengl texture) so that if the barycentric
157    * coordinate goes past the end of the triangle it is not always clamped
158    * to the same value, gives ugly patterns */
159   u /= max;
160   float fu = floorf(u);
161   u = u - fu;
162 
163   return ((((int)fu) & 1) ? 1.0f - u : u) * max;
164 }
165 
kernel_bake_shader_bsdf(KernelGlobals * kg,ShaderData * sd,const ShaderEvalType type)166 ccl_device_inline float3 kernel_bake_shader_bsdf(KernelGlobals *kg,
167                                                  ShaderData *sd,
168                                                  const ShaderEvalType type)
169 {
170   switch (type) {
171     case SHADER_EVAL_DIFFUSE:
172       return shader_bsdf_diffuse(kg, sd);
173     case SHADER_EVAL_GLOSSY:
174       return shader_bsdf_glossy(kg, sd);
175     case SHADER_EVAL_TRANSMISSION:
176       return shader_bsdf_transmission(kg, sd);
177     default:
178       kernel_assert(!"Unknown bake type passed to BSDF evaluate");
179       return make_float3(0.0f, 0.0f, 0.0f);
180   }
181 }
182 
kernel_bake_evaluate_direct_indirect(KernelGlobals * kg,ShaderData * sd,PathState * state,float3 direct,float3 indirect,const ShaderEvalType type,const int pass_filter)183 ccl_device float3 kernel_bake_evaluate_direct_indirect(KernelGlobals *kg,
184                                                        ShaderData *sd,
185                                                        PathState *state,
186                                                        float3 direct,
187                                                        float3 indirect,
188                                                        const ShaderEvalType type,
189                                                        const int pass_filter)
190 {
191   float3 color;
192   const bool is_color = (pass_filter & BAKE_FILTER_COLOR) != 0;
193   const bool is_direct = (pass_filter & BAKE_FILTER_DIRECT) != 0;
194   const bool is_indirect = (pass_filter & BAKE_FILTER_INDIRECT) != 0;
195   float3 out = make_float3(0.0f, 0.0f, 0.0f);
196 
197   if (is_color) {
198     if (is_direct || is_indirect) {
199       /* Leave direct and diffuse channel colored. */
200       color = make_float3(1.0f, 1.0f, 1.0f);
201     }
202     else {
203       /* surface color of the pass only */
204       shader_eval_surface(kg, sd, state, NULL, 0);
205       return kernel_bake_shader_bsdf(kg, sd, type);
206     }
207   }
208   else {
209     shader_eval_surface(kg, sd, state, NULL, 0);
210     color = kernel_bake_shader_bsdf(kg, sd, type);
211   }
212 
213   if (is_direct) {
214     out += safe_divide_even_color(direct, color);
215   }
216 
217   if (is_indirect) {
218     out += safe_divide_even_color(indirect, color);
219   }
220 
221   return out;
222 }
223 
kernel_bake_evaluate(KernelGlobals * kg,ccl_global float * buffer,int sample,int x,int y,int offset,int stride)224 ccl_device void kernel_bake_evaluate(
225     KernelGlobals *kg, ccl_global float *buffer, int sample, int x, int y, int offset, int stride)
226 {
227   /* Setup render buffers. */
228   const int index = offset + x + y * stride;
229   const int pass_stride = kernel_data.film.pass_stride;
230   buffer += index * pass_stride;
231 
232   ccl_global float *primitive = buffer + kernel_data.film.pass_bake_primitive;
233   ccl_global float *differential = buffer + kernel_data.film.pass_bake_differential;
234   ccl_global float *output = buffer + kernel_data.film.pass_combined;
235 
236   int prim = __float_as_uint(primitive[1]);
237   if (prim == -1)
238     return;
239 
240   prim += kernel_data.bake.tri_offset;
241 
242   /* Random number generator. */
243   uint rng_hash = hash_uint2(x, y) ^ kernel_data.integrator.seed;
244   int num_samples = kernel_data.integrator.aa_samples;
245 
246   float filter_x, filter_y;
247   if (sample == 0) {
248     filter_x = filter_y = 0.5f;
249   }
250   else {
251     path_rng_2D(kg, rng_hash, sample, num_samples, PRNG_FILTER_U, &filter_x, &filter_y);
252   }
253 
254   /* Barycentric UV with subpixel offset. */
255   float u = primitive[2];
256   float v = primitive[3];
257 
258   float dudx = differential[0];
259   float dudy = differential[1];
260   float dvdx = differential[2];
261   float dvdy = differential[3];
262 
263   if (sample > 0) {
264     u = bake_clamp_mirror_repeat(u + dudx * (filter_x - 0.5f) + dudy * (filter_y - 0.5f), 1.0f);
265     v = bake_clamp_mirror_repeat(v + dvdx * (filter_x - 0.5f) + dvdy * (filter_y - 0.5f),
266                                  1.0f - u);
267   }
268 
269   /* Shader data setup. */
270   int object = kernel_data.bake.object_index;
271   int shader;
272   float3 P, Ng;
273 
274   triangle_point_normal(kg, object, prim, u, v, &P, &Ng, &shader);
275 
276   ShaderData sd;
277   shader_setup_from_sample(
278       kg,
279       &sd,
280       P,
281       Ng,
282       Ng,
283       shader,
284       object,
285       prim,
286       u,
287       v,
288       1.0f,
289       0.5f,
290       !(kernel_tex_fetch(__object_flag, object) & SD_OBJECT_TRANSFORM_APPLIED),
291       LAMP_NONE);
292   sd.I = sd.N;
293 
294   /* Setup differentials. */
295   sd.dP.dx = sd.dPdu * dudx + sd.dPdv * dvdx;
296   sd.dP.dy = sd.dPdu * dudy + sd.dPdv * dvdy;
297   sd.du.dx = dudx;
298   sd.du.dy = dudy;
299   sd.dv.dx = dvdx;
300   sd.dv.dy = dvdy;
301 
302   /* Set RNG state for shaders that use sampling. */
303   PathState state = {0};
304   state.rng_hash = rng_hash;
305   state.rng_offset = 0;
306   state.sample = sample;
307   state.num_samples = num_samples;
308   state.min_ray_pdf = FLT_MAX;
309 
310   /* Light passes if we need more than color. */
311   PathRadiance L;
312   int pass_filter = kernel_data.bake.pass_filter;
313 
314   if (kernel_data.bake.pass_filter & ~BAKE_FILTER_COLOR)
315     compute_light_pass(kg, &sd, &L, rng_hash, pass_filter, sample);
316 
317   float3 out = make_float3(0.0f, 0.0f, 0.0f);
318 
319   ShaderEvalType type = (ShaderEvalType)kernel_data.bake.type;
320   switch (type) {
321     /* data passes */
322     case SHADER_EVAL_NORMAL:
323     case SHADER_EVAL_ROUGHNESS:
324     case SHADER_EVAL_EMISSION: {
325       if (type != SHADER_EVAL_NORMAL || (sd.flag & SD_HAS_BUMP)) {
326         int path_flag = (type == SHADER_EVAL_EMISSION) ? PATH_RAY_EMISSION : 0;
327         shader_eval_surface(kg, &sd, &state, NULL, path_flag);
328       }
329 
330       if (type == SHADER_EVAL_NORMAL) {
331         float3 N = sd.N;
332         if (sd.flag & SD_HAS_BUMP) {
333           N = shader_bsdf_average_normal(kg, &sd);
334         }
335 
336         /* encoding: normal = (2 * color) - 1 */
337         out = N * 0.5f + make_float3(0.5f, 0.5f, 0.5f);
338       }
339       else if (type == SHADER_EVAL_ROUGHNESS) {
340         float roughness = shader_bsdf_average_roughness(&sd);
341         out = make_float3(roughness, roughness, roughness);
342       }
343       else {
344         out = shader_emissive_eval(&sd);
345       }
346       break;
347     }
348     case SHADER_EVAL_UV: {
349       out = primitive_uv(kg, &sd);
350       break;
351     }
352 #  ifdef __PASSES__
353     /* light passes */
354     case SHADER_EVAL_AO: {
355       out = L.ao;
356       break;
357     }
358     case SHADER_EVAL_COMBINED: {
359       if ((pass_filter & BAKE_FILTER_COMBINED) == BAKE_FILTER_COMBINED) {
360         float alpha;
361         out = path_radiance_clamp_and_sum(kg, &L, &alpha);
362         break;
363       }
364 
365       if ((pass_filter & BAKE_FILTER_DIFFUSE_DIRECT) == BAKE_FILTER_DIFFUSE_DIRECT)
366         out += L.direct_diffuse;
367       if ((pass_filter & BAKE_FILTER_DIFFUSE_INDIRECT) == BAKE_FILTER_DIFFUSE_INDIRECT)
368         out += L.indirect_diffuse;
369 
370       if ((pass_filter & BAKE_FILTER_GLOSSY_DIRECT) == BAKE_FILTER_GLOSSY_DIRECT)
371         out += L.direct_glossy;
372       if ((pass_filter & BAKE_FILTER_GLOSSY_INDIRECT) == BAKE_FILTER_GLOSSY_INDIRECT)
373         out += L.indirect_glossy;
374 
375       if ((pass_filter & BAKE_FILTER_TRANSMISSION_DIRECT) == BAKE_FILTER_TRANSMISSION_DIRECT)
376         out += L.direct_transmission;
377       if ((pass_filter & BAKE_FILTER_TRANSMISSION_INDIRECT) == BAKE_FILTER_TRANSMISSION_INDIRECT)
378         out += L.indirect_transmission;
379 
380       if ((pass_filter & BAKE_FILTER_EMISSION) != 0)
381         out += L.emission;
382 
383       break;
384     }
385     case SHADER_EVAL_SHADOW: {
386       out = L.shadow;
387       break;
388     }
389     case SHADER_EVAL_DIFFUSE: {
390       out = kernel_bake_evaluate_direct_indirect(
391           kg, &sd, &state, L.direct_diffuse, L.indirect_diffuse, type, pass_filter);
392       break;
393     }
394     case SHADER_EVAL_GLOSSY: {
395       out = kernel_bake_evaluate_direct_indirect(
396           kg, &sd, &state, L.direct_glossy, L.indirect_glossy, type, pass_filter);
397       break;
398     }
399     case SHADER_EVAL_TRANSMISSION: {
400       out = kernel_bake_evaluate_direct_indirect(
401           kg, &sd, &state, L.direct_transmission, L.indirect_transmission, type, pass_filter);
402       break;
403     }
404 #  endif
405 
406     /* extra */
407     case SHADER_EVAL_ENVIRONMENT: {
408       /* setup ray */
409       Ray ray;
410 
411       ray.P = make_float3(0.0f, 0.0f, 0.0f);
412       ray.D = normalize(P);
413       ray.t = 0.0f;
414 #  ifdef __CAMERA_MOTION__
415       ray.time = 0.5f;
416 #  endif
417 
418 #  ifdef __RAY_DIFFERENTIALS__
419       ray.dD = differential3_zero();
420       ray.dP = differential3_zero();
421 #  endif
422 
423       /* setup shader data */
424       shader_setup_from_background(kg, &sd, &ray);
425 
426       /* evaluate */
427       int path_flag = 0; /* we can't know which type of BSDF this is for */
428       shader_eval_surface(kg, &sd, &state, NULL, path_flag | PATH_RAY_EMISSION);
429       out = shader_background_eval(&sd);
430       break;
431     }
432     default: {
433       /* no real shader, returning the position of the verts for debugging */
434       out = normalize(P);
435       break;
436     }
437   }
438 
439   /* write output */
440   const float4 result = make_float4(out.x, out.y, out.z, 1.0f);
441   kernel_write_pass_float4(output, result);
442 }
443 
444 #endif /* __BAKING__ */
445 
kernel_displace_evaluate(KernelGlobals * kg,ccl_global uint4 * input,ccl_global float4 * output,int i)446 ccl_device void kernel_displace_evaluate(KernelGlobals *kg,
447                                          ccl_global uint4 *input,
448                                          ccl_global float4 *output,
449                                          int i)
450 {
451   ShaderData sd;
452   PathState state = {0};
453   uint4 in = input[i];
454 
455   /* setup shader data */
456   int object = in.x;
457   int prim = in.y;
458   float u = __uint_as_float(in.z);
459   float v = __uint_as_float(in.w);
460 
461   shader_setup_from_displace(kg, &sd, object, prim, u, v);
462 
463   /* evaluate */
464   float3 P = sd.P;
465   shader_eval_displacement(kg, &sd, &state);
466   float3 D = sd.P - P;
467 
468   object_inverse_dir_transform(kg, &sd, &D);
469 
470   /* write output */
471   output[i] += make_float4(D.x, D.y, D.z, 0.0f);
472 }
473 
kernel_background_evaluate(KernelGlobals * kg,ccl_global uint4 * input,ccl_global float4 * output,int i)474 ccl_device void kernel_background_evaluate(KernelGlobals *kg,
475                                            ccl_global uint4 *input,
476                                            ccl_global float4 *output,
477                                            int i)
478 {
479   ShaderData sd;
480   PathState state = {0};
481   uint4 in = input[i];
482 
483   /* setup ray */
484   Ray ray;
485   float u = __uint_as_float(in.x);
486   float v = __uint_as_float(in.y);
487 
488   ray.P = make_float3(0.0f, 0.0f, 0.0f);
489   ray.D = equirectangular_to_direction(u, v);
490   ray.t = 0.0f;
491 #ifdef __CAMERA_MOTION__
492   ray.time = 0.5f;
493 #endif
494 
495 #ifdef __RAY_DIFFERENTIALS__
496   ray.dD = differential3_zero();
497   ray.dP = differential3_zero();
498 #endif
499 
500   /* setup shader data */
501   shader_setup_from_background(kg, &sd, &ray);
502 
503   /* evaluate */
504   int path_flag = 0; /* we can't know which type of BSDF this is for */
505   shader_eval_surface(kg, &sd, &state, NULL, path_flag | PATH_RAY_EMISSION);
506   float3 color = shader_background_eval(&sd);
507 
508   /* write output */
509   output[i] += make_float4(color.x, color.y, color.z, 0.0f);
510 }
511 
512 CCL_NAMESPACE_END
513