diff options
author | Brecht Van Lommel <brechtvanlommel@pandora.be> | 2012-12-20 01:17:16 +0400 |
---|---|---|
committer | Brecht Van Lommel <brechtvanlommel@pandora.be> | 2012-12-20 01:17:16 +0400 |
commit | 54729df02096da1f3404d4d4891f30752bf90778 (patch) | |
tree | 5fd2ef2365e5e8b1f55b7857dae899f22da5a394 /intern/cycles/util | |
parent | 8d4c61a2ab386f212bab2865aab76501fe29b48f (diff) |
Cycles OSL: diffuse_toon and specular_toon closures. These are toon shaders with
a size parameter between 0.0 and 1.0 that gives a angle of reflection between
0° and 90°, and a smooth parameter that gives and angle over which a smooth
transition from full to no reflection happens.
These work with global illumination and do importance sampling of the area within
the angle. Note that unlike most other BSDF's these are not energy conserving in
general, in particular if their weight is 1.0 and size > 2/3 (or 60°) they will
add more energy in each bounce.
Diffuse: http://www.pasteall.org/pic/show.php?id=42119
Specular: http://www.pasteall.org/pic/show.php?id=42120
Diffstat (limited to 'intern/cycles/util')
-rw-r--r-- | intern/cycles/util/util_math.h | 69 |
1 files changed, 69 insertions, 0 deletions
diff --git a/intern/cycles/util/util_math.h b/intern/cycles/util/util_math.h index 70adee4385b..8932c85db07 100644 --- a/intern/cycles/util/util_math.h +++ b/intern/cycles/util/util_math.h @@ -1092,6 +1092,75 @@ __device_inline float3 rotate_around_axis(float3 p, float3 axis, float angle) return r; } +/* NaN-safe math ops */ + +__device float safe_asinf(float a) +{ + if(a <= -1.0f) + return -M_PI_2_F; + else if(a >= 1.0f) + return M_PI_2_F; + + return asinf(a); +} + +__device float safe_acosf(float a) +{ + if(a <= -1.0f) + return M_PI_F; + else if(a >= 1.0f) + return 0.0f; + + return acosf(a); +} + +__device float compatible_powf(float x, float y) +{ + /* GPU pow doesn't accept negative x, do manual checks here */ + if(x < 0.0f) { + if(fmod(-y, 2.0f) == 0.0f) + return powf(-x, y); + else + return -powf(-x, y); + } + else if(x == 0.0f) + return 0.0f; + + return powf(x, y); +} + +__device float safe_powf(float a, float b) +{ + if(b == 0.0f) + return 1.0f; + if(a == 0.0f) + return 0.0f; + if(a < 0.0f && b != (int)b) + return 0.0f; + + return compatible_powf(a, b); +} + +__device float safe_logf(float a, float b) +{ + if(a < 0.0f || b < 0.0f) + return 0.0f; + + return logf(a)/logf(b); +} + +__device float safe_divide(float a, float b) +{ + float result; + + if(b == 0.0f) + result = 0.0f; + else + result = a/b; + + return result; +} + CCL_NAMESPACE_END #endif /* __UTIL_MATH_H__ */ |