/core/externals/google-toolbox-for-mac/iPhone/GTMFadeTruncatingLabel.m
Objective C | 131 lines | 89 code | 17 blank | 25 comment | 5 complexity | 0d411df232f4508e231c7147fb81b00b MD5 | raw file
1// 2// GTMFadeTruncatingLabel.m 3// 4// Copyright 2012 Google Inc. 5// 6// Licensed under the Apache License, Version 2.0 (the "License"); you may not 7// use this file except in compliance with the License. You may obtain a copy 8// of the License at 9// 10// http://www.apache.org/licenses/LICENSE-2.0 11// 12// Unless required by applicable law or agreed to in writing, software 13// distributed under the License is distributed on an "AS IS" BASIS, WITHOUT 14// WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. See the 15// License for the specific language governing permissions and limitations under 16// the License. 17// 18#import "GTMFadeTruncatingLabel.h" 19 20@interface GTMFadeTruncatingLabel () 21- (void)setup; 22@end 23 24@implementation GTMFadeTruncatingLabel 25 26@synthesize truncateMode = truncateMode_; 27 28- (void)setup { 29 self.backgroundColor = [UIColor clearColor]; 30 truncateMode_ = GTMFadeTruncatingTail; 31} 32 33- (id)initWithFrame:(CGRect)frame { 34 self = [super initWithFrame:frame]; 35 if (self) { 36 // Use clip as a default value. 37 self.lineBreakMode = NSLineBreakByClipping; 38 [self setup]; 39 } 40 return self; 41} 42 43- (void)awakeFromNib { 44 [self setup]; 45} 46 47// Draw fade gradient mask if text is wider than rect. 48- (void)drawTextInRect:(CGRect)requestedRect { 49 CGContextRef context = UIGraphicsGetCurrentContext(); 50 CGContextSaveGState(context); 51 52 CGSize size = [self.text sizeWithFont:self.font]; 53 if (size.width > requestedRect.size.width) { 54 UIImage* image = [[self class] 55 getLinearGradient:requestedRect 56 fadeHead:((self.truncateMode & GTMFadeTruncatingHead) > 0) 57 fadeTail:((self.truncateMode & GTMFadeTruncatingTail) > 0)]; 58 CGContextClipToMask(context, self.bounds, image.CGImage); 59 } 60 61 if (self.shadowColor) { 62 CGContextSetFillColorWithColor(context, self.shadowColor.CGColor); 63 CGRect shadowRect = CGRectOffset(requestedRect, self.shadowOffset.width, 64 self.shadowOffset.height); 65 [self.text drawInRect:shadowRect 66 withFont:self.font 67 lineBreakMode:self.lineBreakMode 68 alignment:self.textAlignment]; 69 } 70 71 CGContextSetFillColorWithColor(context, self.textColor.CGColor); 72 [self.text drawInRect:requestedRect 73 withFont:self.font 74 lineBreakMode:self.lineBreakMode 75 alignment:self.textAlignment]; 76 77 CGContextRestoreGState(context); 78} 79 80// Create gradient opacity mask based on direction. 81+ (UIImage*)getLinearGradient:(CGRect)rect 82 fadeHead:(BOOL)fadeHead 83 fadeTail:(BOOL)fadeTail { 84 // Create an opaque context. 85 CGColorSpaceRef colorSpace = CGColorSpaceCreateDeviceGray(); 86 CGContextRef context = CGBitmapContextCreate(NULL, 87 rect.size.width, 88 rect.size.height, 89 8, 90 4*rect.size.width, 91 colorSpace, 92 (CGBitmapInfo)kCGImageAlphaNone); 93 94 // White background will mask opaque, black gradient will mask transparent. 95 CGContextSetFillColorWithColor(context, [UIColor whiteColor].CGColor); 96 CGContextFillRect(context, rect); 97 98 // Create gradient from white to black. 99 CGFloat locs[2] = { 0.0f, 1.0f }; 100 CGFloat components[4] = { 1.0f, 1.0f, 0.0f, 1.0f }; 101 CGGradientRef gradient = 102 CGGradientCreateWithColorComponents(colorSpace, components, locs, 2); 103 CGColorSpaceRelease(colorSpace); 104 105 // Draw head and/or tail gradient. 106 CGFloat fadeWidth = MIN(rect.size.height * 2, floor(rect.size.width / 4)); 107 CGFloat minX = CGRectGetMinX(rect); 108 CGFloat maxX = CGRectGetMaxX(rect); 109 if (fadeTail) { 110 CGFloat startX = maxX - fadeWidth; 111 CGPoint startPoint = CGPointMake(startX, CGRectGetMidY(rect)); 112 CGPoint endPoint = CGPointMake(maxX, CGRectGetMidY(rect)); 113 CGContextDrawLinearGradient(context, gradient, startPoint, endPoint, 0); 114 } 115 if (fadeHead) { 116 CGFloat startX = minX + fadeWidth; 117 CGPoint startPoint = CGPointMake(startX, CGRectGetMidY(rect)); 118 CGPoint endPoint = CGPointMake(minX, CGRectGetMidY(rect)); 119 CGContextDrawLinearGradient(context, gradient, startPoint, endPoint, 0); 120 } 121 CGGradientRelease(gradient); 122 123 // Clean up, return image. 124 CGImageRef ref = CGBitmapContextCreateImage(context); 125 UIImage* image = [UIImage imageWithCGImage:ref]; 126 CGImageRelease(ref); 127 CGContextRelease(context); 128 return image; 129} 130 131@end