396 votes

L'iPhone masque la barre de navigation uniquement sur la première page

J'ai le code ci-dessous qui masque et affiche la barre de navigation. Elle est cachée lorsque la première vue se charge et ensuite cachée lorsque les "enfants" sont appelés. Le problème est que je n'arrive pas à trouver l'événement/action qui déclenche le masquage de la barre de navigation lorsqu'ils reviennent à la vue principale.....

J'ai un bouton "test" sur la page racine qui effectue manuellement l'action mais ce n'est pas joli et je veux que ce soit automatique.

-(void)hideBar 
{
    self.navController.navigationBarHidden = YES;
}
-(void)showBar 
{       
    self.navController.navigationBarHidden = NO;
}

1053voto

Alan Rogers Points 8400

La plus belle solution que j'ai trouvée consiste à faire ce qui suit dans le fichier premier contrôleur de vue .

Objectif-C

- (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];
}

Swift

override func viewWillAppear(_ animated: Bool) {
    self.navigationController?.setNavigationBarHidden(true, animated: animated)
    super.viewWillAppear(animated)
}

override func viewWillDisappear(_ animated: Bool) {
    self.navigationController?.setNavigationBarHidden(false, animated: animated)
    super.viewWillDisappear(animated)
} 

Ainsi, la barre de navigation s'animera à partir de la gauche (en même temps que la vue suivante) lorsque vous appuierez sur le bouton "next". UIViewController sur la pile, et se déplacent vers la gauche (en même temps que l'ancienne vue), lorsque vous appuyez sur le bouton "retour" de la fenêtre UINavigationBar .

Notez également qu'il ne s'agit pas de méthodes déléguées, mais d'une surcharge de l'ordre du jour. UIViewController L'implémentation de ces méthodes par l'utilisateur et, selon la documentation, l'utilisation de ces méthodes par l'utilisateur. doit appeler l'implémentation du super quelque part dans votre implémentation. .

2 votes

C'est vraiment génial ! Je me débattais avec ça depuis au moins un jour. Merci ! !!

0 votes

Je pensais que le cadre d'affichage aurait changé mais c'est le cas jusqu'à ce que viewDidAppear : :( Donc si vous avez besoin du cadre exact après avoir masqué la barre de navigation, ce n'est pas la solution.

0 votes

La barre supérieure de mon deuxième contrôleur de vues est également masquée :(

73voto

Chad M. Points 71

Une autre approche que j'ai trouvée consiste à définir un délégué pour la fonction NavigationController :

navigationController.delegate = self;

et utiliser setNavigationBarHidden en navigationController:willShowViewController:animated:

- (void)navigationController:(UINavigationController *)navigationController 
      willShowViewController:(UIViewController *)viewController 
                    animated:(BOOL)animated 
{   
    // Hide the nav bar if going home.
    BOOL hide = viewController != homeViewController;
    [navigationController setNavigationBarHidden:hide animated:animated];
}

Un moyen facile de personnaliser le comportement pour chaque ViewController tout en un seul endroit.

0 votes

Quand cela sera-t-il appelé ?

2 votes

Une solution parfaite. Cela devrait être la réponse acceptée. Merci !

1 votes

Réponse parfaite. Cela fonctionne également dans le cas où nous ne pouvons pas surcharger les méthodes viewWillAppear et viewWillDisappear sur le premier contrôleur de vue.

19voto

dalewking Points 590

Une légère modification que j'ai dû apporter aux autres réponses consiste à ne démasquer la barre dans viewWillDisappear que si la raison de sa disparition est due à un élément de navigation poussé dessus. En effet, la vue peut disparaître pour d'autres raisons.

Je ne décachette donc la barre que si cette vue n'est plus la vue la plus haute :

- (void) viewWillDisappear:(BOOL)animated
{
    if (self.navigationController.topViewController != self)
    {
        [self.navigationController setNavigationBarHidden:NO animated:animated];
    }

    [super viewWillDisappear:animated];
}

3 votes

+1, vous généralement ne veulent pas afficher la barre de navigation lorsqu'ils poussent un dialogue modal.

18voto

Pablo Santa Cruz Points 73944

Je mettrais le code dans le viewWillAppear sur chaque vue affichée :

Comme ici où vous devez le cacher :

- (void)viewWillAppear:(BOOL)animated
{
        [yourObject hideBar];
}

Comme ici où vous devez le montrer :

- (void)viewWillAppear:(BOOL)animated
{
        [yourObject showBar];
}

0 votes

Lee, si cela a réglé votre problème, marquez la réponse de Pablo comme étant la réponse "solution".

2 votes

Le seul problème est que la barre de navigation apparaît et disparaît lorsque vous passez d'une vue à l'autre. Est-il possible de faire en sorte que la barre de navigation ne soit pas présente sur la première vue, et que la barre de navigation soit présente sur la deuxième vue, sans qu'elle ne saute ?

2 votes

@henning Pour faire glisser la barre de navigation comme vous le souhaitez, vous devez utiliser setNavigationBarHidden:animated :. Voir la réponse d'Alan Rogers ci-dessous (qui devrait vraiment être marquée comme la "solution").

6voto

verma Points 416

Après de multiples essais, voici comment j'ai réussi à obtenir ce que je voulais. Voici ce que j'essayais. - J'ai une vue avec une image, et je voulais que l'image passe en plein écran. - J'ai un contrôleur de navigation avec une barre d'onglets également. J'ai donc besoin de la cacher aussi. - En outre, ma principale exigence n'était pas seulement de cacher, mais d'avoir un effet de fondu pendant l'affichage et le masquage.

Voici comment je l'ai fait fonctionner.

Étape 1 - J'ai une image et l'utilisateur tape une fois sur cette image. Je capture ce geste et le pousse dans le nouveau fichier de l'image. imageViewController il est dans le imageViewController Je veux avoir une image en plein écran.

- (void)handleSingleTap:(UIGestureRecognizer *)gestureRecognizer {  
NSLog(@"Single tap");
ImageViewController *imageViewController =
[[ImageViewController alloc] initWithNibName:@"ImageViewController" bundle:nil];

godImageViewController.imgName  = // pass the image.
godImageViewController.hidesBottomBarWhenPushed=YES;// This is important to note. 

[self.navigationController pushViewController:godImageViewController animated:YES];
// If I remove the line below, then I get this error. [CALayer retain]: message sent to deallocated instance . 
// [godImageViewController release];
} 

Étape 2 - Toutes les étapes ci-dessous sont dans le ImageViewController

Étape 2.1 - Dans ViewDidLoad, afficher la navBar

- (void)viewDidLoad
{
[super viewDidLoad];
// Do any additional setup after loading the view from its nib.
NSLog(@"viewDidLoad");
[[self navigationController] setNavigationBarHidden:NO animated:YES];
}

Étape 2.2 - Dans viewDidAppear J'ai mis en place une tâche de minuterie avec un délai (j'ai mis un délai de 1 seconde). Et après le délai, ajoutez un effet de fondu. J'utilise l'alpha pour utiliser le fondu.

- (void)viewDidAppear:(BOOL)animated
{
NSLog(@"viewDidAppear");

myTimer = [NSTimer scheduledTimerWithTimeInterval:1.0 target:self     selector:@selector(fadeScreen) userInfo:nil repeats:NO];
}

- (void)fadeScreen
{
[UIView beginAnimations:nil context:nil]; // begins animation block
[UIView setAnimationDuration:1.95];        // sets animation duration
self.navigationController.navigationBar.alpha = 0.0;       // Fades the alpha channel of   this view to "0.0" over the animationDuration of "0.75" seconds
[UIView commitAnimations];   // commits the animation block.  This Block is done.
}

étape 2.3 - Sous viewWillAppear ajoutez le geste singleTap à l'image et rendez la barre de navigation translucide.

- (void) viewWillAppear:(BOOL)animated
{

NSLog(@"viewWillAppear");

NSString *path = [[NSBundle mainBundle] pathForResource:self.imgName ofType:@"png"];

UIImage *theImage = [UIImage imageWithContentsOfFile:path];

self.imgView.image = theImage;

// add tap gestures 
UITapGestureRecognizer *singleTap = [[UITapGestureRecognizer alloc] initWithTarget:self action:@selector(handleTap:)];  
[self.imgView addGestureRecognizer:singleTap];  
[singleTap release];  

// to make the image go full screen
self.navigationController.navigationBar.translucent=YES;
}

- (void)handleTap:(UIGestureRecognizer *)gestureRecognizer 
{ 
 NSLog(@"Handle Single tap");
 [self finishedFading];
  // fade again. You can choose to skip this can add a bool, if you want to fade again when user taps again. 
 myTimer = [NSTimer scheduledTimerWithTimeInterval:5.0 target:self  selector:@selector(fadeScreen) userInfo:nil repeats:NO];
 }

Étape 3 - Enfin dans viewWillDisappear assure-toi de remettre toutes les choses en place

- (void)viewWillDisappear: (BOOL)animated 
{ 
self.hidesBottomBarWhenPushed = NO; 
self.navigationController.navigationBar.translucent=NO;

if (self.navigationController.topViewController != self)
{
    [self.navigationController setNavigationBarHidden:NO animated:animated];
}

[super viewWillDisappear:animated];
}

Prograide.com

Prograide est une communauté de développeurs qui cherche à élargir la connaissance de la programmation au-delà de l'anglais.
Pour cela nous avons les plus grands doutes résolus en français et vous pouvez aussi poser vos propres questions ou résoudre celles des autres.

Powered by:

X