69 votes

"Appels non équilibrés pour commencer / terminer les transitions d'apparence pour DetailViewController" lors de l'application de plusieurs contrôleurs de vue de détail

J'ai une vue contrôleur qui contient une vue de la table, les éléments du tableau peuvent être sélectionnées et une vue de détail contrôleur dûment créé.

Les éléments dans le tableau représentent les éléments qui peuvent avoir une base de temps de déclenchement associé avec eux et un local de notification est prévue pour chaque élément, si l'application est au premier plan lorsqu'une notification locale expire alors la vue de détail de l'élément est automatiquement affiché.

J'ai un problème qui se manifeste lorsque deux notifications expirent en même temps qui résultats dans les points de vue ne s'affichent pas correctement, et en plus les journaux de la console: "Déséquilibré appels de début/fin de l'apparence de transitions pour NNN" où NNN est mon détail-vue-contrôleur.

La table view controller) est créé comme suit:

 self.tableViewController = [[TableViewController alloc] initWithNibName:@"TableView" bundle:nil];
 UINavigationController *navController = [[UINavigationController alloc] initWithRootViewController:self.tableViewController];
 self.window.rootViewController = navController;

Lorsqu'une notification locale expire et didReceiveLocalNotification: est appelée l'application diffuse une notification à l'aide de NSNotifcationCenter postNotificationName: et pour lequel la table view controller est à l'écoute pour. Lors de la table-vue-contrôleur reçoit cette notification, il crée la vue de détail de contrôleur et il pousse à la pile:

[self.navigationController pushViewController:detailViewController animated:YES]; 

J'ai lu quelque part qu'il pourrait y avoir un problème si un view controller pousse un autre point de vue contrôleur quand il n'est pas sur le haut de la pile - j'ai donc pensé que ce doit être le problème, parce que lors de l'affichage de la table contrôleur reçoit le 2ème notification de ne plus être sur le dessus de la pile de navigation, car il aura déjà tout juste poussé une vue de détail du contrôleur sur la pile lors de la première notification d'arrivée.

J'ai donc changé le pousser code:

[[self.navigationController topViewController].navigationController pushViewController:detailController animated:YES];

Mais il ne fait aucune différence.

Donc ensuite, j'ai pensé qu'il pourrait y avoir un problème car le premier détail-vue-contrôleur n'a pas la chance d'afficher entièrement avant la 2e - vue-contrôleur a été poussé - et j'ai donc changé de notification de l'application affichage de l'aide:

[[NSNotificationCenter defaultCenter] postNotificationName: 

pour

[[NSNotificationQueue defaultQueue] enqueueNotification: postingStyle:NSPostWhenIdle]

De sorte que la pousse ne pas se produire dans le même iteraction de l'application de la boucle. Mais cela ne fait pas de différence, ni ne tente d'introduire un retard à la poussée de la vue de détail controlle:

double delayInSeconds = 0.1;
dispatch_time_t popTime = dispatch_time(DISPATCH_TIME_NOW, (int64_t)(delayInSeconds * NSEC_PER_SEC));
dispatch_after(popTime, dispatch_get_main_queue(), ^(void){
    [[self.navigationController topViewController].navigationController     pushViewController:detailController animated:YES]; 
});

Je n'ai aucune idée de ce que le problème est ou de ce à essayer ensuite, des idées?

126voto

railwayparade Points 3448

"Le déséquilibre des appels de début/fin de l'apparence de transitions"

se produit lorsque vous essayez d'afficher une nouvelle viewcontroller avant le point de vue actuel contrôleur est fini de l'affichage. Vous pouvez le reproduire en naviguant dans viewWillAppear.

Fondamentalement, vous êtes en essayant de repousser les deux contrôleurs sur la pile à peu près le même temps. Vous suggérons de maintenir une file d'attente dans la tableview contrôleur qui tient à jour une liste des vues de détail qui ont besoin de l'affichage. Pousser un à un sur la pile et vérifier à la sortie de l'actuel de la vue de détail s'il existe des mises en file d'attente des vues de détail qui ont besoin de l'affichage.

Ce type de navigation va être source de confusion pour l'utilisateur. Il peut être préférable d'envisager de faire votre vue de détail en charge plusieurs éléments.

12voto

infiniteLoop Points 333

'Appels non équilibrés pour commencer / terminer les transitions d'apparence'

Dit qu'une animation est démarrée avant que la dernière animation associée ne soit pas terminée. Alors, ouvrez-vous un contrôleur de vue avant d’appuyer sur le nouveau? Ou peut être popping à la racine? Si oui, essayez de le faire sans animation. c'est à dire,

 [self.navigationController popToRootViewControllerAnimated:NO];
 

Et voir si cela résout le problème, Dans mon cas, cela a fait l'affaire.

7voto

Gabriel Points 195

"Le déséquilibre des appels de début/fin de l'apparence de transitions" erreur se produit lorsque vous essayez d'afficher une nouvelle viewcontroller avant le point de vue actuel contrôleur est fini de l'affichage.

Donc, vous devez être sûr que vous avez l'habitude de présenter un nouveau VC jusqu'à la première des finitions de ses animations.

Utilisation didShowViewController et willShowViewController pour bloquer la présentation d'un nouveau VC avant de l'ancien termine son animation. C'est pour backButtonAction qui fait un popViewController avec Animation: OUI.

- (void)navigationController:(UINavigationController *)navigationController didShowViewController:(UIViewController *)viewController animated:(BOOL)animated
{
    [self.myNavView.backButton addTarget:self action:@selector(backButtonAction) forControlEvents:UIControlEventTouchUpInside];
}

- (void)navigationController:(UINavigationController *)navigationController willShowViewController:(UIViewController *)viewController animated:(BOOL)animated
{
    [self.myNavView.backButton removeTarget:self action:@selector(backButtonAction) forControlEvents:UIControlEventTouchUpInside];
}

3voto

user1647700 Points 76

Cela peut également arriver lorsque vous essayez d'extraire un VC de la pile plusieurs fois. Sur mon cas, la méthode qui a sauté le VC a été appelée à plusieurs reprises par erreur. Une fois que j'ai nettoyé cela, le problème a disparu.

1voto

ymutlu Points 1923

En fait, vous devez attendre la fin de l'animation push. Ainsi, vous pouvez déléguer UINavigationController et empêcher de pousser jusqu’à la fin de l’animation.

 - (void)navigationController:(UINavigationController *)navigationController didShowViewController:(UIViewController *)viewController animated:(BOOL)animated{
    waitNavigation = NO;
}


-(void)showGScreen:(id)gvc{

    if (!waitNavigation) {
        waitNavigation = YES;
        [_nav popToRootViewControllerAnimated:NO];
        [_nav pushViewController:gvc animated:YES];
    }
}
 

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