Reputation: 29896
How does one draw a CGGradient with 3 colors?
I have an array like so:
CFArrayRef colors = (__bridge CFArrayRef) [NSArray arrayWithObjects:(id)lightGradientColor.CGColor,
(id)darkGradientColor.CGColor, (id)lightGradientColor.CGColor,
nil];
but I dont see the dark color in the middle with light on top and bottom sections, but rather just light on top, with dark until the bottom.
Upvotes: 1
Views: 2001
Reputation: 4196
Pass multiple colours using CGGradient instead of CAGardientLayer for smoother results:
A. Create a custom UIView class with an @property NSArray * colours in the header. In the implementation file, paste the following drawRect method.
-(void)drawRect:(CGRect)rect {
//1. create vars
float increment = 1.0f / (colours.count-1);
CGFloat * locations = (CGFloat *)malloc((int)colours.count*sizeof(CGFloat));
CFMutableArrayRef mref = CFArrayCreateMutable(kCFAllocatorDefault, 0, &kCFTypeArrayCallBacks);
//2. go through the colours, creating cgColors and locations
for (int n = 0; n < colours.count; n++){
CFArrayAppendValue(mref, (id)[colours[n] CGColor]);
locations[n]=(n*increment);
}
//3. create gradient
CGContextRef ref = UIGraphicsGetCurrentContext();
CGColorSpaceRef spaceRef = CGColorSpaceCreateDeviceRGB();
CGGradientRef gradientRef = CGGradientCreateWithColors(spaceRef, mref, locations);
CGContextDrawLinearGradient(ref, gradientRef, CGPointMake(0.0, 0.0), CGPointMake(0.0, self.frame.size.height), kCGGradientDrawsAfterEndLocation);
CGColorSpaceRelease(spaceRef);
CGGradientRelease(gradientRef);
}
B. In the viewController you want to use the custom class, initialise it, set the frame and its colours. It works for anything more than one colour, and in this case runs from top to bottom.
Background * bg = [Background new];
[bg setFrame:self.view.bounds];
[bg setColours:@[[UIColor blueColor],[UIColor purpleColor]]];
[self.view addSubview:bg];
It's a smoother gradient than using the CAGradientLayer, and more noticeable if you drop the alpha on a colour:
Upvotes: 0
Reputation: 104698
Have you tried specifying/verifying the locations of your colors? The range is [0...1]:
const CGFloat locations[3] = {0.0, 0.5, 1.0};
CGGradientRef grad = CGGradientCreateWithColors(colorspace, colors, locations);
note: The locations above should be the same as passing 0
for the locations
parameter.
Upvotes: 3