/core/externals/google-toolbox-for-mac/iPhone/GTMFadeTruncatingLabel.m

http://macfuse.googlecode.com/ · 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. @interface GTMFadeTruncatingLabel ()
  20. - (void)setup;
  21. @end
  22. @implementation GTMFadeTruncatingLabel
  23. @synthesize truncateMode = truncateMode_;
  24. - (void)setup {
  25. self.backgroundColor = [UIColor clearColor];
  26. truncateMode_ = GTMFadeTruncatingTail;
  27. }
  28. - (id)initWithFrame:(CGRect)frame {
  29. self = [super initWithFrame:frame];
  30. if (self) {
  31. // Use clip as a default value.
  32. self.lineBreakMode = NSLineBreakByClipping;
  33. [self setup];
  34. }
  35. return self;
  36. }
  37. - (void)awakeFromNib {
  38. [self setup];
  39. }
  40. // Draw fade gradient mask if text is wider than rect.
  41. - (void)drawTextInRect:(CGRect)requestedRect {
  42. CGContextRef context = UIGraphicsGetCurrentContext();
  43. CGContextSaveGState(context);
  44. CGSize size = [self.text sizeWithFont:self.font];
  45. if (size.width > requestedRect.size.width) {
  46. UIImage* image = [[self class]
  47. getLinearGradient:requestedRect
  48. fadeHead:((self.truncateMode & GTMFadeTruncatingHead) > 0)
  49. fadeTail:((self.truncateMode & GTMFadeTruncatingTail) > 0)];
  50. CGContextClipToMask(context, self.bounds, image.CGImage);
  51. }
  52. if (self.shadowColor) {
  53. CGContextSetFillColorWithColor(context, self.shadowColor.CGColor);
  54. CGRect shadowRect = CGRectOffset(requestedRect, self.shadowOffset.width,
  55. self.shadowOffset.height);
  56. [self.text drawInRect:shadowRect
  57. withFont:self.font
  58. lineBreakMode:self.lineBreakMode
  59. alignment:self.textAlignment];
  60. }
  61. CGContextSetFillColorWithColor(context, self.textColor.CGColor);
  62. [self.text drawInRect:requestedRect
  63. withFont:self.font
  64. lineBreakMode:self.lineBreakMode
  65. alignment:self.textAlignment];
  66. CGContextRestoreGState(context);
  67. }
  68. // Create gradient opacity mask based on direction.
  69. + (UIImage*)getLinearGradient:(CGRect)rect
  70. fadeHead:(BOOL)fadeHead
  71. fadeTail:(BOOL)fadeTail {
  72. // Create an opaque context.
  73. CGColorSpaceRef colorSpace = CGColorSpaceCreateDeviceGray();
  74. CGContextRef context = CGBitmapContextCreate(NULL,
  75. rect.size.width,
  76. rect.size.height,
  77. 8,
  78. 4*rect.size.width,
  79. colorSpace,
  80. (CGBitmapInfo)kCGImageAlphaNone);
  81. // White background will mask opaque, black gradient will mask transparent.
  82. CGContextSetFillColorWithColor(context, [UIColor whiteColor].CGColor);
  83. CGContextFillRect(context, rect);
  84. // Create gradient from white to black.
  85. CGFloat locs[2] = { 0.0f, 1.0f };
  86. CGFloat components[4] = { 1.0f, 1.0f, 0.0f, 1.0f };
  87. CGGradientRef gradient =
  88. CGGradientCreateWithColorComponents(colorSpace, components, locs, 2);
  89. CGColorSpaceRelease(colorSpace);
  90. // Draw head and/or tail gradient.
  91. CGFloat fadeWidth = MIN(rect.size.height * 2, floor(rect.size.width / 4));
  92. CGFloat minX = CGRectGetMinX(rect);
  93. CGFloat maxX = CGRectGetMaxX(rect);
  94. if (fadeTail) {
  95. CGFloat startX = maxX - fadeWidth;
  96. CGPoint startPoint = CGPointMake(startX, CGRectGetMidY(rect));
  97. CGPoint endPoint = CGPointMake(maxX, CGRectGetMidY(rect));
  98. CGContextDrawLinearGradient(context, gradient, startPoint, endPoint, 0);
  99. }
  100. if (fadeHead) {
  101. CGFloat startX = minX + fadeWidth;
  102. CGPoint startPoint = CGPointMake(startX, CGRectGetMidY(rect));
  103. CGPoint endPoint = CGPointMake(minX, CGRectGetMidY(rect));
  104. CGContextDrawLinearGradient(context, gradient, startPoint, endPoint, 0);
  105. }
  106. CGGradientRelease(gradient);
  107. // Clean up, return image.
  108. CGImageRef ref = CGBitmapContextCreateImage(context);
  109. UIImage* image = [UIImage imageWithCGImage:ref];
  110. CGImageRelease(ref);
  111. CGContextRelease(context);
  112. return image;
  113. }
  114. @end