Cycles: better path termination for transparency.
[blender.git] / intern / cycles / kernel / closure / bsdf_transparent.h
index 22ca7f3847e0b8f6ab6eb2a5fd3fc4d2a4edab05..79ee9dc4537c2ea996ad77dcf0b8df26b57aff3b 100644 (file)
 
 CCL_NAMESPACE_BEGIN
 
-ccl_device void bsdf_transparent_setup(ShaderData *sd, const float3 weight)
+ccl_device void bsdf_transparent_setup(ShaderData *sd, const float3 weight, int path_flag)
 {
        if(sd->flag & SD_TRANSPARENT) {
                sd->closure_transparent_extinction += weight;
+
+               for(int i = 0; i < sd->num_closure; i++) {
+                       ShaderClosure *sc = &sd->closure[i];
+
+                       if(sc->type == CLOSURE_BSDF_TRANSPARENT_ID) {
+                               sc->weight += weight;
+                               sc->sample_weight += fabsf(average(weight));
+                               break;
+                       }
+               }
        }
        else {
                sd->flag |= SD_BSDF|SD_TRANSPARENT;
                sd->closure_transparent_extinction = weight;
-       }
 
-       ShaderClosure *bsdf = bsdf_alloc(sd, sizeof(ShaderClosure), weight);
+               if(path_flag & PATH_RAY_TERMINATE) {
+                       /* In this case the number of closures is set to zero to disable
+                        * all others, but we still want to get transparency so increase
+                        * the number just for this. */
+                       sd->num_closure_left = 1;
+               }
+
+               ShaderClosure *bsdf = bsdf_alloc(sd, sizeof(ShaderClosure), weight);
 
-       if(bsdf) {
-               bsdf->N = sd->N;
-               bsdf->type = CLOSURE_BSDF_TRANSPARENT_ID;
+               if(bsdf) {
+                       bsdf->N = sd->N;
+                       bsdf->type = CLOSURE_BSDF_TRANSPARENT_ID;
+               }
        }
 }