2013-08-28 9 views
5

Quando chiamo dismissViewControllerAnimated:completion: per respingere un UIViewController blocco completamento viene mai eseguito quando la vista corrispondente è nel mezzo di essere animata sullo schermo (usando presentViewController:animated:completion:).dismissViewControllerAnimated: completamento: senza eseguito

Il UIViewController non scompare nemmeno. È come se dismissViewControllerAnimated:completion: fosse ignorato.

Il seguente codice è un esempio di codice semplificato perché l'originale è molto più grande. Il codice che ho indicato di seguito simula un caso d'uso in cui un errore di comunicazione di rete potrebbe innescare fine di popup mentre un altro punto di vista è inoltre in fase di spuntato-up allo stesso tempo ..

Codice esempio:

NSLog(@"Presenting view"); 

[self presentViewController:changeLocationViewController animated:YES completion:^{ 
    NSLog(@"View done presenting"); 
}]; 

NSLog(@"Dismissing view"); 

[self dismissViewControllerAnimated:NO completion:^{ 
    NSLog(@"View done dismissing"); 
}]; 

uscita log è:

2013-08-28 16: 14: 12.162 [1708 c07] Presentare vista
2013/08/28 16: 14: 12,178 [1708 c07] vista Allontanando
2013 -08-28 16: 14: 12,583 [1708: c07] Visualizza done presenti ng


Qualcuno sa come respingere il UIViewController in queste circostanze?

Grazie in anticipo.

+0

Che tipo di 'UIViewController' è? L'hai sottoclassata da solo o è una terza parte? –

+0

È un UIViewController sottoclusterato. Ma niente di straordinario. Mostra solo del testo e un pulsante – MhaW

+2

mostra un po 'di codice! –

risposta

4

Il motivo per cui questo snippet di codice non funziona è perché il blocco di completamento in questi metodi viene eseguito in un secondo momento dopo che le animazioni sono state completate. Puoi vedere questo nei tuoi registri: "Eliminare la vista" prima di "Visualizza fatto presentando". Prova a modificare:

NSLog(@"Presenting view"); 

[self presentViewController:changeLocationViewController animated:YES completion:^{ 
    NSLog(@"View done presenting"); 
    NSLog(@"Dismissing view"); 

    [self dismissViewControllerAnimated:NO completion:^{ 
     NSLog(@"View done dismissing"); 
    }]; 
}]; 

EDIT:

Se è necessario assicurarsi che la vista è respinto quando l'errore di rete si verifica, provare a impostare una variabile di istanza booleano chiamato networkErrorFound.

Al termine della connessione di rete, impostare su YES se si verifica un errore. Quindi utilizzare questo codice:

[self presentViewController:changeLocationViewController animated:YES completion:^{ 
    NSLog(@"View done presenting"); 
    NSLog(@"Dismissing view"); 

    if (self.networkErrorFound) { 
     [self dismissViewControllerAnimated:NO completion:^{ 
      NSLog(@"View done dismissing"); 
     }]; 
    } 
}]; 

In questo modo, attenderà fino a quando non si presenta presentando di respingere. Dovresti anche gestire il caso in cui l'errore si verifica dopo che l'animazione è stata eseguita (ad esempio, una connessione lenta che alla fine non riesce), ma questo è al di fuori dello scopo di questa domanda.

+1

+1. Ma perché sta cercando di presentare e licenziare uno dopo l'altro ??? Sta cercando di infiammare le persone con il suo VC? Posso immaginare una causa sul modo in cui si sostiene che la sua app causa attacchi epilettici :) – CaptJak

+0

Ma, quando metto uno stop tra le due chiamate (bloccando così l'UIThread), anche il blocco di completamento di 'presentViewControllerAnimated: completion:' non viene chiamato. Quindi stavo pensando che il completamento fosse effettivamente eseguito su UIThread ..? – MhaW

+0

@CaptJak haha, si. – aopsfan

0

Perché non lo si spegne quando viene caricato?

[self presentViewController:changeLocationViewController animated:YES completion:^{ 
    NSLog(@"View done presenting"); 

    NSLog(@"Dismissing view"); 

    [self dismissViewControllerAnimated:NO completion:^{ 
     NSLog(@"View done dismissing"); 
    }]; 
}]; 
+1

bwahaha Ti ho battuto di 7 secondi :-) – aopsfan

0

OK. Sembra che tu voglia presentare un VC, ma se non è stata trovata alcuna rete, chiudi il VC. L'unica ragione per cui posso pensare di doverlo fare in questo modo è se la rete viene controllata solo nel nuovo VC che stai presentando (e vuoi eliminare se non riesce a connettersi).

E si sarebbe in grado di farlo implementando il codice mostrato nella risposta fornita da @aopsfan.

Ma pensate a quel flusso dell'interfaccia utente. Stai dicendo a un uomo affamato (l'utente) che può avere un sandwich (il prossimo VC che vuole vedere) ... Ma ASPETTA! (licenzia il VC desiderato) No, non puoi avere il sandwich (nessuna rete)! Ti ha imbrogliato !.

Il modo per mantenere il flusso dell'interfaccia utente piacevole e non aggravante, sarebbe quello di verificare la connessione di rete prima di presentare il VC. Probabilmente controllate la presenza della rete nell'IBAction (?) Che utilizzate per presentare il nuovo VC. In questo modo, puoi controllare prima di presentare. Invece di annullare il presente

Heck, potresti persino mostrare un HUD "in corso" Visualizza per far sapere all'utente cosa sta succedendo!

+0

La connessione di rete è globalmente nell'app.Se la connessione di rete viene persa, indipendentemente da dove si trova l'utente nell'applicazione, l'applicazione chiude qualsiasi cosa l'utente stia facendo e mostra una vista di "rete persa" – MhaW

+0

@MhaW, non fa alcuna differenza. Dovresti comunque controllarlo ** prima ** presentando il prossimo VC. – CaptJak

+0

Hmm, non sono d'accordo. Ho una classe che gestisce la roba di rete, con watchdog e tutto, soprattutto per non dover controllare la connessione di rete ovunque .. Ma questo è un altro argomento, haha! :) Ma grazie per i vostri pensieri e tempo! :) – MhaW

-2

provare avvolgere la funzione con UIView animation.like:

[UIView animateWithDuration:0.f 
        animations:^{ 
         [self.presentedViewController dismissViewControllerAnimated:NO completion:^{ 

         }]; 
        } completion:^(BOOL finished) { 

         [self presentViewController:controller animated:YES completion:nil]; 
        }]; 
Problemi correlati