2010-08-22 4 views
1

J'ai un problème étrange avec le UINavigationController. J'ai écrit une application pour afficher les données dans trois niveaux. (RootView: Sélectionnez Données I, Deuxième vue: Sélectionnez Données II, Troisième vue: Données d'affichage). Cela fonctionne très bien, pas de problèmes.UINavigationController plantant une application lors de l'utilisation de setViewControllers

Le problème apparaît quand un PushMessage arrive: Dans ce cas, je suis en train de créer une pile viewController manuellement, en utilisant la méthode setViewControllers: animation: du UINavigationController:

J'initialisant les trois contrôleurs de vue (avec Data, title, etc) et en les ajoutant à un tableau. Ce tableau est passé à la méthode mentionnée (setViewCOntrollers), et la vue du ViewController supérieur est affichée correctement. Mais lorsqu'un utilisateur touche le bouton Précédent en haut à gauche, l'application plante. Le titre de ce bouton est le titre du ViewController précédent dans la pile, donc la pile semble être correcte. Cette erreur se produit uniquement si la vue de rootViewController est affichée lors de la réception de la notification push (ce qui signifie l'appel de la méthode setViewControllers).

Mon code:

EMASubstituteTeacherScheduleAppDelegate *appDelegate = [[UIApplication sharedApplication] delegate]; 
UINavigationController *navController = [appDelegate viewController]; 

MainViewController *main = [[MainViewController alloc] initWithNibName: @"MainViewController" bundle: nil]; 
main.navigationItem.title = @"Test"; 

FormViewController *formSelect = [[FormViewController alloc] initWithNibName: @"FormViewController" bundle: nil]; 
formSelect.navigationItem.title = @"Test (Level 2)"; 
formSelect.substDate = [pushData objectForKey: @"date"]; 

SubstitutesViewController *substDisplay = [[SubstitutesViewController alloc] initWithNibName: @"SubstitutesViewController" bundle: nil]; 
substDisplay.navigationItem.title = @"Test (Top)"; 
substDisplay.substDate = [pushData objectForKey: @"date"]; 
substDisplay.substForm = [pushData objectForKey: @"form"]; 

NSArray *controllers = [[NSArray alloc] initWithObjects: main, formSelect, substDisplay, nil]; 
[navController setViewControllers: controllers animated:YES]; 

Le message présenté à la console: Programme signal reçu: « EXC_BAD_ACCESS ».

Stack Appel:

'#0 0x3433886c in objc_msgSend' 
'#1 0x3061a828 in -[UIApplication sendAction:to:from:forEvent:] 
'#2 0x3061a7c8 in -[UIApplication sendAction:toTarget:fromSender:forEvent:] 
'#3 0x3061a79a in -[UIControl sendAction:to:forEvent:] 
'#4 0x3061a4ec in -[UIControl(Internal) _sendActionsForEvents:withEvent:] 
'#5 0x3061ab3a in -[UIControl touchesEnded:withEvent:] 
'#6 0x306194ec in -[UIWindow _sendTouchesForEvent:] 
'#7 0x30618e66 in -[UIWindow sendEvent:] 
'#8 0x30614b5a in -[UIApplication sendEvent:] 
'#9 0x30614506 in _UIApplicationHandleEvent 
'#10 0x3323a146 in PurpleEventCallback 
'#11 0x3293daaa in __CFRUNLOOP_IS_CALLING_OUT_TO_A_SOURCE1_PERFORM_FUNCTION__ 
'#12 0x3293f84e in __CFRunLoopDoSource1 
'#13 0x3294062c in __CFRunLoopRun 
'#14 0x328e98ea in CFRunLoopRunSpecific 
'#15 0x328e97f2 in CFRunLoopRunInMode 
'#16 0x332396ee in GSEventRunModal 
'#17 0x3323979a in GSEventRun 
'#18 0x305be2a6 in -[UIApplication _run] 
'#19 0x305bce16 in UIApplicationMain 
'#20 0x00002512 in main at main.m:14 

Merci à l'avance!

Répondre

0

Je suppose que vous faites vos mises à jour de l'interface utilisateur dans le fil principal.

Une fois j'ai eu un plantage sur la navigation lorsque j'ai essayé de mettre un contrôleur de vue d'une pile de navigation à une autre pile de navigation. Il semble que le contrôleur de vue, que j'essaye de définir à une autre une pile de navigation, ne peut pas actuellement avoir de parent.

Votre contrôleur MainViewController est-il le rootViewController de navigationController lorsque la notification push arrive? Si tel est le cas, l'infrastructure risque de ne pas l'aimer lorsque vous essayez de placer MainViewController dans la pile de navigation manuellement. Vous devrez peut-être d'abord supprimer le module mainViewController de la pile de navigation avant de le placer dans le tableau pour définir viewControllers. Une solution de contournement serait d'avoir un viewController fictif comme rootViewController afin que vous puissiez facilement supprimer votre ViewController racine de la pile en utilisant popToRootViewController avant d'utiliser viewController sur une nouvelle pile de navigation.

C'est une pensée qui vient à moi de votre question. Votre cas pourrait être ou ne pas être le même que ce que j'ai rencontré.

0

ont le même problème, résolu avec ceci:

@interface MyNavController() 

@property (nonatomic, strong) NSDate* setVCDate; 

@end 

- (void)setViewControllers:(NSArray *)viewControllers animated:(BOOL)animated 
{ 
    if (self.setVCDate == nil || [[NSDate date] timeIntervalSinceDate:self.setVCDate] > 1.0) { 
     [super setViewControllers:viewControllers animated:animated]; 
     self.setVCDate = [NSDate date]; 
    } else { 
     DLog(@" ***** [UINavigationController setViewControllers:animated: called too fast, ignoring until Apple will fix their s###"); 
    } 
} 
Questions connexes