Skip to content

Instantly share code, notes, and snippets.

@ccgus
Created August 21, 2014 20:46
Show Gist options
  • Star 0 You must be signed in to star a gist
  • Fork 0 You must be signed in to fork a gist
  • Save ccgus/40b91ce357a4456561ad to your computer and use it in GitHub Desktop.
Save ccgus/40b91ce357a4456561ad to your computer and use it in GitHub Desktop.
Color Wheel Thing
var filter = [JSTQuickCIFilter quickFilterWithKernel:"""
bool isOdd(int v) {
float dividend = float(v) / 2.0;
return dividend != floor(dividend);
}
vec4 hsvToRgb(vec4 hsv) {
float h = hsv.r;
float s = hsv.g;
float v = hsv.b;
int i = int(floor(h));
float f = isOdd(i) ? h - float(i) : 1.0 - (h - float(i));
float m = v * (1.0 - s);
float n = v * (1.0 - s * f);
vec4 result = (i == 0) ? vec4(v, n, m, hsv.a) : ((i == 1) ?
vec4(n, v, m, hsv.a) : ((i == 2) ? vec4(m, v, n, hsv.a) : ((i == 3) ?
vec4(m, n, v, hsv.a) : ((i == 4) ? vec4(n, m, v, hsv.a) : ((i == 5) ?
vec4(v, m, n, hsv.a) : vec4(v, n, m, hsv.a))))));
return (h == -1.0) ? vec4(v, v, v, hsv.a) : result;
}
kernel vec4 colorWheel(float radius, float segmentCount) {
float pi = 3.14159265;
vec2 center = vec2(radius, radius);
vec2 v0 = destCoord();
vec2 v1 = vec2(v0.x, radius);
float a = distance(v0, v1);
float b = distance(v1, center);
float angle = atan(a,b);
angle = 1.570796326794897;
angle = (v0.x>radius)?((v0.y>radius)?
(atan(b,a)+pi/2.0):atan(a,b)+pi):
(v0.y<radius)?(atan(b,a)+(pi*1.5)):atan(a,b);
vec4 theColor = vec4(1.0);
float c = 360.0 / segmentCount;
float dist = length(destCoord() - center);
angle = dist < radius * 0.8 ? angle : (floor((angle*(180.0/pi) + c / 2.0) / c) * c) * (pi/180.0);
//angle = angle*(180.0/pi);
//angle = floor(angle / c) * c;
//angle = angle*(pi/180.0);
theColor.r = (angle * 3.0) / pi;
// make it a cirlce
theColor.a = clamp(radius - dist, 0.0, 1.0);
// cut out the middle
theColor.a = theColor.a - clamp(radius - (radius * .4) - dist, 0.0, theColor.a);
vec4 f = hsvToRgb(theColor);
// give it a white background.
vec4 D = vec4(1.0, 1.0, 1.0, 1.0);
vec4 S = f;
vec4 R = S + D*(1.0 - S.a);
f = R;
return premultiply(f);
}
"""];
var radius = 400;
[filter addKernelArgument:[NSNumber numberWithInt:radius]];
[filter addKernelArgument:[NSNumber numberWithInt:18]];
var img = [filter outputImage];
var f = [CIFilter filterWithName:@"CILanczosScaleTransform"];
[f setDefaults];
[f setValue:[NSNumber numberWithFloat:.5] forKey:@"inputScale"];
[f setValue:img forKey:@"inputImage"];
img = [f valueForKey:@"outputImage"];
img = [img imageByApplyingTransform:CGAffineTransformMakeTranslation(10, 10)];
//[JSTImageTools setShouldUseCICPURenderer:false];
//[JSTImageTools setShouldUseCICPURenderer:true];
[JSTImageTools viewCIImage:img inWindowNamed:"test" extent:CGRectMake(0, 0, radius*2, radius*2)];
@ccgus
Copy link
Author

ccgus commented Aug 21, 2014

@regexident
Copy link

Given that GPUs hate branching conditionals in code (of which there appear to be 7 in your hsvToRgb function) you might want to take a look at branch-less HSV<->RGB conversion.

OpenGL-specific, but should be possible to translate to OpenCL in some way, I think:
http://lolengine.net/blog/2013/07/27/rgb-to-hsv-in-glsl

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment