用石英填充PNG的梯度

时间:2013-09-05 14:12:51

标签: ios objective-c quartz-graphics

如何用线性渐变填充PNG UIImage的非透明区域?我想为MKAnnotationViews重用PNG形状,但是改变每个注释的属性的渐变。

2 个答案:

答案 0 :(得分:1)

要将图像用作渐变的蒙版(即,使图像的非透明像素具有渐变),您可以:

  • 使用渐变创建一个简单视图(您可以创建一个简单的UIView并使用下面显示的addGradientLayerToView为其提供渐变,或者您可以提前创建渐变PNG将它添加到您的包中。)

  • 将PNG作为掩码应用于该渐变视图:

    UIImage *mask = [UIImage imageNamed:@"mask.png"];
    CALayer *maskLayer = [CALayer layer];
    maskLayer.frame = CGRectMake(0, 0, mask.size.width, mask.size.height);
    maskLayer.contents = (id)[mask CGImage];
    gradientViewToMask.layer.mask = maskLayer;
    

要将渐变应用于透明像素,您可以:

  1. 使用渐变创建新图像:

    - (UIImage *)imageWithGradient:(UIImage *)image
    {
        UIGraphicsBeginImageContextWithOptions(image.size, NO, 1.0);
    
        CGContextRef context = UIGraphicsGetCurrentContext();
    
        size_t locationCount = 2;
        CGFloat locations[2] = { 0.0, 1.0 };
        CGFloat components[8] = { 0.0, 0.8, 0.8, 1.0,   // Start color
                                  0.9, 0.9, 0.9, 1.0 }; // End color
    
        CGColorSpaceRef colorspace = CGColorSpaceCreateDeviceRGB();
    
        CGGradientRef gradient = CGGradientCreateWithColorComponents (colorspace, components, locations, locationCount):
    
        CGPoint startPoint = CGPointMake(0.0, 0.0);
        CGPoint endPoint   = CGPointMake(0.0, image.size.height);
        CGContextDrawLinearGradient (context, gradient, startPoint, endPoint, 0);
    
        CGContextTranslateCTM(context, 0, image.size.height);
        CGContextScaleCTM(context, 1.0, -1.0);
    
        CGContextDrawImage(context, CGRectMake(0.0, 0.0, image.size.width, image.size.height), [image CGImage]);
    
        UIImage *gradientImage = UIGraphicsGetImageFromCurrentImageContext();
        UIGraphicsEndImageContext();
    
        CGGradientRelease(gradient);
        CGColorSpaceRelease(colorspace);
    
        return gradientImage;
    }
    
  2. 您还可以向视图添加CAGradientLayer,然后将UIImageView添加为该视图的子视图。

    - (void)addGradientLayerToView:(UIView *)view
    {
        CAGradientLayer *gradient = [CAGradientLayer layer];
        gradient.frame = view.bounds;
        gradient.colors = @[(id)[[UIColor colorWithRed:0.0 green:0.8 blue:0.8 alpha:1.0] CGColor],
                            (id)[[UIColor colorWithRed:0.9 green:0.9 blue:0.9 alpha:1.0] CGColor]];
        [view.layer insertSublayer:gradient atIndex:0];
    }
    

    注意,您必须#import <QuartzCore/QuartzCore.h>以及将QuartzCore框架添加到您的项目中。

答案 1 :(得分:1)

我最终乱砍了一些Rob的代码和我在http://coffeeshopped.com/2010/09/iphone-how-to-dynamically-color-a-uiimage找到的UIImage的扩展

+ (UIImage *)imageNamed:(NSString *)name withGradient:(CGGradientRef)gradient
{
    // load the image
    UIImage *img = [UIImage imageNamed:name];

    // begin a new image context, to draw our colored image onto
    UIGraphicsBeginImageContextWithOptions(img.size, NO, [[UIScreen mainScreen] scale]);

    // get a reference to that context we created
    CGContextRef context = UIGraphicsGetCurrentContext();

    // translate/flip the graphics context (for transforming from CG* coords to UI* coords
    CGContextTranslateCTM(context, 0, img.size.height);
    CGContextScaleCTM(context, 1.0, -1.0);

    // set the blend mode to overlay, and the original image
    CGContextSetBlendMode(context, kCGBlendModeOverlay);
    CGRect rect = CGRectMake(0, 0, img.size.width, img.size.height);

    // set a mask that matches the shape of the image, then draw (overlay) a colored rectangle
    CGContextClipToMask(context, rect, img.CGImage);
    CGContextAddRect(context, rect);

    //gradient
    CGPoint startPoint = CGPointMake(0.0, img.size.height);
    CGPoint endPoint   = CGPointMake(0.0, 0.0);
    CGContextDrawLinearGradient (context, gradient, startPoint, endPoint, 0);

    // generate a new UIImage from the graphics context we drew onto
    UIImage *coloredImg = UIGraphicsGetImageFromCurrentImageContext();
    UIGraphicsEndImageContext();
    CGGradientRelease(gradient);

    //return the color-burned image
    return coloredImg;

}