UINavigationBar appearance setBackgroundImage:nil doesn´t work on ios 5.1 - ios

i set my UINavigationBar appearance with the following line:
UIImage *navigationBarBackground = [UIImage imageNamed:#"HeaderNavBar.png"];
[[UINavigationBar appearance] setBackgroundImage:navigationBarBackground forBarMetrics:UIBarMetricsDefault];
I remove it with the following line:
[[UINavigationBar appearance] setBackgroundImage:nil forBarMetrics:UIBarMetricsDefault];
This works on every ios, except on ios 5.1...Does somebody know why?!

"When the contents of your view change, you do not redraw those changes directly. Instead, you invalidate the view using either the setNeedsDisplay or setNeedsDisplayInRect: method." (View Programming Guide). Do you still have that issue after redrawing the view?
See also: UIView Class Reference: setNeedsDisplay

[[UINavigationBar appearanceWhenContainedIn:[self class], nil] setBackgroundImage:navigationBarBackground forBarMetrics:UIBarMetricsDefault];
and then:
[[UINavigationBar appearanceWhenContainedIn:[self class], nil] setBackgroundImage:nil forBarMetrics:UIBarMetricsDefault];
It is recommended here.

Related

Change ios8 Extension Navigation Bar color

I am working on iOS8 App Extension (Photo Editing Extension)
I have tried these method to update the Navigation Bar color, but failed:
[[UINavigationBar appearance] setBarTintColor:[UIColor yellowColor]];
[[UINavigationBar appearance] setTintColor:[UIColor blueColor]];
[[UINavigationBar appearance] setBackgroundColor:[UIColor blueColor]];
It displays a default translucent gray nav bar.
Does anybody have idea on how to change the navigation bar color in iOS8 extension?
Try self.navigationController.navigationBar.barTintColor = UIColor.yellow first.
This should work for some host apps but not all. Because some host apps configure the colors in UIAppearance settings.
I found some info in here: https://pspdfkit.com/blog/2017/action-extension/#uiappearance
According to the link above, the extension will "picks up the UIAppearance settings from its host app" and this has a higher priority than the "setColor" message you send to the instance.
In this case what you can do is to modify the plist of the extension:
In NSExtension dictionary you can add a key NSExtensionOverridesHostUIAppearance and set value to YES. This will make your extension override the UIApprearance setting of the host app. Unfortunately this is only available in iOS 10 and later.
Hope you find it helpful.
Try setting the translucency of the UINavigationBar to NO like below, I believe then it should start picking up the colours
[[UINavigationBar appearance] setTranslucent:NO];
Here's the Apple Documentation for UINavigationBar translucent property
I have put your code in the appDelegate didFinishLaunchWithOption
- (BOOL)application:(UIApplication *)application didFinishLaunchingWithOptions:(NSDictionary *)launchOptions {
// Override point for customization after application launch.
[[UINavigationBar appearance] setBarTintColor:[UIColor yellowColor]];
[[UINavigationBar appearance] setTintColor:[UIColor blueColor]];
[[UINavigationBar appearance] setBackgroundColor:[UIColor blueColor]];
return YES;
}
And works...

Mail app segue (open-with) with incorrect navigation bar colors

I am currently attempting to open up the iOS mail all to create a draft with an attachment generated from my app. Here is a code snippet:
NSURL *fileLocation = [NSURL fileURLWithPath:self.site.dataFileLoc];
if(fileLocation) {
self.documentController = [UIDocumentInteractionController interactionControllerWithURL:fileLocation];
[self.documentController setDelegate:self];
[self.documentController presentOptionsMenuFromRect:self.view.bounds inView:self.view animated:YES];
}
However, what I am finding is that the navigation bar colours are completely off. In the AppDelegate, I am currently using these lines to set the global navigation bar appearance:
[[UINavigationBar appearance] setTintColor:[UIColor whiteColor]];
[[UINavigationBar appearance] setBarStyle:UIBarStyleBlack];
[[UINavigationBar appearance] setBackgroundImage:[UIImage imageNamed:#"navbarBackground"] forBarPosition:UIBarPositionAny barMetrics:UIBarMetricsDefault];
[[UINavigationBar appearanceWhenContainedIn:[UIViewController class], nil] setShadowImage:[UIImage imageNamed:#"shadow"]];
[[UITabBar appearance] setSelectedImageTintColor:[UIColor whiteColor]];
[[UITabBar appearance] setTintColor:[UIColor whiteColor]];
[[UIApplication sharedApplication] setStatusBarStyle:UIStatusBarStyleLightContent animated:NO];
Unfortunately, the title of the mail view controller that appears is still black, despite my attempt to set the bar style to black (which should make the title white in return) and blue bar buttons. It does, however, seem to work fine for the "presentPreviewAnimated" view controller. How can I make the navigation bar of the mail view controller consistent?
Are there any nibs associated??
I usually try to avoid the desired level of UI customization (navigation bar styles, colors, custom background w/image) because drawing UI at runtime (unless dynamically required) generally gets me in trouble...
Why not mock it up in a .nib file and make use of the fancy-dance-y tools in Xcode?? Can be therapeutic to quickly obtain the desired grain of detail without having to hit run...

UINavigationBar custom background image applied in one view controller and then affecting every single view controller in the app

I am working with themes in my app. Each theme comes with a custom navigation bar. As a default, I have applied a custom navigation bar in my AppDelegate:
[UIApplication sharedApplication].statusBarStyle = UIStatusBarStyleLightContent;
UIImage *navBackgroundImage = [UIImage imageNamed:#"purplynav.png"];
[[UINavigationBar appearance] setBackgroundImage:navBackgroundImage forBarMetrics:UIBarMetricsDefault];
If I go to a specific Table View Controller in my app and in the viewWillAppear, I put:
if ([self.selectedTheme isEqualToString:#"Blur"])
{
UIImage *navBackgroundImage = [UIImage imageNamed:#"pastelpinknav.png"];
[[UINavigationBar appearance] setBackgroundImage:navBackgroundImage forBarMetrics:UIBarMetricsDefault];
}
The "pastelpinknav" suddenly gets applied to every single navigation bar in my app, even though I'm only setting it in this one Table View Controller.
How do I set it so that the navigation bar only applies to this one view controller when set, but is still set to default in the App Delegate when a theme is not set?
Thanks in advance!
You have to change again the navigationBar image in viewWillDisappear
UIImage *navBackgroundImage = [UIImage imageNamed:#"purplynav.png"];
[[UINavigationBar appearance] setBackgroundImage:navBackgroundImage forBarMetrics:UIBarMetricsDefault];
Because you are using [UINavigationBar appearance] it will commonly changes the UINavigationBar appearance.
From your view controller call:
[[UINavigationBar appearanceWhenContainedIn:[self class], nil] setBackgroundImage:navBackgroundImage
forBarMetrics:UIBarMetricsDefault];
Explenation:
This will change the foo color of the entire app:
[[UINavigationBar appearance] setFooColor:#"blue"]
In order to change appearance of specific container (i.e your view controller), you need to implement UIAppearanceContainer and then call (UIViewController already implements it):
[UINavigationBar appearanceWhenContainedIn:(Class<UIAppearanceContainer>), ..., nil]

How to change NavBar Image from different View Controller

Previously when I only needed 1 navbar image, I would just do
UIImage *navBarImage = [UIImage imageNamed:#"navbarimage.png"];
[[UINavigationBar appearance]setBackgroundImage:navBarImage forBarMetrics:UIBarMetricsDefault];
in AppDelegate, and that would stay throughout the app.
However, now I need to change the navbar images when going from a rootview to a tableview.
I tried putting
UIImage *navBarImage = [UIImage imageNamed:#"vybeNavBarEmpty.png"];
[[UINavigationBar appearance]setBackgroundImage:navBarImage forBarMetrics:UIBarMetricsDefault];
in the viewwillappear of my tableview class, but nothing changes.
Any idea how to do this?
Try with below code:
[self.navigationController.navigationBar setBackgroundImage:[UIImage imageNamed:#"vybeNavBarEmpty.png"] forBarMetrics:UIBarMetricsDefault];
Try this one:
[self.navigationController.navigationBar setBackgroundImage:[UIImage imageNamed:#"newImage.png"]];

How to block UIAppearance proxy for some control

I set custom appearance to some of my UI classes.
[[UIBarButtonItem appearance] setTintColor:someColor];
...
[[UINavigationBar appearance] setBackgroundImage:someImage forBarMetrics:UIBarMetricsDefault];
So when i create UIBarButtonItem's or UINavigationBar's objects in my application they will have defined appearance.
But if want some object to have standart appearance(Not to use defined by proxy), I need to set all it's properties to default values manually.
So the quesion is: Is there any way to block using UIAppearance for some object?
Thank you.
Edit:
Its probably not 100% what you want to do but you could use appearanceWhenContainedIn.
[[UIBarButtonItem appearanceWhenContainedIn:[UINavigationBar class], nil] setTintColor:[UIColor redColor]];
[[UIBarButtonItem appearanceWhenContainedIn:[UIToolbar class], nil] setTintColor:[UIColor yellowColor]];
This way you can control the behavior to a certain degree.
Setting the properties to nil will use the default appearance:
[self.navigationController.navigationBar setTintColor:nil];

Resources