Ciclo di vita app Universal Windows Platform (UWP)

In questo argomento viene descritto il ciclo di vita di un'applicazione UWP (Universal Windows Platform) dal momento in cui viene attivata fino alla chiusura.

Una storia breve

Prima di Windows 8, le app avevano un ciclo di vita semplice. Le app Win32 e .NET sono in esecuzione o non sono in esecuzione. Quando un utente le riduce al minimo o si allontana da esse, continuano a essere eseguite. Questo andava bene fino a quando i dispositivi portatili e il risparmio energetico hanno acquisito sempre più importanza.

Windows 8 ha introdotto un nuovo modello di applicazione con le app UWP. A livello generale è stato aggiunto un nuovo stato sospeso. Un'app UWP viene sospesa poco dopo che l'utente la riduce a icona o passa a un'altra app. Ciò significa che i thread dell'app vengono arrestati e l'app viene lasciata in memoria, a meno che il sistema operativo non debba recuperare le risorse. Quando l'utente torna all'app, può essere ripristinata rapidamente in uno stato di esecuzione.

Esistono vari modi per cui le app che devono continuare a funzionare quando sono in background, ad esempio, la funzionalità attività in background, esecuzione estesa ed esecuzione sponsorizzata dell'attività (ad esempio BackgroundMediaEnabled che consente a un'app di continuare a riprodurre elementi multimediali in background). Inoltre, le operazioni di trasferimento in background possono continuare anche se l'app viene sospesa o terminata. Per altre info, vedere Come scaricare un file.

Per impostazione predefinita, le app che non sono in primo piano vengono sospese. Ciò comporta un risparmio energetico e più risorse disponibili per l'app attualmente in primo piano.

Lo stato sospeso aggiunge nuovi requisiti per l'utente come sviluppatore perché il sistema operativo può scegliere di terminare un'app sospesa per liberare risorse. L'app terminata verrà comunque visualizzata nella barra delle applicazioni. Quando l'utente fa clic su di esso, l'app deve ripristinare lo stato in cui si trovava prima che fosse terminata perché l'utente non sarà a conoscenza del fatto che il sistema ha chiuso l'app. Penserà che sia rimasta in attesa in background mentre stava facendo altro e si aspetterà che sia nello stesso stato in cui si trovava quando l'ha lasciata. In questo argomento verrà illustrato come eseguire questa operazione.

Windows 10, versione 1607, ha introdotto altri due stati del modello di app: In esecuzione in primo piano e In esecuzione in background. Questi stati aggiuntivi verranno esaminati nelle sezioni seguenti.

Stato di esecuzione dell'app

Questa illustrazione rappresenta i possibili stati del modello di app a partire da Windows 10 versione 1607. Esaminiamo il ciclo di vita tipico di un'app UWP.

state diagram showing transitions between app execution states

Le app immettono lo stato in esecuzione in background quando vengono avviate o attivate. Se l'app deve essere spostata in primo piano a causa di un avvio dell'app in primo piano, l'app ottiene l'evento LeavingBackground.

Anche se "avvio" e "attivazione" possono sembrare termini simili, fanno riferimento a modi diversi in cui il sistema operativo può avviare l'app. Esaminiamo prima di tutto l'avvio di un'app.

Avvio delle app

Il metodo OnLaunched viene chiamato all'avvio di un'app. Viene passato un parametro LaunchActivatedEventArgs che fornisce, tra le altre cose, gli argomenti passati all'app, l'identificatore del riquadro che ha avviato l'app e lo stato precedente in cui si trovava l'app.

Ottenere lo stato precedente dell'app da LaunchActivatedEventArgs.PreviousExecutionState che restituisce un oggetto ApplicationExecutionState. I valori e l'azione appropriata da intraprendere a causa di tale stato sono i seguenti:

ApplicationExecutionState Spiegazione Azione da eseguire
Non in esecuzione Un'app potrebbe trovarsi in questo stato perché non è stata avviata dall'ultima volta che l'utente ha riavviato o eseguito l'accesso. Può anche essere in questo stato se era in esecuzione ma poi si è arrestata in modo anomalo o perché l'utente l'ha chiusa in precedenza. Inizializzare l'app come se fosse in esecuzione per la prima volta nella sessione utente corrente.
Sospesa L'utente ha ridotto a icona o è uscito dall'app e non vi è più tornato entro pochi secondi. Quando l'app è stata sospesa, il relativo stato è rimasto in memoria. È sufficiente riacquisire eventuali handle di file o altre risorse rilasciate quando l'app è stata sospesa.
Terminato L'app è stata sospesa in precedenza, ma è stata arrestata a un certo punto perché il sistema doveva recuperare memoria. Ripristina lo stato in cui si trovava l'app quando l'utente si è staccato.
ClosedByUser L'utente ha chiuso l'app con il pulsante di chiusura del sistema o con ALT+F4. Quando l'utente chiude l'app, viene prima sospesa e quindi terminata. Poiché l'app ha essenzialmente seguito gli stessi passaggi che portano allo stato Terminato, gestiscilo come faresti per lo stato Terminato.
In esecuzione L'app era già aperta quando l'utente ha tentato di avviarla di nuovo. Nessuna operazione. Si noti che non viene avviata un'altra istanza dell'app. L'istanza già in esecuzione viene semplicemente attivata.

Nota

La sessione utente corrente è basata sull'accesso a Windows. Finché l'utente corrente non si è disconnesso, non ha arrestato o riavviato Windows, la sessione utente corrente persiste attraverso eventi come l'autenticazione della schermata di blocco, il cambio utente e così via.

Una circostanza importante da tenere presente è che se il dispositivo dispone di risorse sufficienti, il sistema operativo preavvierà le app usate di frequente che hanno optato per tale comportamento per ottimizzare la velocità di risposta. Le app preavviate vengono avviate in background e quindi sospese rapidamente in modo che quando l'utente passa ad esse, possano essere riprese, il che è più veloce dell'avvio dell'app.

A causa del preavvio, il metodo OnLaunched() può essere avviato dal sistema anziché dall'utente. Poiché l'app è preavviata in background, potrebbe essere necessario eseguire un'azione diversa in OnLaunched(). Ad esempio, se l'app inizia a riprodurre musica all'avvio, non saprà da dove proviene perché l'app è preavviata in background. Dopo aver preavviato l'app in background, viene seguita da una chiamata a Application.Suspending. Quindi, quando l'utente avvia l'app, viene richiamato l'evento di ripresa, nonché il metodo OnLaunched().. Vedere Gestire il preavvio dell'app per altre informazioni su come gestire lo scenario di preavvio. Vengono preavviate solo le app che acconsentono esplicitamente.

Solo le app che accettano l'attivazione vengono preavviate. Per configurare la schermata iniziale, vedere Aggiunta di una schermata iniziale.

Mentre viene visualizzata la schermata iniziale, l'app deve registrare i gestori eventi e configurare qualsiasi interfaccia utente personalizzata necessaria per la pagina iniziale. Si noti che queste attività in esecuzione nel costruttore dell'applicazione e OnLaunched() vengono completate entro pochi secondi o il sistema potrebbe pensare che l'app non risponde e la termina. Se un'app deve richiedere dati dalla rete o deve recuperare grandi quantità di dati dal disco, queste attività devono essere completate al di fuori dell'avvio. Un'app può usare un'interfaccia utente di caricamento personalizzata o una schermata iniziale estesa mentre attende il completamento delle operazioni a esecuzione prolungata. Per altre informazioni, vedere Visualizzare una schermata iniziale per più tempo e l'esempio della schermata iniziale.

Al termine dell'avvio dell'app, entra nello stato In esecuzione e la schermata iniziale scompare e tutte le risorse e gli oggetti della schermata iniziale vengono cancellati.

Attivazione dell'app

A differenza dell'avvio da parte dell'utente, un'app può essere attivata dal sistema. Un'app può essere attivata da un contratto, ad esempio il contratto di condivisione. Oppure può essere attivata per gestire un protocollo URI personalizzato o un file con un'estensione per la quale la tua app è registrata. Per un elenco dei modi in cui l'app può essere attivata, vedere ActivationKind.

La classe Windows.UI.Xaml.Application definisce i metodi di cui puoi eseguire l'override per gestire i vari modi in cui l'app può essere attivata. OnActivated può gestire tutti i possibili tipi di attivazione. Tuttavia, è più comune usare metodi specifici per gestire i tipi di attivazione più comuni e usare OnActivated come metodo di fallback per i tipi di attivazione meno comuni. Questi sono i metodi aggiuntivi per attivazioni specifiche:

OnCachedFileUpdaterActivated
OnFileActivated
OnFileOpenPickerActivatedOnFileSavePickerActivated
OnSearchActivated
OnShareTargetActivated

I dati dell'evento per questi metodi includono la stessa proprietà PreviousExecutionState illustrata in precedenza, che indica lo stato in cui si trovava l'app prima dell'attivazione. Interpretare lo stato e le operazioni da eseguire nello stesso modo descritto in precedenza nella sezione Avvio dell'app.

Nota Se accedi usando l'account Amministratore del computer, non puoi attivare le app UWP.

In esecuzione in background.

A partire da Windows 10 versione 1607, le app possono eseguire attività in background nello stesso processo dell'app. Per altre informazioni, vedere Attività in background con il modello a processo singolo. In questo articolo non approfondiremo l'elaborazione in background in corso, ma il modo in cui ciò influisce sul ciclo di vita dell'app consiste nel fatto che sono stati aggiunti due nuovi eventi relativi al momento in cui l'app è in background. Si tratta di: EnteredBackground e LeavingBackground.

Questi eventi riflettono anche se l'utente può visualizzare l'interfaccia utente dell'app.

L'esecuzione in background è lo stato predefinito in cui viene avviata, attivata o ripresa un'applicazione. In questo stato l'interfaccia utente dell'applicazione non è ancora visibile.

Esecuzione in primo piano

L'esecuzione in primo piano indica che l'interfaccia utente dell'app è visibile.

L'evento LeavingBackground viene generato subito prima che l'interfaccia utente dell'applicazione sia visibile e prima di immettere lo stato in esecuzione in primo piano. Viene generato anche quando l'utente torna all'app.

In precedenza, la posizione migliore per caricare gli asset dell'interfaccia utente era nei gestori eventi Activated o Resuming. Ora LeavingBackground è la posizione migliore per verificare che l'interfaccia utente sia pronta.

È importante verificare che gli asset visivi siano pronti per questa volta perché questa è l'ultima opportunità di lavorare prima che l'applicazione sia visibile all'utente. Tutto il lavoro dell'interfaccia utente in questo gestore eventi deve essere completato rapidamente, in quanto influisce sull'avvio e sul tempo di ripresa dell'esperienza utente. LeavingBackground è il tempo necessario per assicurarsi che il primo fotogramma dell'interfaccia utente sia pronto. L'archiviazione a esecuzione prolungata o le chiamate di rete devono quindi essere gestite in modo asincrono in modo che il gestore eventi possa restituire.

Quando l'utente passa dall'applicazione, l'app torna allo stato in esecuzione in background.

Reinserire lo stato dello sfondo

L'evento EnteredBackground indica che l'app non è più visibile in primo piano. Sul desktop EnteredBackground viene attivato quando l'app è ridotta a icona; al telefono, quando si passa alla schermata iniziale o a un'altra app.

Ridurre l'utilizzo della memoria dell'app

Poiché l'app non è più visibile all'utente, questa è la posizione migliore per arrestare il lavoro e le animazioni per il rendering dell'interfaccia utente. È possibile usare LeavingBackground per ricominciare a funzionare.

Se hai intenzione di lavorare in background, questo è il posto giusto per prepararti. È consigliabile controllare MemoryManager.AppMemoryUsageLevel e, se necessario, ridurre la quantità di memoria usata dall'app quando è in esecuzione in background in modo che l'app non rischi di essere terminata dal sistema per liberare risorse.

Per altri dettagli, vedere Ridurre l'utilizzo della memoria quando l'app passa allo stato in background.

Salva il tuo stato

Il gestore eventi di sospensione è la posizione migliore per salvare lo stato dell'app. Tuttavia, se si lavora in background (ad esempio, la riproduzione audio, usando una sessione di esecuzione estesa o un'attività in background in-proc), è anche consigliabile salvare i dati in modo asincrono dal gestore eventi EnteredBackground. Ciò è dovuto al fatto che è possibile che l'app venga terminata mentre si trova a una priorità inferiore in background. E poiché l'app non avrà superato lo stato sospeso in questo caso, i dati andranno persi.

Il salvataggio dei dati nel gestore eventi EnteredBackground, prima dell'inizio dell'attività in background, garantisce un'esperienza utente ottimale quando l'utente riporta l'app in primo piano. È possibile usare le API dati dell'applicazione per salvare dati e impostazioni. Per altre info, vedere Archiviare e recuperare le impostazioni e altri dati dell'app.

Dopo aver salvato i dati, se hai superato il limite di utilizzo della memoria, puoi liberare i dati dalla memoria poiché potrai ricaricarli in seguito. In questo modo verrà liberata la memoria che può essere usata dagli asset necessari per l'attività in background.

Tieni presente che se la tua app ha un'attività in background in corso, può passare dallo stato di esecuzione in background allo stato di esecuzione in primo piano senza mai raggiungere lo stato sospeso.

Nota

Quando l'app viene chiusa dall'utente, è possibile che l'evento OnSuspending venga generato prima dell'evento EnteredBackground. In alcuni casi, l'evento EnteredBackground potrebbe non essere attivato prima che l'app venga terminata. È importante salvare i dati nel gestore eventi OnSuspending.

Lavoro asincrono e differimenti

Se si effettua una chiamata asincrona all'interno del gestore, il controllo ritorna immediatamente da tale chiamata asincrona. Ciò significa che l'esecuzione può quindi far restituire dal gestore eventi e l'app passerà allo stato successivo anche se la chiamata asincrona non è ancora stata completata. Utilizzare il metodo GetDeferral sull'oggetto EnteredBackgroundEventArgs che è passato all'handler dell'evento per ritardare la sospensione fino a dopo il richiamo del metodo Complete sull'oggetto Windows.Foundation.Deferral restituito.

Un differimento non aumenta la quantità di tempo necessario per eseguire il codice prima che l'app venga terminata. Ritarda solo la terminazione fino a quando non viene chiamato il metodo Complete, o la deadline è superata-quale dei due eventi si verifica prima.

Se hai bisogno di più tempo per salvare il tuo stato, esamina i modi per salvare il tuo stato in più fasi prima che l'app entri nello stato in background in modo che ci sia meno da salvare nel gestore eventi OnSuspending. In alternativa, è possibile richiedere una ExtendedExecutionSession per ottenere più tempo. Non c'è garanzia che la richiesta verrà concessa, tuttavia, quindi è consigliabile trovare modi per ridurre al minimo la quantità di tempo necessario per salvare lo stato.

Sospensione dell'app

Quando l'utente riduce a icona un'app, Windows attende alcuni secondi per vedere se l'utente tornerà ad essa. Se non torna entro questo intervallo di tempo e non è attiva alcuna esecuzione estesa, attività in background o esecuzione sponsorizzata dall'attività, Windows sospende l'app. Un'app viene sospesa anche quando viene visualizzata la schermata di blocco purché non sia attiva alcuna sessione di esecuzione estesa e così via.

Quando un'app viene sospesa, richiama l'evento Application.Suspending. I modelli di progetto UWP di Visual Studio forniscono un gestore per questo evento denominato OnSuspending in App.xaml.cs. È necessario inserire il codice per salvare lo stato dell'applicazione qui.

Si devono liberare risorse e handle di file esclusivi in modo che altre app possano accedervi mentre l'app è sospesa. Esempi di risorse esclusive includono fotocamere, dispositivi I/O, dispositivi esterni e risorse di rete. Il rilascio esplicito di risorse esclusive e handle di file consente di garantire che altre app possano accedervi durante la sospensione dell'app. Quando l'app viene ripresa, deve riacquisire le risorse esclusive e gli handle di file.

Tenere presente la scadenza

Per garantire un dispositivo veloce e reattivo, è previsto un limite per il tempo necessario per eseguire il codice nel gestore eventi di sospensione. È diverso per ogni dispositivo ed è possibile scoprire cosa sta usando una proprietà dell'oggetto SuspendingOperation chiamata la scadenza.

Come per il gestore eventi EnteredBackground, se si effettua una chiamata asincrona dal gestore, il controllo restituisce immediatamente da tale chiamata asincrona. Ciò significa che l'esecuzione può quindi ritornare dal gestore eventi e l'app passerà allo stato di sospensione anche se la chiamata asincrona non è stata ancora completata. Utilizzare il metodo GetDeferral sull'oggetto SuspendingOperation (disponibile tramite gli argomenti dell'evento) per ritardare l'immissione dello stato sospeso fino a quando non si chiama il metodo Complete sull'oggetto restituito SuspendingDeferral.

Se è necessario più tempo, è possibile richiedere una ExtendedExecutionSession. Non c'è garanzia che la richiesta venga concessa, tuttavia, è consigliabile trovare modi per ridurre al minimo la quantità di tempo necessario nel gestore eventi Suspended.

Termina l'app

Il sistema tenta di mantenere l'app e i relativi dati in memoria mentre è sospeso. Tuttavia, se il sistema non dispone delle risorse per mantenere l'app in memoria, il sistema terminerà l'app. Le app non ricevono una notifica di chiusura, quindi l'unica opportunità che hai è quella di salvare i dati della tua app nel gestore eventi OnSuspending.

Quando l'app determina che è stata attivata dopo essere stata terminata, dovrebbe caricare i dati dell'applicazione salvati in modo che l'app si trovi nello stesso stato in cui si trovava prima di essere terminata. Quando l'utente torna a un'app sospesa che è stata terminata, l'app deve ripristinare i dati dell'applicazione nel metodo OnLaunched. Il sistema non invia una notifica a un'app quando viene terminata, quindi l'app deve salvare i dati dell'applicazione e rilasciare risorse e handle di file esclusivi prima che venga sospesa e ripristinarli quando l'app viene attivata dopo la chiusura.

Una nota sul debug con Visual Studio: Visual Studio impedisce a Windows di sospendere un'app collegata al debugger. Ciò consente all'utente di visualizzare l'interfaccia utente di debug di Visual Studio mentre l'app è in esecuzione. Quando si esegue il debug di un'app, è possibile inviare un evento di sospensione usando Visual Studio. Verificare che la arra degli strumenti Posizione di debug sia visualizzata, quindi fare clic sull'icona Sospendi .

Ripristino dell'app

Un'app sospesa viene ripristinata quando l'utente passa ad essa o quando è l'app attiva quando il dispositivo esce da uno stato di basso consumo.

Quando un'app viene ripristinata dallo stato Sospeso, passa allo stato In esecuzione in background e il sistema ripristina l'app in cui è stata interrotta in modo che appaia all'utente come se fosse in esecuzione tutto il tempo. Nessun dato dell'app archiviato in memoria viene perso. Pertanto, la maggior parte delle app non ha bisogno di ripristinare lo stato quando viene ripresa, anche se dovrebbe riacquisire tutti gli handle di file o dispositivo rilasciati al momento della sospensione e ripristinare qualsiasi stato rilasciato esplicitamente quando l'app è stata sospesa.

L'app potrebbe essere sospesa per ore o giorni. Se l'app ha connessioni di rete o contenuto non aggiornate, queste devono essere aggiornate quando l'app riprende. Se un'app ha registrato un gestore eventi per l'evento Application.Resuming viene chiamata quando l'app viene ripresa dallo stato Sospeso. È possibile aggiornare il contenuto e i dati dell'app in questo gestore eventi.

Se un'app sospesa viene attivata per partecipare a un contratto o un'estensione dell'app, riceve prima l'evento Ripresa in corso, quindi l'evento Attivato.

Se l'app sospesa è stata terminata, non esiste alcun evento Ripresa in corso e viene invece chiamato con OnLaunched()ApplicationExecutionState di Terminato. Poiché lo stato è stato salvato quando l'app è stata sospesa, è possibile ripristinare tale stato durante OnLaunched() in modo che la tua app appaia all'utente com'era quando l'ha abbandonata.

Quando un'app è sospesa, non riceve alcun evento di rete per cui si è registrata. Questi eventi di rete non vengono accodati, ma semplicemente persi. Di conseguenza, l'app deve testare lo stato della rete quando viene ripresa.

Nota Poiché l'evento Ripresa in corso non viene generato dal thread dell'interfaccia utente, è necessario usare un dispatcher se il codice nel gestore di ripresa comunica con l'interfaccia utente. Per un esempio di codice su come eseguire questa operazione, vedere Aggiornare il thread dell'interfaccia utente da un thread in background.

Per le linee guida generali, vedere Linee guida per la sospensione e la ripresa dell'app.

Chiudi app

In genere, gli utenti non devono chiudere le app, possono consentire a Windows di gestirle. Tuttavia, gli utenti possono scegliere di chiudere un'app usando il movimento di chiusura o premendo ALT+F4 o usando l'interruttore attività di Windows Phone.

Non è presente alcun evento che indichi che l'utente ha chiuso l'app. Quando un'app viene chiusa dall'utente, viene prima sospesa per poterne salvare lo stato. In Windows 8.1 e versioni successive, dopo che un'app è stata chiusa dall'utente, viene rimossa dalla schermata e dall'elenco di opzioni, ma non viene terminata in modo esplicito.

Comportamento chiusa dall'utente: se l'app deve eseguire operazioni diverse quando viene chiusa dall'utente rispetto a quando viene chiusa da Windows, puoi usare il gestore eventi di attivazione per determinare se l'app è stata terminata dall'utente o da Windows. Vedere le descrizioni degli stati ClosedByUser e Terminato nel riferimento per l'enumerazione ApplicationExecutionState.

Consigliamo di non chiudere le app a livello di codice a meno che non sia strettamente necessario. Ad esempio, se un'app rileva una perdita di memoria, può chiudersi per garantire la sicurezza dei dati personali dell'utente.

Arresto anomalo dell'app

L'esperienza di arresto anomalo del sistema è progettata per riportare gli utenti a ciò che stavano facendo il più rapidamente possibile. Non dovresti fornire una finestra di dialogo di avviso o altra notifica perché ciò rallenterebbe l'utente.

Se l'app si arresta in modo anomalo, smette di rispondere o genera un'eccezione, viene inviato un report per il problema a Microsoft in base alle impostazioni di diagnostica e feedback dell'utente. Microsoft fornisce un sottoinsieme dei dati degli errori nel report dei problemi in modo da poterli usare per migliorare l'app. Sarà possibile visualizzare questi dati nella pagina Qualità dell'app nel dashboard.

Quando l'utente attiva un'app dopo l'arresto anomalo, il gestore eventi di attivazione riceve un valore ApplicationExecutionState di NotRunning e deve visualizzare l'interfaccia utente e i dati iniziali. Dopo un arresto anomalo, non usare regolarmente i dati dell'app che avresti usato per lo stato Ripresa in corso con Sospeso perché i dati potrebbero essere danneggiati. Vedere le Linee guida per la sospensione e la ripresa dell'app.

Rimozione dell'app

Quando un utente elimina l'app, viene rimossa insieme a tutti i dati locali. La rimozione di un'app non influisce sui dati dell'utente archiviati in posizioni comuni, ad esempio le raccolte documenti o immagini.

Ciclo di vita dell'app e modelli di progetto di Visual Studio

Il codice di base rilevante per il ciclo di vita dell'app viene fornito nei modelli di progetto di Visual Studio. L'app di base gestisce l'attivazione dell'avvio, fornisce una posizione in cui ripristinare i dati dell'app e visualizza l'interfaccia utente primaria anche prima di aver aggiunto un codice personalizzato. Per altre info, vedere modelli di progetto C#, VB e C++ per le app.

API principali del ciclo di vita dell'applicazione