<languageVersion: 1.0;>

kernel Whirl
<	vendor : "MIT Media Laboratory";
	namespace : "filters";
	version : 1;
	description : "Scratch Whirl";
>
{
	parameter float whirlRadians
	<
		minValue: float(-100.0);
		maxValue: float(100.0);
		defaultValue: float(0);
	>;
	parameter float2 center
	<
		minValue:float2(0, 0);
		maxValue:float2(1000, 1000);
		defaultValue:float2(100, 100);
	>;
	parameter float radius
	<
		minValue: float(0);
		maxValue: float(500);
		defaultValue: float(100);
	>;
	parameter float2 scale
	<
		minValue:float2(0, 0);
		maxValue:float2(10, 10);
		defaultValue:float2(1, 1);
	>;

	input image4 src;
	output float4 dst;

	void evaluatePixel() {
		float2 vec = scale * (outCoord() - center);
		float d = length(vec);
		float factor = 1.0 - (d / radius);
		float a = whirlRadians * (factor * factor);
		// matrix to rotate the vector from the center
		float sinAngle = sin(a);
		float cosAngle = cos(a);
		float2x2 rotationMat = float2x2(
			cosAngle,	-sinAngle,
			sinAngle,	 cosAngle
		);
		// rotate, unscale, and compute source point
		float2 p = ((rotationMat * vec) / scale) + center;
		dst = sampleNearest(src, p);
		if (d > radius) dst = sampleNearest(src, outCoord());
	}
}
