2015-07-30 11 views
8

Quando la mia app si avvia per la prima volta, devo caricare alcuni dati salvati in precedenza. Se esiste -> quindi vai alla pagina TabbedPage. Altrimenti, una pagina di accesso.Come posso chiamare questo metodo asincrono nei miei moduli Xamarin all'avvio della mia app?

Non sono sicuro di come posso chiamare il mio metodo asincrono nel supervisore dell'app o anche in un altro metodo?

Come posso fare questo?

Ecco il mio codice ..

namespace Foo 
{ 
    public class App : Application 
    { 
     public App() 
     { 
      Page page; 

      LoadStorageDataAsync(); // TODO: HALP! 

      if (Account != null) 
      { 
       // Lets show the dashboard. 
       page = new DashboardPage(); 
      } 
      else 
      { 
       // We need to login to figure out who we are. 
       page = CreateAuthenticationPage(); 
      } 

      MainPage = page; 
     } 

    ... snip ... 
} 

Allora, perché è LoadStorageDataAsync asincrona? Perché è using the library PCLStorage e questo è tutto asincrono.

Qualcuno può aiutare, per favore?

risposta

10

As far as the docs say, si ha l'evento Application.OnStart che è possibile ignorare:

Gli sviluppatori di applicazioni sovrascrivere questo metodo per eseguire azioni quando si avvia l'applicazione .

È possibile eseguire il metodo async là dove si può effettivamente essere atteso:

public override async void OnStart() 
{ 
    await LoadStorageDataAsync(); 
} 
1

Costruttori non può essere async, ma i gestori di eventi può essere. Se è possibile si dovrebbe spostare la logica che al gestore OnStart evento (o uno più appropriato):

public override async void OnStart (EventArgs e) 
{ 
    // stuff 
    await LoadStorageDataAsync(); 
    // stuff 
} 

Se non può, voi non avere una migliore scelta che semplicemente bloccando in modo sincrono su quel compito di ottieni il risultato Dovresti essere consapevole che ciò può portare a deadlock.

+0

Se hai notato, sto ereditando da 'Applicazione'. Non esiste alcun override 'Async void OnStart (...)'? –

+1

Ahh -> è 'public override async void OnStart()' –

+0

@ Pure.Krome Cerco di non includere i modificatori perché non sono realmente correlati alla maggior parte delle risposte. Modificatori – i3arnon

5

Fai un passo indietro e pensa a come funziona l'interfaccia utente. Quando la tua app viene inizialmente visualizzata, il framework costruisce ViewModel e View, quindi mostra qualcosa immediatamente (il prima possibile). Questo è un luogo inappropriato per l'attività di rete.

Invece, quello che dovresti fare è avviare l'operazione asincrona e poi (in modo sincrono) caricare e mostrare una pagina di "caricamento". Al termine dell'operazione asincrona, è possibile passare alle altre pagine (o ad una pagina di "errore" se, ad esempio, l'utente non ha accesso alla rete).

Non sono sicuro che Xamarin Forms sia in grado di eseguire il binding dei dati su un oggetto di pagina, ma se lo è, il mio NotifyTaskCompletion type potrebbe essere utile.

0

L'utilizzo di metodi asincroni in un costruttore è considerato un codice errato. Non si dovrebbero usare metodi asincroni nei costruttori di classi.

Si potrebbe provare a cambiare per evitare situazioni di stallo:

Func<Task> task = async() => { 
    await YourCustomMethodAsync().ConfigureAwait(false); 
}; 
task().Wait(); 

... ma io non lo consiglio.

Problemi correlati