uniform sampler2D t,b; //t is a texture containing the last frame, b is the rendered base geometry
uniform float p[14]; //fourteen parameters
const float pixelsize = 1/1600.; //we need to know how large a pixel is
void main( void )
{
vec2 pos = mat2(cos(p[12]),-sin(p[12]),sin(p[12]),cos(p[12]))*(gl_TexCoord[0].st - vec2(0.5,0.5))*(1.0+p[11]) + vec2(0.5,0.5); //rotation and zoom
vec4 orig = (texture2D(t,pos)*4.0 +
p[0]*(texture2D(t,pos+pixelsize*vec2(0.0, 1.0)) +
texture2D(t,pos+pixelsize*vec2(0.0,-1.0)) +
texture2D(t,pos+pixelsize*vec2(1.0, 0.0)) +
texture2D(t,pos+pixelsize*vec2(-1.0,0.0))) )/4.0/(1.0+p[0]); //smoothing/sharpening
vec4 hsv = rgbToHsv(orig);
float angle = -hsv.x -p[1];
vec4 color = rgbToHsv(texture2D(t,gl_TexCoord[0].st + vec2(cos (angle), sin (angle)) * (p[2] + p[3] * hsv.y + p[4] * hsv.z + p[5]*(hsv.y*hsv.z)) * pixelsize)); //sample new color from somewhere else, according to the color value at this pixel
color += vec4( p[7] + p[8]*color.y, p[9], p[10], 0.0); // manipulate output color in hsv
gl_FragColor = mix(mix(orig, hsvToRgb(color),p[6]),texture2D(b,gl_TexCoord[0].st),p[13]); //convert back to rgb, blend with last frame and with geometry
}