Modulo
From Odwiki
The main difference between this and the VEX '%' operator (or the C fmod() function) is that it doesn't "change polarity" at the zero-crossing -- it takes into account the sign of the remainder, and returns the actual modulo. For those familiar with RSL, this duplicates the behaviour of the mod() function.
Use this function (instead of the '%' operator) whenever you have a repeating pattern, but are unsure whether the target range will straddle the 0-line, or, know are certain that it will, and want to avoid having the pattern "flip" as it crosses 0.
To visualize the difference between the two (function vs. operator), try the following simple shader on a default parametric grid (e.g: mesh):
#pragma choice test "op" "Operator %"
#pragma choice test "mod" "modulo()"
surface testModulo(string test = "op") {
Cf = test=="op" ? 4.*abs((s-.5)%.25) : 4.*modulo(s-.5,.25);
}
!!ACHTUNG!!
As implemented below, these functions all assume that the parameter 'b' is always positive!
If you want a more robust version, then use the operation indicated as "Alternatively:..." in the version for floats below. It calls floor() so it's slower. I personally prefer to just remember that b should be positive.
Here are the function definitions:
// Modulo //-------------------------------------------------------------- // Float float modulo(float a,{ // Alternatively: return a-(b*floor(a/b)); float rem=a%b; return rem<0 ? rem+b : rem; } // Vector vector moduloV(vector a; float
{ vector rem=a%b; return set ( rem.x<0 ? rem.x+b : rem.x, rem.y<0 ? rem.y+b : rem.y, rem.z<0 ? rem.z+b : rem.z ); } // Vector4 vector4 moduloV4(vector4 a; float
{ vector4 rem=a%b; return set ( rem.x<0 ? rem.x+b : rem.x, rem.y<0 ? rem.y+b : rem.y, rem.z<0 ? rem.z+b : rem.z, rem.w<0 ? rem.w+b : rem.w ); }



