// stdlib.aws // //-------------------------------------------- // Built-in operators. // // operator+ for same types float operator+ (float f1, float f2); float2 operator+ (float2 v1, float2 v2); float3 operator+ (float3 v1, float3 v2); float4 operator+ (float4 v1, float4 v2); matrix2 operator+ (matrix2 m1, matrix2 m2); matrix3 operator+ (matrix3 m1, matrix3 m2); matrix4 operator+ (matrix4 m1, matrix4 m2); // operator- for same types float operator- (float f1, float f2); float2 operator- (float2 v1, float2 v2); float3 operator- (float3 v1, float3 v2); float4 operator- (float4 v1, float4 v2); matrix2 operator- (matrix2 m1, matrix2 m2); matrix3 operator- (matrix3 m1, matrix3 m2); matrix4 operator- (matrix4 m1, matrix4 m2); // operator* for same types float operator* (float f1, float f2); float2 operator* (float2 v1, float2 v2); float3 operator* (float3 v1, float3 v2); float4 operator* (float4 v1, float4 v2); matrix2 operator* (matrix2 m1, matrix2 m2); matrix3 operator* (matrix3 m1, matrix3 m2); matrix4 operator* (matrix4 m1, matrix4 m2); // operator* by float (commutative) float2 operator* (float2 v, float f); float2 operator* (float f, float2 v); float3 operator* (float3 v, float f); float3 operator* (float f, float3 v); float4 operator* (float4 v, float f); float4 operator* (float f, float4 v); matrix2 operator* (matrix2 m1, float f); matrix2 operator* (float f, matrix2 m1); matrix3 operator* (matrix3 m1, float f); matrix3 operator* (float f, matrix3 m1); matrix4 operator* (matrix4 m1, float f); matrix4 operator* (float f, matrix4 m1); // Matrix by vector multiplies. float4 operator* (matrix4 m, float4 v); float3 operator* (matrix3 m, float3 v); float2 operator* (matrix2 m, float2 v); // Equivalent syntax. float2 mul(float2 v, matrix2 m); float3 mul(float3 v, matrix3 m); float4 mul(float4 v, matrix4 m); // operator/ for same types float operator/ (float f1, float f2); float2 operator/ (float2 v1, float2 v2); float3 operator/ (float3 v1, float3 v2); float4 operator/ (float4 v1, float4 v2); matrix2 operator/ (matrix2 m1, matrix2 m2); matrix3 operator/ (matrix3 m1, matrix3 m2); matrix4 operator/ (matrix4 m1, matrix4 m2); // operator/ by float (right-side only) float2 operator/ (float2 v, float f); float3 operator/ (float3 v, float f); float4 operator/ (float4 v, float f); matrix2 operator/ (matrix2 m1, float f); matrix3 operator/ (matrix3 m1, float f); matrix4 operator/ (matrix4 m1, float f); // operator% for same types float operator% (float f1, float f2); float2 operator% (float2 v1, float2 v2); float3 operator% (float3 v1, float3 v2); float4 operator% (float4 v1, float4 v2); matrix2 operator% (matrix2 m1, matrix2 m2); matrix3 operator% (matrix3 m1, matrix3 m2); matrix4 operator% (matrix4 m1, matrix4 m2); // operator% by float (right-side only) float2 operator% (float2 v, float f); float3 operator% (float3 v, float f); float4 operator% (float4 v, float f); matrix2 operator% (matrix2 m1, float f); matrix3 operator% (matrix3 m1, float f); matrix4 operator% (matrix4 m1, float f); // Swizzle operator float swizzle (float i, constant int s); float swizzle (float2 i, constant int s); float swizzle (float3 i, constant int s); float swizzle (float4 i, constant int s); float2 swizzle (float i, constant int2 s); float2 swizzle (float2 i, constant int2 s); float2 swizzle (float3 i, constant int2 s); float2 swizzle (float4 i, constant int2 s); float3 swizzle (float i, constant int3 s); float3 swizzle (float2 i, constant int3 s); float3 swizzle (float3 i, constant int3 s); float3 swizzle (float4 i, constant int3 s); float4 swizzle (float i, constant int4 s); float4 swizzle (float2 i, constant int4 s); float4 swizzle (float3 i, constant int4 s); float4 swizzle (float4 i, constant int4 s); // Array indexing operator float operator[] (float f, constant int index); float operator[] (float2 vec, constant int index); float operator[] (float3 vec, constant int index); float operator[] (float4 vec, constant int index); float2 operator[] (matrix2 mat, constant int index); float3 operator[] (matrix3 mat, constant int index); float4 operator[] (matrix4 mat, constant int index); // Conditional operators bool operator== (float a, float b); bool operator!= (float a, float b); bool operator> (float a, float b); bool operator< (float a, float b); bool operator>= (float a, float b); bool operator<= (float a, float b); // Other equality test operators bool operator== (float2 a, float2 b); bool operator== (float3 a, float3 b); bool operator== (float4 a, float4 b); bool operator&& (bool a, bool b); bool operator|| (bool a, bool b); // Computation-frequency promotion typecast operators. fragment bool operator fragment(bool i); fragment float operator fragment(float i); fragment float2 operator fragment(float2 i); fragment float3 operator fragment(float3 i); fragment float4 operator fragment(float4 i); fragment matrix2 operator fragment(matrix2 i); fragment matrix3 operator fragment(matrix3 i); fragment matrix4 operator fragment(matrix4 i); vertex bool operator vertex(constant:vertex bool i); vertex float operator vertex(constant:vertex float i); vertex float2 operator vertex(constant:vertex float2 i); vertex float3 operator vertex(constant:vertex float3 i); vertex float4 operator vertex(constant:vertex float4 i); vertex matrix2 operator vertex(constant:vertex matrix2 i); vertex matrix3 operator vertex(constant:vertex matrix3 i); vertex matrix4 operator vertex(constant:vertex matrix4 i); // Float vector constructors float operator float(float a); float2 operator float2(float a, float b); float3 operator float3(float a, float b, float c); float4 operator float4(float a, float b, float c, float d); float4 operator float4(float3 abc, float d); float4 operator float4(float2 ab, float c, float d); // Matrix column constructors. matrix2 operator matrix2(float2 c0, float2 c1); matrix3 operator matrix3(float3 c0, float3 c1, float3 c2); matrix4 operator matrix4(float4 c0, float4 c1, float4 c2, float4 c3); // Matrix element constructors. matrix2 operator matrix2(float e0, float e1, float e2, float e3); matrix3 operator matrix3(float e0, float e1, float e2, float e3, float e4, float e5, float e6, float e7, float e8); matrix4 operator matrix4(float e0, float e1, float e2, float e3, float e4, float e5, float e6, float e7, float e8, float e9, float e10, float e11, float e12, float e13, float e14, float e15); // Selection operator. Equivalent to "predicate ? a : b". bool select(bool p, bool a, bool b); float select(bool p, float a, float b); float2 select(bool p, float2 a, float2 b); float3 select(bool p, float3 a, float3 b); float4 select(bool p, float4 a, float4 b); matrix2 select(bool p, matrix2 a, matrix2 b); matrix3 select(bool p, matrix3 a, matrix3 b); matrix4 select(bool p, matrix4 a, matrix4 b); uniform sampler1D select(bool p, uniform sampler1D a, uniform sampler1D b); uniform sampler2D select(bool p, uniform sampler2D a, uniform sampler2D b); uniform sampler3D select(bool p, uniform sampler3D a, uniform sampler3D b); uniform samplerCube select(bool p, uniform samplerCube a, uniform samplerCube b); uniform sampler1DShadow select(bool p, uniform sampler1DShadow a, uniform sampler1DShadow b); uniform sampler2DShadow select(bool p, uniform sampler2DShadow a, uniform sampler2DShadow b); float abs(float a); float2 abs(float2 a); float3 abs(float3 a); float4 abs(float4 a); // START BIG SECTION float acos( float a ); float2 acos( float2 a ); float3 acos( float3 a ); float4 acos( float4 a ); float asin( float a ); float2 asin( float2 a ); float3 asin( float3 a ); float4 asin( float4 a ); float atan( float x ); float2 atan( float2 x ); float3 atan( float3 x ); float4 atan( float4 x ); float atan2( float y, float x ); float2 atan2( float2 y, float2 x ); float3 atan2( float3 y, float3 x ); float4 atan2( float4 y, float4 x ); float ceil( float a ); float2 ceil( float2 a ); float3 ceil( float3 a ); float4 ceil( float4 a ); float clamp( float x, float a, float b ); float2 clamp( float2 x, float2 a, float2 b ); float3 clamp( float3 x, float3 a, float3 b ); float4 clamp( float4 x, float4 a, float4 b ); float cos( float a ); float2 cos( float2 a ); float3 cos( float3 a ); float4 cos( float4 a ); float cosh( float a ); float2 cosh( float2 a ); float3 cosh( float3 a ); float4 cosh( float4 a ); float3 cross( float3 a, float3 b ); float ddx( float a ); float2 ddx( float2 a ); float3 ddx( float3 a ); float4 ddx( float4 a ); float ddy( float a ); float2 ddy( float2 a ); float3 ddy( float3 a ); float4 ddy( float4 a ); float degrees( float a ); float2 degrees( float2 a ); float3 degrees( float3 a ); float4 degrees( float4 a ); float dot( float2 a, float2 b ); float dot( float3 a, float3 b ); float dot( float4 a, float4 b ); float exp( float x ); float2 exp( float2 x ); float3 exp( float3 x ); float4 exp( float4 x ); float exp2( float x ); float2 exp2( float2 x ); float3 exp2( float3 x ); float4 exp2( float4 x ); float floor( float x ); float2 floor( float2 x ); float3 floor( float3 x ); float4 floor( float4 x ); float fmod( float a, float b ); float2 fmod( float2 a, float2 b ); float3 fmod( float3 a, float3 b ); float4 fmod( float4 a, float4 b ); float frexp( float x, out float expon ); float2 frexp( float2 x, out float2 expon ); float3 frexp( float3 x, out float3 expon ); float4 frexp( float4 x, out float4 expon ); float frac( float x ); float2 frac( float2 x ); float3 frac( float3 x ); float4 frac( float4 x ); float ldexp( float x, float n ); float2 ldexp( float2 x, float2 n ); float3 ldexp( float3 x, float3 n ); float4 ldexp( float4 x, float4 n ); float log( float x ); float2 log( float2 x ); float3 log( float3 x ); float4 log( float4 x ); float log( float b, float x ); float2 log( float2 b, float2 x ); float3 log( float3 b, float3 x ); float4 log( float4 b, float4 x ); float log2( float x ); float2 log2( float2 x ); float3 log2( float3 x ); float4 log2( float4 x ); float log10( float x ); float2 log10( float2 x ); float3 log10( float3 x ); float4 log10( float4 x ); float max( float a, float b ); float2 max( float2 a, float2 b ); float3 max( float3 a, float3 b ); float4 max( float4 a, float4 b ); float min( float a, float b ); float2 min( float2 a, float2 b ); float3 min( float3 a, float3 b ); float4 min( float4 a, float4 b ); // [claforte] Some of these should probably be complex. float mix( float a, float b, float frac ); float2 mix( float2 a, float2 b, float frac ); float3 mix( float3 a, float3 b, float frac ); float4 mix( float4 a, float4 b, float frac ); float2 mix( float2 a, float2 b, float2 frac ); float3 mix( float3 a, float3 b, float3 frac ); float4 mix( float4 a, float4 b, float4 frac ); // [claforte] Should we support those? // float modf( float x, out float ip ); // float2 modf( float2 x, out float2 ip ); // float3 modf( float3 x, out float3 ip ); // float4 modf( float4 x, out float4 ip ); // [claforte] Should probably be complex. float noise( float x ); float noise( float x, float y ); float noise( float x, float y, float z ); float noise( float2 x ); float noise( float3 x ); float pow( float x, float y ); float2 pow( float2 x, float2 y ); float3 pow( float3 x, float3 y ); float4 pow( float4 x, float4 y ); float radians( float a ); float2 radians( float2 a ); float3 radians( float3 a ); float4 radians( float4 a ); float round( float a ); float2 round( float2 a ); float3 round( float3 a ); float4 round( float4 a ); float rsqrt( float x ); float2 rsqrt( float2 x ); float3 rsqrt( float3 x ); float4 rsqrt( float4 x ); float sign( float a ); float2 sign( float2 a ); float3 sign( float3 a ); float4 sign( float4 a ); float sin( float a ); float2 sin( float2 a ); float3 sin( float3 a ); float4 sin( float4 a ); float sinh( float a ); float2 sinh( float2 a ); float3 sinh( float3 a ); float4 sinh( float4 a ); float smoothstep( float a, float b, float x ); float2 smoothstep( float2 a, float2 b, float2 x ); float3 smoothstep( float3 a, float3 b, float3 x ); float4 smoothstep( float4 a, float4 b, float4 x ); float step( float a, float x ); float2 step( float2 a, float2 x ); float3 step( float3 a, float3 x ); float4 step( float4 a, float4 x ); float sqrt( float a ); float2 sqrt( float2 a ); float3 sqrt( float3 a ); float4 sqrt( float4 a ); float tan( float a ); float2 tan( float2 a ); float3 tan( float3 a ); float4 tan( float4 a ); float tanh( float a ); float2 tanh( float2 a ); float3 tanh( float3 a ); float4 tanh( float4 a ); // Geometrical Prototypes float distance( float2 pt1, float2 pt2 ); float distance( float3 pt1, float3 pt2 ); float distance( float4 pt1, float4 pt2 ); // [claforte] Should be complex. float fresnel( float3 i, float3 n, float eta ); float fresnel( float3 i, float3 n, float eta, out float kt ); float fresnel( float3 i, float3 n, float eta, out float kt, out float3 r, out float3 t ); float fresnel( float3 i, float3 n, float eta, out float3 r, out float3 t ); // [claforte] Should be complex. float length( float2 v ); float length( float3 v ); float length( float4 v ); float2 normalize( float2 v ); float3 normalize( float3 v ); float4 normalize( float4 v ); // Normalize and return the length at the same time. float2 normalize( float2 v, out float length ); float3 normalize( float3 v, out float length ); float4 normalize( float4 v, out float length ); float3 reflect( float3 i, float3 n ); float3 reflectn( float3 i, float3 n ); float3 refract( float3 i, float3 n ); float3 refractn( float3 i, float3 n ); // Texture functions // [claforte] TODO: add LOD versions // fragment float4 texture1D (uniform sampler1D tex, float s); fragment float4 texture1DProj (uniform sampler1D tex, float2 sq); fragment float4 texture2D (uniform sampler2D tex, float2 s); fragment float4 texture2DProj (uniform sampler2D tex, float3 sq); fragment float4 texture3D (uniform sampler3D tex, float3 s); fragment float4 texture3DProj (uniform sampler3D tex, float4 sq); fragment float4 textureCube (uniform samplerCube tex, float3 s); fragment float shadow1D (uniform sampler1DShadow tex, float3 s); fragment float shadow1DProj (uniform sampler1DShadow tex, float4 s); fragment float shadow2D (uniform sampler2DShadow tex, float3 s); fragment float shadow2DProj (uniform sampler2DShadow tex, float4 s); // Unary operators // [claforte] ++ and -- won't work until inputs are treated as variables. //float operator++(float input); //float operator--(float input); //useless operator: float operator+(float input); float operator-(float input); bool operator!(bool input); // Linear interpolator float4 lerp (float4 a, float4 b, float afrac) { return afrac * a + (1 - afrac) * b; } // Bilinear interpolator. float4 bilerp (float4 v00, float4 v01, float4 v10, float4 v11, float frac0, float frac1) { float4 v0 = lerp(v00, v01, frac0); float4 v1 = lerp(v10, v11, frac0); return lerp(v0, v1, frac1); } // TESTS // float testArray(float3 a, matrix3 b) { //doesn't work: // float3 c = b[0]; // return a[0] + c[1]; // doesn't work: return b[2][0]; return a[2]; } float3 testConstructor(float s, float t, float r, float w) { return float3(s, t, r); } matrix4 testConstructor2(float4 c0, float4 c1, float4 c2, float a, float b, float c, float d) { return matrix4(c0, c1, c2, float4(a, b, c, d)); } bool test1(float a, float b, float c, float d) { bool b1, b2; b1 = b2 = a > b; b2 = b1 && (c > d || b2); return b1 || b2; } bool test2(float a, float b, float c, float d) { bool b1 = a*b > -(b+a) || b > a; bool b2 = c <= d && !b1; return !b2; } void test3(float a, float b, out float o_a) { o_a = a * b; } void test4(float a, float b, out float o_a, out float o_b) { o_a = a*b; o_b = 3.1415926; } float test5(float a, float b, float c) { a += b; a /= c + b; a -= c + b; a %= c + b; a *= c + b; b = c = a; return c; } float4 test6(float4 in) { return in * { 0.0, 0, 1, -1.39 } / { 299292.2, -299292.2, 777, -888} / in; } void test7(float in1, float in2, out float out1, out float out2) { out1 = in1; out2 = in2; } void anotherTest(float3 in1, float in2, out float3 out1, out float out2) { out1 = float3(0.0,0.0,0.0); out2 = in2; } float test8(float a, float b) { float temp1; float temp2; test7(a, b, temp1, temp2); return temp1 * temp2; } float2 test9(float4 in1) { return in1.xy; } float3 test10(float3 in1) { return in1 * 3.1415926.xxx; } float4 test11() { return {0,1,2,3}.abgr; } float4 test12(uniform matrix4 modelview, uniform matrix4 projection, vertex float4 obj_pos) { return projection * (modelview * obj_pos); } // // Lights // light point_light_vertex( out float3 outLightWorldDir, out float3 outLightAmbientColor, out float3 outLightDiffuseColor, out float3 outLightSpecularColor, uniform float3 light_pos, uniform float hasSize, uniform float light_shape, uniform float3 light_corner1, uniform float3 light_corner2, uniform float3 light_corner3, uniform float3 light_corner4, uniform matrix4 transform, uniform float3 light_color, uniform float light_intensity, uniform float4 light_decay, uniform float depthBias, uniform float nearCP, uniform float farCP, uniform float depthMapSize, uniform float useDepthMapShadows, uniform float3 shadowColor) { // Compute light vector, pointing toward the object to be lit. // [claforte] Should use the transform's position instead // of "light_pos". outLightWorldDir = normalize(light_pos - gWorldPos); float3 finalLightColor = light_color * light_intensity; outLightDiffuseColor = finalLightColor; outLightSpecularColor = finalLightColor; outLightAmbientColor = float3(0.0,0.0,0.0); } light spot_light_vertex( out float3 outLightWorldDir, out float3 outLightAmbientColor, out float3 outLightDiffuseColor, out float3 outLightSpecularColor, uniform matrix4 transform, uniform float3 light_pos, uniform float3 light_color, uniform float light_intensity, uniform float4 light_decay, uniform float light_exponent, uniform float light_cutOff, uniform float cone_angle, uniform float penumbra_angle, uniform float drop_off, uniform float depthBias, uniform float nearCP, uniform float farCP, uniform float depthMapSize, uniform float useDepthMapShadows, uniform float proj_tex, uniform sampler2D color_tex, uniform float3 shadowColor) { // Compute light vector, pointing toward the object to be lit. // [claforte] Should use the transform's position instead // of "light_pos". outLightWorldDir = normalize(light_pos - gWorldPos); float3 finalLightColor = light_color * light_intensity; outLightDiffuseColor = finalLightColor; outLightSpecularColor = finalLightColor; outLightAmbientColor = float3(0.0,0.0,0.0); } light directional_light_vertex( out float3 outLightWorldDir, out float3 outLightAmbientColor, out float3 outLightDiffuseColor, out float3 outLightSpecularColor, uniform matrix4 transform, uniform float3 light_color, uniform float light_intensity, uniform float depthBias, uniform float nearCP, uniform float farCP, uniform float depthMapSize, uniform float useDepthMapShadows, uniform float3 shadowColor) { outLightWorldDir = transform[2].xyz; float3 finalLightColor = light_color * light_intensity; outLightDiffuseColor = finalLightColor; outLightSpecularColor = finalLightColor; outLightAmbientColor = float3(0.0,0.0,0.0); } light point_light_fragment( out float3 outLightWorldDir, out float3 outLightAmbientColor, out float3 outLightDiffuseColor, out float3 outLightSpecularColor, uniform float3 light_pos, uniform float hasSize, uniform float light_shape, uniform float3 light_corner1, uniform float3 light_corner2, uniform float3 light_corner3, uniform float3 light_corner4, uniform matrix4 transform, uniform float3 light_color, uniform float light_intensity, uniform float depthBias, uniform float nearCP, uniform float farCP, uniform float depthMapSize, uniform float useDepthMapShadows, uniform float3 shadowColor, // Intermediate values, will soon be // phased out in favour of the later // computed values. uniform float4 light_decay, // Computed values... will soon use these exclusively. uniform float lightDecayExponent) { // Compute light vector, pointing toward the object to be lit. // [claforte] Should use the transform's position instead // of "light_pos". float3 wLightDir = light_pos - gWorldPos; float wLightDistance = length(wLightDir); outLightWorldDir = wLightDir / wLightDistance; // Compute the light's distance decay float undecayedRatio = 1 / pow(wLightDistance, lightDecayExponent); float3 finalLightColor = (undecayedRatio * light_intensity) * light_color; outLightDiffuseColor = finalLightColor; outLightSpecularColor = finalLightColor; outLightAmbientColor = float3(0.0,0.0,0.0); } light directional_light_fragment( out float3 outLightWorldDir, out float3 outLightAmbientColor, out float3 outLightDiffuseColor, out float3 outLightSpecularColor, uniform matrix4 transform, uniform sampler2DShadow shadowTex, uniform matrix4 dirWorldToProjLightMatrix, uniform float light_intensity, uniform float3 light_color, uniform float depthBias, uniform float nearCP, uniform float farCP, uniform float depthMapSize, uniform float useDepthMapShadows, uniform float3 shadowColor) { outLightWorldDir = (mul(float4(0.0, 0.0, 1.0, 0.0), transform)).xyz; // Get the shadowed value. float unshadowedRatio = 1.0; float4 projTexCoords = mul(float4(gWorldPos, 1.0), dirWorldToProjLightMatrix); if (useDepthMapShadows > 0.5) { unshadowedRatio = shadow2DProj(shadowTex, projTexCoords); } float3 finalLightColor = unshadowedRatio * light_color * light_intensity; outLightDiffuseColor = finalLightColor; outLightSpecularColor = finalLightColor; outLightAmbientColor = float3(0.0,0.0,0.0); } light spot_light_fragment( out float3 outLightWorldDir, out float3 outLightAmbientColor, out float3 outLightDiffuseColor, out float3 outLightSpecularColor, uniform matrix4 transform, uniform float3 light_pos, uniform float3 light_color, uniform float light_intensity, uniform float light_exponent, uniform float light_cutOff, uniform float depthBias, uniform float depthMapSize, uniform float useDepthMapShadows, uniform float3 shadowColor, uniform float proj_tex, uniform sampler2D color_tex, uniform sampler2DShadow shadowTex, uniform float drop_off, // Intermediate values, will soon be // phased out in favour of the later // computed values. uniform float4 light_decay, uniform float cone_angle, uniform float penumbra_angle, uniform float nearCP, uniform float farCP, // Computed values... will soon use these exclusively. uniform matrix4 spotWorldToProjLightMatrix, uniform float spotCosPenumbra, uniform float spotCosUmbra, uniform float lightDecayExponent, uniform float lightScale) { // Compute light vector, pointing toward the object to be lit. // [claforte] Should use the transform's position instead // of "light_pos". float3 wLightDir = light_pos - gWorldPos; float wLightDistance = length(wLightDir); outLightWorldDir = wLightDir / wLightDistance; float3 wSpotDir = normalize((mul(float4(0.0, 0.0, 1.0, 0.0), transform)).xyz); // Compute the spot light's radial attenuation. // The spot cone of influence is divided into // two regions: the penumbra (outer region) and // umbra (inner region). // NOTE: at this point the penumbra angle is assumed // to be positive, and both the umbra and penumbra angle // are assumed to be greater than 0. // float SdotL = dot(outLightWorldDir, wSpotDir); float spotRadialIntensity; if (SdotL < spotCosPenumbra) { // The angle is larger than the total angle, // therefore it's outside of the cone. // spotRadialIntensity = 0; } else { // Make an exponential decay over the inner region. // spotRadialIntensity = pow(SdotL, drop_off); if (SdotL < spotCosUmbra) { // Linearly interpolate between // the penumbra and umbra angle. // spotRadialIntensity = spotRadialIntensity * (SdotL - spotCosPenumbra) / (spotCosUmbra - spotCosPenumbra); } } // Get the projected light color. float4 projTexCoords = mul(float4(gWorldPos, 1.0), spotWorldToProjLightMatrix); float3 projLightTexCoords = projTexCoords.xyz / projTexCoords.w; projLightTexCoords = (projLightTexCoords - 0.5) * lightScale + 0.5; float3 projLightColor = f3tex2D(color_tex, projLightTexCoords.xy); // Get the shadowed value. float unshadowedRatio = 1.0; if (useDepthMapShadows > 0.5) { unshadowedRatio = shadow2DProj(shadowTex, projTexCoords); } // Compute the light's distance decay float undecayedRatio = 1.0 / pow(wLightDistance, lightDecayExponent); float3 finalLightColor = (unshadowedRatio * undecayedRatio) * light_color * light_intensity * spotRadialIntensity * projLightColor; outLightDiffuseColor = finalLightColor; outLightSpecularColor = finalLightColor; outLightAmbientColor = float3(0.0,0.0,0.0); } light ambient_light_vertex( out float3 outLightWorldDir, out float3 outLightAmbientColor, out float3 outLightDiffuseColor, out float3 outLightSpecularColor, uniform float3 light_pos, uniform float3 light_color, uniform float light_intensity, uniform float ambient_shade) { // Compute light vector, pointing toward the object to be lit. float3 L = normalize(light_pos - gWorldPos); float LdotN = dot(L, gWorldBumpedNormal); float as = ambient_shade * (LdotN - 1.0); outLightAmbientColor = light_color * light_intensity * (1.0 + as).xxx; // This light never contributes to diffuse or specular. outLightDiffuseColor = float3(0.0,0.0,0.0); outLightSpecularColor = float3(0.0,0.0,0.0); } light ambient_light_fragment( out float3 outLightWorldDir, out float3 outLightAmbientColor, out float3 outLightDiffuseColor, out float3 outLightSpecularColor, uniform float3 light_pos, uniform float3 light_color, uniform float light_intensity, uniform float ambient_shade) { // Compute light vector, pointing toward the object to be lit. float3 L = normalize(light_pos - gWorldPos); float LdotN = dot(L, gWorldBumpedNormal); float as = ambient_shade * (LdotN - 1); outLightAmbientColor = light_color * light_intensity * (1.0 + as).xxx; // This light never contributes to diffuse or specular. outLightDiffuseColor = float3(0.0,0.0,0.0); outLightSpecularColor = float3(0.0,0.0,0.0); // The ambient light's direction is set to 0. outLightWorldDir = float3(0.0,0.0,0.0); } material Maya_phong( vertex float3 gWorldPos, vertex float3 gWorldNormal, vertex float3 gWorldTangent, uniform sampler2D bump_tex, uniform matrix4 bump_texmatrix, uniform sampler2D color_tex, uniform matrix4 color_texmatrix, uniform sampler2D diffuse_tex, uniform matrix4 diffuse_texmatrix, uniform sampler2D incan_tex, uniform matrix4 incan_texmatrix, uniform sampler2D spec_exp_tex, uniform matrix4 spec_exp_texmatrix, uniform sampler2D transp_tex, uniform matrix4 transp_texmatrix, uniform sampler2D ambient_tex, uniform matrix4 ambient_texmatrix, uniform sampler2D reflectivity_tex, uniform matrix4 reflectivity_texmatrix, uniform sampler2D reflectedCol_tex, uniform matrix4 reflectedCol_texmatrix, uniform sampler2D environmentCol_tex, uniform float translucence, uniform float translucenceFocus, uniform float translucenceDepth, uniform float refractiveIndex, uniform float colorAlphaIsOpacity, // [claforte] Should be bool uniform float hasBump, // [claforte] Should be bool uniform float determinantSign, // -1 if determinant of transform is negative uniform float normalMultiplier, // -1 if back of transparent surface uniform float4 gWorldEyePos, // TODO: replace by matrix. uniform float useBlinnShader, uniform float eccentricity, uniform float specularRollOff, uniform float needSpecularity, uniform float specularity, // UVs. [claforte] This innefficient way to handle uv's // (by exploding all possibilities) will soon be phased out // and be replaced by on-demand compilation. vertex float2 bump_uv, vertex float2 color_uv, vertex float2 color_uv2, // Second set of uvs vertex float2 color_uv3, // Third set of uvs vertex float2 color_uv4, // Fourth set of uvs vertex float2 diffuse_uv, vertex float2 spec_exp_uv, vertex float2 transp_uv, vertex float2 ambient_uv, vertex float2 incan_uv, vertex float2 reflectivity_uv, vertex float2 environ_uv, // Standard output. out fragment float4 outRGBA) { // Compute gWorldBumpedNormal. // float3 gWorldBumpedNormal = float3(0.0,0.0,0.0); gWorldNormal = normalMultiplier * normalize(gWorldNormal); gWorldTangent = normalize(gWorldTangent); // [claforte] Workaround for Cg scoping bug, fetch from the color texture // before doing the illumination loop, in case the light also has a color_tex // variable. float2 placed_color_uv = mul(float4(color_uv, 0.0, 1.0), color_texmatrix).xy; float4 fetchedColorRGBA = texture2D(color_tex, placed_color_uv); float3 worldViewDir = normalize(gWorldEyePos.xyz - gWorldPos.xyz); { float2 placed_bump_uv = mul(float4(bump_uv, 0.0, 1.0), bump_texmatrix).xy; float3 tangentSpaceBumpedNormal = texture2D(bump_tex, placed_bump_uv).xyz; // Scale and bias the bumped normal. tangentSpaceBumpedNormal = normalize(tangentSpaceBumpedNormal * 2.0 - 1.0); // Transform the normal from tangent space to world space. // [claforte] This determinantSign mess can be simplified... // TODO later. matrix3 tangentToWorldMatrix = matrix3(gWorldTangent, determinantSign * normalMultiplier * cross(gWorldNormal, gWorldTangent), gWorldNormal); gWorldBumpedNormal = mul(tangentSpaceBumpedNormal, tangentToWorldMatrix); if (hasBump < 0.5) gWorldBumpedNormal = gWorldNormal; } float3 worldReflectedViewDir = reflect(-worldViewDir, gWorldBumpedNormal); float2 placed_spec_exp_uv = mul(float4(spec_exp_uv, 0.0, 1.0), spec_exp_texmatrix).xy; float4 fetchedSpecColorExp = texture2D(spec_exp_tex, placed_spec_exp_uv); float cosinePower = fetchedSpecColorExp.a * 128.0; float3 ambientIrradiance = float3(0.0,0.0,0.0); float3 diffuseIrradiance = float3(0.0,0.0,0.0); float3 specularIrradiance = float3(0.0,0.0,0.0); illuminance { // Accumulate the different types of irradiance. ambientIrradiance += gLightAmbientColor; diffuseIrradiance += max(dot(gWorldBumpedNormal, gLightWorldDir), 0.0) * gLightDiffuseColor; // Accumulate the specular irradiance. float RvDotL = max(dot(gLightWorldDir, worldReflectedViewDir), 0.0); specularIrradiance += pow(RvDotL, cosinePower) * gLightSpecularColor; } // Alpha opacity or RGB transparency? float2 placed_transp_uv = mul(float4(transp_uv, 0.0, 1.0), transp_texmatrix).xy; float3 coloredOpacity = (colorAlphaIsOpacity == 1.0) ? fetchedColorRGBA.aaa : (float3(1.0,1.0,1.0) - texture2D(transp_tex, placed_transp_uv).rgb); // Compute the diffuse color. float2 placed_diffuse_uv = mul(float4(diffuse_uv, 0.0, 1.0), diffuse_texmatrix).xy; //float2 placed_ambient_uv = mul(float4(ambient_uv, 0.0, 1.0), ambient_texmatrix).xy; diffuseIrradiance = diffuseIrradiance * texture2D(diffuse_tex, placed_diffuse_uv).a; //ambientIrradiance = ambientIrradiance + texture2D(ambient_tex, placed_ambient_uv).xyz; float3 diffuseAndAmbientColor = (diffuseIrradiance + ambientIrradiance) * fetchedColorRGBA.rgb * coloredOpacity; // Compute the specular color. float3 specularColor = specularIrradiance * fetchedSpecColorExp.rgb; outRGBA = float4(specularColor + diffuseAndAmbientColor, 1.0); } material Maya_blinn( vertex float3 gWorldPos, vertex float3 gWorldNormal, vertex float3 gWorldTangent, uniform sampler2D bump_tex, uniform matrix4 bump_texmatrix, uniform sampler2D color_tex, uniform matrix4 color_texmatrix, uniform sampler2D diffuse_tex, uniform matrix4 diffuse_texmatrix, uniform sampler2D incan_tex, uniform matrix4 incan_texmatrix, uniform sampler2D spec_exp_tex, uniform matrix4 spec_exp_texmatrix, uniform sampler2D transp_tex, uniform matrix4 transp_texmatrix, uniform sampler2D ambient_tex, uniform matrix4 ambient_texmatrix, uniform sampler2D reflectivity_tex, uniform matrix4 reflectivity_texmatrix, uniform sampler2D reflectedCol_tex, uniform matrix4 reflectedCol_texmatrix, uniform float eccentricity, uniform float specularRollOff, uniform float refractiveIndex, uniform float colorAlphaIsOpacity, // [claforte] Should be bool uniform float hasBump, // [claforte] Should be bool uniform float determinantSign, // -1 if determinant of transform is negative uniform float normalMultiplier, // -1 if back of transparent surface uniform float4 gWorldEyePos, // UVs. [claforte] This innefficient way to handle uv's // (by exploding all possibilities) will soon be phased out // and be replaced by on-demand compilation. vertex float2 bump_uv, vertex float2 color_uv, vertex float2 diffuse_uv, vertex float2 spec_exp_uv, vertex float2 transp_uv, vertex float2 ambient_uv, vertex float2 incan_uv, vertex float2 reflectivity_uv, // Standard output. out fragment float4 outRGBA) { // Compute gWorldBumpedNormal. // float3 gWorldBumpedNormal = float3(0.0,0.0,0.0); gWorldNormal = normalMultiplier * normalize(gWorldNormal); gWorldTangent = normalize(gWorldTangent); // [claforte] Workaround for Cg scoping bug, fetch from the color texture // before doing the illumination loop, in case the light also has a color_tex // variable. float2 placed_color_uv = mul(float4(color_uv, 0.0, 1.0), color_texmatrix).xy; float4 fetchedColorRGBA = texture2D(color_tex, placed_color_uv); float3 worldViewDir = normalize(gWorldEyePos.xyz - gWorldPos.xyz); { float2 placed_bump_uv = mul(float4(bump_uv, 0.0, 1.0), bump_texmatrix).xy; float3 tangentSpaceBumpedNormal = texture2D(bump_tex, placed_bump_uv).xyz; // Scale and bias the bumped normal. tangentSpaceBumpedNormal = normalize(tangentSpaceBumpedNormal * 2.0 - 1.0); // Transform the normal from tangent space to world space. // [claforte] This determinantSign mess can be simplified... // TODO later. matrix3 tangentToWorldMatrix = matrix3(gWorldTangent, determinantSign * normalMultiplier * cross(gWorldNormal, gWorldTangent), gWorldNormal); gWorldBumpedNormal = mul(tangentSpaceBumpedNormal, tangentToWorldMatrix); if (hasBump < 0.5) gWorldBumpedNormal = gWorldNormal; } float3 worldReflectedViewDir = reflect(-worldViewDir, gWorldBumpedNormal); float2 placed_spec_exp_uv = mul(float4(spec_exp_uv, 0.0, 1.0), spec_exp_texmatrix).xy; float4 fetchedSpecColorExp = texture2D(spec_exp_tex, placed_spec_exp_uv); // Light-independant Blinn specular parameters float cosne = dot(gWorldBumpedNormal, worldViewDir); float computedEcc = eccentricity * eccentricity - 1.0; float3 ambientIrradiance = float3(0.0,0.0,0.0); float3 diffuseIrradiance = float3(0.0,0.0,0.0); float3 specularIrradiance = float3(0.0,0.0,0.0); illuminance { // Accumulate the different types of irradiance. ambientIrradiance += gLightAmbientColor; float cosln = max(dot(gWorldBumpedNormal, gLightWorldDir), 0.0); diffuseIrradiance += cosln * gLightDiffuseColor; // All of the following should ideally only be done if // (cosln > 0.0). // float3 wHalfAngleDir = normalize(gLightWorldDir + worldViewDir); float coseh = dot(wHalfAngleDir, worldViewDir); float cosnh = dot(wHalfAngleDir, gWorldBumpedNormal); float Dd = ( computedEcc + 1.0) / ( 1.0 + computedEcc * cosnh * cosnh ); Dd = Dd * Dd; cosnh = 2 * cosnh; float Gg; if (cosne < cosln) Gg = (cosne*cosnh < coseh) ? cosnh / coseh : 1.0 / cosne; else Gg = (cosln*cosnh < coseh) ? cosln * cosnh / (coseh * cosne) : 1.0 / cosne; // Fresnel calculation. // coseh = 1.0 - coseh; coseh = coseh * coseh * coseh; float Ff = coseh + (1.0 - coseh) * specularRollOff; float specularCoefficient = max(Dd * Gg * Ff, 0.0); if (cosln > 0.0) specularIrradiance += specularCoefficient * gLightSpecularColor; } // Alpha opacity or RGB transparency? float2 placed_transp_uv = mul(float4(transp_uv, 0.0, 1.0), transp_texmatrix).xy; float3 coloredOpacity = (colorAlphaIsOpacity == 1.0) ? fetchedColorRGBA.aaa : (float3(1.0,1.0,1.0) - texture2D(transp_tex, placed_transp_uv).rgb); // Compute the diffuse color. float2 placed_diffuse_uv = mul(float4(diffuse_uv, 0.0, 1.0), diffuse_texmatrix).xy; //float2 placed_ambient_uv = mul(float4(ambient_uv, 0.0, 1.0), ambient_texmatrix).xy; diffuseIrradiance = diffuseIrradiance * texture2D(diffuse_tex, placed_diffuse_uv).a; //ambientIrradiance = ambientIrradiance + texture2D(ambient_tex, placed_ambient_uv).xyz; float3 diffuseAndAmbientColor = (diffuseIrradiance + ambientIrradiance) * fetchedColorRGBA.rgb * coloredOpacity; // Compute the specular color. float3 specularColor = specularIrradiance * fetchedSpecColorExp.rgb; outRGBA = float4(specularColor + diffuseAndAmbientColor, 1.0); } material Maya_blinn_postLighting( vertex float3 gWorldPos, vertex float3 gWorldNormal, vertex float3 gWorldTangent, uniform sampler2D bump_tex, uniform matrix4 bump_texmatrix, uniform sampler2D color_tex, uniform matrix4 color_texmatrix, uniform sampler2D incan_tex, uniform matrix4 incan_texmatrix, uniform sampler2D spec_exp_tex, uniform matrix4 spec_exp_texmatrix, uniform sampler2D transp_tex, uniform matrix4 transp_texmatrix, uniform sampler2D ambient_tex, uniform matrix4 ambient_texmatrix, uniform sampler2D reflectivity_tex, uniform matrix4 reflectivity_texmatrix, uniform samplerCube reflectedCubeCol_tex, uniform matrix4 reflectedCubeCol_texmatrix_inv_ortho_neg23, uniform sampler2D reflectedSphereCol_tex, uniform matrix4 reflectedSphereCol_texmatrix_inv_ortho, uniform float eccentricity, uniform float specularRollOff, uniform float refractiveIndex, uniform float colorAlphaIsOpacity, // [claforte] Should be bool uniform float hasBump, // [claforte] Should be bool uniform float reflectedCubeLookup, // [claforte] Should be bool uniform float reflectedSphereLookup, // [claforte] Should be bool uniform float determinantSign, // -1 if determinant of transform is negative uniform float normalMultiplier, // -1 if back of transparent surface uniform float4 gWorldEyePos, // TODO: replace by matrix. // UVs. [claforte] This innefficient way to handle uv's // (by exploding all possibilities) will soon be phased out // and be replaced by on-demand compilation. vertex float2 bump_uv, vertex float2 color_uv, vertex float2 spec_exp_uv, vertex float2 transp_uv, vertex float2 ambient_uv, vertex float2 incan_uv, vertex float2 reflectivity_uv, // Standard output. out fragment float4 outRGBA) { // Compute gWorldBumpedNormal. // float3 gWorldBumpedNormal = float3(0.0,0.0,0.0); gWorldNormal = normalMultiplier * normalize(gWorldNormal); gWorldTangent = normalize(gWorldTangent); // [claforte] Workaround for Cg scoping bug, fetch from the color texture // before doing the illumination loop, in case the light also has a color_tex // variable. float2 placed_color_uv = mul(float4(color_uv, 0.0, 1.0), color_texmatrix).xy; float4 fetchedColorRGBA = texture2D(color_tex, placed_color_uv); float3 worldViewDir = normalize(gWorldEyePos.xyz - gWorldPos.xyz); { float2 placed_bump_uv = mul(float4(bump_uv, 0.0, 1.0), bump_texmatrix).xy; float3 tangentSpaceBumpedNormal = texture2D(bump_tex, placed_bump_uv).xyz; // Scale and bias the bumped normal. tangentSpaceBumpedNormal = normalize(tangentSpaceBumpedNormal * 2.0 - 1.0); // Transform the normal from tangent space to world space. // [claforte] This determinantSign mess can be simplified... // TODO later. matrix3 tangentToWorldMatrix = matrix3(gWorldTangent, determinantSign * normalMultiplier * cross(gWorldNormal, gWorldTangent), gWorldNormal); gWorldBumpedNormal = mul(tangentSpaceBumpedNormal, tangentToWorldMatrix); if (hasBump < 0.5) gWorldBumpedNormal = gWorldNormal; } float3 worldReflectedViewDir = normalize(reflect(-worldViewDir, gWorldBumpedNormal)); float2 placed_spec_exp_uv = mul(float4(spec_exp_uv, 0.0, 1.0), spec_exp_texmatrix).xy; float4 fetchedSpecColorExp = texture2D(spec_exp_tex, placed_spec_exp_uv); // Alpha opacity or RGB transparency? float2 placed_transp_uv = mul(float4(transp_uv, 0.0, 1.0), transp_texmatrix).xy; float3 coloredOpacity = (colorAlphaIsOpacity == 1.0) ? fetchedColorRGBA.aaa : (float3(1.0,1.0,1.0) - texture2D(transp_tex, placed_transp_uv).rgb); // Fetch the reflected color. // [claforte] Yeah, it's wasteful to repeat operations for sphere and cube // map, but this ugly code will go away as soon as MSL is in place. float4 cReflectCubeDir = mul(float4(worldReflectedViewDir, 0.0), reflectedCubeCol_texmatrix_inv_ortho_neg23); float4 cReflectSphereDir = mul(float4(worldReflectedViewDir, 0.0), reflectedSphereCol_texmatrix_inv_ortho); float3 reflectedColor = float3(0.0,0.0,0.0); if (reflectedCubeLookup > 0.5) { // Transform the reflection vector from world space to // cube space. Ideally, we'd take the full cube placement // information into account, but since this is quite // complicated, we use the traditional OpenGL-shortcut of // only applying a rotation. // reflectedColor = textureCube(reflectedCubeCol_tex, cReflectCubeDir.xyz).rgb; } else if (reflectedSphereLookup > 0.5) { // This calculation is directly taken from the OpenGL spec's sphere // mapping section. // float x = cReflectSphereDir.x; float y = cReflectSphereDir.y; float z = cReflectSphereDir.z + 1.0; float m = 2.0 * sqrt(x * x + y * y + z * z); float2 sphereUv = cReflectSphereDir.xy / m + 0.5; reflectedColor = texture2D(reflectedSphereCol_tex, sphereUv).rgb; } // Compute the fresnel term used to modulate reflectivity. // float cosne = dot(gWorldBumpedNormal, worldViewDir); cosne = 1.0 - cosne; cosne = cosne * cosne * cosne; float reflectance = cosne + (1.0 - cosne) * specularRollOff; reflectance = max(reflectance, 0.0); // Modulate reflectance by reflectivity. float2 placed_reflectivity_uv = mul(float4(reflectivity_uv, 0.0, 1.0), reflectivity_texmatrix).xy; reflectance = reflectance * texture2D(reflectivity_tex, placed_reflectivity_uv).a; // Add incandescence. float2 placed_incan_uv = mul(float4(incan_uv, 0.0, 1.0), incan_texmatrix).xy; float3 incandescence = texture2D(incan_tex, placed_incan_uv).rgb; outRGBA = float4(reflectance * reflectedColor + incandescence, 1.0); }