
kernel vec4 spinBlur(sampler image, vec2 cxy, vec4 sinR0, vec4 sinR1, vec4 sinR2, vec4 sinR3, vec4 cosR0, vec4 cosR1, vec4 cosR2, vec4 cosR3)
{
	const vec2 xy = destCoord();
	const vec2 dxy = xy - cxy;

    vec4 p = 0;

    //  R0
    
	p += sample(
        image,
        samplerTransform(
            image,
            vec2(
                ((dxy.x * +cosR0.x) + (dxy.y * -sinR0.x)),
                ((dxy.x * +sinR0.x) + (dxy.y * +cosR0.x))
            ) + cxy
        )
    );
	p += sample(
        image,
        samplerTransform(
            image,
            vec2(
                ((dxy.x * +cosR0.y) + (dxy.y * -sinR0.y)),
                ((dxy.x * +sinR0.y) + (dxy.y * +cosR0.y))
            ) + cxy
        )
    );
	p += sample(
        image,
        samplerTransform(
            image,
            vec2(
                ((dxy.x * +cosR0.z) + (dxy.y * -sinR0.z)),
                ((dxy.x * +sinR0.z) + (dxy.y * +cosR0.z))
            ) + cxy
        )
    );
	p += sample(
        image,
        samplerTransform(
            image,
            vec2(
                ((dxy.x * +cosR0.w) + (dxy.y * -sinR0.w)),
                ((dxy.x * +sinR0.w) + (dxy.y * +cosR0.w))
            ) + cxy
        )
    );

    //  R1
    
	p += sample(
        image,
        samplerTransform(
            image,
            vec2(
                ((dxy.x * +cosR1.x) + (dxy.y * -sinR1.x)),
                ((dxy.x * +sinR1.x) + (dxy.y * +cosR1.x))
            ) + cxy
        )
    );
	p += sample(
        image,
        samplerTransform(
            image,
            vec2(
                ((dxy.x * +cosR1.y) + (dxy.y * -sinR1.y)),
                ((dxy.x * +sinR1.y) + (dxy.y * +cosR1.y))
            ) + cxy
        )
    );
	p += sample(
        image,
        samplerTransform(
            image,
            vec2(
                ((dxy.x * +cosR1.z) + (dxy.y * -sinR1.z)),
                ((dxy.x * +sinR1.z) + (dxy.y * +cosR1.z))
            ) + cxy
        )
    );
	p += sample(
        image,
        samplerTransform(
            image,
            vec2(
                ((dxy.x * +cosR1.w) + (dxy.y * -sinR1.w)),
                ((dxy.x * +sinR1.w) + (dxy.y * +cosR1.w))
            ) + cxy
        )
    );

    //  R2
    
	p += sample(
        image,
        samplerTransform(
            image,
            vec2(
                ((dxy.x * +cosR2.x) + (dxy.y * -sinR2.x)),
                ((dxy.x * +sinR2.x) + (dxy.y * +cosR2.x))
            ) + cxy
        )
    );
	p += sample(
        image,
        samplerTransform(
            image,
            vec2(
                ((dxy.x * +cosR2.y) + (dxy.y * -sinR2.y)),
                ((dxy.x * +sinR2.y) + (dxy.y * +cosR2.y))
            ) + cxy
        )
    );
	p += sample(
        image,
        samplerTransform(
            image,
            vec2(
                ((dxy.x * +cosR2.z) + (dxy.y * -sinR2.z)),
                ((dxy.x * +sinR2.z) + (dxy.y * +cosR2.z))
            ) + cxy
        )
    );
	p += sample(
        image,
        samplerTransform(
            image,
            vec2(
                ((dxy.x * +cosR2.w) + (dxy.y * -sinR2.w)),
                ((dxy.x * +sinR2.w) + (dxy.y * +cosR2.w))
            ) + cxy
        )
    );

    //  R3
    
	p += sample(
        image,
        samplerTransform(
            image,
            vec2(
                ((dxy.x * +cosR3.x) + (dxy.y * -sinR3.x)),
                ((dxy.x * +sinR3.x) + (dxy.y * +cosR3.x))
            ) + cxy
        )
    );
	p += sample(
        image,
        samplerTransform(
            image,
            vec2(
                ((dxy.x * +cosR3.y) + (dxy.y * -sinR3.y)),
                ((dxy.x * +sinR3.y) + (dxy.y * +cosR3.y))
            ) + cxy
        )
    );
	p += sample(
        image,
        samplerTransform(
            image,
            vec2(
                ((dxy.x * +cosR3.z) + (dxy.y * -sinR3.z)),
                ((dxy.x * +sinR3.z) + (dxy.y * +cosR3.z))
            ) + cxy
        )
    );
	p += sample(
        image,
        samplerTransform(
            image,
            vec2(
                ((dxy.x * +cosR3.w) + (dxy.y * -sinR3.w)),
                ((dxy.x * +sinR3.w) + (dxy.y * +cosR3.w))
            ) + cxy
        )
    );

    return p / 16.0;
}
