From 3068b78ccc89a661fe9fbb58f4b75b23b2c81a3b Mon Sep 17 00:00:00 2001 From: Jeremy Foo Date: Fri, 4 May 2012 03:27:54 +0800 Subject: [PATCH 01/48] added more generic shadow drawing --- PrettyKit/PrettyDrawing.h | 6 ++++++ PrettyKit/PrettyDrawing.m | 10 ++++++++-- 2 files changed, 14 insertions(+), 2 deletions(-) diff --git a/PrettyKit/PrettyDrawing.h b/PrettyKit/PrettyDrawing.h index bff338e..855fb94 100644 --- a/PrettyKit/PrettyDrawing.h +++ b/PrettyKit/PrettyDrawing.h @@ -79,6 +79,12 @@ typedef enum { */ - (void) dropShadowWithOpacity:(float)opacity; +/** Drops a shadow with the given opacity and offset. + + @warning This method uses the UILayer shadow properties. + */ +- (void) dropShadowOffset:(CGSize)offset WithOpacity:(float)opacity; + @end diff --git a/PrettyKit/PrettyDrawing.m b/PrettyKit/PrettyDrawing.m index 8850915..ec8a627 100644 --- a/PrettyKit/PrettyDrawing.m +++ b/PrettyKit/PrettyDrawing.m @@ -119,13 +119,19 @@ + (void) drawGradient:(CGGradientRef)gradient rect:(CGRect)rect @implementation UIView (PrettyKit) -- (void) dropShadowWithOpacity:(float)opacity { +- (void) dropShadowOffset:(CGSize)offset WithOpacity:(float)opacity { self.layer.masksToBounds = NO; - self.layer.shadowOffset = CGSizeMake(0, 0); + self.layer.shadowOffset = offset; self.layer.shadowOpacity = opacity; self.layer.shadowPath = [UIBezierPath bezierPathWithRect:self.bounds].CGPath; } +- (void) dropShadowWithOpacity:(float)opacity { + [self dropShadowOffset:CGSizeMake(0, 0) WithOpacity:opacity]; + +} + + @end From 7ad0d8fd9525bf56ea18e5f938bd23e74786b99c Mon Sep 17 00:00:00 2001 From: Jeremy Foo Date: Fri, 4 May 2012 03:28:12 +0800 Subject: [PATCH 02/48] alignment for default shadow opacity --- PrettyKit/PrettyNavigationBar.m | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/PrettyKit/PrettyNavigationBar.m b/PrettyKit/PrettyNavigationBar.m index b53d2a1..5bc58e1 100644 --- a/PrettyKit/PrettyNavigationBar.m +++ b/PrettyKit/PrettyNavigationBar.m @@ -36,7 +36,7 @@ @implementation PrettyNavigationBar @synthesize shadowOpacity, gradientEndColor, gradientStartColor, topLineColor, bottomLineColor, roundedCornerRadius, roundedCornerColor; -#define default_shadow_opacity 0.5 +#define default_shadow_opacity 0.5 #define default_gradient_end_color [UIColor colorWithHex:0x297CB7] #define default_gradient_start_color [UIColor colorWithHex:0x53A4DE] #define default_top_line_color [UIColor colorWithHex:0x84B7D5] From 9c5232b9127191f87ecec04e3bb2bd194e649cd0 Mon Sep 17 00:00:00 2001 From: Jeremy Foo Date: Fri, 4 May 2012 03:31:33 +0800 Subject: [PATCH 03/48] pretty tab bar now draws an upwards and downwards shadow --- PrettyKit/PrettyTabBar.h | 10 ++++++++++ PrettyKit/PrettyTabBar.m | 14 ++++++++++---- 2 files changed, 20 insertions(+), 4 deletions(-) diff --git a/PrettyKit/PrettyTabBar.h b/PrettyKit/PrettyTabBar.h index e20260f..e751883 100644 --- a/PrettyKit/PrettyTabBar.h +++ b/PrettyKit/PrettyTabBar.h @@ -43,6 +43,16 @@ */ @interface PrettyTabBar : UITabBar +/** Specifies the navigation bar upwards shadow's opacity. + + By default is `0.5`. */ +@property (nonatomic, assign) float upwardsShadowOpacity; + +/** Specifies the navigation bar downwards shadow's opacity. + + By default is `0.5`. */ +@property (nonatomic, assign) float downwardsShadowOpacity; + /** Specifies the gradient's start color. By default is a black tone. */ diff --git a/PrettyKit/PrettyTabBar.m b/PrettyKit/PrettyTabBar.m index 3bf8514..acb90d0 100644 --- a/PrettyKit/PrettyTabBar.m +++ b/PrettyKit/PrettyTabBar.m @@ -30,12 +30,14 @@ #import "PrettyTabBar.h" #import "PrettyDrawing.h" -#define default_gradient_start_color [UIColor colorWithHex:0x444444] -#define default_gradient_end_color [UIColor colorWithHex:0x060606] -#define default_separator_line_color [UIColor colorWithHex:0x666666] +#define default_upwards_shadow_opacity 0.5 +#define default_downwards_shadow_opacity 0.5 +#define default_gradient_start_color [UIColor colorWithHex:0x444444] +#define default_gradient_end_color [UIColor colorWithHex:0x060606] +#define default_separator_line_color [UIColor colorWithHex:0x666666] @implementation PrettyTabBar -@synthesize gradientStartColor, gradientEndColor, separatorLineColor; +@synthesize upwardsShadowOpacity, downwardsShadowOpacity, gradientStartColor, gradientEndColor, separatorLineColor; - (void) dealloc { self.gradientStartColor = nil; @@ -49,6 +51,8 @@ - (void) initializeVars { self.contentMode = UIViewContentModeRedraw; + self.upwardsShadowOpacity = default_upwards_shadow_opacity; + self.downwardsShadowOpacity = default_downwards_shadow_opacity; self.gradientStartColor = default_gradient_start_color; self.gradientEndColor = default_gradient_end_color; self.separatorLineColor = default_separator_line_color; @@ -83,6 +87,8 @@ - (id)init { - (void) drawRect:(CGRect)rect { [super drawRect:rect]; + [self dropShadowOffset:CGSizeMake(0, -1) withOpacity:self.upwardsShadowOpacity]; + [self dropShadowOffset:CGSizeMake(0, 0) withOpacity:self.downwardsShadowOpacity]; [PrettyDrawing drawGradient:rect fromColor:self.gradientStartColor toColor:self.gradientEndColor]; [PrettyDrawing drawLineAtHeight:0.5 rect:rect color:self.separatorLineColor width:2.5]; } From 43f40e53cafe5d93ba72fcfa0d98ba2aa348af87 Mon Sep 17 00:00:00 2001 From: Jeremy Foo Date: Fri, 4 May 2012 03:32:29 +0800 Subject: [PATCH 04/48] renamed selector to fit camel case --- PrettyKit/PrettyDrawing.h | 2 +- PrettyKit/PrettyDrawing.m | 4 ++-- 2 files changed, 3 insertions(+), 3 deletions(-) diff --git a/PrettyKit/PrettyDrawing.h b/PrettyKit/PrettyDrawing.h index 855fb94..938fd1b 100644 --- a/PrettyKit/PrettyDrawing.h +++ b/PrettyKit/PrettyDrawing.h @@ -83,7 +83,7 @@ typedef enum { @warning This method uses the UILayer shadow properties. */ -- (void) dropShadowOffset:(CGSize)offset WithOpacity:(float)opacity; +- (void) dropShadowOffset:(CGSize)offset withOpacity:(float)opacity; @end diff --git a/PrettyKit/PrettyDrawing.m b/PrettyKit/PrettyDrawing.m index ec8a627..ee3e5a3 100644 --- a/PrettyKit/PrettyDrawing.m +++ b/PrettyKit/PrettyDrawing.m @@ -119,7 +119,7 @@ + (void) drawGradient:(CGGradientRef)gradient rect:(CGRect)rect @implementation UIView (PrettyKit) -- (void) dropShadowOffset:(CGSize)offset WithOpacity:(float)opacity { +- (void) dropShadowOffset:(CGSize)offset withOpacity:(float)opacity { self.layer.masksToBounds = NO; self.layer.shadowOffset = offset; self.layer.shadowOpacity = opacity; @@ -127,7 +127,7 @@ - (void) dropShadowOffset:(CGSize)offset WithOpacity:(float)opacity { } - (void) dropShadowWithOpacity:(float)opacity { - [self dropShadowOffset:CGSizeMake(0, 0) WithOpacity:opacity]; + [self dropShadowOffset:CGSizeMake(0, 0) withOpacity:opacity]; } From 135484e4bb54287ce1a06fad9579eda6819d63e9 Mon Sep 17 00:00:00 2001 From: Jeremy Foo Date: Fri, 4 May 2012 03:33:13 +0800 Subject: [PATCH 05/48] don't draw if opacity is 0. --- PrettyKit/PrettyTabBar.m | 8 ++++++-- 1 file changed, 6 insertions(+), 2 deletions(-) diff --git a/PrettyKit/PrettyTabBar.m b/PrettyKit/PrettyTabBar.m index acb90d0..195cbe4 100644 --- a/PrettyKit/PrettyTabBar.m +++ b/PrettyKit/PrettyTabBar.m @@ -87,8 +87,12 @@ - (id)init { - (void) drawRect:(CGRect)rect { [super drawRect:rect]; - [self dropShadowOffset:CGSizeMake(0, -1) withOpacity:self.upwardsShadowOpacity]; - [self dropShadowOffset:CGSizeMake(0, 0) withOpacity:self.downwardsShadowOpacity]; + if (self.upwardsShadowOpacity > 0) + [self dropShadowOffset:CGSizeMake(0, -1) withOpacity:self.upwardsShadowOpacity]; + + if (self.downwardsShadowOpacity > 0) + [self dropShadowOffset:CGSizeMake(0, 0) withOpacity:self.downwardsShadowOpacity]; + [PrettyDrawing drawGradient:rect fromColor:self.gradientStartColor toColor:self.gradientEndColor]; [PrettyDrawing drawLineAtHeight:0.5 rect:rect color:self.separatorLineColor width:2.5]; } From e9e79f0ec8d84ebaf3523bac5ffef74fb7725d79 Mon Sep 17 00:00:00 2001 From: Jeremy Foo Date: Fri, 4 May 2012 18:31:04 +0800 Subject: [PATCH 06/48] initial skeleton for PrettyTabBarButton --- PrettyKit/PrettyTabBarButton.h | 45 ++++++++++++++ PrettyKit/PrettyTabBarButton.m | 104 +++++++++++++++++++++++++++++++++ 2 files changed, 149 insertions(+) create mode 100644 PrettyKit/PrettyTabBarButton.h create mode 100644 PrettyKit/PrettyTabBarButton.m diff --git a/PrettyKit/PrettyTabBarButton.h b/PrettyKit/PrettyTabBarButton.h new file mode 100644 index 0000000..a9c2c6f --- /dev/null +++ b/PrettyKit/PrettyTabBarButton.h @@ -0,0 +1,45 @@ +// +// PrettyTabBarButton.h +// PrettyExample +// +// Created by Jeremy Foo on 4/5/12. + +// Copyright (c) 2012 Jeremy Foo. (@echoz) +// http://ornyx.net +// +// Permission is hereby granted, free of charge, to any person obtaining a copy of +// this software and associated documentation files (the "Software"), to deal in +// the Software without restriction, including without limitation the rights to +// use, copy, modify, merge, publish, distribute, sublicense, and/or sell copies of +// the Software, and to permit persons to whom the Software is furnished to do so, +// subject to the following conditions: +// +// The above copyright notice and this permission notice shall be included in all +// copies or substantial portions of the Software. +// +// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR +// IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, +// FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE +// AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER +// LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, +// OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE +// SOFTWARE. + +#import + +@interface PrettyTabBarButton : UIView + +@property (nonatomic, copy) NSString *title; +@property (nonatomic, retain) UIImage *image; +@property (nonatomic, copy) NSString *badgeValue; + +@property (nonatomic) BOOL selected; + +@property (nonatomic, retain) UIColor *textColor; +@property (nonatomic, retain) UIColor *highlightedTextColor; + +@property (nonatomic, retain) UIImage *highlightedImage; + +-(id)initWithTitle:(NSString *)title image:(UIImage *)image; + +@end diff --git a/PrettyKit/PrettyTabBarButton.m b/PrettyKit/PrettyTabBarButton.m new file mode 100644 index 0000000..22d966e --- /dev/null +++ b/PrettyKit/PrettyTabBarButton.m @@ -0,0 +1,104 @@ +// +// PrettyTabBarButton.m +// PrettyExample +// +// Created by Jeremy Foo on 4/5/12. + +// Copyright (c) 2012 Jeremy Foo. (@echoz) +// http://ornyx.net +// +// Permission is hereby granted, free of charge, to any person obtaining a copy of +// this software and associated documentation files (the "Software"), to deal in +// the Software without restriction, including without limitation the rights to +// use, copy, modify, merge, publish, distribute, sublicense, and/or sell copies of +// the Software, and to permit persons to whom the Software is furnished to do so, +// subject to the following conditions: +// +// The above copyright notice and this permission notice shall be included in all +// copies or substantial portions of the Software. +// +// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR +// IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, +// FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE +// AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER +// LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, +// OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE +// SOFTWARE. + +#import "PrettyTabBarButton.h" +#import "PrettyDrawing.h" + +#define default_text_color [UIColor colorWithWhite:0.20 alpha:1.0] +#define default_highlighted_text_color [UIColor colorWithWhite:8.20 alpha:1.0] + +@implementation PrettyTabBarButton +@synthesize title = _title, image = _image, badgeValue = _badgeValue; +@synthesize selected = _selected; +@synthesize textColor, highlightedTextColor, highlightedImage; + +-(id)initWithTitle:(NSString *)title image:(UIImage *)image { + if ((self = [super init])) { + [self initializeVars]; + + self.title = title; + self.image = image; + + } + return self; +} + +-(id)init { + if ((self = [super init])) { + [self initializeVars]; + } + + return self; +} + +-(id)initWithFrame:(CGRect)frame { + if ((self = [super initWithFrame:frame])) { + [self initializeVars]; + } + return self; +} + +-(id)initWithCoder:(NSCoder *)aDecoder { + if ((self = [super initWithCoder:aDecoder])) { + [self initializeVars]; + } + return self; +} + +-(void)dealloc { + [_title release], _title = nil; + [_image release], _image = nil; + [_badgeValue release], _badgeValue = nil; + + [super dealloc]; +} + +- (void) initializeVars +{ + self.contentMode = UIViewContentModeRedraw; + + self.title = nil; + self.image = nil; + self.badgeValue = nil; + + self.selected = NO; + + self.textColor = default_text_color; + self.highlightedTextColor = default_highlighted_text_color; + self.highlightedImage = nil; + + self.opaque = NO; + self.backgroundColor = [UIColor clearColor]; + +} + +- (void)drawRect:(CGRect)rect +{ + [super drawRect:rect]; +} + +@end From 6580196fbfbc6ae64e28d3cf942c5b881664a1d5 Mon Sep 17 00:00:00 2001 From: Jeremy Foo Date: Sat, 5 May 2012 00:04:17 +0800 Subject: [PATCH 07/48] Set a mode to use PrettyTabBarButtons instead of UITabBarButtons. This uses an internal representation as well as reflecting it in the view hierarchy to allow more configurable tab bar buttons. --- PrettyKit/PrettyTabBar.h | 7 +++ PrettyKit/PrettyTabBar.m | 117 ++++++++++++++++++++++++++++++++++++++- 2 files changed, 123 insertions(+), 1 deletion(-) diff --git a/PrettyKit/PrettyTabBar.h b/PrettyKit/PrettyTabBar.h index e751883..ae82ec8 100644 --- a/PrettyKit/PrettyTabBar.h +++ b/PrettyKit/PrettyTabBar.h @@ -68,4 +68,11 @@ By default is a black tone. */ @property (nonatomic, retain) UIColor *separatorLineColor; +/** Specifies that PrettyTabBarButtons should be used instead of the + default UITabBarButtons + + By default is NO. */ +@property (nonatomic) BOOL prettyTabBarButtons; + + @end diff --git a/PrettyKit/PrettyTabBar.m b/PrettyKit/PrettyTabBar.m index 195cbe4..18966f2 100644 --- a/PrettyKit/PrettyTabBar.m +++ b/PrettyKit/PrettyTabBar.m @@ -29,6 +29,7 @@ #import "PrettyTabBar.h" #import "PrettyDrawing.h" +#import "PrettyTabBarButton.h" #define default_upwards_shadow_opacity 0.5 #define default_downwards_shadow_opacity 0.5 @@ -36,14 +37,28 @@ #define default_gradient_end_color [UIColor colorWithHex:0x060606] #define default_separator_line_color [UIColor colorWithHex:0x666666] +@interface PrettyTabBar (/* Private Methods */) +@property (nonatomic, retain) NSMutableArray *_prettyTabBarButtons; +@property (nonatomic, retain) NSMutableArray *_originalTabBarButtons; +-(void)_prettyTabButtonTapped:(UIGestureRecognizer *)gestureRecognizer; +@end + @implementation PrettyTabBar @synthesize upwardsShadowOpacity, downwardsShadowOpacity, gradientStartColor, gradientEndColor, separatorLineColor; +@synthesize prettyTabBarButtons = _prettyTabBarItems; + +@synthesize _prettyTabBarButtons = __prettyTabBarButtons, _originalTabBarButtons = __originalTabBarButtons; + +#pragma mark - Object Life Cycle - (void) dealloc { self.gradientStartColor = nil; self.gradientEndColor = nil; self.separatorLineColor = nil; + self._originalTabBarButtons = nil; + self._prettyTabBarButtons = nil; + [super dealloc]; } @@ -51,11 +66,16 @@ - (void) initializeVars { self.contentMode = UIViewContentModeRedraw; + self.prettyTabBarButtons = NO; + self.upwardsShadowOpacity = default_upwards_shadow_opacity; self.downwardsShadowOpacity = default_downwards_shadow_opacity; self.gradientStartColor = default_gradient_start_color; self.gradientEndColor = default_gradient_end_color; self.separatorLineColor = default_separator_line_color; + + __prettyTabBarButtons = [[NSMutableArray arrayWithCapacity:5] retain]; + __originalTabBarButtons = [[NSMutableArray arrayWithCapacity:0] retain]; } - (id)initWithCoder:(NSCoder *)coder { @@ -83,10 +103,105 @@ - (id)init { return self; } +#pragma mark - Overrides to handle internal PrettyTabBarButton if mode is set + +-(void)setPrettyTabBarItems:(BOOL)prettyTabBarItems { + + _prettyTabBarItems = prettyTabBarItems; + + for (UIView *view in __originalTabBarButtons) { + [self addSubview:view]; + } + + [__originalTabBarButtons removeAllObjects]; + + [self setNeedsLayout]; +} + +-(void)setSelectedItem:(UITabBarItem *)selectedItem { + if (self.prettyTabBarButtons) { + // do stuff + NSInteger index = [self.items indexOfObject:selectedItem]; + + for (int i=0;i<[__prettyTabBarButtons count];i++) { + if (i != index) { + ((PrettyTabBarButton *)[__prettyTabBarButtons objectAtIndex:i]).selected = NO; + } else { + ((PrettyTabBarButton *)[__prettyTabBarButtons objectAtIndex:i]).selected = YES; + } + } + + if ([self.delegate respondsToSelector:@selector(tabBar:didSelectItem:)]) { + [self.delegate tabBar:self didSelectItem:[self.items objectAtIndex:index]]; + } + + } else { + [super setSelectedItem:selectedItem]; + } + +} + +-(void)_prettyTabButtonTapped:(UIGestureRecognizer *)gestureRecognizer { + NSInteger index = gestureRecognizer.view.tag; + [self setSelectedItem:[self.items objectAtIndex:index]]; +} + +#pragma mark - Display + +-(void)layoutSubviews { + [super layoutSubviews]; + + if ([self.items count] > 5) + self.prettyTabBarButtons = NO; + + for (UIView *view in self.subviews) { + + if (self.prettyTabBarButtons) { + if (![view isKindOfClass:[PrettyTabBarButton class]]) { + [__originalTabBarButtons addObject:view]; + } + [view removeFromSuperview]; + } else { + if ([view isKindOfClass:[PrettyTabBarButton class]]) { + [view removeFromSuperview]; + } + } + } + + if (self.prettyTabBarButtons) { + + if (self.prettyTabBarButtons) { + [__prettyTabBarButtons removeAllObjects]; + + // do stuff + PrettyTabBarButton *button = nil; + UITabBarItem *item = nil; + + CGFloat itemWidth = self.frame.size.width/[self.items count]; + + for (int i=0;i<[self.items count];i++) { + item = [self.items objectAtIndex:i]; + button = [[PrettyTabBarButton alloc] initWithTitle:item.title image:item.image tag:i]; + button.frame = CGRectMake(i * itemWidth, 0, itemWidth, self.frame.size.height); + button.autoresizingMask = UIViewAutoresizingFlexibleHeight | UIViewAutoresizingFlexibleWidth; + + UITapGestureRecognizer *tappedButton = [[UITapGestureRecognizer alloc] initWithTarget:self action:@selector(_prettyTabButtonTapped:)]; + tappedButton.numberOfTapsRequired = 1; + [button addGestureRecognizer:tappedButton]; + [tappedButton release]; + + [self addSubview:button]; + [__prettyTabBarButtons addObject:button]; + [button release]; + } + } + } + +} - (void) drawRect:(CGRect)rect { [super drawRect:rect]; - + if (self.upwardsShadowOpacity > 0) [self dropShadowOffset:CGSizeMake(0, -1) withOpacity:self.upwardsShadowOpacity]; From 92dec25b05e30ebfb429fae527a0331e79cfc960 Mon Sep 17 00:00:00 2001 From: Jeremy Foo Date: Sat, 5 May 2012 00:06:17 +0800 Subject: [PATCH 08/48] added PrettyTabBarButton class --- PrettyExample.xcodeproj/project.pbxproj | 6 ++++++ 1 file changed, 6 insertions(+) diff --git a/PrettyExample.xcodeproj/project.pbxproj b/PrettyExample.xcodeproj/project.pbxproj index 411245f..576164b 100644 --- a/PrettyExample.xcodeproj/project.pbxproj +++ b/PrettyExample.xcodeproj/project.pbxproj @@ -7,6 +7,7 @@ objects = { /* Begin PBXBuildFile section */ + 3F8D2269155435E40042B767 /* PrettyTabBarButton.m in Sources */ = {isa = PBXBuildFile; fileRef = 3F8D2268155435E40042B767 /* PrettyTabBarButton.m */; }; 572B2E6615348E1B0002228B /* RotableTabBarController.m in Sources */ = {isa = PBXBuildFile; fileRef = 572B2E6515348E1B0002228B /* RotableTabBarController.m */; }; 572B2E6A153496880002228B /* background.png in Resources */ = {isa = PBXBuildFile; fileRef = 572B2E68153496870002228B /* background.png */; }; 572B2E6B153496880002228B /* background@2x.png in Resources */ = {isa = PBXBuildFile; fileRef = 572B2E69153496870002228B /* background@2x.png */; }; @@ -36,6 +37,8 @@ /* End PBXBuildFile section */ /* Begin PBXFileReference section */ + 3F8D2267155435E40042B767 /* PrettyTabBarButton.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = PrettyTabBarButton.h; sourceTree = ""; }; + 3F8D2268155435E40042B767 /* PrettyTabBarButton.m */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.objc; path = PrettyTabBarButton.m; sourceTree = ""; }; 572B2E6415348E1B0002228B /* RotableTabBarController.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = RotableTabBarController.h; sourceTree = ""; }; 572B2E6515348E1B0002228B /* RotableTabBarController.m */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.objc; path = RotableTabBarController.m; sourceTree = ""; }; 572B2E68153496870002228B /* background.png */ = {isa = PBXFileReference; lastKnownFileType = image.png; path = background.png; sourceTree = ""; }; @@ -174,6 +177,8 @@ 578998C01535E02000E06FCA /* PrettyShadowPlainTableview.m */, 578998C11535E02000E06FCA /* PrettyTabBar.h */, 578998C21535E02000E06FCA /* PrettyTabBar.m */, + 3F8D2267155435E40042B767 /* PrettyTabBarButton.h */, + 3F8D2268155435E40042B767 /* PrettyTabBarButton.m */, EDA7DCAF1548EBD1002219BA /* PrettyToolbar.h */, EDA7DCB01548EBD1002219BA /* PrettyToolbar.m */, ); @@ -277,6 +282,7 @@ 578998CB1535E02000E06FCA /* PrettyTabBar.m in Sources */, EDA7DCB11548EBD1002219BA /* PrettyToolbar.m in Sources */, EDA7DCB61548ED3F002219BA /* ModalViewController.m in Sources */, + 3F8D2269155435E40042B767 /* PrettyTabBarButton.m in Sources */, ); runOnlyForDeploymentPostprocessing = 0; }; From 5c88dfc1d9fb4b402a8e9a428efc81a53ce2c1e1 Mon Sep 17 00:00:00 2001 From: Jeremy Foo Date: Sat, 5 May 2012 00:15:51 +0800 Subject: [PATCH 09/48] some text drawing options plus drawing of text in the correct spot --- PrettyKit/PrettyTabBarButton.h | 7 ++++- PrettyKit/PrettyTabBarButton.m | 52 +++++++++++++++++++++++++++++----- 2 files changed, 51 insertions(+), 8 deletions(-) diff --git a/PrettyKit/PrettyTabBarButton.h b/PrettyKit/PrettyTabBarButton.h index a9c2c6f..d7e5901 100644 --- a/PrettyKit/PrettyTabBarButton.h +++ b/PrettyKit/PrettyTabBarButton.h @@ -35,11 +35,16 @@ @property (nonatomic) BOOL selected; +@property (nonatomic, retain) UIFont *font; @property (nonatomic, retain) UIColor *textColor; @property (nonatomic, retain) UIColor *highlightedTextColor; +@property (readwrite) CGFloat textShadowOpacity; +@property (readwrite) CGSize textShadowOffset; +@property (readwrite) BOOL wantTextShadow; + @property (nonatomic, retain) UIImage *highlightedImage; --(id)initWithTitle:(NSString *)title image:(UIImage *)image; +-(id)initWithTitle:(NSString *)title image:(UIImage *)image tag:(NSInteger)tag; @end diff --git a/PrettyKit/PrettyTabBarButton.m b/PrettyKit/PrettyTabBarButton.m index 22d966e..b3c10bc 100644 --- a/PrettyKit/PrettyTabBarButton.m +++ b/PrettyKit/PrettyTabBarButton.m @@ -28,18 +28,24 @@ #import "PrettyTabBarButton.h" #import "PrettyDrawing.h" +#define default_want_text_shadow YES +#define default_text_shadow_offset CGSizeMake(0,1) +#define default_text_shadow_opacity 0.5 +#define default_font [UIFont fontWithName:@"HelveticaNeue-Bold" size:11] #define default_text_color [UIColor colorWithWhite:0.20 alpha:1.0] -#define default_highlighted_text_color [UIColor colorWithWhite:8.20 alpha:1.0] +#define default_highlighted_text_color [UIColor colorWithWhite:0.80 alpha:1.0] @implementation PrettyTabBarButton @synthesize title = _title, image = _image, badgeValue = _badgeValue; @synthesize selected = _selected; -@synthesize textColor, highlightedTextColor, highlightedImage; +@synthesize textColor, font, highlightedTextColor, highlightedImage; +@synthesize wantTextShadow, textShadowOpacity, textShadowOffset; --(id)initWithTitle:(NSString *)title image:(UIImage *)image { +-(id)initWithTitle:(NSString *)title image:(UIImage *)image tag:(NSInteger)tag { if ((self = [super init])) { [self initializeVars]; + self.tag = tag; self.title = title; self.image = image; @@ -81,24 +87,56 @@ - (void) initializeVars { self.contentMode = UIViewContentModeRedraw; + // default configuration + self.font = default_font; + self.textColor = default_text_color; + self.highlightedTextColor = default_highlighted_text_color; + self.highlightedImage = nil; + self.wantTextShadow = default_want_text_shadow; + self.textShadowOpacity = default_text_shadow_opacity; + self.textShadowOffset = default_text_shadow_offset; + + // intialize values; + self.tag = -1; + self.title = nil; self.image = nil; self.badgeValue = nil; self.selected = NO; - self.textColor = default_text_color; - self.highlightedTextColor = default_highlighted_text_color; - self.highlightedImage = nil; - self.opaque = NO; self.backgroundColor = [UIColor clearColor]; } +-(void)setSelected:(BOOL)selected { + _selected = selected; + [self setNeedsDisplay]; +} + - (void)drawRect:(CGRect)rect { [super drawRect:rect]; + + CGContextRef context = UIGraphicsGetCurrentContext(); + + CGContextSaveGState(context); + + if (self.wantTextShadow) { + CGContextSetShadow(context, self.textShadowOffset, self.textShadowOpacity); + } + + if (self.selected) { + [self.highlightedTextColor setFill]; + } else { + [self.textColor setFill]; + } + + CGSize titleSize = [_title sizeWithFont:self.font constrainedToSize:CGSizeMake(self.frame.size.width, 10.0)]; + [_title drawInRect:CGRectMake((self.frame.size.width - titleSize.width)/2, self.frame.size.height - titleSize.height, titleSize.width, titleSize.height) withFont:self.font]; + + CGContextRestoreGState(context); } @end From efb9247d8fd262b9bb3555f958b25f269d08b76a Mon Sep 17 00:00:00 2001 From: Jeremy Foo Date: Sat, 5 May 2012 01:51:44 +0800 Subject: [PATCH 10/48] if badge value changes, we should update the view's badge value too. --- PrettyKit/PrettyTabBar.m | 59 ++++++++++++++++++++++++---------------- 1 file changed, 35 insertions(+), 24 deletions(-) diff --git a/PrettyKit/PrettyTabBar.m b/PrettyKit/PrettyTabBar.m index 18966f2..7d6e08f 100644 --- a/PrettyKit/PrettyTabBar.m +++ b/PrettyKit/PrettyTabBar.m @@ -146,6 +146,15 @@ -(void)_prettyTabButtonTapped:(UIGestureRecognizer *)gestureRecognizer { [self setSelectedItem:[self.items objectAtIndex:index]]; } +-(void)observeValueForKeyPath:(NSString *)keyPath ofObject:(id)object change:(NSDictionary *)change context:(void *)context { + if ([keyPath isEqualToString:@"badgeValue"]) { + PrettyTabBarButton *button = (PrettyTabBarButton *)context; + button.badgeValue = [change objectForKey:NSKeyValueChangeNewKey]; + } else { + [super observeValueForKeyPath:keyPath ofObject:object change:change context:context]; + } +} + #pragma mark - Display -(void)layoutSubviews { @@ -168,34 +177,36 @@ -(void)layoutSubviews { } } - if (self.prettyTabBarButtons) { - if (self.prettyTabBarButtons) { - [__prettyTabBarButtons removeAllObjects]; + if (self.prettyTabBarButtons) { + [__prettyTabBarButtons removeAllObjects]; - // do stuff - PrettyTabBarButton *button = nil; - UITabBarItem *item = nil; + // do stuff + PrettyTabBarButton *button = nil; + UITabBarItem *item = nil; + + CGFloat itemWidth = self.frame.size.width/[self.items count]; + + for (int i=0;i<[self.items count];i++) { + item = [self.items objectAtIndex:i]; + [item removeObserver:self forKeyPath:@"badgeValue"]; + + button = [[PrettyTabBarButton alloc] initWithTitle:item.title image:item.image tag:i]; + button.frame = CGRectMake(i * itemWidth, 0, itemWidth, self.frame.size.height); + button.autoresizingMask = UIViewAutoresizingFlexibleHeight | UIViewAutoresizingFlexibleWidth; + button.badgeValue = item.badgeValue; + [item addObserver:self forKeyPath:@"badgeValue" options:NSKeyValueObservingOptionNew context:button]; - CGFloat itemWidth = self.frame.size.width/[self.items count]; + UITapGestureRecognizer *tappedButton = [[UITapGestureRecognizer alloc] initWithTarget:self action:@selector(_prettyTabButtonTapped:)]; + tappedButton.numberOfTapsRequired = 1; + [button addGestureRecognizer:tappedButton]; + [tappedButton release]; - for (int i=0;i<[self.items count];i++) { - item = [self.items objectAtIndex:i]; - button = [[PrettyTabBarButton alloc] initWithTitle:item.title image:item.image tag:i]; - button.frame = CGRectMake(i * itemWidth, 0, itemWidth, self.frame.size.height); - button.autoresizingMask = UIViewAutoresizingFlexibleHeight | UIViewAutoresizingFlexibleWidth; - - UITapGestureRecognizer *tappedButton = [[UITapGestureRecognizer alloc] initWithTarget:self action:@selector(_prettyTabButtonTapped:)]; - tappedButton.numberOfTapsRequired = 1; - [button addGestureRecognizer:tappedButton]; - [tappedButton release]; - - [self addSubview:button]; - [__prettyTabBarButtons addObject:button]; - [button release]; - } - } - } + [self addSubview:button]; + [__prettyTabBarButtons addObject:button]; + [button release]; + } + } } From 457907dc1b69681685c8b569da00d3de9a6620a0 Mon Sep 17 00:00:00 2001 From: Jeremy Foo Date: Sat, 5 May 2012 02:49:26 +0800 Subject: [PATCH 11/48] observe badgeValue and update accordingly. also corrected logic flow for selection of tabbarbuttons --- PrettyKit/PrettyTabBar.m | 22 ++++++++++++---------- 1 file changed, 12 insertions(+), 10 deletions(-) diff --git a/PrettyKit/PrettyTabBar.m b/PrettyKit/PrettyTabBar.m index 7d6e08f..38495ac 100644 --- a/PrettyKit/PrettyTabBar.m +++ b/PrettyKit/PrettyTabBar.m @@ -124,10 +124,10 @@ -(void)setSelectedItem:(UITabBarItem *)selectedItem { NSInteger index = [self.items indexOfObject:selectedItem]; for (int i=0;i<[__prettyTabBarButtons count];i++) { - if (i != index) { - ((PrettyTabBarButton *)[__prettyTabBarButtons objectAtIndex:i]).selected = NO; - } else { + if (i == index) { ((PrettyTabBarButton *)[__prettyTabBarButtons objectAtIndex:i]).selected = YES; + } else { + ((PrettyTabBarButton *)[__prettyTabBarButtons objectAtIndex:i]).selected = NO; } } @@ -147,9 +147,12 @@ -(void)_prettyTabButtonTapped:(UIGestureRecognizer *)gestureRecognizer { } -(void)observeValueForKeyPath:(NSString *)keyPath ofObject:(id)object change:(NSDictionary *)change context:(void *)context { - if ([keyPath isEqualToString:@"badgeValue"]) { - PrettyTabBarButton *button = (PrettyTabBarButton *)context; - button.badgeValue = [change objectForKey:NSKeyValueChangeNewKey]; + + if (([keyPath isEqualToString:@"badgeValue"]) && (self.prettyTabBarButtons)) { + UITabBarItem *item = (UITabBarItem *)context; + NSUInteger index = [self.items indexOfObject:item]; + + [[self._prettyTabBarButtons objectAtIndex:index] setBadgeValue:[change objectForKey:NSKeyValueChangeNewKey]]; } else { [super observeValueForKeyPath:keyPath ofObject:object change:change context:context]; } @@ -188,14 +191,13 @@ -(void)layoutSubviews { CGFloat itemWidth = self.frame.size.width/[self.items count]; for (int i=0;i<[self.items count];i++) { - item = [self.items objectAtIndex:i]; - [item removeObserver:self forKeyPath:@"badgeValue"]; - + item = [self.items objectAtIndex:i]; + [item addObserver:self forKeyPath:@"badgeValue" options:NSKeyValueObservingOptionNew context:item]; + button = [[PrettyTabBarButton alloc] initWithTitle:item.title image:item.image tag:i]; button.frame = CGRectMake(i * itemWidth, 0, itemWidth, self.frame.size.height); button.autoresizingMask = UIViewAutoresizingFlexibleHeight | UIViewAutoresizingFlexibleWidth; button.badgeValue = item.badgeValue; - [item addObserver:self forKeyPath:@"badgeValue" options:NSKeyValueObservingOptionNew context:button]; UITapGestureRecognizer *tappedButton = [[UITapGestureRecognizer alloc] initWithTarget:self action:@selector(_prettyTabButtonTapped:)]; tappedButton.numberOfTapsRequired = 1; From 024c513469cea5d00f0ab7bbb9e25a24ce6c0e34 Mon Sep 17 00:00:00 2001 From: Jeremy Foo Date: Sat, 5 May 2012 02:51:27 +0800 Subject: [PATCH 12/48] draw selection background. updated highlighted text to one that's more obvious. setting of badge value does the correct things by copying as well as setting that a redraw is needed. --- PrettyKit/PrettyTabBarButton.m | 19 ++++++++++++++++++- 1 file changed, 18 insertions(+), 1 deletion(-) diff --git a/PrettyKit/PrettyTabBarButton.m b/PrettyKit/PrettyTabBarButton.m index b3c10bc..3e07603 100644 --- a/PrettyKit/PrettyTabBarButton.m +++ b/PrettyKit/PrettyTabBarButton.m @@ -33,7 +33,7 @@ #define default_text_shadow_opacity 0.5 #define default_font [UIFont fontWithName:@"HelveticaNeue-Bold" size:11] #define default_text_color [UIColor colorWithWhite:0.20 alpha:1.0] -#define default_highlighted_text_color [UIColor colorWithWhite:0.80 alpha:1.0] +#define default_highlighted_text_color [UIColor colorWithWhite:0.10 alpha:1.0] @implementation PrettyTabBarButton @synthesize title = _title, image = _image, badgeValue = _badgeValue; @@ -115,11 +115,28 @@ -(void)setSelected:(BOOL)selected { [self setNeedsDisplay]; } +-(void)setBadgeValue:(NSString *)badgeValue { + if (_badgeValue != badgeValue) { + [_badgeValue release]; + _badgeValue = [badgeValue copy]; + } + + [self setNeedsDisplay]; +} - (void)drawRect:(CGRect)rect { [super drawRect:rect]; CGContextRef context = UIGraphicsGetCurrentContext(); + + // draw selection background + if (self.selected) { + if (self.highlightedImage) { + + } else { + [PrettyDrawing drawGradient:rect fromColor:[UIColor colorWithWhite:0.9 alpha:1.0] toColor:[UIColor colorWithWhite:0.8 alpha:1.0]]; + } + } CGContextSaveGState(context); From 02d8ea5e428e298288c2379fe9761c24cae8c84c Mon Sep 17 00:00:00 2001 From: Jeremy Foo Date: Sat, 5 May 2012 02:51:40 +0800 Subject: [PATCH 13/48] initial drawing of badges --- PrettyKit/PrettyTabBarButton.m | 36 ++++++++++++++++++++++++++++++++++ 1 file changed, 36 insertions(+) diff --git a/PrettyKit/PrettyTabBarButton.m b/PrettyKit/PrettyTabBarButton.m index 3e07603..d335953 100644 --- a/PrettyKit/PrettyTabBarButton.m +++ b/PrettyKit/PrettyTabBarButton.m @@ -123,6 +123,10 @@ -(void)setBadgeValue:(NSString *)badgeValue { [self setNeedsDisplay]; } + +#define BADGE_HEIGHT 10.0 +#define BADGE_FONT [UIFont fontWithName:@"HelveticaNeue-Bold" size:14] + - (void)drawRect:(CGRect)rect { [super drawRect:rect]; @@ -138,6 +142,7 @@ - (void)drawRect:(CGRect)rect } } + // draw text CGContextSaveGState(context); if (self.wantTextShadow) { @@ -154,6 +159,37 @@ - (void)drawRect:(CGRect)rect [_title drawInRect:CGRectMake((self.frame.size.width - titleSize.width)/2, self.frame.size.height - titleSize.height, titleSize.width, titleSize.height) withFont:self.font]; CGContextRestoreGState(context); + + // draw badge + if (self.badgeValue) { + CGSize badgeTextSize = [self.badgeValue sizeWithFont:BADGE_FONT constrainedToSize:CGSizeMake(self.frame.size.width, BADGE_HEIGHT)]; + CGFloat width = badgeTextSize.width; + if ((BADGE_HEIGHT - width) < 0) + width += BADGE_HEIGHT * 0.8; + + if (width < (BADGE_HEIGHT * 2)) + width += BADGE_HEIGHT * 2; + + + CGRect badgeFrame = CGRectMake(self.frame.size.width - width - 1, 1, width, BADGE_HEIGHT * 2); + CGContextSetStrokeColorWithColor(context, [[UIColor purpleColor] CGColor]); + CGContextStrokeRect(context, badgeFrame); + + CGMutablePathRef path = CGPathCreateMutable(); + CGPathAddArc(path, NULL, self.frame.size.width - width + BADGE_HEIGHT, BADGE_HEIGHT, BADGE_HEIGHT, M_PI / 2, M_PI * 3 / 2, YES); + CGPathAddArc(path, NULL, self.frame.size.width - BADGE_HEIGHT, BADGE_HEIGHT, BADGE_HEIGHT, M_PI * 3 / 2, M_PI / 2, YES); + + CGContextSetFillColorWithColor(context, [[UIColor redColor] CGColor]); + CGContextAddPath(context, path); + CGContextDrawPath(context, kCGPathFill); + + [[UIColor blueColor] setFill]; + [self.badgeValue drawInRect:CGRectMake(badgeFrame.origin.x + (badgeFrame.size.width - badgeTextSize.width)/2, badgeFrame.origin.y + (badgeFrame.size.height - badgeTextSize.height)/2, badgeTextSize.width, badgeTextSize.height) withFont:BADGE_FONT]; + + CGPathRelease(path); + + } + } @end From 241e719ae0629045ff6d745a46d66d28451f1e6d Mon Sep 17 00:00:00 2001 From: Jeremy Foo Date: Sat, 5 May 2012 03:34:48 +0800 Subject: [PATCH 14/48] setup options for badge --- PrettyKit/PrettyTabBarButton.h | 12 ++++-- PrettyKit/PrettyTabBarButton.m | 68 ++++++++++++++++++++++++---------- 2 files changed, 58 insertions(+), 22 deletions(-) diff --git a/PrettyKit/PrettyTabBarButton.h b/PrettyKit/PrettyTabBarButton.h index d7e5901..9bd29a8 100644 --- a/PrettyKit/PrettyTabBarButton.h +++ b/PrettyKit/PrettyTabBarButton.h @@ -39,12 +39,18 @@ @property (nonatomic, retain) UIColor *textColor; @property (nonatomic, retain) UIColor *highlightedTextColor; -@property (readwrite) CGFloat textShadowOpacity; -@property (readwrite) CGSize textShadowOffset; -@property (readwrite) BOOL wantTextShadow; +@property (nonatomic) CGFloat textShadowOpacity; +@property (nonatomic) CGSize textShadowOffset; +@property (nonatomic) BOOL wantTextShadow; @property (nonatomic, retain) UIImage *highlightedImage; +@property (nonatomic, retain) UIColor *badgeBorderColor; +@property (nonatomic, retain) UIColor *badgeColor; +@property (nonatomic) CGFloat badgeShadowOpacity; +@property (nonatomic) CGSize badgeShadowOffset; +@property (nonatomic, retain) UIFont *badgeFont; + -(id)initWithTitle:(NSString *)title image:(UIImage *)image tag:(NSInteger)tag; @end diff --git a/PrettyKit/PrettyTabBarButton.m b/PrettyKit/PrettyTabBarButton.m index d335953..b965e3c 100644 --- a/PrettyKit/PrettyTabBarButton.m +++ b/PrettyKit/PrettyTabBarButton.m @@ -34,12 +34,18 @@ #define default_font [UIFont fontWithName:@"HelveticaNeue-Bold" size:11] #define default_text_color [UIColor colorWithWhite:0.20 alpha:1.0] #define default_highlighted_text_color [UIColor colorWithWhite:0.10 alpha:1.0] +#define default_badge_font [UIFont fontWithName:@"HelveticaNeue-Bold" size:13] +#define default_badge_color [UIColor redColor] +#define default_badge_border_color [UIColor whiteColor] +#define default_badge_shadow_opacity 0.5 +#define default_badge_shadow_offset CGSizeMake(0,1) @implementation PrettyTabBarButton @synthesize title = _title, image = _image, badgeValue = _badgeValue; @synthesize selected = _selected; @synthesize textColor, font, highlightedTextColor, highlightedImage; @synthesize wantTextShadow, textShadowOpacity, textShadowOffset; +@synthesize badgeBorderColor, badgeColor, badgeFont, badgeShadowOffset, badgeShadowOpacity; -(id)initWithTitle:(NSString *)title image:(UIImage *)image tag:(NSInteger)tag { if ((self = [super init])) { @@ -80,6 +86,14 @@ -(void)dealloc { [_image release], _image = nil; [_badgeValue release], _badgeValue = nil; + self.font = nil; + self.textColor = nil; + self.highlightedTextColor = nil; + self.highlightedImage = nil; + self.badgeBorderColor = nil; + self.badgeColor = nil; + self.badgeFont = nil; + [super dealloc]; } @@ -95,7 +109,12 @@ - (void) initializeVars self.wantTextShadow = default_want_text_shadow; self.textShadowOpacity = default_text_shadow_opacity; self.textShadowOffset = default_text_shadow_offset; - + self.badgeBorderColor = default_badge_border_color; + self.badgeColor = default_badge_color; + self.badgeShadowOffset = default_badge_shadow_offset; + self.badgeShadowOpacity = default_badge_shadow_opacity; + self.badgeFont = default_badge_font; + // intialize values; self.tag = -1; @@ -124,9 +143,6 @@ -(void)setBadgeValue:(NSString *)badgeValue { [self setNeedsDisplay]; } -#define BADGE_HEIGHT 10.0 -#define BADGE_FONT [UIFont fontWithName:@"HelveticaNeue-Bold" size:14] - - (void)drawRect:(CGRect)rect { [super drawRect:rect]; @@ -162,32 +178,46 @@ - (void)drawRect:(CGRect)rect // draw badge if (self.badgeValue) { - CGSize badgeTextSize = [self.badgeValue sizeWithFont:BADGE_FONT constrainedToSize:CGSizeMake(self.frame.size.width, BADGE_HEIGHT)]; - CGFloat width = badgeTextSize.width; - if ((BADGE_HEIGHT - width) < 0) - width += BADGE_HEIGHT * 0.8; - - if (width < (BADGE_HEIGHT * 2)) - width += BADGE_HEIGHT * 2; + CGSize badgeTextSize = [self.badgeValue sizeWithFont:self.badgeFont forWidth:(self.frame.size.width * 0.5) lineBreakMode:UILineBreakModeTailTruncation]; + CGFloat badgeWidth = badgeTextSize.width; + CGFloat badgeHeight = badgeTextSize.height + 4; + if ((badgeHeight - badgeWidth) < 0) + badgeWidth += badgeHeight * 0.8; - CGRect badgeFrame = CGRectMake(self.frame.size.width - width - 1, 1, width, BADGE_HEIGHT * 2); - CGContextSetStrokeColorWithColor(context, [[UIColor purpleColor] CGColor]); - CGContextStrokeRect(context, badgeFrame); + if (badgeWidth < (badgeHeight * 2)) + badgeWidth = badgeHeight * 2; + CGRect badgeFrame = CGRectMake(self.frame.size.width - badgeWidth - 2, 2, badgeWidth, badgeHeight); + CGMutablePathRef path = CGPathCreateMutable(); - CGPathAddArc(path, NULL, self.frame.size.width - width + BADGE_HEIGHT, BADGE_HEIGHT, BADGE_HEIGHT, M_PI / 2, M_PI * 3 / 2, YES); - CGPathAddArc(path, NULL, self.frame.size.width - BADGE_HEIGHT, BADGE_HEIGHT, BADGE_HEIGHT, M_PI * 3 / 2, M_PI / 2, YES); + CGPathAddArc(path, NULL, badgeFrame.origin.x + badgeHeight, badgeFrame.origin.y + badgeHeight, badgeHeight, M_PI / 2, M_PI * 3 / 2, NO); + CGPathAddArc(path, NULL, badgeFrame.origin.x + badgeFrame.size.width - badgeHeight, badgeFrame.origin.y + badgeHeight, badgeHeight, M_PI * 3 / 2, M_PI / 2, NO); - CGContextSetFillColorWithColor(context, [[UIColor redColor] CGColor]); + CGContextSaveGState(context); + + CGContextSetShadow(context, self.badgeShadowOffset, self.badgeShadowOpacity); + CGContextSetFillColorWithColor(context, [[UIColor whiteColor] CGColor]); CGContextAddPath(context, path); CGContextDrawPath(context, kCGPathFill); + CGPathRelease(path); - [[UIColor blueColor] setFill]; - [self.badgeValue drawInRect:CGRectMake(badgeFrame.origin.x + (badgeFrame.size.width - badgeTextSize.width)/2, badgeFrame.origin.y + (badgeFrame.size.height - badgeTextSize.height)/2, badgeTextSize.width, badgeTextSize.height) withFont:BADGE_FONT]; + CGContextRestoreGState(context); + path = CGPathCreateMutable(); + CGPathAddArc(path, NULL, badgeFrame.origin.x + badgeHeight, badgeFrame.origin.y + badgeHeight, badgeHeight - 2, M_PI / 2, M_PI * 3 / 2, NO); + CGPathAddArc(path, NULL, badgeFrame.origin.x + badgeFrame.size.width - badgeHeight, badgeFrame.origin.y + badgeHeight, badgeHeight - 2, M_PI * 3 / 2, M_PI / 2, NO); + CGContextSetFillColorWithColor(context, [[UIColor redColor] CGColor]); + CGContextAddPath(context, path); + CGContextDrawPath(context, kCGPathFill); CGPathRelease(path); + + [[UIColor whiteColor] setFill]; + [self.badgeValue drawInRect:CGRectMake(badgeFrame.origin.x + (badgeFrame.size.width - badgeTextSize.width)/2, badgeFrame.origin.y + (badgeFrame.size.height - badgeTextSize.height)/2, badgeTextSize.width, badgeTextSize.height) + withFont:self.badgeFont + lineBreakMode:UILineBreakModeTailTruncation]; + } } From 17bdab1447fbe71b5b95d98dc27b9408e1f99af0 Mon Sep 17 00:00:00 2001 From: Jeremy Foo Date: Sat, 5 May 2012 03:43:58 +0800 Subject: [PATCH 15/48] draws badges according to font size. --- PrettyKit/PrettyTabBarButton.h | 3 ++- PrettyKit/PrettyTabBarButton.m | 49 ++++++++++++++++++---------------- 2 files changed, 28 insertions(+), 24 deletions(-) diff --git a/PrettyKit/PrettyTabBarButton.h b/PrettyKit/PrettyTabBarButton.h index 9bd29a8..8d3d85a 100644 --- a/PrettyKit/PrettyTabBarButton.h +++ b/PrettyKit/PrettyTabBarButton.h @@ -46,7 +46,8 @@ @property (nonatomic, retain) UIImage *highlightedImage; @property (nonatomic, retain) UIColor *badgeBorderColor; -@property (nonatomic, retain) UIColor *badgeColor; +@property (nonatomic, retain) UIColor *badgeGradientStartColor; +@property (nonatomic, retain) UIColor *badgeGradientEndColor; @property (nonatomic) CGFloat badgeShadowOpacity; @property (nonatomic) CGSize badgeShadowOffset; @property (nonatomic, retain) UIFont *badgeFont; diff --git a/PrettyKit/PrettyTabBarButton.m b/PrettyKit/PrettyTabBarButton.m index b965e3c..65825cb 100644 --- a/PrettyKit/PrettyTabBarButton.m +++ b/PrettyKit/PrettyTabBarButton.m @@ -28,24 +28,25 @@ #import "PrettyTabBarButton.h" #import "PrettyDrawing.h" -#define default_want_text_shadow YES -#define default_text_shadow_offset CGSizeMake(0,1) -#define default_text_shadow_opacity 0.5 -#define default_font [UIFont fontWithName:@"HelveticaNeue-Bold" size:11] -#define default_text_color [UIColor colorWithWhite:0.20 alpha:1.0] -#define default_highlighted_text_color [UIColor colorWithWhite:0.10 alpha:1.0] -#define default_badge_font [UIFont fontWithName:@"HelveticaNeue-Bold" size:13] -#define default_badge_color [UIColor redColor] -#define default_badge_border_color [UIColor whiteColor] -#define default_badge_shadow_opacity 0.5 -#define default_badge_shadow_offset CGSizeMake(0,1) +#define default_want_text_shadow YES +#define default_text_shadow_offset CGSizeMake(0,1) +#define default_text_shadow_opacity 0.5 +#define default_font [UIFont fontWithName:@"HelveticaNeue-Bold" size:11] +#define default_text_color [UIColor colorWithWhite:0.20 alpha:1.0] +#define default_highlighted_text_color [UIColor colorWithWhite:0.10 alpha:1.0] +#define default_badge_font [UIFont fontWithName:@"HelveticaNeue-Bold" size:13] +#define default_badge_gradient_start_color [UIColor redColor] +#define default_badge_gradient_end_color [UIColor redColor] +#define default_badge_border_color [UIColor whiteColor] +#define default_badge_shadow_opacity 0.5 +#define default_badge_shadow_offset CGSizeMake(0,1) @implementation PrettyTabBarButton @synthesize title = _title, image = _image, badgeValue = _badgeValue; @synthesize selected = _selected; @synthesize textColor, font, highlightedTextColor, highlightedImage; @synthesize wantTextShadow, textShadowOpacity, textShadowOffset; -@synthesize badgeBorderColor, badgeColor, badgeFont, badgeShadowOffset, badgeShadowOpacity; +@synthesize badgeBorderColor, badgeGradientEndColor, badgeGradientStartColor, badgeFont, badgeShadowOffset, badgeShadowOpacity; -(id)initWithTitle:(NSString *)title image:(UIImage *)image tag:(NSInteger)tag { if ((self = [super init])) { @@ -91,7 +92,8 @@ -(void)dealloc { self.highlightedTextColor = nil; self.highlightedImage = nil; self.badgeBorderColor = nil; - self.badgeColor = nil; + self.badgeGradientStartColor = nil; + self.badgeGradientEndColor = nil; self.badgeFont = nil; [super dealloc]; @@ -110,7 +112,8 @@ - (void) initializeVars self.textShadowOpacity = default_text_shadow_opacity; self.textShadowOffset = default_text_shadow_offset; self.badgeBorderColor = default_badge_border_color; - self.badgeColor = default_badge_color; + self.badgeGradientStartColor = default_badge_gradient_start_color; + self.badgeGradientEndColor = default_badge_gradient_end_color; self.badgeShadowOffset = default_badge_shadow_offset; self.badgeShadowOpacity = default_badge_shadow_opacity; self.badgeFont = default_badge_font; @@ -178,26 +181,26 @@ - (void)drawRect:(CGRect)rect // draw badge if (self.badgeValue) { - CGSize badgeTextSize = [self.badgeValue sizeWithFont:self.badgeFont forWidth:(self.frame.size.width * 0.5) lineBreakMode:UILineBreakModeTailTruncation]; + CGSize badgeTextSize = [self.badgeValue sizeWithFont:self.badgeFont forWidth:(self.frame.size.width * 0.45) lineBreakMode:UILineBreakModeTailTruncation]; CGFloat badgeWidth = badgeTextSize.width; CGFloat badgeHeight = badgeTextSize.height + 4; if ((badgeHeight - badgeWidth) < 0) badgeWidth += badgeHeight * 0.8; - if (badgeWidth < (badgeHeight * 2)) - badgeWidth = badgeHeight * 2; + if (badgeWidth < (badgeHeight)) + badgeWidth = badgeHeight; CGRect badgeFrame = CGRectMake(self.frame.size.width - badgeWidth - 2, 2, badgeWidth, badgeHeight); CGMutablePathRef path = CGPathCreateMutable(); - CGPathAddArc(path, NULL, badgeFrame.origin.x + badgeHeight, badgeFrame.origin.y + badgeHeight, badgeHeight, M_PI / 2, M_PI * 3 / 2, NO); - CGPathAddArc(path, NULL, badgeFrame.origin.x + badgeFrame.size.width - badgeHeight, badgeFrame.origin.y + badgeHeight, badgeHeight, M_PI * 3 / 2, M_PI / 2, NO); + CGPathAddArc(path, NULL, badgeFrame.origin.x + badgeHeight/2, badgeFrame.origin.y + badgeHeight/2, badgeHeight/2, M_PI / 2, M_PI * 3 / 2, NO); + CGPathAddArc(path, NULL, badgeFrame.origin.x + badgeFrame.size.width - badgeHeight/2, badgeFrame.origin.y + badgeHeight/2, badgeHeight/2, M_PI * 3 / 2, M_PI / 2, NO); CGContextSaveGState(context); CGContextSetShadow(context, self.badgeShadowOffset, self.badgeShadowOpacity); - CGContextSetFillColorWithColor(context, [[UIColor whiteColor] CGColor]); + CGContextSetFillColorWithColor(context, [self.badgeBorderColor CGColor]); CGContextAddPath(context, path); CGContextDrawPath(context, kCGPathFill); CGPathRelease(path); @@ -205,9 +208,9 @@ - (void)drawRect:(CGRect)rect CGContextRestoreGState(context); path = CGPathCreateMutable(); - CGPathAddArc(path, NULL, badgeFrame.origin.x + badgeHeight, badgeFrame.origin.y + badgeHeight, badgeHeight - 2, M_PI / 2, M_PI * 3 / 2, NO); - CGPathAddArc(path, NULL, badgeFrame.origin.x + badgeFrame.size.width - badgeHeight, badgeFrame.origin.y + badgeHeight, badgeHeight - 2, M_PI * 3 / 2, M_PI / 2, NO); - CGContextSetFillColorWithColor(context, [[UIColor redColor] CGColor]); + CGPathAddArc(path, NULL, badgeFrame.origin.x + badgeHeight/2, badgeFrame.origin.y + badgeHeight/2, badgeHeight/2 - 2, M_PI / 2, M_PI * 3 / 2, NO); + CGPathAddArc(path, NULL, badgeFrame.origin.x + badgeFrame.size.width - badgeHeight/2, badgeFrame.origin.y + badgeHeight/2, badgeHeight/2 - 2, M_PI * 3 / 2, M_PI / 2, NO); + CGContextSetFillColorWithColor(context, [self.badgeGradientStartColor CGColor]); CGContextAddPath(context, path); CGContextDrawPath(context, kCGPathFill); CGPathRelease(path); From cd6811a8249741a2f012dffb5fda50115d3106bf Mon Sep 17 00:00:00 2001 From: Jeremy Foo Date: Sat, 5 May 2012 03:54:25 +0800 Subject: [PATCH 16/48] adjusted opacity values. added todos --- PrettyKit/PrettyTabBarButton.m | 9 ++++++--- 1 file changed, 6 insertions(+), 3 deletions(-) diff --git a/PrettyKit/PrettyTabBarButton.m b/PrettyKit/PrettyTabBarButton.m index 65825cb..988cedd 100644 --- a/PrettyKit/PrettyTabBarButton.m +++ b/PrettyKit/PrettyTabBarButton.m @@ -38,8 +38,8 @@ #define default_badge_gradient_start_color [UIColor redColor] #define default_badge_gradient_end_color [UIColor redColor] #define default_badge_border_color [UIColor whiteColor] -#define default_badge_shadow_opacity 0.5 -#define default_badge_shadow_offset CGSizeMake(0,1) +#define default_badge_shadow_opacity 0.75 +#define default_badge_shadow_offset CGSizeMake(0,1.5) @implementation PrettyTabBarButton @synthesize title = _title, image = _image, badgeValue = _badgeValue; @@ -179,6 +179,8 @@ - (void)drawRect:(CGRect)rect CGContextRestoreGState(context); + // TODO: draw image + // draw badge if (self.badgeValue) { CGSize badgeTextSize = [self.badgeValue sizeWithFont:self.badgeFont forWidth:(self.frame.size.width * 0.45) lineBreakMode:UILineBreakModeTailTruncation]; @@ -207,6 +209,8 @@ - (void)drawRect:(CGRect)rect CGContextRestoreGState(context); + //TODO: Fill badge color with gradient and apply nice embossing effect + path = CGPathCreateMutable(); CGPathAddArc(path, NULL, badgeFrame.origin.x + badgeHeight/2, badgeFrame.origin.y + badgeHeight/2, badgeHeight/2 - 2, M_PI / 2, M_PI * 3 / 2, NO); CGPathAddArc(path, NULL, badgeFrame.origin.x + badgeFrame.size.width - badgeHeight/2, badgeFrame.origin.y + badgeHeight/2, badgeHeight/2 - 2, M_PI * 3 / 2, M_PI / 2, NO); @@ -214,7 +218,6 @@ - (void)drawRect:(CGRect)rect CGContextAddPath(context, path); CGContextDrawPath(context, kCGPathFill); CGPathRelease(path); - [[UIColor whiteColor] setFill]; [self.badgeValue drawInRect:CGRectMake(badgeFrame.origin.x + (badgeFrame.size.width - badgeTextSize.width)/2, badgeFrame.origin.y + (badgeFrame.size.height - badgeTextSize.height)/2, badgeTextSize.width, badgeTextSize.height) From 8444b94fb3514affab820ea9ed89520ebbc3efb8 Mon Sep 17 00:00:00 2001 From: Jeremy Foo Date: Sat, 5 May 2012 04:10:03 +0800 Subject: [PATCH 17/48] default values for text colors and highlights --- PrettyKit/PrettyTabBarButton.m | 17 +++++++++++++---- 1 file changed, 13 insertions(+), 4 deletions(-) diff --git a/PrettyKit/PrettyTabBarButton.m b/PrettyKit/PrettyTabBarButton.m index 988cedd..59be2bb 100644 --- a/PrettyKit/PrettyTabBarButton.m +++ b/PrettyKit/PrettyTabBarButton.m @@ -32,8 +32,8 @@ #define default_text_shadow_offset CGSizeMake(0,1) #define default_text_shadow_opacity 0.5 #define default_font [UIFont fontWithName:@"HelveticaNeue-Bold" size:11] -#define default_text_color [UIColor colorWithWhite:0.20 alpha:1.0] -#define default_highlighted_text_color [UIColor colorWithWhite:0.10 alpha:1.0] +#define default_text_color [UIColor colorWithWhite:0.40 alpha:1.0] +#define default_highlighted_text_color [UIColor colorWithWhite:0.90 alpha:1.0] #define default_badge_font [UIFont fontWithName:@"HelveticaNeue-Bold" size:13] #define default_badge_gradient_start_color [UIColor redColor] #define default_badge_gradient_end_color [UIColor redColor] @@ -156,8 +156,17 @@ - (void)drawRect:(CGRect)rect if (self.selected) { if (self.highlightedImage) { - } else { - [PrettyDrawing drawGradient:rect fromColor:[UIColor colorWithWhite:0.9 alpha:1.0] toColor:[UIColor colorWithWhite:0.8 alpha:1.0]]; + } else { + + // for iOS 4.3 + CGContextSetFillColorWithColor(context, [[UIColor colorWithWhite:0.75 alpha:1.0] CGColor]); + CGContextFillRect(context, CGRectMake(0, 2, self.frame.size.width, self.frame.size.height - 2)); + + // works for iOS 5.0 so just layering it on + [PrettyDrawing drawGradient:CGRectMake(0, 2, self.frame.size.width, self.frame.size.height - 2) + fromColor:[UIColor colorWithWhite:0.75 alpha:1.0] + toColor:[UIColor colorWithWhite:0.1 alpha:1.0]]; + } } From ad8822a5b834dc4d9f71ee33c2a6145119cf1446 Mon Sep 17 00:00:00 2001 From: Jeremy Foo Date: Sat, 5 May 2012 04:12:06 +0800 Subject: [PATCH 18/48] activate pretty tab bar buttons --- PrettyExample/AppDelegate.m | 3 ++- 1 file changed, 2 insertions(+), 1 deletion(-) diff --git a/PrettyExample/AppDelegate.m b/PrettyExample/AppDelegate.m index 25f9417..58a61a2 100644 --- a/PrettyExample/AppDelegate.m +++ b/PrettyExample/AppDelegate.m @@ -8,6 +8,7 @@ #import "AppDelegate.h" #import "ExampleViewController.h" +#import "PrettyTabBar.h" @implementation AppDelegate @@ -29,7 +30,7 @@ - (BOOL)application:(UIApplication *)application didFinishLaunchingWithOptions:( self.window.backgroundColor = [UIColor whiteColor]; self.window.rootViewController = self.tabBarController; - + ((PrettyTabBar *)self.tabBarController.tabBar).prettyTabBarButtons = YES; [self.window makeKeyAndVisible]; return YES; From 0bf6801d81e96aaad612a3011e37dcec91de639c Mon Sep 17 00:00:00 2001 From: Jeremy Foo Date: Sat, 5 May 2012 17:47:43 +0800 Subject: [PATCH 19/48] customize badge text color and also working gradients for badge --- PrettyKit/PrettyTabBarButton.h | 1 + PrettyKit/PrettyTabBarButton.m | 42 +++++++++++++++++++++++++--------- 2 files changed, 32 insertions(+), 11 deletions(-) diff --git a/PrettyKit/PrettyTabBarButton.h b/PrettyKit/PrettyTabBarButton.h index 8d3d85a..ea5dc22 100644 --- a/PrettyKit/PrettyTabBarButton.h +++ b/PrettyKit/PrettyTabBarButton.h @@ -51,6 +51,7 @@ @property (nonatomic) CGFloat badgeShadowOpacity; @property (nonatomic) CGSize badgeShadowOffset; @property (nonatomic, retain) UIFont *badgeFont; +@property (nonatomic, retain) UIColor *badgeTextColor; -(id)initWithTitle:(NSString *)title image:(UIImage *)image tag:(NSInteger)tag; diff --git a/PrettyKit/PrettyTabBarButton.m b/PrettyKit/PrettyTabBarButton.m index 59be2bb..e35ce71 100644 --- a/PrettyKit/PrettyTabBarButton.m +++ b/PrettyKit/PrettyTabBarButton.m @@ -29,24 +29,25 @@ #import "PrettyDrawing.h" #define default_want_text_shadow YES -#define default_text_shadow_offset CGSizeMake(0,1) +#define default_text_shadow_offset CGSizeMake(0,-1) #define default_text_shadow_opacity 0.5 #define default_font [UIFont fontWithName:@"HelveticaNeue-Bold" size:11] -#define default_text_color [UIColor colorWithWhite:0.40 alpha:1.0] +#define default_text_color [UIColor colorWithWhite:0.2 alpha:1.0] #define default_highlighted_text_color [UIColor colorWithWhite:0.90 alpha:1.0] #define default_badge_font [UIFont fontWithName:@"HelveticaNeue-Bold" size:13] -#define default_badge_gradient_start_color [UIColor redColor] -#define default_badge_gradient_end_color [UIColor redColor] +#define default_badge_gradient_start_color [UIColor colorWithRed:0.9 green:0.000 blue:0.000 alpha:1.000] +#define default_badge_gradient_end_color [UIColor colorWithRed:0.1 green:0.000 blue:0.000 alpha:1.000] #define default_badge_border_color [UIColor whiteColor] #define default_badge_shadow_opacity 0.75 #define default_badge_shadow_offset CGSizeMake(0,1.5) +#define default_badge_text_color [UIColor whiteColor] @implementation PrettyTabBarButton @synthesize title = _title, image = _image, badgeValue = _badgeValue; @synthesize selected = _selected; @synthesize textColor, font, highlightedTextColor, highlightedImage; @synthesize wantTextShadow, textShadowOpacity, textShadowOffset; -@synthesize badgeBorderColor, badgeGradientEndColor, badgeGradientStartColor, badgeFont, badgeShadowOffset, badgeShadowOpacity; +@synthesize badgeBorderColor, badgeGradientEndColor, badgeGradientStartColor, badgeFont, badgeShadowOffset, badgeShadowOpacity, badgeTextColor; -(id)initWithTitle:(NSString *)title image:(UIImage *)image tag:(NSInteger)tag { if ((self = [super init])) { @@ -95,6 +96,7 @@ -(void)dealloc { self.badgeGradientStartColor = nil; self.badgeGradientEndColor = nil; self.badgeFont = nil; + self.badgeTextColor = nil; [super dealloc]; } @@ -117,6 +119,7 @@ - (void) initializeVars self.badgeShadowOffset = default_badge_shadow_offset; self.badgeShadowOpacity = default_badge_shadow_opacity; self.badgeFont = default_badge_font; + self.badgeTextColor = default_badge_text_color; // intialize values; self.tag = -1; @@ -189,6 +192,9 @@ - (void)drawRect:(CGRect)rect CGContextRestoreGState(context); // TODO: draw image + if (self.image) { + + } // draw badge if (self.badgeValue) { @@ -202,8 +208,9 @@ - (void)drawRect:(CGRect)rect if (badgeWidth < (badgeHeight)) badgeWidth = badgeHeight; - CGRect badgeFrame = CGRectMake(self.frame.size.width - badgeWidth - 2, 2, badgeWidth, badgeHeight); + CGRect badgeFrame = CGRectMake(self.frame.size.width - badgeWidth - 2, 3, badgeWidth, badgeHeight); + // draw outter border CGMutablePathRef path = CGPathCreateMutable(); CGPathAddArc(path, NULL, badgeFrame.origin.x + badgeHeight/2, badgeFrame.origin.y + badgeHeight/2, badgeHeight/2, M_PI / 2, M_PI * 3 / 2, NO); CGPathAddArc(path, NULL, badgeFrame.origin.x + badgeFrame.size.width - badgeHeight/2, badgeFrame.origin.y + badgeHeight/2, badgeHeight/2, M_PI * 3 / 2, M_PI / 2, NO); @@ -217,18 +224,31 @@ - (void)drawRect:(CGRect)rect CGPathRelease(path); CGContextRestoreGState(context); - - //TODO: Fill badge color with gradient and apply nice embossing effect + + // draw inner badge color + CGContextSaveGState(context); path = CGPathCreateMutable(); CGPathAddArc(path, NULL, badgeFrame.origin.x + badgeHeight/2, badgeFrame.origin.y + badgeHeight/2, badgeHeight/2 - 2, M_PI / 2, M_PI * 3 / 2, NO); CGPathAddArc(path, NULL, badgeFrame.origin.x + badgeFrame.size.width - badgeHeight/2, badgeFrame.origin.y + badgeHeight/2, badgeHeight/2 - 2, M_PI * 3 / 2, M_PI / 2, NO); - CGContextSetFillColorWithColor(context, [self.badgeGradientStartColor CGColor]); CGContextAddPath(context, path); - CGContextDrawPath(context, kCGPathFill); CGPathRelease(path); - [[UIColor whiteColor] setFill]; + CGContextClip(context); + + CGColorSpaceRef colorSpace = CGColorSpaceCreateDeviceRGB(); + CGFloat locations[] = {0.0, 1.0}; + NSArray *colors = [NSArray arrayWithObjects:(id)[self.badgeGradientStartColor CGColor], (id)[self.badgeGradientEndColor CGColor], nil]; + + CGGradientRef gradient = CGGradientCreateWithColors(colorSpace, (CFArrayRef) colors, locations); + CGContextDrawLinearGradient(context, gradient, CGPointMake(badgeFrame.origin.x + badgeFrame.size.width/2, badgeFrame.origin.y + 0), CGPointMake(badgeFrame.origin.x + badgeFrame.size.width/2, badgeFrame.origin.y + badgeFrame.size.height), 0); + CGGradientRelease(gradient); + CGColorSpaceRelease(colorSpace); + + CGContextRestoreGState(context); + + // draw badgeValue + [self.badgeTextColor setFill]; [self.badgeValue drawInRect:CGRectMake(badgeFrame.origin.x + (badgeFrame.size.width - badgeTextSize.width)/2, badgeFrame.origin.y + (badgeFrame.size.height - badgeTextSize.height)/2, badgeTextSize.width, badgeTextSize.height) withFont:self.badgeFont lineBreakMode:UILineBreakModeTailTruncation]; From b3f59cd9212f2ec7a0d8b582078615cf3dad831e Mon Sep 17 00:00:00 2001 From: Jeremy Foo Date: Sat, 5 May 2012 20:31:54 +0800 Subject: [PATCH 20/48] CF like method to return a mutable path that is in the shape of a rounded rectangle corresponding methods to draw rounded rectangles with a solid fill color and with a gradient. abstracted gradient drawing into a method that will draw to a context you specify. also used a more primitive way of dealing with the colors UIColor additions to deal with getting of converted RGB components in the absence of colorspace conversion mechanics --- PrettyKit/PrettyDrawing.h | 27 +++++++++ PrettyKit/PrettyDrawing.m | 116 +++++++++++++++++++++++++++++++++----- 2 files changed, 129 insertions(+), 14 deletions(-) diff --git a/PrettyKit/PrettyDrawing.h b/PrettyKit/PrettyDrawing.h index 938fd1b..65f2558 100644 --- a/PrettyKit/PrettyDrawing.h +++ b/PrettyKit/PrettyDrawing.h @@ -40,6 +40,26 @@ typedef enum { @interface PrettyDrawing : NSObject +/** + Returns a CGMutablePathRef that is for a Rounded Rectangle in rect with corner radii radius. + */ +CGMutablePathRef PrettyKitCreateMutablePathForRoundedRect(CGRect rect, CGFloat radius); + +/** + Draws a rounded rectangle using the radius and fill color into a rect + */ ++ (void)drawRoundedRect:(CGRect)rect cornerRadius:(CGFloat)radius color:(UIColor *)color; + +/** + Draws a gradient into a context using a startPoint, endPOint and a from and to color + */ ++ (void)drawGradientForContext:(CGContextRef)context startPoint:(CGPoint)startPoint endPoint:(CGPoint)endPoint fromColor:(UIColor *)fromColor toColor:(UIColor *)toColor; + +/** + Draws a rounded rect with a gradient and a corner radius into a rect + */ ++ (void)drawGradientRoundedRect:(CGRect)rect cornerRadius:(CGFloat)radius fromColor:(UIColor *)from toColor:(UIColor *)to; + /** Draws a gradient with the given colors into the given rect. */ @@ -98,4 +118,11 @@ typedef enum { @return A new autoreleased UIColor instance. */ + (UIColor *) colorWithHex:(int)hex; +/** Converts the color to an RGB colorspace and puts values of the components into the components parameter + + @param Pointer to a CGFloat array of the most 4 elements + + */ +-(void)getRGBColorComponents:(CGFloat [4])components; + @end \ No newline at end of file diff --git a/PrettyKit/PrettyDrawing.m b/PrettyKit/PrettyDrawing.m index ee3e5a3..885867b 100644 --- a/PrettyKit/PrettyDrawing.m +++ b/PrettyKit/PrettyDrawing.m @@ -32,30 +32,85 @@ @implementation PrettyDrawing -+ (void) drawGradient:(CGRect)rect fromColor:(UIColor *)from toColor:(UIColor *)to { - CGContextRef ctx = UIGraphicsGetCurrentContext(); - CGContextSaveGState(ctx); +CGMutablePathRef PrettyKitCreateMutablePathForRoundedRect(CGRect rect, CGFloat radius) { + CGMutablePathRef path = CGPathCreateMutable(); + CGPathAddArc(path, NULL, rect.origin.x + radius, rect.origin.y + radius, radius, (180) * M_PI/180, (-90) * M_PI/180, 0); + CGPathAddArc(path, NULL, rect.origin.x + rect.size.width - radius, rect.origin.y + radius, radius, (-90) * M_PI/180, (0) * M_PI/180, 0); + CGPathAddArc(path, NULL, rect.origin.x + rect.size.width - radius, rect.origin.y + rect.size.height - radius, radius, (0) * M_PI/180, (-270) * M_PI/180, 0); + CGPathAddArc(path, NULL, rect.origin.x + radius, rect.origin.y + rect.size.height - radius, radius, (-270) * M_PI/180, (-180) * M_PI/180, 0); + + return path; +} + ++ (void)drawRoundedRect:(CGRect)rect cornerRadius:(CGFloat)radius color:(UIColor *)color { + CGContextRef context = UIGraphicsGetCurrentContext(); + CGContextSaveGState(context); - CGContextAddRect(ctx, rect); - CGContextClip(ctx); + CGMutablePathRef path = PrettyKitCreateMutablePathForRoundedRect(rect, radius); + CGContextAddPath(context, path); + + [color setFill]; + CGContextDrawPath(context, kCGPathFill); + + CGContextRestoreGState(context); + CGPathRelease(path); +} + ++ (void)drawGradientRoundedRect:(CGRect)rect cornerRadius:(CGFloat)radius fromColor:(UIColor *)from toColor:(UIColor *)to { + CGContextRef context = UIGraphicsGetCurrentContext(); + CGContextSaveGState(context); + + CGMutablePathRef path = PrettyKitCreateMutablePathForRoundedRect(rect, radius); + CGContextAddPath(context, path); + CGContextClip(context); + + [PrettyDrawing drawGradientForContext:context + startPoint:CGPointMake(rect.origin.x + rect.size.width/2, rect.origin.y) + endPoint:CGPointMake(rect.origin.x + rect.size.width/2, rect.origin.y + rect.size.height) + fromColor:from + toColor:to]; + CGContextRestoreGState(context); + CGPathRelease(path); + +} + ++ (void)drawGradientForContext:(CGContextRef)context startPoint:(CGPoint)startPoint endPoint:(CGPoint)endPoint fromColor:(UIColor *)fromColor toColor:(UIColor *)toColor { CGColorSpaceRef colorSpace = CGColorSpaceCreateDeviceRGB(); - CGFloat locations[] = { 0.0, 1.0 }; - CGColorRef startColor = from.CGColor; - CGColorRef endColor = to.CGColor; - NSArray *colors = [NSArray arrayWithObjects:(id)startColor, (id)endColor, nil]; + CGFloat locations[] = {0.0, 1.0}; - CGGradientRef gradient = CGGradientCreateWithColors(colorSpace, - (CFArrayRef) colors, locations); + // iOS 4.3 safe way of drawing gradients. not as awesome as CGGradientCreateWithColors + CGFloat fromComponents[4]; + [fromColor getRGBColorComponents:fromComponents]; - CGPoint startPoint = CGPointMake(CGRectGetMidX(rect), CGRectGetMinY(rect)); - CGPoint endPoint = CGPointMake(CGRectGetMidX(rect), CGRectGetMaxY(rect)); + CGFloat toComponents[4]; + [toColor getRGBColorComponents:toComponents]; - CGContextDrawLinearGradient(ctx, gradient, startPoint, endPoint, 0); + CGFloat colors[8] = { fromComponents[0], fromComponents[1], fromComponents[2], fromComponents[3], + toComponents[0], toComponents[1], toComponents[2], toComponents[3]}; + + CGGradientRef gradient = CGGradientCreateWithColorComponents(colorSpace, colors, locations, 2); + + ///////////////////////////////////////////////////////////////////////// + + CGContextDrawLinearGradient(context, gradient, startPoint, endPoint, 0); CGGradientRelease(gradient); CGColorSpaceRelease(colorSpace); +} + ++ (void) drawGradient:(CGRect)rect fromColor:(UIColor *)from toColor:(UIColor *)to { + CGContextRef ctx = UIGraphicsGetCurrentContext(); + CGContextSaveGState(ctx); + + CGContextAddRect(ctx, rect); + CGContextClip(ctx); + CGPoint startPoint = CGPointMake(CGRectGetMidX(rect), CGRectGetMinY(rect)); + CGPoint endPoint = CGPointMake(CGRectGetMidX(rect), CGRectGetMaxY(rect)); + + [PrettyDrawing drawGradientForContext:ctx startPoint:startPoint endPoint:endPoint fromColor:from toColor:to]; + CGContextRestoreGState(ctx); } @@ -144,5 +199,38 @@ + (UIColor *) colorWithHex:(int)hex { blue:((float)(hex & 0xFF))/255.0 alpha:1.0]; } +-(void)getRGBColorComponents:(CGFloat [4])components { + if (CGColorGetNumberOfComponents([self CGColor]) == 4) { + const CGFloat *actualComponents = CGColorGetComponents([self CGColor]); + + components[0] = actualComponents[0]; + components[1] = actualComponents[1]; + components[2] = actualComponents[2]; + components[3] = actualComponents[3]; + + return; + } + + components[3] = CGColorGetAlpha([self CGColor]); + + CGColorSpaceRef rgbColorSpace = CGColorSpaceCreateDeviceRGB(); + unsigned char resultingPixel[4]; + CGContextRef context = CGBitmapContextCreate(&resultingPixel, + 1, + 1, + 8, + 4, + rgbColorSpace, + kCGImageAlphaNoneSkipLast); + CGContextSetFillColorWithColor(context, [self CGColor]); + CGContextFillRect(context, CGRectMake(0, 0, 1, 1)); + CGContextRelease(context); + CGColorSpaceRelease(rgbColorSpace); + + for (int component = 0; component < 3; component++) { + components[component] = resultingPixel[component] / 255.0f; + } +} + @end \ No newline at end of file From 9f5fe0f07454399f63114822a3d17236a2a20976 Mon Sep 17 00:00:00 2001 From: Jeremy Foo Date: Sat, 5 May 2012 20:36:28 +0800 Subject: [PATCH 21/48] make sure when switching, buttons that are selected will be in the correct state --- PrettyKit/PrettyTabBar.m | 22 +++++++++++----------- 1 file changed, 11 insertions(+), 11 deletions(-) diff --git a/PrettyKit/PrettyTabBar.m b/PrettyKit/PrettyTabBar.m index 38495ac..9368fec 100644 --- a/PrettyKit/PrettyTabBar.m +++ b/PrettyKit/PrettyTabBar.m @@ -45,7 +45,7 @@ -(void)_prettyTabButtonTapped:(UIGestureRecognizer *)gestureRecognizer; @implementation PrettyTabBar @synthesize upwardsShadowOpacity, downwardsShadowOpacity, gradientStartColor, gradientEndColor, separatorLineColor; -@synthesize prettyTabBarButtons = _prettyTabBarItems; +@synthesize prettyTabBarButtons = _prettyTabBarButtons; @synthesize _prettyTabBarButtons = __prettyTabBarButtons, _originalTabBarButtons = __originalTabBarButtons; @@ -105,19 +105,13 @@ - (id)init { #pragma mark - Overrides to handle internal PrettyTabBarButton if mode is set --(void)setPrettyTabBarItems:(BOOL)prettyTabBarItems { - - _prettyTabBarItems = prettyTabBarItems; - - for (UIView *view in __originalTabBarButtons) { - [self addSubview:view]; - } - - [__originalTabBarButtons removeAllObjects]; +-(void)setPrettyTabBarButtons:(BOOL)prettyTabBarButtons { + _prettyTabBarButtons = prettyTabBarButtons; [self setNeedsLayout]; } + -(void)setSelectedItem:(UITabBarItem *)selectedItem { if (self.prettyTabBarButtons) { // do stuff @@ -204,11 +198,17 @@ -(void)layoutSubviews { [button addGestureRecognizer:tappedButton]; [tappedButton release]; + if (item == self.selectedItem) { + button.selected = YES; + } else { + button.selected = NO; + } + [self addSubview:button]; [__prettyTabBarButtons addObject:button]; [button release]; } - } + } } From 5206138a2ce984a0af0e25f854bcd854ff0cdbc8 Mon Sep 17 00:00:00 2001 From: Jeremy Foo Date: Sat, 5 May 2012 20:41:28 +0800 Subject: [PATCH 22/48] more options for customization --- PrettyKit/PrettyTabBarButton.h | 8 +++- PrettyKit/PrettyTabBarButton.m | 68 +++++++++++++++++++--------------- 2 files changed, 44 insertions(+), 32 deletions(-) diff --git a/PrettyKit/PrettyTabBarButton.h b/PrettyKit/PrettyTabBarButton.h index ea5dc22..7e2d2d6 100644 --- a/PrettyKit/PrettyTabBarButton.h +++ b/PrettyKit/PrettyTabBarButton.h @@ -30,9 +30,11 @@ @interface PrettyTabBarButton : UIView @property (nonatomic, copy) NSString *title; -@property (nonatomic, retain) UIImage *image; @property (nonatomic, copy) NSString *badgeValue; +@property (nonatomic, retain) UIImage *image; +@property (nonatomic, retain) UIImage *highlightedImage; + @property (nonatomic) BOOL selected; @property (nonatomic, retain) UIFont *font; @@ -43,7 +45,9 @@ @property (nonatomic) CGSize textShadowOffset; @property (nonatomic) BOOL wantTextShadow; -@property (nonatomic, retain) UIImage *highlightedImage; +@property (nonatomic, retain) UIColor *highlightGradientStartColor; +@property (nonatomic, retain) UIColor *highlightGradientEndColor; +@property (nonatomic, retain) UIImage *highlightImage; @property (nonatomic, retain) UIColor *badgeBorderColor; @property (nonatomic, retain) UIColor *badgeGradientStartColor; diff --git a/PrettyKit/PrettyTabBarButton.m b/PrettyKit/PrettyTabBarButton.m index e35ce71..8b2117f 100644 --- a/PrettyKit/PrettyTabBarButton.m +++ b/PrettyKit/PrettyTabBarButton.m @@ -28,24 +28,28 @@ #import "PrettyTabBarButton.h" #import "PrettyDrawing.h" -#define default_want_text_shadow YES -#define default_text_shadow_offset CGSizeMake(0,-1) -#define default_text_shadow_opacity 0.5 -#define default_font [UIFont fontWithName:@"HelveticaNeue-Bold" size:11] -#define default_text_color [UIColor colorWithWhite:0.2 alpha:1.0] -#define default_highlighted_text_color [UIColor colorWithWhite:0.90 alpha:1.0] -#define default_badge_font [UIFont fontWithName:@"HelveticaNeue-Bold" size:13] -#define default_badge_gradient_start_color [UIColor colorWithRed:0.9 green:0.000 blue:0.000 alpha:1.000] -#define default_badge_gradient_end_color [UIColor colorWithRed:0.1 green:0.000 blue:0.000 alpha:1.000] -#define default_badge_border_color [UIColor whiteColor] -#define default_badge_shadow_opacity 0.75 -#define default_badge_shadow_offset CGSizeMake(0,1.5) -#define default_badge_text_color [UIColor whiteColor] +#define default_want_text_shadow YES +#define default_text_shadow_offset CGSizeMake(0,-1) +#define default_text_shadow_opacity 0.5 +#define default_font [UIFont fontWithName:@"HelveticaNeue-Bold" size:11] +#define default_text_color [UIColor colorWithWhite:0.2 alpha:1.0] +#define default_highlighted_text_color [UIColor colorWithWhite:0.90 alpha:1.0] +#define default_badge_font [UIFont fontWithName:@"HelveticaNeue-Bold" size:11] +#define default_badge_gradient_start_color [UIColor colorWithRed:1.000 green:0.000 blue:0.000 alpha:1.000] +#define default_badge_gradient_end_color [UIColor colorWithRed:0.6 green:0.000 blue:0.000 alpha:1.000] +#define default_badge_border_color [UIColor whiteColor] +#define default_badge_shadow_opacity 0.75 +#define default_badge_shadow_offset CGSizeMake(0,2) +#define default_badge_text_color [UIColor whiteColor] +#define default_highlight_gradient_start_color [UIColor colorWithWhite:0.4 alpha:1.0] +#define default_highlight_gradient_end_color [UIColor colorWithWhite:0.1 alpha:1.0] + @implementation PrettyTabBarButton -@synthesize title = _title, image = _image, badgeValue = _badgeValue; +@synthesize title = _title, image = _image, highlightedImage, badgeValue = _badgeValue; @synthesize selected = _selected; -@synthesize textColor, font, highlightedTextColor, highlightedImage; +@synthesize textColor, font, highlightedTextColor; +@synthesize highlightImage, highlightGradientStartColor, highlightGradientEndColor; @synthesize wantTextShadow, textShadowOpacity, textShadowOffset; @synthesize badgeBorderColor, badgeGradientEndColor, badgeGradientStartColor, badgeFont, badgeShadowOffset, badgeShadowOpacity, badgeTextColor; @@ -87,16 +91,21 @@ -(void)dealloc { [_title release], _title = nil; [_image release], _image = nil; [_badgeValue release], _badgeValue = nil; - + + self.highlightedImage = nil; + self.font = nil; self.textColor = nil; self.highlightedTextColor = nil; - self.highlightedImage = nil; self.badgeBorderColor = nil; self.badgeGradientStartColor = nil; self.badgeGradientEndColor = nil; self.badgeFont = nil; - self.badgeTextColor = nil; + self.badgeTextColor = nil; + + self.highlightImage = nil; + self.highlightGradientStartColor = nil; + self.highlightGradientEndColor = nil; [super dealloc]; } @@ -120,6 +129,9 @@ - (void) initializeVars self.badgeShadowOpacity = default_badge_shadow_opacity; self.badgeFont = default_badge_font; self.badgeTextColor = default_badge_text_color; + self.highlightImage = nil; + self.highlightGradientStartColor = default_highlight_gradient_start_color; + self.highlightGradientEndColor = default_highlight_gradient_end_color; // intialize values; self.tag = -1; @@ -157,19 +169,15 @@ - (void)drawRect:(CGRect)rect // draw selection background if (self.selected) { - if (self.highlightedImage) { + if (self.highlightImage) { + [self.highlightImage drawInRect:CGRectMake(2, 1, self.frame.size.width - 2, self.frame.size.height - 1)]; - } else { - - // for iOS 4.3 - CGContextSetFillColorWithColor(context, [[UIColor colorWithWhite:0.75 alpha:1.0] CGColor]); - CGContextFillRect(context, CGRectMake(0, 2, self.frame.size.width, self.frame.size.height - 2)); - - // works for iOS 5.0 so just layering it on - [PrettyDrawing drawGradient:CGRectMake(0, 2, self.frame.size.width, self.frame.size.height - 2) - fromColor:[UIColor colorWithWhite:0.75 alpha:1.0] - toColor:[UIColor colorWithWhite:0.1 alpha:1.0]]; + } else { + [PrettyDrawing drawGradientRoundedRect:CGRectMake(2, 3, self.frame.size.width - 4, self.frame.size.height - 5) + cornerRadius:3.0 + fromColor:[UIColor colorWithWhite:0.4 alpha:1.0] + toColor:[UIColor colorWithWhite:0.1 alpha:1.0]]; } } @@ -208,7 +216,7 @@ - (void)drawRect:(CGRect)rect if (badgeWidth < (badgeHeight)) badgeWidth = badgeHeight; - CGRect badgeFrame = CGRectMake(self.frame.size.width - badgeWidth - 2, 3, badgeWidth, badgeHeight); + CGRect badgeFrame = CGRectMake((self.frame.size.width - badgeWidth)/2 + 20, 1, badgeWidth, badgeHeight); // draw outter border CGMutablePathRef path = CGPathCreateMutable(); From c213ccc3290927dcd515e821fefbfbf0c0378650 Mon Sep 17 00:00:00 2001 From: Jeremy Foo Date: Sun, 6 May 2012 15:55:23 +0800 Subject: [PATCH 23/48] tightly coupled interfaces to deal with selection of tab bar also modified font style to match defat UITabBarButtons' --- PrettyKit/PrettyTabBarButton.h | 4 +++ PrettyKit/PrettyTabBarButton.m | 45 ++++++++++++++++++++++++++++++++-- 2 files changed, 47 insertions(+), 2 deletions(-) diff --git a/PrettyKit/PrettyTabBarButton.h b/PrettyKit/PrettyTabBarButton.h index 7e2d2d6..2ca5513 100644 --- a/PrettyKit/PrettyTabBarButton.h +++ b/PrettyKit/PrettyTabBarButton.h @@ -26,6 +26,7 @@ // SOFTWARE. #import +#import "PrettyTabBar.h" @interface PrettyTabBarButton : UIView @@ -57,6 +58,9 @@ @property (nonatomic, retain) UIFont *badgeFont; @property (nonatomic, retain) UIColor *badgeTextColor; +@property (nonatomic, assign) PrettyTabBar *delegate; +@property (nonatomic, assign) UITabBarItem *tabBarItem; + -(id)initWithTitle:(NSString *)title image:(UIImage *)image tag:(NSInteger)tag; @end diff --git a/PrettyKit/PrettyTabBarButton.m b/PrettyKit/PrettyTabBarButton.m index 8b2117f..f50f39e 100644 --- a/PrettyKit/PrettyTabBarButton.m +++ b/PrettyKit/PrettyTabBarButton.m @@ -31,7 +31,7 @@ #define default_want_text_shadow YES #define default_text_shadow_offset CGSizeMake(0,-1) #define default_text_shadow_opacity 0.5 -#define default_font [UIFont fontWithName:@"HelveticaNeue-Bold" size:11] +#define default_font [UIFont fontWithName:@"HelveticaNeue-Bold" size:10] #define default_text_color [UIColor colorWithWhite:0.2 alpha:1.0] #define default_highlighted_text_color [UIColor colorWithWhite:0.90 alpha:1.0] #define default_badge_font [UIFont fontWithName:@"HelveticaNeue-Bold" size:11] @@ -44,10 +44,13 @@ #define default_highlight_gradient_start_color [UIColor colorWithWhite:0.4 alpha:1.0] #define default_highlight_gradient_end_color [UIColor colorWithWhite:0.1 alpha:1.0] +@interface PrettyTabBarButton (/* Pirvate Method */) +-(void)_prettyTabButtonTapped:(UIGestureRecognizer *)gestureRecognizer; +@end @implementation PrettyTabBarButton @synthesize title = _title, image = _image, highlightedImage, badgeValue = _badgeValue; -@synthesize selected = _selected; +@synthesize selected = _selected, delegate, tabBarItem; @synthesize textColor, font, highlightedTextColor; @synthesize highlightImage, highlightGradientStartColor, highlightGradientEndColor; @synthesize wantTextShadow, textShadowOpacity, textShadowOffset; @@ -145,6 +148,42 @@ - (void) initializeVars self.opaque = NO; self.backgroundColor = [UIColor clearColor]; + // Since we're tight coupling PrettyTabBar and its associated PrettyTabBarButton + // its fine if we implement touch detection on the button itself + UITapGestureRecognizer *tappedButton = [[UITapGestureRecognizer alloc] initWithTarget:self action:@selector(_prettyTabButtonTapped:)]; + tappedButton.numberOfTapsRequired = 1; + [self addGestureRecognizer:tappedButton]; + [tappedButton release]; +} + +#pragma mark - Selection and Accessors + +-(void)_prettyTabButtonTapped:(UIGestureRecognizer *)gestureRecognizer { + + // Work around to allow PrettyTabBar with the pretty buttons enabled + // to work properly with UITabBarControllers. + // This is because UITabBars disallow direct manipulation of its properties + // if it is being managed by a UITabBarController. + + if (self.delegate) { + if ([self.delegate respondsToSelector:@selector(_resetSelectionStates)]) + [self.delegate performSelector:@selector(_resetSelectionStates)]; + + if (self.tabBarItem) { + // if delegate is the TabBarController, we can only modify selection + // via its public interfaces + if ([self.delegate.delegate isKindOfClass:[UITabBarController class]]) { + [((UITabBarController *)self.delegate.delegate) setSelectedIndex:self.tag]; + + } else { + [self.delegate setSelectedItem:self.tabBarItem]; + + } + } + + } + + self.selected = YES; } -(void)setSelected:(BOOL)selected { @@ -161,6 +200,8 @@ -(void)setBadgeValue:(NSString *)badgeValue { [self setNeedsDisplay]; } +#pragma mark - Drawing + - (void)drawRect:(CGRect)rect { [super drawRect:rect]; From 43223cafd5b0b5f54a31769310766115e52cc1cd Mon Sep 17 00:00:00 2001 From: Jeremy Foo Date: Sun, 6 May 2012 15:56:01 +0800 Subject: [PATCH 24/48] internal method to handle resetting of selections of prettytabbarbuttons --- PrettyKit/PrettyTabBar.h | 1 - PrettyKit/PrettyTabBar.m | 53 ++++++++++++++-------------------------- 2 files changed, 19 insertions(+), 35 deletions(-) diff --git a/PrettyKit/PrettyTabBar.h b/PrettyKit/PrettyTabBar.h index ae82ec8..71e7c2a 100644 --- a/PrettyKit/PrettyTabBar.h +++ b/PrettyKit/PrettyTabBar.h @@ -74,5 +74,4 @@ By default is NO. */ @property (nonatomic) BOOL prettyTabBarButtons; - @end diff --git a/PrettyKit/PrettyTabBar.m b/PrettyKit/PrettyTabBar.m index 9368fec..8acf62d 100644 --- a/PrettyKit/PrettyTabBar.m +++ b/PrettyKit/PrettyTabBar.m @@ -40,7 +40,7 @@ @interface PrettyTabBar (/* Private Methods */) @property (nonatomic, retain) NSMutableArray *_prettyTabBarButtons; @property (nonatomic, retain) NSMutableArray *_originalTabBarButtons; --(void)_prettyTabButtonTapped:(UIGestureRecognizer *)gestureRecognizer; +-(void)_resetSelectionStates; @end @implementation PrettyTabBar @@ -103,41 +103,21 @@ - (id)init { return self; } -#pragma mark - Overrides to handle internal PrettyTabBarButton if mode is set +#pragma mark - Overrides to handle internal PrettyTabBarButton -(void)setPrettyTabBarButtons:(BOOL)prettyTabBarButtons { _prettyTabBarButtons = prettyTabBarButtons; - [self setNeedsLayout]; + if (self.superview) + [self setNeedsLayout]; } - --(void)setSelectedItem:(UITabBarItem *)selectedItem { +-(void)_resetSelectionStates { if (self.prettyTabBarButtons) { - // do stuff - NSInteger index = [self.items indexOfObject:selectedItem]; - - for (int i=0;i<[__prettyTabBarButtons count];i++) { - if (i == index) { - ((PrettyTabBarButton *)[__prettyTabBarButtons objectAtIndex:i]).selected = YES; - } else { - ((PrettyTabBarButton *)[__prettyTabBarButtons objectAtIndex:i]).selected = NO; - } + for (PrettyTabBarButton *button in __prettyTabBarButtons) { + button.selected = NO; } - - if ([self.delegate respondsToSelector:@selector(tabBar:didSelectItem:)]) { - [self.delegate tabBar:self didSelectItem:[self.items objectAtIndex:index]]; - } - - } else { - [super setSelectedItem:selectedItem]; } - -} - --(void)_prettyTabButtonTapped:(UIGestureRecognizer *)gestureRecognizer { - NSInteger index = gestureRecognizer.view.tag; - [self setSelectedItem:[self.items objectAtIndex:index]]; } -(void)observeValueForKeyPath:(NSString *)keyPath ofObject:(id)object change:(NSDictionary *)change context:(void *)context { @@ -155,6 +135,15 @@ -(void)observeValueForKeyPath:(NSString *)keyPath ofObject:(id)object change:(NS #pragma mark - Display -(void)layoutSubviews { + + if (!self.prettyTabBarButtons) { + for (UIView *view in __originalTabBarButtons) { + [self addSubview:view]; + } + + [__originalTabBarButtons removeAllObjects]; + } + [super layoutSubviews]; if ([self.items count] > 5) @@ -173,8 +162,7 @@ -(void)layoutSubviews { } } } - - + if (self.prettyTabBarButtons) { [__prettyTabBarButtons removeAllObjects]; @@ -192,11 +180,8 @@ -(void)layoutSubviews { button.frame = CGRectMake(i * itemWidth, 0, itemWidth, self.frame.size.height); button.autoresizingMask = UIViewAutoresizingFlexibleHeight | UIViewAutoresizingFlexibleWidth; button.badgeValue = item.badgeValue; - - UITapGestureRecognizer *tappedButton = [[UITapGestureRecognizer alloc] initWithTarget:self action:@selector(_prettyTabButtonTapped:)]; - tappedButton.numberOfTapsRequired = 1; - [button addGestureRecognizer:tappedButton]; - [tappedButton release]; + button.delegate = self; + button.tabBarItem = item; if (item == self.selectedItem) { button.selected = YES; From e93edd85b4da2a11f443238f7593baee8f7c3a45 Mon Sep 17 00:00:00 2001 From: Jeremy Foo Date: Sun, 6 May 2012 17:02:33 +0800 Subject: [PATCH 25/48] documentation for PrettyTabBarButton --- PrettyKit/PrettyTabBarButton.h | 98 +++++++++++++++++++++++++++++++--- PrettyKit/PrettyTabBarButton.m | 8 +-- 2 files changed, 93 insertions(+), 13 deletions(-) diff --git a/PrettyKit/PrettyTabBarButton.h b/PrettyKit/PrettyTabBarButton.h index 2ca5513..834c5d5 100644 --- a/PrettyKit/PrettyTabBarButton.h +++ b/PrettyKit/PrettyTabBarButton.h @@ -30,35 +30,119 @@ @interface PrettyTabBarButton : UIView -@property (nonatomic, copy) NSString *title; -@property (nonatomic, copy) NSString *badgeValue; - -@property (nonatomic, retain) UIImage *image; +/** Specifies the image to use when the Button is selected. + If it is not specified, the button will use the normal image in another tint. + + By default is `nil`. */ @property (nonatomic, retain) UIImage *highlightedImage; -@property (nonatomic) BOOL selected; - +/** Specifies the font to use for the title of the button + + By default is `[UIFont fontWithName:@"HelveticaNeue-Bold" size:10]`. */ @property (nonatomic, retain) UIFont *font; + +/** Specifies the color for the title of the button + + By default is `[UIColor colorWithWhite:0.2 alpha:1.0]`. */ @property (nonatomic, retain) UIColor *textColor; + +/** Specifies the color for the title of the button when its been selected + + By default is `[UIColor colorWithWhite:0.90 alpha:1.0]`. */ @property (nonatomic, retain) UIColor *highlightedTextColor; +/** Specifies the opacity of the title's shadow + + By default is `0.5`. */ @property (nonatomic) CGFloat textShadowOpacity; + +/** Specifies the offset for the title's shadow + + By default is `CGSizeMake(0,-1)`. */ @property (nonatomic) CGSize textShadowOffset; -@property (nonatomic) BOOL wantTextShadow; +/** Specifies the start color for the highlight's gradient (when selected) + + By default is `[UIColor colorWithWhite:0.4 alpha:1.0]`. */ @property (nonatomic, retain) UIColor *highlightGradientStartColor; + +/** Specifies the end color for the highlight's gradient (when selected) + + By default is `[UIColor colorWithWhite:0.1 alpha:1.0]`. */ @property (nonatomic, retain) UIColor *highlightGradientEndColor; + +/** Specifies the image to use in place of the highlight gradient. + + By default is `nil`. */ @property (nonatomic, retain) UIImage *highlightImage; +/** Specifies the border color for the badge + + By default is `[UIColor whiteColor]`. */ @property (nonatomic, retain) UIColor *badgeBorderColor; + +/** Specifies the start color for the badge's gradient + + By default is `[UIColor colorWithRed:1.000 green:0.000 blue:0.000 alpha:1.000]`. */ @property (nonatomic, retain) UIColor *badgeGradientStartColor; + +/** Specifies the end color for the badge's gradient + + By default is `[UIColor colorWithRed:0.6 green:0.000 blue:0.000 alpha:1.000]`. */ @property (nonatomic, retain) UIColor *badgeGradientEndColor; + +/** Specifies the shadow opacity for the badge + + By default is `0.75`. */ @property (nonatomic) CGFloat badgeShadowOpacity; + +/** Specifies the shadow offset for the badge + + By default is `CGSizeMake(0,2)`. */ @property (nonatomic) CGSize badgeShadowOffset; + +/** Specifies the font used for the value of the badge + + By default is `[UIFont fontWithName:@"HelveticaNeue-Bold" size:11]`. */ @property (nonatomic, retain) UIFont *badgeFont; + +/** Specifies the color used for the text in the badge's value + + By default is `[UIColor whiteColor]`. */ @property (nonatomic, retain) UIColor *badgeTextColor; +////////////////////////////////////////////////////////////////////////////// +// Internal Methods for Tight coupling with PrettyTabBar +////////////////////////////////////////////////////////////////////////////// + +/** Specifies the title of the button + + By default is `nil`. */ +@property (nonatomic, copy) NSString *title; + +/** Specifies the value of the badge on the button + + By default is `nil`. */ +@property (nonatomic, copy) NSString *badgeValue; + +/** Specifies the image of the button + + By default is `nil`. */ +@property (nonatomic, retain) UIImage *image; + +/** Specifies if the button is selected or not + + By default is `NO`. */ +@property (nonatomic) BOOL selected; + +/** Specifies the delegate of the button (PrettyTabBar) + + By default is `nil`. */ @property (nonatomic, assign) PrettyTabBar *delegate; + +/** Specifies the tabBarItem associated with this button + + By default is `nil`. */ @property (nonatomic, assign) UITabBarItem *tabBarItem; -(id)initWithTitle:(NSString *)title image:(UIImage *)image tag:(NSInteger)tag; diff --git a/PrettyKit/PrettyTabBarButton.m b/PrettyKit/PrettyTabBarButton.m index f50f39e..82f65df 100644 --- a/PrettyKit/PrettyTabBarButton.m +++ b/PrettyKit/PrettyTabBarButton.m @@ -28,7 +28,6 @@ #import "PrettyTabBarButton.h" #import "PrettyDrawing.h" -#define default_want_text_shadow YES #define default_text_shadow_offset CGSizeMake(0,-1) #define default_text_shadow_opacity 0.5 #define default_font [UIFont fontWithName:@"HelveticaNeue-Bold" size:10] @@ -53,7 +52,7 @@ @implementation PrettyTabBarButton @synthesize selected = _selected, delegate, tabBarItem; @synthesize textColor, font, highlightedTextColor; @synthesize highlightImage, highlightGradientStartColor, highlightGradientEndColor; -@synthesize wantTextShadow, textShadowOpacity, textShadowOffset; +@synthesize textShadowOpacity, textShadowOffset; @synthesize badgeBorderColor, badgeGradientEndColor, badgeGradientStartColor, badgeFont, badgeShadowOffset, badgeShadowOpacity, badgeTextColor; -(id)initWithTitle:(NSString *)title image:(UIImage *)image tag:(NSInteger)tag { @@ -122,7 +121,6 @@ - (void) initializeVars self.textColor = default_text_color; self.highlightedTextColor = default_highlighted_text_color; self.highlightedImage = nil; - self.wantTextShadow = default_want_text_shadow; self.textShadowOpacity = default_text_shadow_opacity; self.textShadowOffset = default_text_shadow_offset; self.badgeBorderColor = default_badge_border_color; @@ -225,9 +223,7 @@ - (void)drawRect:(CGRect)rect // draw text CGContextSaveGState(context); - if (self.wantTextShadow) { - CGContextSetShadow(context, self.textShadowOffset, self.textShadowOpacity); - } + CGContextSetShadow(context, self.textShadowOffset, self.textShadowOpacity); if (self.selected) { [self.highlightedTextColor setFill]; From 4607a00e292c8649e60dfd4de746471d885f0eab Mon Sep 17 00:00:00 2001 From: Jeremy Foo Date: Sun, 6 May 2012 17:09:49 +0800 Subject: [PATCH 26/48] switched to using a UIControl subclass. Clearer separation between Views and Controllers. --- PrettyKit/PrettyTabBar.m | 16 +++++++++----- PrettyKit/PrettyTabBarButton.h | 18 +--------------- PrettyKit/PrettyTabBarButton.m | 38 ++-------------------------------- 3 files changed, 14 insertions(+), 58 deletions(-) diff --git a/PrettyKit/PrettyTabBar.m b/PrettyKit/PrettyTabBar.m index 8acf62d..ed638e6 100644 --- a/PrettyKit/PrettyTabBar.m +++ b/PrettyKit/PrettyTabBar.m @@ -40,7 +40,7 @@ @interface PrettyTabBar (/* Private Methods */) @property (nonatomic, retain) NSMutableArray *_prettyTabBarButtons; @property (nonatomic, retain) NSMutableArray *_originalTabBarButtons; --(void)_resetSelectionStates; +-(void)_prettyTabBarButtonTapped:(id)sender; @end @implementation PrettyTabBar @@ -112,11 +112,19 @@ -(void)setPrettyTabBarButtons:(BOOL)prettyTabBarButtons { [self setNeedsLayout]; } --(void)_resetSelectionStates { +-(void)_prettyTabBarButtonTapped:(id)sender { if (self.prettyTabBarButtons) { for (PrettyTabBarButton *button in __prettyTabBarButtons) { button.selected = NO; } + + ((PrettyTabBarButton *)sender).selected = YES; + + if ([sender isKindOfClass:[PrettyTabBarButton class]]) { + if ([self.delegate isKindOfClass:[UITabBarController class]]) { + [((UITabBarController *)self.delegate) setSelectedIndex:((PrettyTabBarButton *)sender).tag]; + } + } } } @@ -133,7 +141,6 @@ -(void)observeValueForKeyPath:(NSString *)keyPath ofObject:(id)object change:(NS } #pragma mark - Display - -(void)layoutSubviews { if (!self.prettyTabBarButtons) { @@ -180,8 +187,7 @@ -(void)layoutSubviews { button.frame = CGRectMake(i * itemWidth, 0, itemWidth, self.frame.size.height); button.autoresizingMask = UIViewAutoresizingFlexibleHeight | UIViewAutoresizingFlexibleWidth; button.badgeValue = item.badgeValue; - button.delegate = self; - button.tabBarItem = item; + [button addTarget:self action:@selector(_prettyTabBarButtonTapped:) forControlEvents:UIControlEventTouchUpInside]; if (item == self.selectedItem) { button.selected = YES; diff --git a/PrettyKit/PrettyTabBarButton.h b/PrettyKit/PrettyTabBarButton.h index 834c5d5..92ca41d 100644 --- a/PrettyKit/PrettyTabBarButton.h +++ b/PrettyKit/PrettyTabBarButton.h @@ -26,9 +26,8 @@ // SOFTWARE. #import -#import "PrettyTabBar.h" -@interface PrettyTabBarButton : UIView +@interface PrettyTabBarButton : UIControl /** Specifies the image to use when the Button is selected. If it is not specified, the button will use the normal image in another tint. @@ -130,21 +129,6 @@ By default is `nil`. */ @property (nonatomic, retain) UIImage *image; -/** Specifies if the button is selected or not - - By default is `NO`. */ -@property (nonatomic) BOOL selected; - -/** Specifies the delegate of the button (PrettyTabBar) - - By default is `nil`. */ -@property (nonatomic, assign) PrettyTabBar *delegate; - -/** Specifies the tabBarItem associated with this button - - By default is `nil`. */ -@property (nonatomic, assign) UITabBarItem *tabBarItem; - -(id)initWithTitle:(NSString *)title image:(UIImage *)image tag:(NSInteger)tag; @end diff --git a/PrettyKit/PrettyTabBarButton.m b/PrettyKit/PrettyTabBarButton.m index 82f65df..b7f5054 100644 --- a/PrettyKit/PrettyTabBarButton.m +++ b/PrettyKit/PrettyTabBarButton.m @@ -44,12 +44,12 @@ #define default_highlight_gradient_end_color [UIColor colorWithWhite:0.1 alpha:1.0] @interface PrettyTabBarButton (/* Pirvate Method */) --(void)_prettyTabButtonTapped:(UIGestureRecognizer *)gestureRecognizer; + @end @implementation PrettyTabBarButton @synthesize title = _title, image = _image, highlightedImage, badgeValue = _badgeValue; -@synthesize selected = _selected, delegate, tabBarItem; +@synthesize selected = _selected; @synthesize textColor, font, highlightedTextColor; @synthesize highlightImage, highlightGradientStartColor, highlightGradientEndColor; @synthesize textShadowOpacity, textShadowOffset; @@ -146,44 +146,10 @@ - (void) initializeVars self.opaque = NO; self.backgroundColor = [UIColor clearColor]; - // Since we're tight coupling PrettyTabBar and its associated PrettyTabBarButton - // its fine if we implement touch detection on the button itself - UITapGestureRecognizer *tappedButton = [[UITapGestureRecognizer alloc] initWithTarget:self action:@selector(_prettyTabButtonTapped:)]; - tappedButton.numberOfTapsRequired = 1; - [self addGestureRecognizer:tappedButton]; - [tappedButton release]; } #pragma mark - Selection and Accessors --(void)_prettyTabButtonTapped:(UIGestureRecognizer *)gestureRecognizer { - - // Work around to allow PrettyTabBar with the pretty buttons enabled - // to work properly with UITabBarControllers. - // This is because UITabBars disallow direct manipulation of its properties - // if it is being managed by a UITabBarController. - - if (self.delegate) { - if ([self.delegate respondsToSelector:@selector(_resetSelectionStates)]) - [self.delegate performSelector:@selector(_resetSelectionStates)]; - - if (self.tabBarItem) { - // if delegate is the TabBarController, we can only modify selection - // via its public interfaces - if ([self.delegate.delegate isKindOfClass:[UITabBarController class]]) { - [((UITabBarController *)self.delegate.delegate) setSelectedIndex:self.tag]; - - } else { - [self.delegate setSelectedItem:self.tabBarItem]; - - } - } - - } - - self.selected = YES; -} - -(void)setSelected:(BOOL)selected { _selected = selected; [self setNeedsDisplay]; From 62fc918ab831f4b56c5409c8f5d6c6b089759393 Mon Sep 17 00:00:00 2001 From: Jeremy Foo Date: Sun, 6 May 2012 17:27:45 +0800 Subject: [PATCH 27/48] set custom prettytabbarbutton properties --- PrettyKit/PrettyTabBar.h | 82 +++++++++++++++++++++++++++++++++++++++- PrettyKit/PrettyTabBar.m | 63 +++++++++++++++++++++++++++--- 2 files changed, 138 insertions(+), 7 deletions(-) diff --git a/PrettyKit/PrettyTabBar.h b/PrettyKit/PrettyTabBar.h index 71e7c2a..968f5c6 100644 --- a/PrettyKit/PrettyTabBar.h +++ b/PrettyKit/PrettyTabBar.h @@ -68,10 +68,88 @@ By default is a black tone. */ @property (nonatomic, retain) UIColor *separatorLineColor; -/** Specifies that PrettyTabBarButtons should be used instead of the - default UITabBarButtons +///////////////////////////////////////////////////////////////////////////// +// Pretty Tab Bar Button Implementation & Customization +///////////////////////////////////////////////////////////////////////////// + +/** Specifies that PrettyTabBarButtons should be used instead of the default UITabBarButtons By default is NO. */ @property (nonatomic) BOOL prettyTabBarButtons; +/** Specifies the font to use for the title of the button + + By default is `[UIFont fontWithName:@"HelveticaNeue-Bold" size:10]`. */ +@property (nonatomic, retain) UIFont *prettyButtonTitleFont; + +/** Specifies the color for the title of the button + + By default is `[UIColor colorWithWhite:0.2 alpha:1.0]`. */ +@property (nonatomic, retain) UIColor *prettyButtonTitleTextColor; + +/** Specifies the color for the title of the button when its been selected + + By default is `[UIColor colorWithWhite:0.90 alpha:1.0]`. */ +@property (nonatomic, retain) UIColor *prettyButtonTitleHighlightedTextColor; + +/** Specifies the opacity of the title's shadow + + By default is `0.5`. */ +@property (nonatomic) CGFloat prettyButtonTitleTextShadowOpacity; + +/** Specifies the offset for the title's shadow + + By default is `CGSizeMake(0,-1)`. */ +@property (nonatomic) CGSize prettyButtonTitleTextShadowOffset; + +/** Specifies the start color for the highlight's gradient (when selected) + + By default is `[UIColor colorWithWhite:0.4 alpha:1.0]`. */ +@property (nonatomic, retain) UIColor *prettyButtonHighlightGradientStartColor; + +/** Specifies the end color for the highlight's gradient (when selected) + + By default is `[UIColor colorWithWhite:0.1 alpha:1.0]`. */ +@property (nonatomic, retain) UIColor *prettyButtonHighlightGradientEndColor; + +/** Specifies the image to use in place of the highlight gradient. + + By default is `nil`. */ +@property (nonatomic, retain) UIImage *prettyButtonHighlightImage; + +/** Specifies the border color for the badge + + By default is `[UIColor whiteColor]`. */ +@property (nonatomic, retain) UIColor *prettyButtonBadgeBorderColor; + +/** Specifies the start color for the badge's gradient + + By default is `[UIColor colorWithRed:1.000 green:0.000 blue:0.000 alpha:1.000]`. */ +@property (nonatomic, retain) UIColor *prettyButtonBadgeGradientStartColor; + +/** Specifies the end color for the badge's gradient + + By default is `[UIColor colorWithRed:0.6 green:0.000 blue:0.000 alpha:1.000]`. */ +@property (nonatomic, retain) UIColor *prettyButtonBadgeGradientEndColor; + +/** Specifies the shadow opacity for the badge + + By default is `0.75`. */ +@property (nonatomic) CGFloat prettyButtonBadgeShadowOpacity; + +/** Specifies the shadow offset for the badge + + By default is `CGSizeMake(0,2)`. */ +@property (nonatomic) CGSize prettyButtonBadgeShadowOffset; + +/** Specifies the font used for the value of the badge + + By default is `[UIFont fontWithName:@"HelveticaNeue-Bold" size:11]`. */ +@property (nonatomic, retain) UIFont *prettyButtonBadgeFont; + +/** Specifies the color used for the text in the badge's value + + By default is `[UIColor whiteColor]`. */ +@property (nonatomic, retain) UIColor *prettyButtonBadgeTextColor; + @end diff --git a/PrettyKit/PrettyTabBar.m b/PrettyKit/PrettyTabBar.m index ed638e6..b4e090d 100644 --- a/PrettyKit/PrettyTabBar.m +++ b/PrettyKit/PrettyTabBar.m @@ -31,11 +31,26 @@ #import "PrettyDrawing.h" #import "PrettyTabBarButton.h" -#define default_upwards_shadow_opacity 0.5 -#define default_downwards_shadow_opacity 0.5 -#define default_gradient_start_color [UIColor colorWithHex:0x444444] -#define default_gradient_end_color [UIColor colorWithHex:0x060606] -#define default_separator_line_color [UIColor colorWithHex:0x666666] +#define default_upwards_shadow_opacity 0.5 +#define default_downwards_shadow_opacity 0.5 +#define default_gradient_start_color [UIColor colorWithHex:0x444444] +#define default_gradient_end_color [UIColor colorWithHex:0x060606] +#define default_separator_line_color [UIColor colorWithHex:0x666666] + +#define default_text_shadow_offset CGSizeMake(0,-1) +#define default_text_shadow_opacity 0.5 +#define default_font [UIFont fontWithName:@"HelveticaNeue-Bold" size:10] +#define default_text_color [UIColor colorWithWhite:0.2 alpha:1.0] +#define default_highlighted_text_color [UIColor colorWithWhite:0.90 alpha:1.0] +#define default_badge_font [UIFont fontWithName:@"HelveticaNeue-Bold" size:11] +#define default_badge_gradient_start_color [UIColor colorWithRed:1.000 green:0.000 blue:0.000 alpha:1.000] +#define default_badge_gradient_end_color [UIColor colorWithRed:0.6 green:0.000 blue:0.000 alpha:1.000] +#define default_badge_border_color [UIColor whiteColor] +#define default_badge_shadow_opacity 0.75 +#define default_badge_shadow_offset CGSizeMake(0,2) +#define default_badge_text_color [UIColor whiteColor] +#define default_highlight_gradient_start_color [UIColor colorWithWhite:0.4 alpha:1.0] +#define default_highlight_gradient_end_color [UIColor colorWithWhite:0.1 alpha:1.0] @interface PrettyTabBar (/* Private Methods */) @property (nonatomic, retain) NSMutableArray *_prettyTabBarButtons; @@ -47,6 +62,10 @@ @implementation PrettyTabBar @synthesize upwardsShadowOpacity, downwardsShadowOpacity, gradientStartColor, gradientEndColor, separatorLineColor; @synthesize prettyTabBarButtons = _prettyTabBarButtons; +@synthesize prettyButtonTitleFont, prettyButtonTitleTextColor, prettyButtonTitleHighlightedTextColor, prettyButtonTitleTextShadowOpacity, prettyButtonTitleTextShadowOffset; +@synthesize prettyButtonHighlightGradientStartColor, prettyButtonHighlightGradientEndColor, prettyButtonHighlightImage; +@synthesize prettyButtonBadgeBorderColor, prettyButtonBadgeGradientStartColor, prettyButtonBadgeGradientEndColor, prettyButtonBadgeShadowOpacity, prettyButtonBadgeShadowOffset, prettyButtonBadgeFont, prettyButtonBadgeTextColor; + @synthesize _prettyTabBarButtons = __prettyTabBarButtons, _originalTabBarButtons = __originalTabBarButtons; #pragma mark - Object Life Cycle @@ -74,8 +93,25 @@ - (void) initializeVars self.gradientEndColor = default_gradient_end_color; self.separatorLineColor = default_separator_line_color; + // pretty button stuff __prettyTabBarButtons = [[NSMutableArray arrayWithCapacity:5] retain]; __originalTabBarButtons = [[NSMutableArray arrayWithCapacity:0] retain]; + + self.prettyButtonTitleFont = default_font; + self.prettyButtonTitleTextColor = default_text_color; + self.prettyButtonTitleHighlightedTextColor = default_highlighted_text_color; + self.prettyButtonTitleTextShadowOpacity = default_text_shadow_opacity; + self.prettyButtonTitleTextShadowOffset = default_text_shadow_offset; + self.prettyButtonBadgeBorderColor = default_badge_border_color; + self.prettyButtonBadgeGradientStartColor = default_badge_gradient_start_color; + self.prettyButtonBadgeGradientEndColor = default_badge_gradient_end_color; + self.prettyButtonBadgeShadowOffset = default_badge_shadow_offset; + self.prettyButtonBadgeShadowOpacity = default_badge_shadow_opacity; + self.prettyButtonBadgeFont = default_badge_font; + self.prettyButtonBadgeTextColor = default_badge_text_color; + self.prettyButtonHighlightImage = nil; + self.prettyButtonHighlightGradientStartColor = default_highlight_gradient_start_color; + self.prettyButtonHighlightGradientEndColor = default_highlight_gradient_end_color; } - (id)initWithCoder:(NSCoder *)coder { @@ -189,6 +225,23 @@ -(void)layoutSubviews { button.badgeValue = item.badgeValue; [button addTarget:self action:@selector(_prettyTabBarButtonTapped:) forControlEvents:UIControlEventTouchUpInside]; + // set button properties + button.font = self.prettyButtonTitleFont; + button.textColor =self.prettyButtonTitleTextColor; + button.highlightedTextColor =self.prettyButtonTitleHighlightedTextColor; + button.textShadowOpacity =self.prettyButtonTitleTextShadowOpacity; + button.textShadowOffset =self.prettyButtonTitleTextShadowOffset; + button.badgeBorderColor =self.prettyButtonBadgeBorderColor; + button.badgeGradientStartColor =self.prettyButtonBadgeGradientStartColor; + button.badgeGradientEndColor =self.prettyButtonBadgeGradientEndColor; + button.badgeShadowOffset =self.prettyButtonBadgeShadowOffset; + button.badgeShadowOpacity =self.prettyButtonBadgeShadowOpacity; + button.badgeFont =self.prettyButtonBadgeFont; + button.badgeTextColor =self.prettyButtonBadgeTextColor; + button.highlightImage =self.prettyButtonHighlightImage; + button.highlightGradientStartColor =self.prettyButtonHighlightGradientStartColor; + button.highlightGradientEndColor =self.prettyButtonHighlightGradientEndColor; + if (item == self.selectedItem) { button.selected = YES; } else { From e475503d5029c664ea4cd4ac5ba2ee1d3029dd9c Mon Sep 17 00:00:00 2001 From: Jeremy Foo Date: Sun, 6 May 2012 18:03:22 +0800 Subject: [PATCH 28/48] set correct alignment for assignment of button properties removed sending super observevalueforkeypath. technically not needed. --- PrettyKit/PrettyTabBar.m | 30 ++++++++++++++---------------- 1 file changed, 14 insertions(+), 16 deletions(-) diff --git a/PrettyKit/PrettyTabBar.m b/PrettyKit/PrettyTabBar.m index b4e090d..c5d86a1 100644 --- a/PrettyKit/PrettyTabBar.m +++ b/PrettyKit/PrettyTabBar.m @@ -171,8 +171,6 @@ -(void)observeValueForKeyPath:(NSString *)keyPath ofObject:(id)object change:(NS NSUInteger index = [self.items indexOfObject:item]; [[self._prettyTabBarButtons objectAtIndex:index] setBadgeValue:[change objectForKey:NSKeyValueChangeNewKey]]; - } else { - [super observeValueForKeyPath:keyPath ofObject:object change:change context:context]; } } @@ -227,20 +225,20 @@ -(void)layoutSubviews { // set button properties button.font = self.prettyButtonTitleFont; - button.textColor =self.prettyButtonTitleTextColor; - button.highlightedTextColor =self.prettyButtonTitleHighlightedTextColor; - button.textShadowOpacity =self.prettyButtonTitleTextShadowOpacity; - button.textShadowOffset =self.prettyButtonTitleTextShadowOffset; - button.badgeBorderColor =self.prettyButtonBadgeBorderColor; - button.badgeGradientStartColor =self.prettyButtonBadgeGradientStartColor; - button.badgeGradientEndColor =self.prettyButtonBadgeGradientEndColor; - button.badgeShadowOffset =self.prettyButtonBadgeShadowOffset; - button.badgeShadowOpacity =self.prettyButtonBadgeShadowOpacity; - button.badgeFont =self.prettyButtonBadgeFont; - button.badgeTextColor =self.prettyButtonBadgeTextColor; - button.highlightImage =self.prettyButtonHighlightImage; - button.highlightGradientStartColor =self.prettyButtonHighlightGradientStartColor; - button.highlightGradientEndColor =self.prettyButtonHighlightGradientEndColor; + button.textColor = self.prettyButtonTitleTextColor; + button.highlightedTextColor = self.prettyButtonTitleHighlightedTextColor; + button.textShadowOpacity = self.prettyButtonTitleTextShadowOpacity; + button.textShadowOffset = self.prettyButtonTitleTextShadowOffset; + button.badgeBorderColor = self.prettyButtonBadgeBorderColor; + button.badgeGradientStartColor = self.prettyButtonBadgeGradientStartColor; + button.badgeGradientEndColor = self.prettyButtonBadgeGradientEndColor; + button.badgeShadowOffset = self.prettyButtonBadgeShadowOffset; + button.badgeShadowOpacity = self.prettyButtonBadgeShadowOpacity; + button.badgeFont = self.prettyButtonBadgeFont; + button.badgeTextColor = self.prettyButtonBadgeTextColor; + button.highlightImage = self.prettyButtonHighlightImage; + button.highlightGradientStartColor = self.prettyButtonHighlightGradientStartColor; + button.highlightGradientEndColor = self.prettyButtonHighlightGradientEndColor; if (item == self.selectedItem) { button.selected = YES; From b490332d79daff81cc131201920fc703cbaa0ff3 Mon Sep 17 00:00:00 2001 From: Jeremy Foo Date: Sun, 6 May 2012 20:32:29 +0800 Subject: [PATCH 29/48] draw gradient tint using tint gradient colors specified. --- PrettyKit/PrettyTabBarButton.h | 13 ++++- PrettyKit/PrettyTabBarButton.m | 94 ++++++++++++++++++++++++++-------- 2 files changed, 84 insertions(+), 23 deletions(-) diff --git a/PrettyKit/PrettyTabBarButton.h b/PrettyKit/PrettyTabBarButton.h index 92ca41d..8935321 100644 --- a/PrettyKit/PrettyTabBarButton.h +++ b/PrettyKit/PrettyTabBarButton.h @@ -29,12 +29,21 @@ @interface PrettyTabBarButton : UIControl -/** Specifies the image to use when the Button is selected. - If it is not specified, the button will use the normal image in another tint. +/** Specifies the image to use when the Button is selected. If it is not specified, the button will use the normal image in a gradient tint that is specified. By default is `nil`. */ @property (nonatomic, retain) UIImage *highlightedImage; +/** Specifies the start color for the gradient tint over the image when selected + + By default is `[UIColor colorWithRed:0.276 green:0.733 blue:1.000 alpha:1.000]`. */ +@property (nonatomic, retain) UIColor *highlightedImageGradientStartColor; + +/** Specifies the end color for the gradient tint over the image when selected + + By default is `[UIColor colorWithRed:0.028 green:0.160 blue:0.332 alpha:1.000]`. */ +@property (nonatomic, retain) UIColor *highlightedImageGradientEndColor; + /** Specifies the font to use for the title of the button By default is `[UIFont fontWithName:@"HelveticaNeue-Bold" size:10]`. */ diff --git a/PrettyKit/PrettyTabBarButton.m b/PrettyKit/PrettyTabBarButton.m index b7f5054..c8fbb31 100644 --- a/PrettyKit/PrettyTabBarButton.m +++ b/PrettyKit/PrettyTabBarButton.m @@ -28,28 +28,33 @@ #import "PrettyTabBarButton.h" #import "PrettyDrawing.h" -#define default_text_shadow_offset CGSizeMake(0,-1) -#define default_text_shadow_opacity 0.5 -#define default_font [UIFont fontWithName:@"HelveticaNeue-Bold" size:10] -#define default_text_color [UIColor colorWithWhite:0.2 alpha:1.0] -#define default_highlighted_text_color [UIColor colorWithWhite:0.90 alpha:1.0] -#define default_badge_font [UIFont fontWithName:@"HelveticaNeue-Bold" size:11] -#define default_badge_gradient_start_color [UIColor colorWithRed:1.000 green:0.000 blue:0.000 alpha:1.000] -#define default_badge_gradient_end_color [UIColor colorWithRed:0.6 green:0.000 blue:0.000 alpha:1.000] -#define default_badge_border_color [UIColor whiteColor] -#define default_badge_shadow_opacity 0.75 -#define default_badge_shadow_offset CGSizeMake(0,2) -#define default_badge_text_color [UIColor whiteColor] -#define default_highlight_gradient_start_color [UIColor colorWithWhite:0.4 alpha:1.0] -#define default_highlight_gradient_end_color [UIColor colorWithWhite:0.1 alpha:1.0] +#define default_text_shadow_offset CGSizeMake(0,-1) +#define default_text_shadow_opacity 0.5 +#define default_font [UIFont fontWithName:@"HelveticaNeue-Bold" size:10] +#define default_text_color [UIColor colorWithWhite:0.2 alpha:1.0] +#define default_highlighted_text_color [UIColor colorWithWhite:0.90 alpha:1.0] +#define default_badge_font [UIFont fontWithName:@"HelveticaNeue-Bold" size:11] +#define default_badge_gradient_start_color [UIColor colorWithRed:1.000 green:0.000 blue:0.000 alpha:1.000] +#define default_badge_gradient_end_color [UIColor colorWithRed:0.6 green:0.000 blue:0.000 alpha:1.000] +#define default_badge_border_color [UIColor whiteColor] +#define default_badge_shadow_opacity 0.75 +#define default_badge_shadow_offset CGSizeMake(0,2) +#define default_badge_text_color [UIColor whiteColor] +#define default_highlight_gradient_start_color [UIColor colorWithWhite:0.4 alpha:1.0] +#define default_highlight_gradient_end_color [UIColor colorWithWhite:0.1 alpha:1.0] +#define default_highlighted_image_gradient_start_color [UIColor colorWithRed:0.276 green:0.733 blue:1.000 alpha:1.000] +#define default_highlighted_image_gradient_end_color [UIColor colorWithRed:0.028 green:0.160 blue:0.332 alpha:1.000] + +#define IMAGE_HEIGHT 33.0 +#define IMAGE_WIDTH 33.0 @interface PrettyTabBarButton (/* Pirvate Method */) @end @implementation PrettyTabBarButton -@synthesize title = _title, image = _image, highlightedImage, badgeValue = _badgeValue; -@synthesize selected = _selected; +@synthesize title = _title, image = _image, badgeValue = _badgeValue; +@synthesize highlightedImage, highlightedImageGradientStartColor, highlightedImageGradientEndColor; @synthesize textColor, font, highlightedTextColor; @synthesize highlightImage, highlightGradientStartColor, highlightGradientEndColor; @synthesize textShadowOpacity, textShadowOffset; @@ -133,6 +138,8 @@ - (void) initializeVars self.highlightImage = nil; self.highlightGradientStartColor = default_highlight_gradient_start_color; self.highlightGradientEndColor = default_highlight_gradient_end_color; + self.highlightedImageGradientStartColor = default_highlighted_image_gradient_start_color; + self.highlightedImageGradientEndColor = default_highlighted_image_gradient_end_color; // intialize values; self.tag = -1; @@ -151,7 +158,7 @@ - (void) initializeVars #pragma mark - Selection and Accessors -(void)setSelected:(BOOL)selected { - _selected = selected; + [super setSelected:selected]; [self setNeedsDisplay]; } @@ -181,15 +188,16 @@ - (void)drawRect:(CGRect)rect [PrettyDrawing drawGradientRoundedRect:CGRectMake(2, 3, self.frame.size.width - 4, self.frame.size.height - 5) cornerRadius:3.0 - fromColor:[UIColor colorWithWhite:0.4 alpha:1.0] - toColor:[UIColor colorWithWhite:0.1 alpha:1.0]]; + fromColor:self.highlightGradientStartColor + toColor:self.highlightGradientEndColor]; } } // draw text CGContextSaveGState(context); - CGContextSetShadow(context, self.textShadowOffset, self.textShadowOpacity); + if (self.selected) + CGContextSetShadow(context, self.textShadowOffset, self.textShadowOpacity); if (self.selected) { [self.highlightedTextColor setFill]; @@ -201,15 +209,59 @@ - (void)drawRect:(CGRect)rect [_title drawInRect:CGRectMake((self.frame.size.width - titleSize.width)/2, self.frame.size.height - titleSize.height, titleSize.width, titleSize.height) withFont:self.font]; CGContextRestoreGState(context); + + CGContextSaveGState(context); - // TODO: draw image + // draw image if (self.image) { + CGFloat width = IMAGE_WIDTH; + CGFloat height = IMAGE_HEIGHT; + if (self.image.size.width < IMAGE_WIDTH) + width = self.image.size.width; + + if (self.image.size.height < IMAGE_HEIGHT) + height = self.image.size.height; + + CGRect imageRect = CGRectMake((self.frame.size.width - width)/2, (self.frame.size.height - titleSize.height - self.image.size.height)/2, width, height); + + if (self.selected) { + // do the tint... or use the highlight image + if (self.highlightedImage) { + [self.highlightedImage drawInRect:CGRectMake((self.frame.size.width - width)/2, (self.frame.size.height - titleSize.height - self.highlightedImage.size.height)/2, width, height)]; + + } else { + + // draw tint using gradient + CGContextTranslateCTM(context, 0, self.frame.size.height); + CGContextScaleCTM(context, 1.0, -1.0); + + CGRect flippedImageRect = imageRect; + flippedImageRect.origin.y = ((self.frame.size.height - titleSize.height)/2 - (self.image.size.height/2)) + titleSize.height; + + CGContextClipToMask(context, flippedImageRect, [self.image CGImage]); + + // because the context has been flipped, the gradient start and end colors also has to be flipped; + [PrettyDrawing drawGradientForContext:context + startPoint:CGPointMake(flippedImageRect.origin.x + flippedImageRect.size.width/2, 0) + endPoint:CGPointMake(flippedImageRect.origin.x + flippedImageRect.size.width/2, flippedImageRect.origin.y + flippedImageRect.size.height) + fromColor:self.highlightedImageGradientEndColor + toColor:self.highlightedImageGradientStartColor]; + + } + + } else { + // draw the image as per normal + [self.image drawInRect:imageRect]; + } } + CGContextRestoreGState(context); + // draw badge if (self.badgeValue) { CGSize badgeTextSize = [self.badgeValue sizeWithFont:self.badgeFont forWidth:(self.frame.size.width * 0.45) lineBreakMode:UILineBreakModeTailTruncation]; + CGFloat badgeWidth = badgeTextSize.width; CGFloat badgeHeight = badgeTextSize.height + 4; From fb43356d2eb2297ec02e07dde2252f403c6cd161 Mon Sep 17 00:00:00 2001 From: Jeremy Foo Date: Sun, 6 May 2012 20:41:07 +0800 Subject: [PATCH 30/48] use proper sizes when rendering images --- PrettyKit/PrettyTabBarButton.m | 33 +++++++++++++++++++++------------ 1 file changed, 21 insertions(+), 12 deletions(-) diff --git a/PrettyKit/PrettyTabBarButton.m b/PrettyKit/PrettyTabBarButton.m index c8fbb31..164fcb0 100644 --- a/PrettyKit/PrettyTabBarButton.m +++ b/PrettyKit/PrettyTabBarButton.m @@ -49,7 +49,7 @@ #define IMAGE_WIDTH 33.0 @interface PrettyTabBarButton (/* Pirvate Method */) - +-(CGSize)_sizeForWidth:(CGFloat)width height:(CGFloat)height; @end @implementation PrettyTabBarButton @@ -173,6 +173,19 @@ -(void)setBadgeValue:(NSString *)badgeValue { #pragma mark - Drawing +-(CGSize)_sizeForWidth:(CGFloat)width height:(CGFloat)height { + CGFloat returnWidth = IMAGE_WIDTH; + CGFloat returnHeight = IMAGE_HEIGHT; + + if (width < IMAGE_WIDTH) + returnWidth = self.image.size.width; + + if (height < IMAGE_HEIGHT) + returnHeight = self.image.size.height; + + return CGSizeMake(returnWidth, returnHeight); +} + - (void)drawRect:(CGRect)rect { [super drawRect:rect]; @@ -214,21 +227,17 @@ - (void)drawRect:(CGRect)rect // draw image if (self.image) { - CGFloat width = IMAGE_WIDTH; - CGFloat height = IMAGE_HEIGHT; - - if (self.image.size.width < IMAGE_WIDTH) - width = self.image.size.width; - - if (self.image.size.height < IMAGE_HEIGHT) - height = self.image.size.height; - CGRect imageRect = CGRectMake((self.frame.size.width - width)/2, (self.frame.size.height - titleSize.height - self.image.size.height)/2, width, height); + CGSize imageSize = [self _sizeForWidth:self.image.size.width height:self.image.size.height]; + + CGRect imageRect = CGRectMake((self.frame.size.width - imageSize.width)/2, (self.frame.size.height - titleSize.height - imageSize.height)/2, imageSize.width, imageSize.height); if (self.selected) { // do the tint... or use the highlight image if (self.highlightedImage) { - [self.highlightedImage drawInRect:CGRectMake((self.frame.size.width - width)/2, (self.frame.size.height - titleSize.height - self.highlightedImage.size.height)/2, width, height)]; + CGSize highlightedImageSize = [self _sizeForWidth:self.highlightedImage.size.width height:self.highlightedImage.size.height]; + + [self.highlightedImage drawInRect:CGRectMake((self.frame.size.width - highlightedImageSize.width)/2, (self.frame.size.height - titleSize.height - highlightedImageSize.height)/2, highlightedImageSize.width, highlightedImageSize.height)]; } else { @@ -237,7 +246,7 @@ - (void)drawRect:(CGRect)rect CGContextScaleCTM(context, 1.0, -1.0); CGRect flippedImageRect = imageRect; - flippedImageRect.origin.y = ((self.frame.size.height - titleSize.height)/2 - (self.image.size.height/2)) + titleSize.height; + flippedImageRect.origin.y = ((self.frame.size.height - titleSize.height)/2 - (imageSize.height/2)) + titleSize.height; CGContextClipToMask(context, flippedImageRect, [self.image CGImage]); From e302b1164963c3aface4c9eeb7af6c65cfa15176 Mon Sep 17 00:00:00 2001 From: Jeremy Foo Date: Sun, 6 May 2012 20:49:56 +0800 Subject: [PATCH 31/48] proper memory management --- PrettyKit/PrettyTabBarButton.m | 2 ++ 1 file changed, 2 insertions(+) diff --git a/PrettyKit/PrettyTabBarButton.m b/PrettyKit/PrettyTabBarButton.m index 164fcb0..0cb3aa5 100644 --- a/PrettyKit/PrettyTabBarButton.m +++ b/PrettyKit/PrettyTabBarButton.m @@ -100,6 +100,8 @@ -(void)dealloc { [_badgeValue release], _badgeValue = nil; self.highlightedImage = nil; + self.highlightedImageGradientStartColor = nil; + self.highlightedImageGradientEndColor = nil; self.font = nil; self.textColor = nil; From f6222169d60127a33b7789df688e99b7ca35d8fe Mon Sep 17 00:00:00 2001 From: Jeremy Foo Date: Sun, 6 May 2012 20:50:41 +0800 Subject: [PATCH 32/48] added configuration for the highlighted image's gradient start and end colors as well as an array to specify the highlighted images (if any) --- PrettyKit/PrettyTabBar.h | 19 +++++++++++ PrettyKit/PrettyTabBar.m | 74 +++++++++++++++++++++++++++++----------- 2 files changed, 74 insertions(+), 19 deletions(-) diff --git a/PrettyKit/PrettyTabBar.h b/PrettyKit/PrettyTabBar.h index 968f5c6..39bc603 100644 --- a/PrettyKit/PrettyTabBar.h +++ b/PrettyKit/PrettyTabBar.h @@ -77,6 +77,25 @@ By default is NO. */ @property (nonatomic) BOOL prettyTabBarButtons; +/** Specifies that images to display when a button is selected. + Use [NSNull null] if that particular button should use the gradient tints specified. + Otherwise supply a UIImage of the appropriate size. + + Images must be added at the same index that the relevant UITabBarItem's index + + By default is `nil`. */ +@property (nonatomic, copy) NSArray *prettyButtonHighlightedImages; + +/** Specifies the start color for the gradient tint over the image when selected + + By default is `[UIColor colorWithRed:0.276 green:0.733 blue:1.000 alpha:1.000]`. */ +@property (nonatomic, retain) UIColor *prettyButtonHighlightedImageGradientStartColor; + +/** Specifies the end color for the gradient tint over the image when selected + + By default is `[UIColor colorWithRed:0.028 green:0.160 blue:0.332 alpha:1.000]`. */ +@property (nonatomic, retain) UIColor *prettyButtonHighlightedImageGradientEndColor; + /** Specifies the font to use for the title of the button By default is `[UIFont fontWithName:@"HelveticaNeue-Bold" size:10]`. */ diff --git a/PrettyKit/PrettyTabBar.m b/PrettyKit/PrettyTabBar.m index c5d86a1..f3844b0 100644 --- a/PrettyKit/PrettyTabBar.m +++ b/PrettyKit/PrettyTabBar.m @@ -31,37 +31,42 @@ #import "PrettyDrawing.h" #import "PrettyTabBarButton.h" -#define default_upwards_shadow_opacity 0.5 -#define default_downwards_shadow_opacity 0.5 -#define default_gradient_start_color [UIColor colorWithHex:0x444444] -#define default_gradient_end_color [UIColor colorWithHex:0x060606] -#define default_separator_line_color [UIColor colorWithHex:0x666666] +#define default_upwards_shadow_opacity 0.5 +#define default_downwards_shadow_opacity 0.5 +#define default_gradient_start_color [UIColor colorWithHex:0x444444] +#define default_gradient_end_color [UIColor colorWithHex:0x060606] +#define default_separator_line_color [UIColor colorWithHex:0x666666] -#define default_text_shadow_offset CGSizeMake(0,-1) -#define default_text_shadow_opacity 0.5 -#define default_font [UIFont fontWithName:@"HelveticaNeue-Bold" size:10] -#define default_text_color [UIColor colorWithWhite:0.2 alpha:1.0] -#define default_highlighted_text_color [UIColor colorWithWhite:0.90 alpha:1.0] -#define default_badge_font [UIFont fontWithName:@"HelveticaNeue-Bold" size:11] -#define default_badge_gradient_start_color [UIColor colorWithRed:1.000 green:0.000 blue:0.000 alpha:1.000] -#define default_badge_gradient_end_color [UIColor colorWithRed:0.6 green:0.000 blue:0.000 alpha:1.000] -#define default_badge_border_color [UIColor whiteColor] -#define default_badge_shadow_opacity 0.75 -#define default_badge_shadow_offset CGSizeMake(0,2) -#define default_badge_text_color [UIColor whiteColor] -#define default_highlight_gradient_start_color [UIColor colorWithWhite:0.4 alpha:1.0] -#define default_highlight_gradient_end_color [UIColor colorWithWhite:0.1 alpha:1.0] +// pretty buttons +#define default_text_shadow_offset CGSizeMake(0,-1) +#define default_text_shadow_opacity 0.5 +#define default_font [UIFont fontWithName:@"HelveticaNeue-Bold" size:10] +#define default_text_color [UIColor colorWithWhite:0.2 alpha:1.0] +#define default_highlighted_text_color [UIColor colorWithWhite:0.90 alpha:1.0] +#define default_badge_font [UIFont fontWithName:@"HelveticaNeue-Bold" size:11] +#define default_badge_gradient_start_color [UIColor colorWithRed:1.000 green:0.000 blue:0.000 alpha:1.000] +#define default_badge_gradient_end_color [UIColor colorWithRed:0.6 green:0.000 blue:0.000 alpha:1.000] +#define default_badge_border_color [UIColor whiteColor] +#define default_badge_shadow_opacity 0.75 +#define default_badge_shadow_offset CGSizeMake(0,2) +#define default_badge_text_color [UIColor whiteColor] +#define default_highlight_gradient_start_color [UIColor colorWithWhite:0.4 alpha:1.0] +#define default_highlight_gradient_end_color [UIColor colorWithWhite:0.1 alpha:1.0] +#define default_highlighted_image_gradient_start_color [UIColor colorWithRed:0.276 green:0.733 blue:1.000 alpha:1.000] +#define default_highlighted_image_gradient_end_color [UIColor colorWithRed:0.028 green:0.160 blue:0.332 alpha:1.000] @interface PrettyTabBar (/* Private Methods */) @property (nonatomic, retain) NSMutableArray *_prettyTabBarButtons; @property (nonatomic, retain) NSMutableArray *_originalTabBarButtons; -(void)_prettyTabBarButtonTapped:(id)sender; +-(UIImage *)_imageForPrettyButtonImagesOfIndex:(NSInteger)index; @end @implementation PrettyTabBar @synthesize upwardsShadowOpacity, downwardsShadowOpacity, gradientStartColor, gradientEndColor, separatorLineColor; @synthesize prettyTabBarButtons = _prettyTabBarButtons; +@synthesize prettyButtonHighlightedImageGradientStartColor, prettyButtonHighlightedImageGradientEndColor, prettyButtonHighlightedImages; @synthesize prettyButtonTitleFont, prettyButtonTitleTextColor, prettyButtonTitleHighlightedTextColor, prettyButtonTitleTextShadowOpacity, prettyButtonTitleTextShadowOffset; @synthesize prettyButtonHighlightGradientStartColor, prettyButtonHighlightGradientEndColor, prettyButtonHighlightImage; @synthesize prettyButtonBadgeBorderColor, prettyButtonBadgeGradientStartColor, prettyButtonBadgeGradientEndColor, prettyButtonBadgeShadowOpacity, prettyButtonBadgeShadowOffset, prettyButtonBadgeFont, prettyButtonBadgeTextColor; @@ -78,6 +83,22 @@ - (void) dealloc { self._originalTabBarButtons = nil; self._prettyTabBarButtons = nil; + self.prettyButtonHighlightedImages = nil; + + self.prettyButtonHighlightedImageGradientStartColor = nil; + self.prettyButtonHighlightedImageGradientEndColor = nil; + self.prettyButtonTitleFont = nil; + self.prettyButtonTitleTextColor = nil; + self.prettyButtonTitleHighlightedTextColor = nil; + self.prettyButtonBadgeBorderColor = nil; + self.prettyButtonBadgeGradientStartColor = nil; + self.prettyButtonBadgeGradientEndColor = nil; + self.prettyButtonBadgeFont = nil; + self.prettyButtonBadgeTextColor = nil; + self.prettyButtonHighlightImage = nil; + self.prettyButtonHighlightGradientStartColor = nil; + self.prettyButtonHighlightGradientEndColor = nil; + [super dealloc]; } @@ -96,7 +117,10 @@ - (void) initializeVars // pretty button stuff __prettyTabBarButtons = [[NSMutableArray arrayWithCapacity:5] retain]; __originalTabBarButtons = [[NSMutableArray arrayWithCapacity:0] retain]; + self.prettyButtonHighlightedImages = nil; + self.prettyButtonHighlightedImageGradientStartColor = default_highlighted_image_gradient_start_color; + self.prettyButtonHighlightedImageGradientEndColor = default_highlighted_image_gradient_end_color; self.prettyButtonTitleFont = default_font; self.prettyButtonTitleTextColor = default_text_color; self.prettyButtonTitleHighlightedTextColor = default_highlighted_text_color; @@ -175,6 +199,15 @@ -(void)observeValueForKeyPath:(NSString *)keyPath ofObject:(id)object change:(NS } #pragma mark - Display +-(UIImage *)_imageForPrettyButtonImagesOfIndex:(NSInteger)index { + id image = [self.prettyButtonHighlightedImages objectAtIndex:index]; + + if ([image isKindOfClass:[NSNull class]]) + return nil; + + return image; +} + -(void)layoutSubviews { if (!self.prettyTabBarButtons) { @@ -239,6 +272,9 @@ -(void)layoutSubviews { button.highlightImage = self.prettyButtonHighlightImage; button.highlightGradientStartColor = self.prettyButtonHighlightGradientStartColor; button.highlightGradientEndColor = self.prettyButtonHighlightGradientEndColor; + button.highlightedImage = [self _imageForPrettyButtonImagesOfIndex:i]; + button.highlightedImageGradientStartColor = self.prettyButtonHighlightedImageGradientStartColor; + button.highlightedImageGradientEndColor = self.prettyButtonHighlightedImageGradientEndColor; if (item == self.selectedItem) { button.selected = YES; From 79ad15eab38aeb7a266347bd4a603635638260c3 Mon Sep 17 00:00:00 2001 From: Jeremy Foo Date: Mon, 7 May 2012 03:00:53 +0800 Subject: [PATCH 33/48] more logical layout of code. helps with memory management of observation status code to add buttons to the view are done at the switch. layoutSubViews does it namesake, it lays things out and also sets properties. --- PrettyKit/PrettyTabBar.m | 132 ++++++++++++++++++++++++--------------- 1 file changed, 83 insertions(+), 49 deletions(-) diff --git a/PrettyKit/PrettyTabBar.m b/PrettyKit/PrettyTabBar.m index f3844b0..6cf7017 100644 --- a/PrettyKit/PrettyTabBar.m +++ b/PrettyKit/PrettyTabBar.m @@ -166,10 +166,76 @@ - (id)init { #pragma mark - Overrides to handle internal PrettyTabBarButton -(void)setPrettyTabBarButtons:(BOOL)prettyTabBarButtons { - _prettyTabBarButtons = prettyTabBarButtons; - if (self.superview) - [self setNeedsLayout]; + // we should only change the status if its different + + if (_prettyTabBarButtons != prettyTabBarButtons) { + + if (prettyTabBarButtons) { + // changing from original to pretty implementation + + // remove views that are not prettytabbarbuttons + // they are usually the original buttons so add them to temp storage + for (UIView *view in self.subviews) { + if (![view isKindOfClass:[PrettyTabBarButton class]]) + [__originalTabBarButtons addObject:view]; + + [view removeFromSuperview]; + } + + UITabBarItem *item = nil; + PrettyTabBarButton *button = nil; + + // iterate over the data objects (UITabBarItem) and create the + // pretty tabbar buttons that they represent and position them + // in the view. + // we leave setting of properties to the laying out of subviews + // where its always supposed to be anyways + if ([self.items count] > 0) { + for (int i=0;i<[self.items count];i++) { + item = [self.items objectAtIndex:i]; + [item addObserver:self forKeyPath:@"badgeValue" options:NSKeyValueObservingOptionNew context:item]; + + button = [[PrettyTabBarButton alloc] initWithTitle:item.title image:item.image tag:i]; + button.autoresizingMask = UIViewAutoresizingFlexibleHeight | UIViewAutoresizingFlexibleWidth; + [button addTarget:self action:@selector(_prettyTabBarButtonTapped:) forControlEvents:UIControlEventTouchUpInside]; + + [self addSubview:button]; + [__prettyTabBarButtons addObject:button]; + [button release]; + } + } + + + } else { + // changing from pretty to original implementation + + // remove observation status and remove the object from super view + for (int i=0;i<[self.items count];i++) { + [[self.items objectAtIndex:i] removeObserver:self forKeyPath:@"badgeValue"]; + [[__prettyTabBarButtons objectAtIndex:i] removeFromSuperview]; + } + + [__prettyTabBarButtons removeAllObjects]; + + // lets add all the original buttons back into the view! + for (UIView *view in self._originalTabBarButtons) { + [self addSubview:view]; + } + + [__originalTabBarButtons removeAllObjects]; + + } + + // finally set the status of our internal representation + _prettyTabBarButtons = prettyTabBarButtons; + + // finally, layout if there is a superview, ie. our view has been + // added as a view somewhere + if (self.superview) + [self setNeedsLayout]; + } + } -(void)_prettyTabBarButtonTapped:(id)sender { @@ -210,52 +276,24 @@ -(UIImage *)_imageForPrettyButtonImagesOfIndex:(NSInteger)index { -(void)layoutSubviews { - if (!self.prettyTabBarButtons) { - for (UIView *view in __originalTabBarButtons) { - [self addSubview:view]; - } - - [__originalTabBarButtons removeAllObjects]; - } - [super layoutSubviews]; + // make sure item count is not greater than 5. as we didn't + // cater for customization of items. if ([self.items count] > 5) self.prettyTabBarButtons = NO; - - for (UIView *view in self.subviews) { - - if (self.prettyTabBarButtons) { - if (![view isKindOfClass:[PrettyTabBarButton class]]) { - [__originalTabBarButtons addObject:view]; - } - [view removeFromSuperview]; - } else { - if ([view isKindOfClass:[PrettyTabBarButton class]]) { - [view removeFromSuperview]; - } - } - } - - if (self.prettyTabBarButtons) { - [__prettyTabBarButtons removeAllObjects]; - - // do stuff + + // so if we are the right mode and there are actual data objects + // lets go ahead and layout the pretty buttons + if ((self.prettyTabBarButtons) && ([self.items count] > 0)) { PrettyTabBarButton *button = nil; UITabBarItem *item = nil; - CGFloat itemWidth = self.frame.size.width/[self.items count]; - + // set frame and set all properties! for (int i=0;i<[self.items count];i++) { - item = [self.items objectAtIndex:i]; - [item addObserver:self forKeyPath:@"badgeValue" options:NSKeyValueObservingOptionNew context:item]; - - button = [[PrettyTabBarButton alloc] initWithTitle:item.title image:item.image tag:i]; - button.frame = CGRectMake(i * itemWidth, 0, itemWidth, self.frame.size.height); - button.autoresizingMask = UIViewAutoresizingFlexibleHeight | UIViewAutoresizingFlexibleWidth; - button.badgeValue = item.badgeValue; - [button addTarget:self action:@selector(_prettyTabBarButtonTapped:) forControlEvents:UIControlEventTouchUpInside]; - + button = [self._prettyTabBarButtons objectAtIndex:i]; + button.frame = CGRectMake(i * (self.frame.size.width/[self.items count]), 0, (self.frame.size.width/[self.items count]), self.frame.size.height); + // set button properties button.font = self.prettyButtonTitleFont; button.textColor = self.prettyButtonTitleTextColor; @@ -276,16 +314,12 @@ -(void)layoutSubviews { button.highlightedImageGradientStartColor = self.prettyButtonHighlightedImageGradientStartColor; button.highlightedImageGradientEndColor = self.prettyButtonHighlightedImageGradientEndColor; - if (item == self.selectedItem) { + button.selected = NO; + + if (item == self.selectedItem) button.selected = YES; - } else { - button.selected = NO; - } - - [self addSubview:button]; - [__prettyTabBarButtons addObject:button]; - [button release]; } + } } From 708d220b7d477d3091f4bbdc4ae67ebb2bc57be6 Mon Sep 17 00:00:00 2001 From: Jeremy Foo Date: Mon, 7 May 2012 03:11:24 +0800 Subject: [PATCH 34/48] forgot to check for if items count is equal to 0 here. also checked to make sure the index returned is not NSNotFound --- PrettyKit/PrettyTabBar.m | 11 +++++++---- 1 file changed, 7 insertions(+), 4 deletions(-) diff --git a/PrettyKit/PrettyTabBar.m b/PrettyKit/PrettyTabBar.m index 6cf7017..8e93ef3 100644 --- a/PrettyKit/PrettyTabBar.m +++ b/PrettyKit/PrettyTabBar.m @@ -211,9 +211,11 @@ -(void)setPrettyTabBarButtons:(BOOL)prettyTabBarButtons { // changing from pretty to original implementation // remove observation status and remove the object from super view - for (int i=0;i<[self.items count];i++) { - [[self.items objectAtIndex:i] removeObserver:self forKeyPath:@"badgeValue"]; - [[__prettyTabBarButtons objectAtIndex:i] removeFromSuperview]; + if ([self.items count] > 0) { + for (int i=0;i<[self.items count];i++) { + [[self.items objectAtIndex:i] removeObserver:self forKeyPath:@"badgeValue"]; + [[__prettyTabBarButtons objectAtIndex:i] removeFromSuperview]; + } } [__prettyTabBarButtons removeAllObjects]; @@ -260,7 +262,8 @@ -(void)observeValueForKeyPath:(NSString *)keyPath ofObject:(id)object change:(NS UITabBarItem *item = (UITabBarItem *)context; NSUInteger index = [self.items indexOfObject:item]; - [[self._prettyTabBarButtons objectAtIndex:index] setBadgeValue:[change objectForKey:NSKeyValueChangeNewKey]]; + if (index != NSNotFound) + [[self._prettyTabBarButtons objectAtIndex:index] setBadgeValue:[change objectForKey:NSKeyValueChangeNewKey]]; } } From b040cc0560890b55ad97ac72f392d7442d720633 Mon Sep 17 00:00:00 2001 From: Jeremy Foo Date: Mon, 7 May 2012 03:13:55 +0800 Subject: [PATCH 35/48] forgot to check for if items count is equal to 0 here. also checked to make sure the index returned is not NSNotFound --- PrettyKit/PrettyTabBar.m | 11 +++++++---- 1 file changed, 7 insertions(+), 4 deletions(-) diff --git a/PrettyKit/PrettyTabBar.m b/PrettyKit/PrettyTabBar.m index 6cf7017..8e93ef3 100644 --- a/PrettyKit/PrettyTabBar.m +++ b/PrettyKit/PrettyTabBar.m @@ -211,9 +211,11 @@ -(void)setPrettyTabBarButtons:(BOOL)prettyTabBarButtons { // changing from pretty to original implementation // remove observation status and remove the object from super view - for (int i=0;i<[self.items count];i++) { - [[self.items objectAtIndex:i] removeObserver:self forKeyPath:@"badgeValue"]; - [[__prettyTabBarButtons objectAtIndex:i] removeFromSuperview]; + if ([self.items count] > 0) { + for (int i=0;i<[self.items count];i++) { + [[self.items objectAtIndex:i] removeObserver:self forKeyPath:@"badgeValue"]; + [[__prettyTabBarButtons objectAtIndex:i] removeFromSuperview]; + } } [__prettyTabBarButtons removeAllObjects]; @@ -260,7 +262,8 @@ -(void)observeValueForKeyPath:(NSString *)keyPath ofObject:(id)object change:(NS UITabBarItem *item = (UITabBarItem *)context; NSUInteger index = [self.items indexOfObject:item]; - [[self._prettyTabBarButtons objectAtIndex:index] setBadgeValue:[change objectForKey:NSKeyValueChangeNewKey]]; + if (index != NSNotFound) + [[self._prettyTabBarButtons objectAtIndex:index] setBadgeValue:[change objectForKey:NSKeyValueChangeNewKey]]; } } From abbe52c21292c15c5863a1f0add7831c6838ec54 Mon Sep 17 00:00:00 2001 From: Jeremy Foo Date: Mon, 7 May 2012 03:42:55 +0800 Subject: [PATCH 36/48] forgotten to intercept setting of items and rebuilding the representation also more stringent checks on the count of objects in an array --- PrettyKit/PrettyTabBar.m | 151 +++++++++++++++++++++++---------------- 1 file changed, 89 insertions(+), 62 deletions(-) diff --git a/PrettyKit/PrettyTabBar.m b/PrettyKit/PrettyTabBar.m index 8e93ef3..3631007 100644 --- a/PrettyKit/PrettyTabBar.m +++ b/PrettyKit/PrettyTabBar.m @@ -60,6 +60,7 @@ @interface PrettyTabBar (/* Private Methods */) @property (nonatomic, retain) NSMutableArray *_originalTabBarButtons; -(void)_prettyTabBarButtonTapped:(id)sender; -(UIImage *)_imageForPrettyButtonImagesOfIndex:(NSInteger)index; +-(void)_setupTabBarSubviews; @end @implementation PrettyTabBar @@ -165,73 +166,91 @@ - (id)init { #pragma mark - Overrides to handle internal PrettyTabBarButton --(void)setPrettyTabBarButtons:(BOOL)prettyTabBarButtons { - - // we should only change the status if its different +-(void)setItems:(NSArray *)items { + [super setItems:items]; - if (_prettyTabBarButtons != prettyTabBarButtons) { - - if (prettyTabBarButtons) { - // changing from original to pretty implementation - - // remove views that are not prettytabbarbuttons - // they are usually the original buttons so add them to temp storage - for (UIView *view in self.subviews) { - if (![view isKindOfClass:[PrettyTabBarButton class]]) - [__originalTabBarButtons addObject:view]; + [self _setupTabBarSubviews]; +} + +-(void)setItems:(NSArray *)items animated:(BOOL)animated { + [super setItems:items animated:animated]; + + [self _setupTabBarSubviews]; +} - [view removeFromSuperview]; - } - - UITabBarItem *item = nil; - PrettyTabBarButton *button = nil; - - // iterate over the data objects (UITabBarItem) and create the - // pretty tabbar buttons that they represent and position them - // in the view. - // we leave setting of properties to the laying out of subviews - // where its always supposed to be anyways - if ([self.items count] > 0) { - for (int i=0;i<[self.items count];i++) { - item = [self.items objectAtIndex:i]; - [item addObserver:self forKeyPath:@"badgeValue" options:NSKeyValueObservingOptionNew context:item]; - - button = [[PrettyTabBarButton alloc] initWithTitle:item.title image:item.image tag:i]; - button.autoresizingMask = UIViewAutoresizingFlexibleHeight | UIViewAutoresizingFlexibleWidth; - [button addTarget:self action:@selector(_prettyTabBarButtonTapped:) forControlEvents:UIControlEventTouchUpInside]; - - [self addSubview:button]; - [__prettyTabBarButtons addObject:button]; - [button release]; - } - } +-(void)_setupTabBarSubviews { + if (_prettyTabBarButtons) { + // changing from original to pretty implementation + + // remove views that are not prettytabbarbuttons + // they are usually the original buttons so add them to temp storage + for (UIView *view in self.subviews) { + if (![view isKindOfClass:[PrettyTabBarButton class]]) + [__originalTabBarButtons addObject:view]; - } else { - // changing from pretty to original implementation - - // remove observation status and remove the object from super view - if ([self.items count] > 0) { - for (int i=0;i<[self.items count];i++) { - [[self.items objectAtIndex:i] removeObserver:self forKeyPath:@"badgeValue"]; - [[__prettyTabBarButtons objectAtIndex:i] removeFromSuperview]; - } - } + [view removeFromSuperview]; + } + + PrettyTabBarButton *button = nil; + // iterate over the data objects (UITabBarItem) and create the + // pretty tabbar buttons that they represent and position them + // in the view. + // we leave setting of properties to the laying out of subviews + // where its always supposed to be anyways + NSUInteger i = 0; + + for (UITabBarItem *item in self.items) { + [item addObserver:self forKeyPath:@"badgeValue" options:NSKeyValueObservingOptionNew context:item]; - [__prettyTabBarButtons removeAllObjects]; + button = [[PrettyTabBarButton alloc] initWithTitle:item.title image:item.image tag:i]; + button.autoresizingMask = UIViewAutoresizingFlexibleHeight | UIViewAutoresizingFlexibleWidth; + [button addTarget:self action:@selector(_prettyTabBarButtonTapped:) forControlEvents:UIControlEventTouchUpInside]; - // lets add all the original buttons back into the view! - for (UIView *view in self._originalTabBarButtons) { - [self addSubview:view]; - } + [self addSubview:button]; + [__prettyTabBarButtons addObject:button]; + [button release]; + i++; + } + + + } else { + // changing from pretty to original implementation + + // remove observation status and remove the object from super view + NSUInteger i = 0; + + for (UITabBarItem *item in self.items) { + [item removeObserver:self forKeyPath:@"badgeValue"]; + if ([__prettyTabBarButtons count] > 0) + [[__prettyTabBarButtons objectAtIndex:i] removeFromSuperview]; - [__originalTabBarButtons removeAllObjects]; - + i++; + } + + [__prettyTabBarButtons removeAllObjects]; + + // lets add all the original buttons back into the view! + for (UIView *view in self._originalTabBarButtons) { + [self addSubview:view]; } - // finally set the status of our internal representation + [__originalTabBarButtons removeAllObjects]; + + } +} + +-(void)setPrettyTabBarButtons:(BOOL)prettyTabBarButtons { + + // we should only change the status if its different + + if (_prettyTabBarButtons != prettyTabBarButtons) { + + // set the status of our internal representation _prettyTabBarButtons = prettyTabBarButtons; + [self _setupTabBarSubviews]; + // finally, layout if there is a superview, ie. our view has been // added as a view somewhere if (self.superview) @@ -262,13 +281,16 @@ -(void)observeValueForKeyPath:(NSString *)keyPath ofObject:(id)object change:(NS UITabBarItem *item = (UITabBarItem *)context; NSUInteger index = [self.items indexOfObject:item]; - if (index != NSNotFound) + if ((index != NSNotFound) && ([self._prettyTabBarButtons count] > 0)) [[self._prettyTabBarButtons objectAtIndex:index] setBadgeValue:[change objectForKey:NSKeyValueChangeNewKey]]; } } #pragma mark - Display -(UIImage *)_imageForPrettyButtonImagesOfIndex:(NSInteger)index { + if ([self.prettyButtonHighlightedImages count] == 0) + return nil; + id image = [self.prettyButtonHighlightedImages objectAtIndex:index]; if ([image isKindOfClass:[NSNull class]]) @@ -279,21 +301,24 @@ -(UIImage *)_imageForPrettyButtonImagesOfIndex:(NSInteger)index { -(void)layoutSubviews { - [super layoutSubviews]; - // make sure item count is not greater than 5. as we didn't // cater for customization of items. if ([self.items count] > 5) self.prettyTabBarButtons = NO; + [super layoutSubviews]; + // so if we are the right mode and there are actual data objects // lets go ahead and layout the pretty buttons - if ((self.prettyTabBarButtons) && ([self.items count] > 0)) { + if (self.prettyTabBarButtons) { PrettyTabBarButton *button = nil; - UITabBarItem *item = nil; + NSUInteger i = 0; // set frame and set all properties! - for (int i=0;i<[self.items count];i++) { + for (UITabBarItem *item in self.items) { + if ([self._prettyTabBarButtons count] == 0) + break; + button = [self._prettyTabBarButtons objectAtIndex:i]; button.frame = CGRectMake(i * (self.frame.size.width/[self.items count]), 0, (self.frame.size.width/[self.items count]), self.frame.size.height); @@ -321,6 +346,8 @@ -(void)layoutSubviews { if (item == self.selectedItem) button.selected = YES; + + i++; } } From 818caede4e063d8f843c57dda8516fda972a9a3f Mon Sep 17 00:00:00 2001 From: Jeremy Foo Date: Mon, 7 May 2012 13:22:20 +0800 Subject: [PATCH 37/48] forgotten to free up observer --- PrettyKit/PrettyTabBar.m | 6 ++++++ 1 file changed, 6 insertions(+) diff --git a/PrettyKit/PrettyTabBar.m b/PrettyKit/PrettyTabBar.m index 3631007..99f7ddc 100644 --- a/PrettyKit/PrettyTabBar.m +++ b/PrettyKit/PrettyTabBar.m @@ -77,6 +77,12 @@ @implementation PrettyTabBar #pragma mark - Object Life Cycle - (void) dealloc { + + if (self.prettyTabBarButtons) { + for (UITabBarItem *item in self.items) + [item removeObserver:self forKeyPath:@"badgeValue"]; + } + self.gradientStartColor = nil; self.gradientEndColor = nil; self.separatorLineColor = nil; From 3bfce0329b39ba581ebe4cc2202077b8246034a3 Mon Sep 17 00:00:00 2001 From: Jeremy Foo Date: Mon, 7 May 2012 16:17:23 +0800 Subject: [PATCH 38/48] fixed bug where badge value being removed from initial uitabaritems when switching causes crashes also fixed issues with pretty buttons not appearing --- PrettyKit/PrettyTabBar.m | 12 +++++++++--- 1 file changed, 9 insertions(+), 3 deletions(-) diff --git a/PrettyKit/PrettyTabBar.m b/PrettyKit/PrettyTabBar.m index 99f7ddc..2f60b25 100644 --- a/PrettyKit/PrettyTabBar.m +++ b/PrettyKit/PrettyTabBar.m @@ -176,12 +176,16 @@ -(void)setItems:(NSArray *)items { [super setItems:items]; [self _setupTabBarSubviews]; + + [self setNeedsLayout]; } -(void)setItems:(NSArray *)items animated:(BOOL)animated { [super setItems:items animated:animated]; [self _setupTabBarSubviews]; + + [self setNeedsLayout]; } @@ -227,9 +231,10 @@ -(void)_setupTabBarSubviews { NSUInteger i = 0; for (UITabBarItem *item in self.items) { - [item removeObserver:self forKeyPath:@"badgeValue"]; - if ([__prettyTabBarButtons count] > 0) + if ([__prettyTabBarButtons count] > 0) { [[__prettyTabBarButtons objectAtIndex:i] removeFromSuperview]; + [item removeObserver:self forKeyPath:@"badgeValue"]; + } i++; } @@ -327,7 +332,8 @@ -(void)layoutSubviews { button = [self._prettyTabBarButtons objectAtIndex:i]; button.frame = CGRectMake(i * (self.frame.size.width/[self.items count]), 0, (self.frame.size.width/[self.items count]), self.frame.size.height); - + [self addSubview:button]; + // set button properties button.font = self.prettyButtonTitleFont; button.textColor = self.prettyButtonTitleTextColor; From 101ada0243dc05158ea649b465e25d5f78c803bc Mon Sep 17 00:00:00 2001 From: Victor Pena Date: Mon, 7 May 2012 11:26:40 +0200 Subject: [PATCH 39/48] Some changes to PrettyTabBar stuff - Changed some default values - Removed unused default values from PrettyTabBarButton - Refactored some code in PrettyTabBarButton - Added tint effect to non-selected tabbar images --- PrettyExample.xcodeproj/project.pbxproj | 8 + PrettyExample/MainWindow.xib | 10 +- PrettyExample/listButton.png | Bin 0 -> 151 bytes PrettyExample/listButton@2x.png | Bin 0 -> 342 bytes PrettyKit/PrettyTabBar.m | 10 +- PrettyKit/PrettyTabBarButton.m | 289 +++++++++++++----------- 6 files changed, 174 insertions(+), 143 deletions(-) create mode 100644 PrettyExample/listButton.png create mode 100644 PrettyExample/listButton@2x.png diff --git a/PrettyExample.xcodeproj/project.pbxproj b/PrettyExample.xcodeproj/project.pbxproj index 576164b..e867da7 100644 --- a/PrettyExample.xcodeproj/project.pbxproj +++ b/PrettyExample.xcodeproj/project.pbxproj @@ -20,6 +20,8 @@ 57360BDD14FF84F600343B7B /* MainWindow.xib in Resources */ = {isa = PBXBuildFile; fileRef = 57360BDC14FF84F600343B7B /* MainWindow.xib */; }; 57360BDF14FF889B00343B7B /* ExampleViewController.xib in Resources */ = {isa = PBXBuildFile; fileRef = 57360BDE14FF889B00343B7B /* ExampleViewController.xib */; }; 57360BE114FF911200343B7B /* QuartzCore.framework in Frameworks */ = {isa = PBXBuildFile; fileRef = 57360BE014FF911200343B7B /* QuartzCore.framework */; }; + 57810A2F1557C01E00974D07 /* listButton.png in Resources */ = {isa = PBXBuildFile; fileRef = 57810A2D1557C01E00974D07 /* listButton.png */; }; + 57810A301557C01E00974D07 /* listButton@2x.png in Resources */ = {isa = PBXBuildFile; fileRef = 57810A2E1557C01E00974D07 /* listButton@2x.png */; }; 578998C41535E02000E06FCA /* PrettyCustomViewTableViewCell.m in Sources */ = {isa = PBXBuildFile; fileRef = 578998B31535E02000E06FCA /* PrettyCustomViewTableViewCell.m */; }; 578998C51535E02000E06FCA /* PrettyGridTableViewCell.m in Sources */ = {isa = PBXBuildFile; fileRef = 578998B51535E02000E06FCA /* PrettyGridTableViewCell.m */; }; 578998C61535E02000E06FCA /* PrettySegmentedControlTableViewCell.m in Sources */ = {isa = PBXBuildFile; fileRef = 578998B71535E02000E06FCA /* PrettySegmentedControlTableViewCell.m */; }; @@ -56,6 +58,8 @@ 57360BDC14FF84F600343B7B /* MainWindow.xib */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = file.xib; path = MainWindow.xib; sourceTree = ""; }; 57360BDE14FF889B00343B7B /* ExampleViewController.xib */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = file.xib; path = ExampleViewController.xib; sourceTree = ""; }; 57360BE014FF911200343B7B /* QuartzCore.framework */ = {isa = PBXFileReference; lastKnownFileType = wrapper.framework; name = QuartzCore.framework; path = System/Library/Frameworks/QuartzCore.framework; sourceTree = SDKROOT; }; + 57810A2D1557C01E00974D07 /* listButton.png */ = {isa = PBXFileReference; lastKnownFileType = image.png; path = listButton.png; sourceTree = ""; }; + 57810A2E1557C01E00974D07 /* listButton@2x.png */ = {isa = PBXFileReference; lastKnownFileType = image.png; path = "listButton@2x.png"; sourceTree = ""; }; 578998B21535E02000E06FCA /* PrettyCustomViewTableViewCell.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = PrettyCustomViewTableViewCell.h; sourceTree = ""; }; 578998B31535E02000E06FCA /* PrettyCustomViewTableViewCell.m */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.objc; path = PrettyCustomViewTableViewCell.m; sourceTree = ""; }; 578998B41535E02000E06FCA /* PrettyGridTableViewCell.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = PrettyGridTableViewCell.h; sourceTree = ""; }; @@ -156,6 +160,8 @@ 5735F8C214FD2FFC00DD7370 /* Supporting Files */ = { isa = PBXGroup; children = ( + 57810A2D1557C01E00974D07 /* listButton.png */, + 57810A2E1557C01E00974D07 /* listButton@2x.png */, 5735F8C314FD2FFC00DD7370 /* PrettyExample-Info.plist */, 5735F8C414FD2FFC00DD7370 /* InfoPlist.strings */, 5735F8C714FD2FFC00DD7370 /* main.m */, @@ -257,6 +263,8 @@ 572B2E6A153496880002228B /* background.png in Resources */, 572B2E6B153496880002228B /* background@2x.png in Resources */, EDA7DCB71548ED3F002219BA /* ModalViewController.xib in Resources */, + 57810A2F1557C01E00974D07 /* listButton.png in Resources */, + 57810A301557C01E00974D07 /* listButton@2x.png in Resources */, ); runOnlyForDeploymentPostprocessing = 0; }; diff --git a/PrettyExample/MainWindow.xib b/PrettyExample/MainWindow.xib index 6f0a18f..0ceb445 100644 --- a/PrettyExample/MainWindow.xib +++ b/PrettyExample/MainWindow.xib @@ -53,6 +53,10 @@ Plain Table + + NSImage + listButton.png + IBCocoaTouchFramework @@ -303,7 +307,7 @@ - 24 + 25 0 @@ -314,6 +318,10 @@ YES 3 + + listButton.png + {22, 16} + 933 diff --git a/PrettyExample/listButton.png b/PrettyExample/listButton.png new file mode 100644 index 0000000000000000000000000000000000000000..6c1d43980699b4a4fe4e2fcb1ee1e12e295a6f5e GIT binary patch literal 151 zcmeAS@N?(olHy`uVBq!ia0vp^Vn8gw!3HFS-u9~jsW?v;#}Es_3bcvA)78&qol`;+0A|-R Ad;kCd literal 0 HcmV?d00001 diff --git a/PrettyExample/listButton@2x.png b/PrettyExample/listButton@2x.png new file mode 100644 index 0000000000000000000000000000000000000000..57ec489b0a37b2dd368b050a5e9a8d0269fd8bce GIT binary patch literal 342 zcmV-c0jd6pP)<8YvxB69BT36J zLbHR)D`6MiAhM*eLAw5sUU0vLa)f~688$Yw@)~$A(TJkidM}|-ZI_R~61(J5kR^p# z-@q_MTD^-@a3oZey@cwXw>x<+v0W=A^K?JmUlq*y o28JmwSLY@v97#xq5t<$J0Sn_-ik Date: Mon, 7 May 2012 21:12:08 +0800 Subject: [PATCH 40/48] set item's badge value when laying out subviews. optionally aggressively passes on KVO observation to super class through the use of a @try..@catch block to prevent exceptions. --- PrettyKit/PrettyTabBar.m | 6 ++++++ 1 file changed, 6 insertions(+) diff --git a/PrettyKit/PrettyTabBar.m b/PrettyKit/PrettyTabBar.m index bba94f2..2eb316a 100644 --- a/PrettyKit/PrettyTabBar.m +++ b/PrettyKit/PrettyTabBar.m @@ -294,6 +294,11 @@ -(void)observeValueForKeyPath:(NSString *)keyPath ofObject:(id)object change:(NS if ((index != NSNotFound) && ([self._prettyTabBarButtons count] > 0)) [[self._prettyTabBarButtons objectAtIndex:index] setBadgeValue:[change objectForKey:NSKeyValueChangeNewKey]]; + } else { + @try { + [super observeValueForKeyPath:keyPath ofObject:object change:change context:context]; + } + @catch (NSException *exception) { } } } @@ -355,6 +360,7 @@ -(void)layoutSubviews { button.highlightedImageGradientEndColor = self.prettyButtonHighlightedImageGradientEndColor; button.selected = NO; + button.badgeValue = item.badgeValue; if (item == self.selectedItem) button.selected = YES; From b2caddb22a0de1835ef143c5129ac420388392e6 Mon Sep 17 00:00:00 2001 From: Jeremy Foo Date: Tue, 29 May 2012 23:16:30 +0800 Subject: [PATCH 41/48] fixes issue where sometimes buttons don't have an image or title. --- PrettyKit/PrettyTabBar.m | 10 ++++++++++ 1 file changed, 10 insertions(+) diff --git a/PrettyKit/PrettyTabBar.m b/PrettyKit/PrettyTabBar.m index 2eb316a..aae436c 100644 --- a/PrettyKit/PrettyTabBar.m +++ b/PrettyKit/PrettyTabBar.m @@ -143,6 +143,7 @@ - (void) initializeVars self.prettyButtonHighlightImage = nil; self.prettyButtonHighlightGradientStartColor = default_highlight_gradient_start_color; self.prettyButtonHighlightGradientEndColor = default_highlight_gradient_end_color; + } - (id)initWithCoder:(NSCoder *)coder { @@ -217,6 +218,12 @@ -(void)_setupTabBarSubviews { button.autoresizingMask = UIViewAutoresizingFlexibleHeight | UIViewAutoresizingFlexibleWidth; [button addTarget:self action:@selector(_prettyTabBarButtonTapped:) forControlEvents:UIControlEventTouchUpInside]; + if (item == self.selectedItem) { + button.selected = YES; + } else { + button.selected = NO; + } + [self addSubview:button]; [__prettyTabBarButtons addObject:button]; [button release]; @@ -294,6 +301,7 @@ -(void)observeValueForKeyPath:(NSString *)keyPath ofObject:(id)object change:(NS if ((index != NSNotFound) && ([self._prettyTabBarButtons count] > 0)) [[self._prettyTabBarButtons objectAtIndex:index] setBadgeValue:[change objectForKey:NSKeyValueChangeNewKey]]; + } else { @try { [super observeValueForKeyPath:keyPath ofObject:object change:change context:context]; @@ -361,6 +369,8 @@ -(void)layoutSubviews { button.selected = NO; button.badgeValue = item.badgeValue; + button.title = item.title; + button.image = item.image; if (item == self.selectedItem) button.selected = YES; From 495916c2b310b14dd017168fb6f696f17a0419aa Mon Sep 17 00:00:00 2001 From: Jeremy Foo Date: Wed, 30 May 2012 17:56:55 +0800 Subject: [PATCH 42/48] bump pretty tab bar button text up by 2 px --- PrettyKit/PrettyTabBarButton.m | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/PrettyKit/PrettyTabBarButton.m b/PrettyKit/PrettyTabBarButton.m index 656aab2..d2f6602 100644 --- a/PrettyKit/PrettyTabBarButton.m +++ b/PrettyKit/PrettyTabBarButton.m @@ -170,7 +170,7 @@ - (CGSize)drawText:(CGContextRef)context } CGSize titleSize = [_title sizeWithFont:self.font constrainedToSize:CGSizeMake(self.frame.size.width, 10.0)]; - [_title drawInRect:CGRectMake((self.frame.size.width - titleSize.width)/2, self.frame.size.height - titleSize.height, titleSize.width, titleSize.height) withFont:self.font]; + [_title drawInRect:CGRectMake((self.frame.size.width - titleSize.width)/2, self.frame.size.height - titleSize.height - 2, titleSize.width, titleSize.height) withFont:self.font]; CGContextRestoreGState(context); return titleSize; From dbc74a6ca7364550db30a2d7e652cc1dccb582cf Mon Sep 17 00:00:00 2001 From: Jeremy Foo Date: Wed, 30 May 2012 18:28:09 +0800 Subject: [PATCH 43/48] set corner radius for highlights --- PrettyKit/PrettyTabBar.h | 5 +++++ PrettyKit/PrettyTabBar.m | 5 ++++- PrettyKit/PrettyTabBarButton.h | 7 ++++++- PrettyKit/PrettyTabBarButton.m | 4 ++-- 4 files changed, 17 insertions(+), 4 deletions(-) diff --git a/PrettyKit/PrettyTabBar.h b/PrettyKit/PrettyTabBar.h index 39bc603..2dddcd1 100644 --- a/PrettyKit/PrettyTabBar.h +++ b/PrettyKit/PrettyTabBar.h @@ -86,6 +86,11 @@ By default is `nil`. */ @property (nonatomic, copy) NSArray *prettyButtonHighlightedImages; +/** Specifies the corner radius for the highlight's gradient (when selected) + + By default is `3.0`. */ +@property (readwrite) CGFloat prettyButtonHighlightCornerRadius; + /** Specifies the start color for the gradient tint over the image when selected By default is `[UIColor colorWithRed:0.276 green:0.733 blue:1.000 alpha:1.000]`. */ diff --git a/PrettyKit/PrettyTabBar.m b/PrettyKit/PrettyTabBar.m index aae436c..8f5b530 100644 --- a/PrettyKit/PrettyTabBar.m +++ b/PrettyKit/PrettyTabBar.m @@ -50,6 +50,7 @@ #define default_badge_shadow_opacity 0.75 #define default_badge_shadow_offset CGSizeMake(0,2) #define default_badge_text_color [UIColor whiteColor] +#define default_highlight_corner_radius 3.0 #define default_highlight_gradient_start_color [UIColor colorWithWhite:0.35 alpha:1.0] #define default_highlight_gradient_end_color [UIColor colorWithWhite:0.2 alpha:1.0] #define default_highlighted_image_gradient_start_color [UIColor colorWithRed:0.276 green:0.733 blue:1.000 alpha:1.000] @@ -69,7 +70,7 @@ @implementation PrettyTabBar @synthesize prettyButtonHighlightedImageGradientStartColor, prettyButtonHighlightedImageGradientEndColor, prettyButtonHighlightedImages; @synthesize prettyButtonTitleFont, prettyButtonTitleTextColor, prettyButtonTitleHighlightedTextColor, prettyButtonTitleTextShadowOpacity, prettyButtonTitleTextShadowOffset; -@synthesize prettyButtonHighlightGradientStartColor, prettyButtonHighlightGradientEndColor, prettyButtonHighlightImage; +@synthesize prettyButtonHighlightGradientStartColor, prettyButtonHighlightGradientEndColor, prettyButtonHighlightImage, prettyButtonHighlightCornerRadius; @synthesize prettyButtonBadgeBorderColor, prettyButtonBadgeGradientStartColor, prettyButtonBadgeGradientEndColor, prettyButtonBadgeShadowOpacity, prettyButtonBadgeShadowOffset, prettyButtonBadgeFont, prettyButtonBadgeTextColor; @synthesize _prettyTabBarButtons = __prettyTabBarButtons, _originalTabBarButtons = __originalTabBarButtons; @@ -126,6 +127,7 @@ - (void) initializeVars __originalTabBarButtons = [[NSMutableArray arrayWithCapacity:0] retain]; self.prettyButtonHighlightedImages = nil; + self.prettyButtonHighlightCornerRadius = default_highlight_corner_radius; self.prettyButtonHighlightedImageGradientStartColor = default_highlighted_image_gradient_start_color; self.prettyButtonHighlightedImageGradientEndColor = default_highlighted_image_gradient_end_color; self.prettyButtonTitleFont = default_font; @@ -366,6 +368,7 @@ -(void)layoutSubviews { button.highlightedImage = [self _imageForPrettyButtonImagesOfIndex:i]; button.highlightedImageGradientStartColor = self.prettyButtonHighlightedImageGradientStartColor; button.highlightedImageGradientEndColor = self.prettyButtonHighlightedImageGradientEndColor; + button.highlightCornerRadius = self.prettyButtonHighlightCornerRadius; button.selected = NO; button.badgeValue = item.badgeValue; diff --git a/PrettyKit/PrettyTabBarButton.h b/PrettyKit/PrettyTabBarButton.h index 8935321..3f7f36f 100644 --- a/PrettyKit/PrettyTabBarButton.h +++ b/PrettyKit/PrettyTabBarButton.h @@ -69,8 +69,13 @@ By default is `CGSizeMake(0,-1)`. */ @property (nonatomic) CGSize textShadowOffset; +/** Specifies the corner radius for the highlight's gradient (when selected) + + By default is `3.0`. */ +@property (readwrite) CGFloat highlightCornerRadius; + /** Specifies the start color for the highlight's gradient (when selected) - + By default is `[UIColor colorWithWhite:0.4 alpha:1.0]`. */ @property (nonatomic, retain) UIColor *highlightGradientStartColor; diff --git a/PrettyKit/PrettyTabBarButton.m b/PrettyKit/PrettyTabBarButton.m index d2f6602..670a28e 100644 --- a/PrettyKit/PrettyTabBarButton.m +++ b/PrettyKit/PrettyTabBarButton.m @@ -40,7 +40,7 @@ @implementation PrettyTabBarButton @synthesize title = _title, image = _image, badgeValue = _badgeValue; @synthesize highlightedImage, highlightedImageGradientStartColor, highlightedImageGradientEndColor; @synthesize textColor, font, highlightedTextColor; -@synthesize highlightImage, highlightGradientStartColor, highlightGradientEndColor; +@synthesize highlightImage, highlightGradientStartColor, highlightGradientEndColor, highlightCornerRadius; @synthesize textShadowOpacity, textShadowOffset; @synthesize badgeBorderColor, badgeGradientEndColor, badgeGradientStartColor, badgeFont, badgeShadowOffset, badgeShadowOpacity, badgeTextColor; @@ -331,7 +331,7 @@ - (void)drawRect:(CGRect)rect } else { [PrettyDrawing drawGradientRoundedRect:CGRectMake(2, 3, self.frame.size.width - 4, self.frame.size.height - 5) - cornerRadius:3.0 + cornerRadius:self.highlightCornerRadius fromColor:self.highlightGradientStartColor toColor:self.highlightGradientEndColor]; } From 2bf5bdd475a9c59772f9abc2c6537f46b452a9e5 Mon Sep 17 00:00:00 2001 From: Jeremy Foo Date: Wed, 30 May 2012 23:50:09 +0800 Subject: [PATCH 44/48] work around to stop instruments complaining about a memory leak that is non existent --- PrettyKit/PrettyTabBar.m | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/PrettyKit/PrettyTabBar.m b/PrettyKit/PrettyTabBar.m index 8f5b530..34f503b 100644 --- a/PrettyKit/PrettyTabBar.m +++ b/PrettyKit/PrettyTabBar.m @@ -123,8 +123,8 @@ - (void) initializeVars self.separatorLineColor = default_separator_line_color; // pretty button stuff - __prettyTabBarButtons = [[NSMutableArray arrayWithCapacity:5] retain]; - __originalTabBarButtons = [[NSMutableArray arrayWithCapacity:0] retain]; + self._prettyTabBarButtons = [NSMutableArray arrayWithCapacity:5]; + self._originalTabBarButtons = [NSMutableArray arrayWithCapacity:0]; self.prettyButtonHighlightedImages = nil; self.prettyButtonHighlightCornerRadius = default_highlight_corner_radius; From 44d715183a91c9ef76f79485f04d84dc1ca4f624 Mon Sep 17 00:00:00 2001 From: Jeremy Foo Date: Fri, 29 Jun 2012 11:58:27 +0800 Subject: [PATCH 45/48] ivar for BOOL prettyTabBarButtons conflicts with internal ivar --- PrettyKit/PrettyTabBar.m | 10 +++++----- 1 file changed, 5 insertions(+), 5 deletions(-) diff --git a/PrettyKit/PrettyTabBar.m b/PrettyKit/PrettyTabBar.m index 34f503b..4ef7f7d 100644 --- a/PrettyKit/PrettyTabBar.m +++ b/PrettyKit/PrettyTabBar.m @@ -66,7 +66,7 @@ -(void)_setupTabBarSubviews; @implementation PrettyTabBar @synthesize upwardsShadowOpacity, downwardsShadowOpacity, gradientStartColor, gradientEndColor, separatorLineColor; -@synthesize prettyTabBarButtons = _prettyTabBarButtons; +@synthesize prettyTabBarButtons; @synthesize prettyButtonHighlightedImageGradientStartColor, prettyButtonHighlightedImageGradientEndColor, prettyButtonHighlightedImages; @synthesize prettyButtonTitleFont, prettyButtonTitleTextColor, prettyButtonTitleHighlightedTextColor, prettyButtonTitleTextShadowOpacity, prettyButtonTitleTextShadowOffset; @@ -193,7 +193,7 @@ -(void)setItems:(NSArray *)items animated:(BOOL)animated { -(void)_setupTabBarSubviews { - if (_prettyTabBarButtons) { + if (self.prettyTabBarButtons) { // changing from original to pretty implementation // remove views that are not prettytabbarbuttons @@ -260,14 +260,14 @@ -(void)_setupTabBarSubviews { } } --(void)setPrettyTabBarButtons:(BOOL)prettyTabBarButtons { +-(void)setPrettyTabBarButtons:(BOOL)prettyTabBarButtons_ { // we should only change the status if its different - if (_prettyTabBarButtons != prettyTabBarButtons) { + if (self.prettyTabBarButtons != prettyTabBarButtons_) { // set the status of our internal representation - _prettyTabBarButtons = prettyTabBarButtons; + self.prettyTabBarButtons = prettyTabBarButtons_; [self _setupTabBarSubviews]; From ea27445e20d01717583b7bca03a8dc4252ae103d Mon Sep 17 00:00:00 2001 From: Jeremy Foo Date: Fri, 29 Jun 2012 14:02:50 +0800 Subject: [PATCH 46/48] use ivar for accessor methods --- PrettyKit/PrettyTabBar.m | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/PrettyKit/PrettyTabBar.m b/PrettyKit/PrettyTabBar.m index 4ef7f7d..92b4487 100644 --- a/PrettyKit/PrettyTabBar.m +++ b/PrettyKit/PrettyTabBar.m @@ -264,10 +264,10 @@ -(void)setPrettyTabBarButtons:(BOOL)prettyTabBarButtons_ { // we should only change the status if its different - if (self.prettyTabBarButtons != prettyTabBarButtons_) { + if (prettyTabBarButtons != prettyTabBarButtons_) { // set the status of our internal representation - self.prettyTabBarButtons = prettyTabBarButtons_; + prettyTabBarButtons = prettyTabBarButtons_; [self _setupTabBarSubviews]; From 93d9c03f110f10dea2c88a9e3fe7f11ed6440d2e Mon Sep 17 00:00:00 2001 From: Jeremy Foo Date: Fri, 10 Aug 2012 15:18:22 +0800 Subject: [PATCH 47/48] added ability to generate iOS 6 styled tabbars --- PrettyKit/PrettyTabBar.h | 6 ++++++ PrettyKit/PrettyTabBar.m | 22 ++++++++++++++++++---- PrettyKit/PrettyTabBarButton.h | 5 +++++ PrettyKit/PrettyTabBarButton.m | 18 +++++++++++++----- 4 files changed, 42 insertions(+), 9 deletions(-) diff --git a/PrettyKit/PrettyTabBar.h b/PrettyKit/PrettyTabBar.h index 2dddcd1..da7ced3 100644 --- a/PrettyKit/PrettyTabBar.h +++ b/PrettyKit/PrettyTabBar.h @@ -72,6 +72,12 @@ // Pretty Tab Bar Button Implementation & Customization ///////////////////////////////////////////////////////////////////////////// +/** Specifies that the PrettyTabBarButtons that should be used is of the iOS 6 styling + that stretches from the bottom to the top of the bar + + By default is NO. */ +@property (nonatomic) BOOL prettyStretchedTabBarButtons; + /** Specifies that PrettyTabBarButtons should be used instead of the default UITabBarButtons By default is NO. */ diff --git a/PrettyKit/PrettyTabBar.m b/PrettyKit/PrettyTabBar.m index 92b4487..d552593 100644 --- a/PrettyKit/PrettyTabBar.m +++ b/PrettyKit/PrettyTabBar.m @@ -66,7 +66,7 @@ -(void)_setupTabBarSubviews; @implementation PrettyTabBar @synthesize upwardsShadowOpacity, downwardsShadowOpacity, gradientStartColor, gradientEndColor, separatorLineColor; -@synthesize prettyTabBarButtons; +@synthesize prettyTabBarButtons, prettyStretchedTabBarButtons; @synthesize prettyButtonHighlightedImageGradientStartColor, prettyButtonHighlightedImageGradientEndColor, prettyButtonHighlightedImages; @synthesize prettyButtonTitleFont, prettyButtonTitleTextColor, prettyButtonTitleHighlightedTextColor, prettyButtonTitleTextShadowOpacity, prettyButtonTitleTextShadowOffset; @@ -115,6 +115,7 @@ - (void) initializeVars self.contentMode = UIViewContentModeRedraw; self.prettyTabBarButtons = NO; + self.prettyStretchedTabBarButtons = NO; self.upwardsShadowOpacity = default_upwards_shadow_opacity; self.downwardsShadowOpacity = default_downwards_shadow_opacity; @@ -179,7 +180,6 @@ -(void)setItems:(NSArray *)items { [super setItems:items]; [self _setupTabBarSubviews]; - [self setNeedsLayout]; } @@ -187,7 +187,13 @@ -(void)setItems:(NSArray *)items animated:(BOOL)animated { [super setItems:items animated:animated]; [self _setupTabBarSubviews]; + [self setNeedsLayout]; +} + +-(void)setSelectedItem:(UITabBarItem *)selectedItem { + [super setSelectedItem:selectedItem]; + [self _setupTabBarSubviews]; [self setNeedsLayout]; } @@ -218,6 +224,8 @@ -(void)_setupTabBarSubviews { button = [[PrettyTabBarButton alloc] initWithTitle:item.title image:item.image tag:i]; button.autoresizingMask = UIViewAutoresizingFlexibleHeight | UIViewAutoresizingFlexibleWidth; + button.stretchedButton = self.prettyStretchedTabBarButtons; + [button addTarget:self action:@selector(_prettyTabBarButtonTapped:) forControlEvents:UIControlEventTouchUpInside]; if (item == self.selectedItem) { @@ -346,7 +354,12 @@ -(void)layoutSubviews { break; button = [self._prettyTabBarButtons objectAtIndex:i]; - button.frame = CGRectMake(i * (self.frame.size.width/[self.items count]), 0, (self.frame.size.width/[self.items count]), self.frame.size.height); + if (self.prettyStretchedTabBarButtons) { + button.frame = CGRectMake(i * (self.frame.size.width/[self.items count]), 0, (self.frame.size.width/[self.items count]) - 1, self.frame.size.height); + } else { + button.frame = CGRectMake(i * (self.frame.size.width/[self.items count]), 0.5, (self.frame.size.width/[self.items count]) - 1, self.frame.size.height); + } + [self addSubview:button]; // set button properties @@ -369,6 +382,7 @@ -(void)layoutSubviews { button.highlightedImageGradientStartColor = self.prettyButtonHighlightedImageGradientStartColor; button.highlightedImageGradientEndColor = self.prettyButtonHighlightedImageGradientEndColor; button.highlightCornerRadius = self.prettyButtonHighlightCornerRadius; + button.stretchedButton = self.prettyStretchedTabBarButtons; button.selected = NO; button.badgeValue = item.badgeValue; @@ -395,7 +409,7 @@ - (void) drawRect:(CGRect)rect { [self dropShadowOffset:CGSizeMake(0, 0) withOpacity:self.downwardsShadowOpacity]; [PrettyDrawing drawGradient:rect fromColor:self.gradientStartColor toColor:self.gradientEndColor]; - [PrettyDrawing drawLineAtHeight:0.5 rect:rect color:self.separatorLineColor width:2.5]; + [PrettyDrawing drawLineAtHeight:0 rect:rect color:self.separatorLineColor width:0.5]; } @end diff --git a/PrettyKit/PrettyTabBarButton.h b/PrettyKit/PrettyTabBarButton.h index 3f7f36f..f24b6be 100644 --- a/PrettyKit/PrettyTabBarButton.h +++ b/PrettyKit/PrettyTabBarButton.h @@ -29,6 +29,11 @@ @interface PrettyTabBarButton : UIControl +/** Specifies the tabbar button should be stretched, a la iOS 6 styling + + By default is `NO`. */ +@property (readwrite) BOOL stretchedButton; + /** Specifies the image to use when the Button is selected. If it is not specified, the button will use the normal image in a gradient tint that is specified. By default is `nil`. */ diff --git a/PrettyKit/PrettyTabBarButton.m b/PrettyKit/PrettyTabBarButton.m index 670a28e..1744224 100644 --- a/PrettyKit/PrettyTabBarButton.m +++ b/PrettyKit/PrettyTabBarButton.m @@ -37,6 +37,7 @@ -(CGSize)_sizeForWidth:(CGFloat)width height:(CGFloat)height; @end @implementation PrettyTabBarButton +@synthesize stretchedButton; @synthesize title = _title, image = _image, badgeValue = _badgeValue; @synthesize highlightedImage, highlightedImageGradientStartColor, highlightedImageGradientEndColor; @synthesize textColor, font, highlightedTextColor; @@ -60,6 +61,8 @@ - (void) initializeVars self.opaque = NO; self.backgroundColor = [UIColor clearColor]; + + self.stretchedButton = NO; } @@ -329,11 +332,16 @@ - (void)drawRect:(CGRect)rect [self.highlightImage drawInRect:CGRectMake(2, 1, self.frame.size.width - 2, self.frame.size.height - 1)]; } else { - - [PrettyDrawing drawGradientRoundedRect:CGRectMake(2, 3, self.frame.size.width - 4, self.frame.size.height - 5) - cornerRadius:self.highlightCornerRadius - fromColor:self.highlightGradientStartColor - toColor:self.highlightGradientEndColor]; + if (self.stretchedButton) { + [PrettyDrawing drawGradient:CGRectMake(0, 0.5, self.frame.size.width, self.frame.size.height) fromColor:self.highlightGradientStartColor toColor:self.highlightGradientEndColor]; + + } else { + [PrettyDrawing drawGradientRoundedRect:CGRectMake(2, 3, self.frame.size.width - 4, self.frame.size.height - 5) + cornerRadius:self.highlightCornerRadius + fromColor:self.highlightGradientStartColor + toColor:self.highlightGradientEndColor]; + + } } } From b11032331a2d3181c70874c935a1f7929d0f12c6 Mon Sep 17 00:00:00 2001 From: Jeremy Foo Date: Wed, 10 Oct 2012 22:04:54 +0800 Subject: [PATCH 48/48] include the correct framework --- PrettyKit/PrettyDrawing.h | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/PrettyKit/PrettyDrawing.h b/PrettyKit/PrettyDrawing.h index 65f2558..d8ba34e 100644 --- a/PrettyKit/PrettyDrawing.h +++ b/PrettyKit/PrettyDrawing.h @@ -27,7 +27,7 @@ // SOFTWARE. -#import +#import typedef enum { LinePositionTop = 0,