I\'m looking for method to add gradually fading or maybe blured border (I don\'t exactly know how to name this effect) to arbitrary UIView. I don\'t need animated effect, I
There's a tutorial at Cocoanetics that does that exact thing.
I've found a solution - I've useed CALayer's property mask:
CALayer *viewLayer = [back layer];
CALayer* maskCompoudLayer = [CALayer layer];
maskLayer.bounds = viewLayer.bounds;
[maskLayer setPosition:CGPointMake(160, CGRectGetHeight(maskCompoudLayer.frame)/2.0)];
CGColorSpaceRef colorSpace = CGColorSpaceCreateDeviceRGB();
CGContextRef context = CGBitmapContextCreate (NULL, 320, 480, 8, 0, colorSpace, kCGImageAlphaPremultipliedLast);
CGFloat colors[] = {
0.5, 0.5, 0.5, 0.0, //BLACK
0.0, 0.0, 0.0, 1.0, //BLACK
};
CGGradientRef gradient = CGGradientCreateWithColorComponents(colorSpace, colors, NULL, sizeof(colors)/(sizeof(colors[0])*4));
CGColorSpaceRelease(colorSpace);
NSUInteger gradientH = 20;
NSUInteger gradientHPos = 0;
CGContextSetFillColorWithColor(context, [UIColor colorWithRed:0.0 green:0.0 blue:0.0 alpha:1.0].CGColor);
CGContextFillRect(context, CGRectMake(0, gradientHPos + gradientH, CGRectGetWidth(maskLayer.frame), CGRectGetHeight(maskLayer.frame)));
CGContextSetFillColorWithColor(context, [UIColor colorWithRed:0.5 green:0.5 blue:0.5 alpha:0.0].CGColor);
CGContextFillRect(context, CGRectMake(0, 0, 320, gradientHPos));
CGContextDrawLinearGradient(context, gradient, CGPointMake(160, gradientHPos), CGPointMake(160, gradientHPos + gradientH), 0);
CGGradientRelease(gradient);
CGImageRef contextImage = CGBitmapContextCreateImage(context);
CGContextRelease(context);
[maskLayer setContents:(id)contextImage];
CGImageRelease (contextImage);
viewLayer.masksToBounds = YES;
viewLayer.mask = maskCompoudLayer;
Using this code I have UITableView with fading border
I'll say this first, iKiR's answer was more than enough for me. I copied the code as it is, and with little experience from my side, I was able to make it work effortlessly (on a UITableView
).
MaskingView
QuartzCore
framework!initWithCoder:
and/or initWithFrame:
as appropriate)MaskingView
. (In Interface Builder, user Editor -> Embed In -> View. Then, choose the class of the new superview as MaskingView
)NOTES:
The Code:
CALayer *viewLayer = [self layer];
CALayer* maskLayer = [CALayer layer];
maskLayer.bounds = viewLayer.bounds;
[maskLayer setPosition:CGPointMake(CGRectGetWidth(viewLayer.frame)/2.0, CGRectGetHeight(viewLayer.frame)/2.0)];
CGColorSpaceRef colorSpace = CGColorSpaceCreateDeviceRGB();
CGContextRef context = CGBitmapContextCreate (NULL, viewLayer.bounds.size.width, viewLayer.bounds.size.height, 8, 0, colorSpace, kCGImageAlphaPremultipliedLast);
CGFloat colors[] = {
0.5, 0.5, 0.5, 0.0, //BLACK
0.0, 0.0, 0.0, 1.0, //BLACK
};
CGGradientRef gradient = CGGradientCreateWithColorComponents(colorSpace, colors, NULL, sizeof(colors)/(sizeof(colors[0])*4));
CGColorSpaceRelease(colorSpace);
NSUInteger gradientH = 20;
NSUInteger gradientHPos = 0;
CGContextSetFillColorWithColor(context, [UIColor colorWithRed:0.0 green:0.0 blue:0.0 alpha:1.0].CGColor);
CGContextFillRect(context, CGRectMake(0, gradientHPos + gradientH, CGRectGetWidth(maskLayer.frame), CGRectGetHeight(maskLayer.frame)));
CGContextSetFillColorWithColor(context, [UIColor colorWithRed:0.5 green:0.5 blue:0.5 alpha:0.0].CGColor);
CGContextFillRect(context, CGRectMake(0, 0, 320, gradientHPos));
CGContextDrawLinearGradient(context, gradient, CGPointMake(160, gradientHPos), CGPointMake(160, gradientHPos + gradientH), 0);
CGGradientRelease(gradient);
CGImageRef contextImage = CGBitmapContextCreateImage(context);
CGContextRelease(context);
[maskLayer setContents:(__bridge id)contextImage];
CGImageRelease (contextImage);
viewLayer.masksToBounds = YES;
viewLayer.mask = maskLayer;
Here's iKiR and Mazyod's answer, translated to Xamarin.iOS (Monotouch). Note that there's no need to draw rectangles before and after the gradient if you just pass the right flags to the the DrawLinearGradient
method:
var vl = myView.Layer;
var l = new CALayer ();
l.Frame = new RectangleF(vl.Frame.Width/2, vl.Frame.Height/2,
vl.Frame.Width, vl.Frame.Height) ;
var cs = CGColorSpace.CreateDeviceRGB ();
var g = new CGBitmapContext (null,
(int) vl.Bounds.Size.Width, (int)vl.Bounds.Size.Height,
8, 0, cs, CGImageAlphaInfo.PremultipliedLast);
var colors = new CGColor[] { UIColor.FromWhiteAlpha(1, 0).CGColor,
UIColor.FromWhiteAlpha(1, 1f).CGColor };
var grad = new CGGradient (cs, colors, new float[] { 0f, 1f });
int gradH = 20, gradHPos = 0;
g.DrawLinearGradient (grad,
new PointF (l.Frame.Width / 2, gradHPos), new PointF (l.Frame.Width / 2, gradHPos + gradH),
CGGradientDrawingOptions.DrawsBeforeStartLocation | CGGradientDrawingOptions.DrawsAfterEndLocation);
grad.Dispose ();
l.Contents = g.ToImage ();
g.Dispose ();
vl.Mask = l;
vl.MasksToBounds = true;
You might try placing a semi-transparent PNG file over the bottom of the UITableView.