Instantly share code, notes, and snippets.
Last active
December 26, 2015 11:19
-
Star
0
(0)
You must be signed in to star a gist -
Fork
0
(0)
You must be signed in to fork a gist
-
Save matej/7142976 to your computer and use it in GitHub Desktop.
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
// | |
// MBStronglyTintedNavigationBar.h | |
// | |
// Created by Matej Bukovinski on 21. 10. 13. | |
// Copyright (c) 2013 Matej Bukovinski. All rights reserved. | |
// | |
#import <UIKit/UIKit.h> | |
@interface MBStronglyTintedNavigationBar : UINavigationBar | |
@end |
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
// | |
// MBStronglyTintedNavigationBar.m | |
// | |
// Created by Matej Bukovinski on 21. 10. 13. | |
// Copyright (c) 2013 Matej Bukovinski. All rights reserved. | |
// | |
#import "MBStronglyTintedNavigationBar.h" | |
#define IS_WIDESCREEN_PHONE UI_USER_INTERFACE_IDIOM() == UIUserInterfaceIdiomPhone && [UIScreen mainScreen].bounds.size.height > 480.f | |
#define IS_IOS703_OR_NEWER [[[UIDevice currentDevice] systemVersion] compare:@"7.0.3" options:NSNumericSearch] != NSOrderedAscending | |
static CGFloat const kSpaceToCoverStatusBars = 20.f; | |
static CGFloat const kSatIncrease = 13.f; | |
@interface MBStronglyTintedNavigationBar () | |
@property (nonatomic, strong) CALayer *colorLayer; | |
@end | |
@implementation MBStronglyTintedNavigationBar | |
#pragma mark - Tint color | |
- (void)setBarTintColor:(UIColor *)barTintColor { | |
// No translucency, no problems | |
if (!self.translucent) { | |
return [super setBarTintColor:barTintColor];; | |
} | |
BOOL supportsBlurOnMap = IS_WIDESCREEN_PHONE; | |
BOOL updatedTintRenderingAvailable = IS_IOS703_OR_NEWER; | |
// Increase the bar tint color saturation, to com pensate for the desaturation the bar applies | |
// (in all cases, except when using a solid overlay layer) | |
if (supportsBlurOnMap || updatedTintRenderingAvailable) { | |
barTintColor = [self colorByIncreasingSaturationFromColor:barTintColor]; | |
} | |
if (supportsBlurOnMap && updatedTintRenderingAvailable) { | |
// Newer devices with iOS 7.0.3+ remove blur almost completeley, | |
// so we decrease the color opacity of the nativ background | |
[super setBarTintColor:[barTintColor colorWithAlphaComponent:0.5]]; | |
} else if (!supportsBlurOnMap) { | |
// Old devices will have problems rendering the bar background when a map view | |
// is involved, so we rather set a translucent background | |
[super setBarTintColor:[UIColor clearColor]]; | |
} else { | |
[super setBarTintColor:barTintColor]; | |
} | |
// Otherwise we add a new layer on top of the navigation bar background | |
if (self.colorLayer == nil) { | |
self.colorLayer = [CALayer layer]; | |
if (supportsBlurOnMap) { | |
// New device, pre iOS 7.0.3 - adding an additonal layer to improve the color saturation | |
// and tone down the heavy translucent blur effect | |
self.colorLayer.opacity = 0.7f; | |
} else { | |
if (updatedTintRenderingAvailable) { | |
// Old device, iOS 7.0.3 - this case exhibits animation glitches during view controller transitions, | |
// so we previously set the bar background to a transpaent color and we use a slightly translucent colored layer | |
self.colorLayer.opacity = 0.95f; | |
} else { | |
// Old device, pre iOS 7.0.3 - the bar background will always be black translcucent, | |
// so we need to cover the system bar background with a non-translucent layer | |
self.colorLayer.opacity = 1.f; | |
// Use the normal color here instrad of the saturated version | |
barTintColor = [VBAppearanceManager highlightColor]; | |
} | |
} | |
[self.layer addSublayer:self.colorLayer]; | |
} | |
self.colorLayer.backgroundColor = barTintColor.CGColor; | |
} | |
- (UIColor *)colorByIncreasingSaturationFromColor:(UIColor *)color { | |
CGFloat h, s, b, a; | |
BOOL ok = [color getHue:&h saturation:&s brightness:&b alpha:&a]; | |
if (!ok) { | |
return color; | |
} | |
s = MIN(s + kSatIncrease, 1.f); | |
return [UIColor colorWithHue:h saturation:s brightness:b alpha:a]; | |
} | |
#pragma mark - Layout | |
- (void)layoutSubviews { | |
[super layoutSubviews]; | |
if (self.colorLayer != nil) { | |
CGRect bounds = self.bounds; | |
CGFloat w = CGRectGetWidth(bounds); | |
CGFloat topExtend = self.barPosition == UIBarPositionTopAttached ? kSpaceToCoverStatusBar : 0.f; | |
CGFloat h = CGRectGetHeight(bounds) + topExtend; | |
self.colorLayer.frame = CGRectMake(0.f, -topExtend, w, h); | |
[self.layer insertSublayer:self.colorLayer atIndex:1]; | |
} | |
} | |
@end |
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment