This bug was firstly found in iOS 7, and it can be reproduced in iOS 8 either.
There is a three view controllers A, B and C. Managed by UINavigationController. And I'd like to hide the navigation bar for controller A, not for others.
Here is the code I've written for controller A.
- (void)viewWillAppear:(BOOL)animated {
[super viewWillAppear:animated];
self.navigationController.navigationBarHidden = YES;
}
- (void)viewWillDisappear:(BOOL)animated {
[super viewWillDisappear:animated];
self.navigationController.navigationBarHidden = NO;
}
When user comes back via navigation backBarButtonItem, it works fine for me. But when user slides backwards and forward from the left side(That is do not actually go backwards to controller A from controller B, but stay in controller B at last), the navigation bar will go into confusional sate.
Here is a demo to show this issue: [Demo]:https://github.com/heistings/NavigationTest
This problem can be simply fixed by disable the interactivePopGestureRecognizer of navigation controller, but can't say it's perfect:
self.navigationController.interactivePopGestureRecognizer.enabled = NO;
use animated property to YES.
- (void)viewWillAppear:(BOOL)animated {
[super viewWillAppear:animated];
[self.navigationController setNavigationBarHidden:YES animated:YES];
}
- (void)viewWillDisappear:(BOOL)animated {
[super viewWillDisappear:animated];
[self.navigationController setNavigationBarHidden:NO animated:YES];
}
Maybe this will help you.
This may be the best way for this issue since we have got the animated from framework:
- (void)viewWillAppear:(BOOL)animated {
[super viewWillAppear:animated];
[self.navigationController setNavigationBarHidden:YES animated:animated];
}
- (void)viewWillDisappear:(BOOL)animated {
[super viewWillDisappear:animated];
[self.navigationController setNavigationBarHidden:NO animated:animated];
}
I got your problem.
First Embed navigation controller to ViewController...
Click on storyboard...
Click on View Controller...
Goto Editor section.
Click on Embed in and then click on navigation controller.
And then Write the code below:
- (void)viewWillAppear:(BOOL)animated {
[super viewWillAppear:animated];
[self.navigationController setNavigationBarHidden:YES animated:animated];
}
- (void)viewWillDisappear:(BOOL)animated {
[super viewWillDisappear:animated];
[self.navigationController setNavigationBarHidden:NO animated:animated];
}
Related
I have a problem about the navigation bar.
I have ViewControllerA with a hidden NavigationBar. I have set the navigationBar hidden using the code below:
- (void)viewWillAppear:(BOOL)animated
{
[super viewWillAppear:animated];
[self.navigationController setNavigationBarHidden:YES animated:animated];
}
-(void)viewWillDisappear:(BOOL)animated
{
[super viewWillDisappear:animated];
[self.navigationController setNavigationBarHidden:NO animated:animated];
}
I push ViewControllerA and then ViewControllerA again. But NavigationBar will appear when I go back to First ViewControllerA by using system gesture.
I hope I can get some ways to solve this problem. Thanks.
You're almost there, hide it in ViewControllerA and then show it in ViewControllerB, don't show it when ViewControllerA will disappear. The below code is all you need, good luck.
ViewControllerA:
- (void)viewWillAppear:(BOOL)animated {
[super viewWillAppear:animated];
[self.navigationController setNavigationBarHidden:YES animated:animated];
}
ViewControllerB:
- (void)viewWillAppear:(BOOL)animated {
[super viewWillAppear:animated];
[self.navigationController setNavigationBarHidden:NO animated:animated];
}
Dear First You are set Navigation bar hidden at Navigation Controller Property (Storyboard->Click Navigation Controller->Property) and You want Navigation Bar in any View Controller Scene so your are add this code in .m file of view controller.
-(void)viewWillAppear:(BOOL)animated{
[self.navigationController setNavigationBarHidden:YES animated:animated];
[super viewWillAppear:animated];
}
I have a master viewController and many detail viewController. Master viewController doesn't have any UINavigationBar but detail viewController has UINavigationBar. So I have some problem. When I swipe from detailVC to masterVC UINavigationBar hiding in detailVC
Have you any solution this?
I use these methods (master viewController )
-(void)viewWillAppear:(BOOL)animated{
[super viewWillAppear:animated];
[self.navigationController setNavigationBarHidden:YES animated:YES];
}
(detail viewController)
-(void)viewWillAppear:(BOOL)animated{
[super viewWillAppear:animated];
[self.navigationController setNavigationBarHidden:NO animated:YES];
}
Finally
I have solved this issue.
I wrote UINavigationBar hiding code for firstVC in the viewDidAppear method.
-(void)viewDidAppear:(BOOL)animated{
[super viewDidAppear:animated];
[self.navigationController setNavigationBarHidden:YES animated:YES];
}
On View1 I hide the navigationBar in viewDidLoad:
- (void)viewDidLoad
{
[super viewDidLoad];
[self.navigationController setNavigationBarHidden:YES];
}
Then I navigate to View2 where I show the navigationBar
- (void)viewDidLoad
{
[super viewDidLoad];
[self.navigationController setNavigationBarHidden:NO];
self.title = #"Title";
}
But on back to View1 again, the navigationBar doesn't hide, even if I did tried to hide it after the pushViewController in View2
[self.navigationController pushViewController:View1 animated:YES];
[self.navigationController setNavigationBarHidden:YES];
I also tried to hide the navigation from viewWillAppear in View1 and it hides it, but there is an ugly delay and I don't find it as a good practice.
So can anyone help me with this issue, how can I hide correctly the navigationBar on back to View1?
The best practice to do what you want is putting bellow in your first viewController:
- (void)viewWillAppear:(BOOL)animated{
[self.navigationController setNavigationBarHidden:YES animated:animated];
[super viewWillAppear:animated];
}
- (void)viewWillDisappear:(BOOL)animated{
[self.navigationController setNavigationBarHidden:NO animated:animated];
[super viewWillDisappear:animated];
}
-(void) viewDidAppear:(BOOL)animated {
[super viewDidAppear:animated];
[self.navigationController setNavigationBarHidden:YES];
}
The ViewController1 is not going to get allocated again and so viewDidLoad is not going to get called.
You can do it in viewWillAppear though. But if you are saying that there is a delay, you can do one more thing.
You can get the reference ofViewController1 in ViewController2. Suppose ViewController1 is the first controller in the navigation controller, then do this:
//ViewController2.m
- (IBAction)backButtonPressed:(id)sender{
ViewController1 *view1 = [self.navigationController.viewControllers objectAtIndex:0];
[view1.navigationController setNavigationBarHidden:YES];
Your code is correct, but you need to write like this:
[self.navigationController setNavigationBarHidden:YES];
first, then write
[self.navigationController pushViewController:View1 animated:YES];
See when you are pushing View2 from View2 in navigation stack than View1 doesn't gets deallocated. it is there in in the stack. So when you popping out View2 that time View1 viewDidLoad won't get called. so your code setNavigationBarHidden to hide navigation bar doesn't executes. So put that code to ViewWillAppear or ViewDidAppear because these methods gets called every time View appears.
- (void)viewWillAppear:(BOOL)animated
{
[super viewWillAppear:animated];
[self.navigationController setNavigationBarHidden:YES];
}
I have UIViewController(1) without navigationBar, and I need to push anouther UIViewController(2) that have navigationBar, and when I click Back on it, navigationBar must hide on 1 controller. I have tried uiviewcontroller delegates.
But nothing is working..
Please help..
This will show the navbar on the second screen:
- (void)viewWillAppear:(BOOL)animated {
[super viewWillAppear:animated];
self.navigationController.navigationBarHidden = NO;
}
You will also need to hide the navbar when you return to the first screen:
- (void)viewDidDisappear:(BOOL)animated {
[super viewDidDisappear:animated];
self.navigationController.navigationBarHidden = YES;
}
I think you want the animated option. If you roll with the approaches above (self.navigationController.navigationBarHidden = value) you get some undesirable visual crumbs.
- (void)viewWillAppear:(BOOL)animated
{
[super viewWillAppear:animated];
[self.navigationController setNavigationBarHidden:NO animated:YES];
}
- (void)viewWillDisappear:(BOOL)animated
{
[super viewWillDisappear:animated];
[self.navigationController setNavigationBarHidden:YES animated:YES];
}
This will push/pop smoothly with the navBar firmly attached to the appearing/disappearing view.
Place this code in first view controller
- (void)viewWillAppear:(BOOL)animated {
[super viewWillAppear:animated];
self.navigationController.navigationBarHidden = YES;
}
Answers from Alfie or Ader would be a disaster if you have many viewcontrollers' navigation bar hidden/show state to manage.
I just have posted code dedicated on UINavigationBar appearance management on github. check out RRViewControllerExtension, it will solve your problem gracefully.
With RRViewControllerExtension, you even don't have to #import the header file, all you have to do is just override any desired method below in your viewcontroller.
//override any of the methods below in your viewcontroller's .m file to make specific navigation bar appearance
-(BOOL)prefersNavigationBarHidden;
-(BOOL)prefersNavigationBarTransparent;
-(nullable UIColor *)preferredNavatationBarColor;
-(nullable UIColor *)preferredNavigationItemColor;
-(nullable UIImage *)preferredNavigationBarBackgroundImage;
-(nullable NSDictionary *)preferredNavigationTitleTextAttributes;
In my app i hav 4 views, i want to hide the navigation bar only from my initial view, when i tried using this code
[[self navigationController] setNavigationBarHidden:YES animated:NO]; it hides the navigation bar of other views too., plz help me to fix this issue ,.
thanks
[[self navigationController] setNavigationBarHidden:NO animated:NO];
add above code in -(void)ViewWillAppear function of other views
Instead of adding [[self navigationController] setNavigationBarHidden:NO animated:NO]; to each of the following views (which may be many), you could just add it to - (void)viewWillDisappear in your initial view... That way it will make sure to add it before leaving that view.
Make sure that you hide the navigation bar in - (void)viewWillAppear, so it'll hide it when you return to the initial view.
The best way to do this and shorter in terms of code is:
- (void)viewWillAppear:(BOOL)animated {
[self.navigationController setNavigationBarHidden:YES animated:animated];
[super viewWillAppear:animated];
}
- (void)viewWillDisappear:(BOOL)animated {
[self.navigationController setNavigationBarHidden:NO animated:animated];
[super viewWillDisappear:animated];
}
On the desired (hidden top bar) view controller.