kernel colorTwist < namespace : "visualrinse"; vendor : "Chad Udell"; version : 1; description : "a variable sepia filter"; > { parameter float negativeTwister; parameter float colorTwister; parameter float multiplier < minValue : 1.0; maxValue : 5.0; defaultValue: 1.0; >; input image4 src; output float4 dst; void evaluatePixel() { // temporary variables to hold the colors. float4 rgbaColor; float4 yiqaColor; // The language implements matrices in column major order. This means // that mathematically, the transform will look like the following: // |Y| |0.299 0.587 0.114 0.0| |R| // |I| = |0.596 -0.275 -0.321 0.0| |G| // |Q| |0.212 -0.523 0.311 0.0| |B| // |A| |0.0 0.0 0.0 1.0| |A| float4x4 YIQMatrix = float4x4( 0.299, 0.596, 0.212, 0.000, 0.587, -0.275, -0.523, 0.000, 0.114, -0.321, 0.311, 0.000, 0.000, 0.000, 0.000, 1.000 ); // Similar to the above matrix, the matrix is in column order. Thus, // the transform will look like the following: // |R| |1.0 0.956 0.621 0.0| |Y| // |G| = |1.0 -0.272 -0.647 0.0| |I| // |B| |1.0 -1.11 1.70 0.0| |Q| // |A| |0.0 0.0 0.0 1.0| |A| float4x4 inverseYIQ = float4x4( 1.0, 1.0, 1.0, 0.0, 0.956, -0.272, -1.10, 0.0, 0.621, -0.647, 1.70, 0.0, 0.0, 0.0, 0.0, 1.0 ); // get the pixel value at our current location rgbaColor = sampleNearest(src, outCoord()); yiqaColor = rgbaColor*multiplier; yiqaColor.s = negativeTwister; yiqaColor.t = colorTwister; // zero out the Q to apply the sepia tone // convert back to RGBA and set the output value to the modified color. dst = inverseYIQ * yiqaColor; } }