Search code examples
iosobjective-cuicolorobjective-c-categoryassociated-object

iOS: Grabbing An object's bounds for -colorWithPatternImage: in UIColor Category?


Is there a way to grab an object's bounds who's backgroundColor is being set in a UIColor category?

For example, I'm trying to apply a UIColor from an image, but I want it to be stretched out accordingly. Would associated references do the job? Or would it be best to implement such method in a UIView category?

Update:

Here is the method that sets the backgroundColor:

+ (UIColor *)colorWithGradientStyle:(GradientStyle)gradientStyle andColors:(NSArray *)colors {

//Create our background gradient layer
CAGradientLayer *backgroundGradientLayer = [CAGradientLayer layer];

//Set the frame to our object's bounds
backgroundGradientLayer.frame = CGRectMake(0, 0, self.bounds.size.width, self.bounds.size.height);

//To simplfy formatting, we'll iterate through our colors array and create a mutable array with their CG counterparts
NSMutableArray *cgColors = [[NSMutableArray alloc] init];
for (UIColor *color in colors) {
    [cgColors addObject:(id)[color CGColor]];
}

switch (gradientStyle) {
    case linearLeftToRight: {

        //Set out gradient's colors
        backgroundGradientLayer.colors = cgColors;

        //Specify the direction our gradient will take
        [backgroundGradientLayer setStartPoint:CGPointMake(0.0, 0.5)];
        [backgroundGradientLayer setEndPoint:CGPointMake(1.0, 0.5)];

        //Convert our CALayer to a UIImage object
        UIGraphicsBeginImageContext(backgroundGradientLayer.bounds.size);
        [backgroundGradientLayer renderInContext:UIGraphicsGetCurrentContext()];
        UIImage * backgroundColorImage = UIGraphicsGetImageFromCurrentImageContext();
        UIGraphicsEndImageContext();

        return [UIColor colorWithPatternImage:backgroundColorImage];
    }

    case linearTopToBottom:
    default: {

        //Set out gradient's colors
        backgroundGradientLayer.colors = cgColors;

        //Convert our CALayer to a UIImage object
        UIGraphicsBeginImageContext(backgroundGradientLayer.bounds.size);
        [backgroundGradientLayer renderInContext:UIGraphicsGetCurrentContext()];
        UIImage * backgroundColorImage = UIGraphicsGetImageFromCurrentImageContext();
        UIGraphicsEndImageContext();

        return [UIColor colorWithPatternImage:backgroundColorImage];
    }

}

}


Solution

  • No matter where you put this code, you will need a reference to the view to get its bounds. You can either pass the view or bounds as a parameter or put it a UIView category or subclass.

    The UIColor class is just for creating colors, it has nothing to do with rendering or positioning them. That is a job for UIView. Therefore UIColor is not the place for this code imho.

    I suggest subclassing UIView and overriding drawRect to draw a gradient. Or create a UIView method like: -(void)setBackgroundGradientWithStyle:(GradientStyle)gradientStyle colors:(NSArray *)colors and put this code there.