Merging r46096 through r46110 from trunk into soc-2011-tomato
[blender-staging.git] / intern / cycles / kernel / kernel_path.h
1 /*
2  * Copyright 2011, Blender Foundation.
3  *
4  * This program is free software; you can redistribute it and/or
5  * modify it under the terms of the GNU General Public License
6  * as published by the Free Software Foundation; either version 2
7  * of the License, or (at your option) any later version.
8  *
9  * This program is distributed in the hope that it will be useful,
10  * but WITHOUT ANY WARRANTY; without even the implied warranty of
11  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
12  * GNU General Public License for more details.
13  *
14  * You should have received a copy of the GNU General Public License
15  * along with this program; if not, write to the Free Software Foundation,
16  * Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
17  */
18
19 #include "kernel_differential.h"
20 #include "kernel_montecarlo.h"
21 #include "kernel_triangle.h"
22 #include "kernel_object.h"
23 #ifdef __QBVH__
24 #include "kernel_qbvh.h"
25 #else
26 #include "kernel_bvh.h"
27 #endif
28 #include "kernel_accumulate.h"
29 #include "kernel_camera.h"
30 #include "kernel_shader.h"
31 #include "kernel_light.h"
32 #include "kernel_emission.h"
33 #include "kernel_random.h"
34 #include "kernel_passes.h"
35
36 CCL_NAMESPACE_BEGIN
37
38 typedef struct PathState {
39         uint flag;
40         int bounce;
41
42         int diffuse_bounce;
43         int glossy_bounce;
44         int transmission_bounce;
45         int transparent_bounce;
46 } PathState;
47
48 __device_inline void path_state_init(PathState *state)
49 {
50         state->flag = PATH_RAY_CAMERA|PATH_RAY_SINGULAR|PATH_RAY_MIS_SKIP;
51         state->bounce = 0;
52         state->diffuse_bounce = 0;
53         state->glossy_bounce = 0;
54         state->transmission_bounce = 0;
55         state->transparent_bounce = 0;
56 }
57
58 __device_inline void path_state_next(KernelGlobals *kg, PathState *state, int label)
59 {
60         /* ray through transparent keeps same flags from previous ray and is
61            not counted as a regular bounce, transparent has separate max */
62         if(label & LABEL_TRANSPARENT) {
63                 state->flag |= PATH_RAY_TRANSPARENT;
64                 state->transparent_bounce++;
65
66                 if(!kernel_data.integrator.transparent_shadows)
67                         state->flag |= PATH_RAY_MIS_SKIP;
68
69                 return;
70         }
71
72         state->bounce++;
73
74         /* reflection/transmission */
75         if(label & LABEL_REFLECT) {
76                 state->flag |= PATH_RAY_REFLECT;
77                 state->flag &= ~(PATH_RAY_TRANSMIT|PATH_RAY_CAMERA|PATH_RAY_TRANSPARENT);
78
79                 if(label & LABEL_DIFFUSE)
80                         state->diffuse_bounce++;
81                 else
82                         state->glossy_bounce++;
83         }
84         else {
85                 kernel_assert(label & LABEL_TRANSMIT);
86
87                 state->flag |= PATH_RAY_TRANSMIT;
88                 state->flag &= ~(PATH_RAY_REFLECT|PATH_RAY_CAMERA|PATH_RAY_TRANSPARENT);
89
90                 state->transmission_bounce++;
91         }
92
93         /* diffuse/glossy/singular */
94         if(label & LABEL_DIFFUSE) {
95                 state->flag |= PATH_RAY_DIFFUSE;
96                 state->flag &= ~(PATH_RAY_GLOSSY|PATH_RAY_SINGULAR|PATH_RAY_MIS_SKIP);
97         }
98         else if(label & LABEL_GLOSSY) {
99                 state->flag |= PATH_RAY_GLOSSY;
100                 state->flag &= ~(PATH_RAY_DIFFUSE|PATH_RAY_SINGULAR|PATH_RAY_MIS_SKIP);
101         }
102         else {
103                 kernel_assert(label & LABEL_SINGULAR);
104
105                 state->flag |= PATH_RAY_GLOSSY|PATH_RAY_SINGULAR|PATH_RAY_MIS_SKIP;
106                 state->flag &= ~PATH_RAY_DIFFUSE;
107         }
108 }
109
110 __device_inline uint path_state_ray_visibility(KernelGlobals *kg, PathState *state)
111 {
112         uint flag = state->flag;
113
114         /* for visibility, diffuse/glossy are for reflection only */
115         if(flag & PATH_RAY_TRANSMIT)
116                 flag &= ~(PATH_RAY_DIFFUSE|PATH_RAY_GLOSSY);
117         /* for camera visibility, use render layer flags */
118         if(flag & PATH_RAY_CAMERA)
119                 flag |= kernel_data.integrator.layer_flag;
120
121         return flag;
122 }
123
124 __device_inline float path_state_terminate_probability(KernelGlobals *kg, PathState *state, const float3 throughput)
125 {
126         if(state->flag & PATH_RAY_TRANSPARENT) {
127                 /* transparent rays treated separately */
128                 if(state->transparent_bounce >= kernel_data.integrator.transparent_max_bounce)
129                         return 0.0f;
130                 else if(state->transparent_bounce <= kernel_data.integrator.transparent_min_bounce)
131                         return 1.0f;
132         }
133         else {
134                 /* other rays */
135                 if((state->bounce >= kernel_data.integrator.max_bounce) ||
136                    (state->diffuse_bounce >= kernel_data.integrator.max_diffuse_bounce) ||
137                    (state->glossy_bounce >= kernel_data.integrator.max_glossy_bounce) ||
138                    (state->transmission_bounce >= kernel_data.integrator.max_transmission_bounce))
139                         return 0.0f;
140                 else if(state->bounce <= kernel_data.integrator.min_bounce)
141                         return 1.0f;
142         }
143
144         /* probalistic termination */
145         return average(throughput);
146 }
147
148 __device_inline bool shadow_blocked(KernelGlobals *kg, PathState *state, Ray *ray, float3 *shadow)
149 {
150         *shadow = make_float3(1.0f, 1.0f, 1.0f);
151
152         if(ray->t == 0.0f)
153                 return false;
154         
155         Intersection isect;
156         bool result = scene_intersect(kg, ray, PATH_RAY_SHADOW_OPAQUE, &isect);
157
158 #ifdef __TRANSPARENT_SHADOWS__
159         if(result && kernel_data.integrator.transparent_shadows) {
160                 /* transparent shadows work in such a way to try to minimize overhead
161                    in cases where we don't need them. after a regular shadow ray is
162                    cast we check if the hit primitive was potentially transparent, and
163                    only in that case start marching. this gives on extra ray cast for
164                    the cases were we do want transparency.
165                    
166                    also note that for this to work correct, multi close sampling must
167                    be used, since we don't pass a random number to shader_eval_surface */
168                 if(shader_transparent_shadow(kg, &isect)) {
169                         float3 throughput = make_float3(1.0f, 1.0f, 1.0f);
170                         float3 Pend = ray->P + ray->D*ray->t;
171                         int bounce = state->transparent_bounce;
172
173                         for(;;) {
174                                 if(bounce >= kernel_data.integrator.transparent_max_bounce) {
175                                         return true;
176                                 }
177                                 else if(bounce >= kernel_data.integrator.transparent_min_bounce) {
178                                         /* todo: get random number somewhere for probabilistic terminate */
179 #if 0
180                                         float probability = average(throughput);
181                                         float terminate = 0.0f;
182
183                                         if(terminate >= probability)
184                                                 return true;
185
186                                         throughput /= probability;
187 #endif
188                                 }
189
190                                 if(!scene_intersect(kg, ray, PATH_RAY_SHADOW_TRANSPARENT, &isect)) {
191                                         *shadow *= throughput;
192                                         return false;
193                                 }
194
195                                 if(!shader_transparent_shadow(kg, &isect))
196                                         return true;
197
198                                 ShaderData sd;
199                                 shader_setup_from_ray(kg, &sd, &isect, ray);
200                                 shader_eval_surface(kg, &sd, 0.0f, PATH_RAY_SHADOW);
201
202                                 throughput *= shader_bsdf_transparency(kg, &sd);
203
204                                 ray->P = ray_offset(sd.P, -sd.Ng);
205                                 if(ray->t != FLT_MAX)
206                                         ray->D = normalize_len(Pend - ray->P, &ray->t);
207
208                                 bounce++;
209                         }
210                 }
211         }
212 #endif
213
214         return result;
215 }
216
217 __device float4 kernel_path_integrate(KernelGlobals *kg, RNG *rng, int sample, Ray ray, __global float *buffer)
218 {
219         /* initialize */
220         PathRadiance L;
221         float3 throughput = make_float3(1.0f, 1.0f, 1.0f);
222         float L_transparent = 0.0f;
223
224         path_radiance_init(&L, kernel_data.film.use_light_pass);
225
226         float min_ray_pdf = FLT_MAX;
227         float ray_pdf = 0.0f;
228         PathState state;
229         int rng_offset = PRNG_BASE_NUM;
230
231         path_state_init(&state);
232
233         /* path iteration */
234         for(;; rng_offset += PRNG_BOUNCE_NUM) {
235                 /* intersect scene */
236                 Intersection isect;
237                 uint visibility = path_state_ray_visibility(kg, &state);
238
239                 if(!scene_intersect(kg, &ray, visibility, &isect)) {
240                         /* eval background shader if nothing hit */
241                         if(kernel_data.background.transparent && (state.flag & PATH_RAY_CAMERA)) {
242                                 L_transparent += average(throughput);
243
244 #ifdef __PASSES__
245                                 if(!(kernel_data.film.pass_flag & PASS_BACKGROUND))
246 #endif
247                                         break;
248                         }
249
250 #ifdef __BACKGROUND__
251                         /* sample background shader */
252                         float3 L_background = indirect_background(kg, &ray, state.flag, ray_pdf);
253                         path_radiance_accum_background(&L, throughput, L_background, state.bounce);
254 #endif
255
256                         break;
257                 }
258
259                 /* setup shading */
260                 ShaderData sd;
261                 shader_setup_from_ray(kg, &sd, &isect, &ray);
262                 float rbsdf = path_rng(kg, rng, sample, rng_offset + PRNG_BSDF);
263                 shader_eval_surface(kg, &sd, rbsdf, state.flag);
264
265                 kernel_write_data_passes(kg, buffer, &L, &sd, sample, state.flag, throughput);
266
267                 /* blurring of bsdf after bounces, for rays that have a small likelihood
268                    of following this particular path (diffuse, rough glossy) */
269                 if(kernel_data.integrator.filter_glossy != FLT_MAX) {
270                         float blur_pdf = kernel_data.integrator.filter_glossy*min_ray_pdf;
271
272                         if(blur_pdf < 1.0f) {
273                                 float blur_roughness = sqrtf(1.0f - blur_pdf)*0.5f;
274                                 shader_bsdf_blur(kg, &sd, blur_roughness);
275                         }
276                 }
277
278                 /* holdout */
279 #ifdef __HOLDOUT__
280                 if((sd.flag & SD_HOLDOUT) && (state.flag & PATH_RAY_CAMERA)) {
281                         float3 holdout_weight = shader_holdout_eval(kg, &sd);
282
283                         if(kernel_data.background.transparent)
284                                 /* any throughput is ok, should all be identical here */
285                                 L_transparent += average(holdout_weight*throughput);
286                 }
287 #endif
288
289 #ifdef __EMISSION__
290                 /* emission */
291                 if(sd.flag & SD_EMISSION) {
292                         float3 emission = indirect_emission(kg, &sd, isect.t, state.flag, ray_pdf);
293                         path_radiance_accum_emission(&L, throughput, emission, state.bounce);
294                 }
295 #endif
296
297                 /* path termination. this is a strange place to put the termination, it's
298                    mainly due to the mixed in MIS that we use. gives too many unneeded
299                    shader evaluations, only need emission if we are going to terminate */
300                 float probability = path_state_terminate_probability(kg, &state, throughput);
301                 float terminate = path_rng(kg, rng, sample, rng_offset + PRNG_TERMINATE);
302
303                 if(terminate >= probability)
304                         break;
305
306                 throughput /= probability;
307
308 #ifdef __AO__
309                 /* ambient occlusion */
310                 if(kernel_data.integrator.use_ambient_occlusion) {
311                         /* todo: solve correlation */
312                         float bsdf_u = path_rng(kg, rng, sample, rng_offset + PRNG_BSDF_U);
313                         float bsdf_v = path_rng(kg, rng, sample, rng_offset + PRNG_BSDF_V);
314
315                         float3 ao_D;
316                         float ao_pdf;
317
318                         sample_cos_hemisphere(sd.N, bsdf_u, bsdf_v, &ao_D, &ao_pdf);
319
320                         if(dot(sd.Ng, ao_D) > 0.0f && ao_pdf != 0.0f) {
321                                 Ray light_ray;
322                                 float3 ao_shadow;
323
324                                 light_ray.P = ray_offset(sd.P, sd.Ng);
325                                 light_ray.D = ao_D;
326                                 light_ray.t = kernel_data.background.ao_distance;
327
328                                 if(!shadow_blocked(kg, &state, &light_ray, &ao_shadow)) {
329                                         float3 ao_bsdf = shader_bsdf_diffuse(kg, &sd)*kernel_data.background.ao_factor;
330                                         path_radiance_accum_ao(&L, throughput, ao_bsdf, ao_shadow, state.bounce);
331                                 }
332                         }
333                 }
334 #endif
335
336 #ifdef __EMISSION__
337                 if(kernel_data.integrator.use_direct_light) {
338                         /* sample illumination from lights to find path contribution */
339                         if(sd.flag & SD_BSDF_HAS_EVAL) {
340                                 float light_t = path_rng(kg, rng, sample, rng_offset + PRNG_LIGHT);
341                                 float light_o = path_rng(kg, rng, sample, rng_offset + PRNG_LIGHT_F);
342                                 float light_u = path_rng(kg, rng, sample, rng_offset + PRNG_LIGHT_U);
343                                 float light_v = path_rng(kg, rng, sample, rng_offset + PRNG_LIGHT_V);
344
345                                 Ray light_ray;
346                                 BsdfEval L_light;
347                                 bool is_lamp;
348
349 #ifdef __MULTI_LIGHT__
350                                 /* index -1 means randomly sample from distribution */
351                                 int i = (kernel_data.integrator.num_distribution)? -1: 0;
352
353                                 for(; i < kernel_data.integrator.num_all_lights; i++) {
354 #else
355                                 const int i = -1;
356 #endif
357                                         if(direct_emission(kg, &sd, i, light_t, light_o, light_u, light_v, &light_ray, &L_light, &is_lamp)) {
358                                                 /* trace shadow ray */
359                                                 float3 shadow;
360
361                                                 if(!shadow_blocked(kg, &state, &light_ray, &shadow)) {
362                                                         /* accumulate */
363                                                         path_radiance_accum_light(&L, throughput, &L_light, shadow, state.bounce, is_lamp);
364                                                 }
365                                         }
366 #ifdef __MULTI_LIGHT__
367                                 }
368 #endif
369                         }
370                 }
371 #endif
372
373                 /* no BSDF? we can stop here */
374                 if(!(sd.flag & SD_BSDF))
375                         break;
376
377                 /* sample BSDF */
378                 float bsdf_pdf;
379                 BsdfEval bsdf_eval;
380                 float3 bsdf_omega_in;
381                 differential3 bsdf_domega_in;
382                 float bsdf_u = path_rng(kg, rng, sample, rng_offset + PRNG_BSDF_U);
383                 float bsdf_v = path_rng(kg, rng, sample, rng_offset + PRNG_BSDF_V);
384                 int label;
385
386                 label = shader_bsdf_sample(kg, &sd, bsdf_u, bsdf_v, &bsdf_eval,
387                         &bsdf_omega_in, &bsdf_domega_in, &bsdf_pdf);
388
389                 shader_release(kg, &sd);
390
391                 if(bsdf_pdf == 0.0f || bsdf_eval_is_zero(&bsdf_eval))
392                         break;
393
394                 /* modify throughput */
395                 path_radiance_bsdf_bounce(&L, &throughput, &bsdf_eval, bsdf_pdf, state.bounce, label);
396
397                 /* set labels */
398                 if(!(label & LABEL_TRANSPARENT)) {
399                         ray_pdf = bsdf_pdf;
400                         min_ray_pdf = fminf(bsdf_pdf, min_ray_pdf);
401                 }
402
403                 /* update path state */
404                 path_state_next(kg, &state, label);
405
406                 /* setup ray */
407                 ray.P = ray_offset(sd.P, (label & LABEL_TRANSMIT)? -sd.Ng: sd.Ng);
408                 ray.D = bsdf_omega_in;
409                 ray.t = FLT_MAX;
410 #ifdef __RAY_DIFFERENTIALS__
411                 ray.dP = sd.dP;
412                 ray.dD = bsdf_domega_in;
413 #endif
414         }
415
416         float3 L_sum = path_radiance_sum(kg, &L);
417
418 #ifdef __CLAMP_SAMPLE__
419         path_radiance_clamp(&L, &L_sum, kernel_data.integrator.sample_clamp);
420 #endif
421
422         kernel_write_light_passes(kg, buffer, &L, sample);
423
424         return make_float4(L_sum.x, L_sum.y, L_sum.z, 1.0f - L_transparent);
425 }
426
427 __device void kernel_path_trace(KernelGlobals *kg,
428         __global float *buffer, __global uint *rng_state,
429         int sample, int x, int y, int offset, int stride)
430 {
431         /* buffer offset */
432         int index = offset + x + y*stride;
433         int pass_stride = kernel_data.film.pass_stride;
434
435         rng_state += index;
436         buffer += index*pass_stride;
437
438         /* initialize random numbers */
439         RNG rng;
440
441         float filter_u;
442         float filter_v;
443
444         path_rng_init(kg, rng_state, sample, &rng, x, y, &filter_u, &filter_v);
445
446         /* sample camera ray */
447         Ray ray;
448
449         float lens_u = path_rng(kg, &rng, sample, PRNG_LENS_U);
450         float lens_v = path_rng(kg, &rng, sample, PRNG_LENS_V);
451
452         camera_sample(kg, x, y, filter_u, filter_v, lens_u, lens_v, &ray);
453
454         /* integrate */
455         float4 L = kernel_path_integrate(kg, &rng, sample, ray, buffer);
456
457         /* accumulate result in output buffer */
458         kernel_write_pass_float4(buffer, sample, L);
459
460         path_rng_end(kg, rng_state, rng);
461 }
462
463 CCL_NAMESPACE_END
464