Re: Transparent Image with Tint Color
Re: Transparent Image with Tint Color
- Subject: Re: Transparent Image with Tint Color
- From: Kyle Sluder <email@hidden>
- Date: Sun, 29 Sep 2013 21:06:56 -0700
On Sep 29, 2013, at 7:37 PM, Paul Scott <email@hidden> wrote:
>
> On Sep 29, 2013, at 6:54 PM, Kyle Sluder <email@hidden> wrote:
>>
>>> How do I get an image rendered in the tint color?
>>
>> Start a bitmap context, set your template image as the image mask, set the full color to the appropriate tintColor, and fill the bounds of the context.
>>
>> Construct a data URI out of the image you get by closing the bitmap context.
>
>
> That works. Thanks. I was already heading down that path, since it seemed kind of obvious after thinking about it. Nevertheless, there are some strange and non-obvious dependencies that exist with various Cocoa and CG objects that aren't particularly well documented, such as [colorObject setFill]; I mean, what kind of magic happens there?
No magic. You could implement it yourself:
@implementation UIColor
- (void)setFill
{
CGContextSetFillColorWithColor(UIGraphicsGetCurrentContext(), self.CGColor);
}
@end
> Normally, I'd expect an instance method to operate on the receiver; but by this incantation the graphics context is involved.
It mimics the NSColor API, which is in turn reflective of the stack-based nature of the Postscript programming language which used to underlie the graphics system of the NeXT. In traditional PostScript, you push a color, then push the operator to select that color as the fill color.
There's only one graphics context in traditional Postscript; when Display Postscript was conceived, the concept of multiple graphics contexts was introduced by maintaining a stack of graphics contexts. This minimizes conflict with traditional PostScript because all operators affect the "current context" at the top of the stack.
Core Graphics doesn't need to maintain that compatibility; the API requires the programmer to specify the graphics context for every operation. CG _does_ maintain the idea of a stack of graphics states _within_ a context. AppKit and UIKit independently build the idea of a stack of _contexts_ atop Core Graphics. On the Mac, the interface is +[NSGraphicsContext currentContext]; on iOS, it's UIGraphicsGetCurrentContext().
>
> UIImage *image = [controller.infoIcon.image imageWithRenderingMode:UIImageRenderingModeAlwaysTemplate];
You don't need this anymore; the image data is not going to change. I doubt it will hurt all that much. If you want to build a reusable ImageByTintingTemplateImage() function out of your code, perhaps instead of creating a template version of the image, you could assert that the image is already a template; that puts the onus on the caller to verify (or at least emptily promise) that they're handing you the correct asset to be tinted.
> NSString *data = [UIImagePNGRepresentation(image) base64EncodedStringWithOptions:nil];
> [webView stringByEvaluatingJavaScriptFromString:
> [NSString stringWithFormat:@"%@%@%@",
> @"( function() {"
> @" var x = document.getElementById('infoIcon');"
> @" if ( !! x ) { "
> @" x.src = 'data:image/png;base64,", data, @"';"
> @" }"
> @"})();"
> ]
> ];
Rather than building up and executing a _very_ long JavaScript, would you be better off accessing the DOM directly?
--Kyle Sluder
_______________________________________________
Cocoa-dev mailing list (email@hidden)
Please do not post admin requests or moderator comments to the list.
Contact the moderators at cocoa-dev-admins(at)lists.apple.com
Help/Unsubscribe/Update your Subscription:
This email sent to email@hidden