Conversione di un progetto di Windows Runtime 8.x in un progetto UWP
Sono disponibili due opzioni quando si inizia il processo di conversione. Uno consiste nel modificare una copia dei file di progetto esistenti, incluso il manifesto del pacchetto dell'app (per tale opzione, vedi le informazioni sull'aggiornamento dei file di progetto in Eseguire la migrazione delle app alla piattaforma UWP (Universal Windows Platform)). L'altra opzione consiste nel creare un nuovo progetto Windows 10 in Visual Studio e copiarvi i file. La prima sezione di questo argomento descrive la seconda opzione, ma il resto dell'argomento include informazioni aggiuntive applicabili a entrambe le opzioni. È anche possibile scegliere di mantenere il nuovo progetto Windows 10 nella stessa soluzione dei progetti esistenti e condividere i file di codice sorgente usando un progetto condiviso. In alternativa, è possibile mantenere il nuovo progetto in una soluzione personalizzata e condividere i file di codice sorgente usando la funzionalità file collegati in Visual Studio.
Creare il progetto e copiarvi i file
Questi passaggi si concentrano sull'opzione per creare un nuovo progetto Windows 10 in Visual Studio e copiarvi i file. Alcune delle specifiche relative al numero di progetti creati e ai file copiati dipendono dai fattori e dalle decisioni descritte in Se si ha un'app Universal 8.1 e le sezioni seguenti. Questi passaggi presuppongono il caso più semplice.
- Avviare Microsoft Visual Studio 2015 e creare un nuovo progetto Applicazione vuota (Windows Universal). Per altre info, vedere Guida introduttiva all'app Windows Runtime 8.x con i modelli (C#, C++, Visual Basic). Il nuovo progetto compila un pacchetto dell'app (un file appx) che verrà eseguito in tutte le famiglie di dispositivi.
- Nel progetto di app Universal 8.1 identificare tutti i file di codice sorgente e i file di asset visivi da riutilizzare. Usando Esplora file, copiare modelli di dati, visualizzare modelli, asset visivi, dizionari risorse, struttura di cartelle e qualsiasi altro elemento da riutilizzare nel nuovo progetto. Copiare o creare sottocartelle su disco in base alle esigenze.
- Copiare anche le visualizzazioni (ad esempio MainPage.xaml e MainPage.xaml.cs) nel nuovo progetto. Anche in questo caso, creare nuove sottocartelle in base alle esigenze e rimuovere le visualizzazioni esistenti dal progetto. Tuttavia, prima di sovrascrivere o rimuovere una visualizzazione generata da Visual Studio, mantenere una copia perché può essere utile farvi riferimento in un secondo momento. La prima fase della conversione di un'app Universal 8.1 è incentrata sul fatto di renderla ottimale e adattarsi a una famiglia di dispositivi. Successivamente, si rivolgerà l'attenzione per assicurarsi che le visualizzazioni si adattino bene a tutti i fattori di forma e, facoltativamente, per aggiungere qualsiasi codice adattivo per ottenere il massimo da una particolare famiglia di dispositivi.
- In Esplora soluzioni assicurarsi che l'opzione Mostra tutti i file sia attivata. SElezionare i file di copiati, fare clic con il tasto destro del mouse su di essi, quindi fare clic su Includi nel progetto. Questo includerà automaticamente le cartelle contenenti. È quindi possibile disattivare Mostra tutti i file se lo si desidera. Un flusso di lavoro alternativo, se si preferisce, consiste nell'usare il comando Aggiungi elemento esistente, dopo aver creato eventuali sottocartelle necessarie in Visual Studio Esplora soluzioni. Verificare che gli asset visivi abbiano Azione di compilazione impostata a Contenuto e Copia in directory in uscita impostato su Non copiare.
- È probabile che vengano visualizzati alcuni errori di compilazione in questa fase. Tuttavia, se si sa cosa è necessario modificare, è possibile usare il comando Trova e sostituisci di Visual Studio per apportare modifiche in blocco al codice sorgente e nell'editor di codice imperativo in Visual Studio usare i comandi Resolve e Organize Usings nel menu di scelta rapida per modifiche più mirate.
Ottimizzazione del markup e del riutilizzo del codice
Si scoprirà che il refactoring di un p ' e/o l'aggiunta di codice adattivo (illustrato di seguito), consentirà di ottimizzare il markup e il codice che funziona in tutte le famiglie di dispositivi. Di seguito sono riportate informazioni dettagliate.
- I file comuni a tutte le famiglie di dispositivi non necessitano di considerazioni speciali. Questi file verranno usati dall'app in tutte le famiglie di dispositivi in cui viene eseguito. Sono inclusi i file di markup XAML, i file di codice sorgente imperativo e i file di asset.
- È possibile che l'app rilevi la famiglia di dispositivi su cui è in esecuzione e passi a una visualizzazione progettata appositamente per la famiglia di dispositivi. Per altri dettagli, vedere Rilevamento della piattaforma in cui è in esecuzione l'app.
- Una tecnica simile che può risultare utile se non esiste un'alternativa consiste nell'assegnare un file di markup o un file ResourceDictionary (o la cartella che contiene il file) un nome speciale in modo che venga caricato automaticamente in fase di esecuzione solo quando l'app viene eseguita in una determinata famiglia di dispositivi. Questa tecnica è illustrata nel case study Bookstore1.
- Si dovrebbe essere in grado di rimuovere molte delle direttive di compilazione condizionale nel codice sorgente dell'app Universal 8.1 se si deve supportare solo Windows 10. Vedere Compilazione condizionale e codice adattivo in questo argomento.
- Per usare le funzionalità non disponibili in tutte le famiglie di dispositivi (ad esempio stampanti, scanner o pulsante della fotocamera), è possibile scrivere codice adattivo. Vedere il terzo esempio in Compilazione condizionale e codice adattivo in questo argomento.
- Se si vuole supportare Windows 8.1, Windows Phone 8.1 e Windows 10, si possono mantenere tre progetti nella stessa soluzione e condividere il codice con un progetto condiviso. In alternativa, è possibile condividere file di codice sorgente tra progetti. Ecco come: in Visual Studio fare clic con il pulsante destro del mouse sul progetto in Solution Explorer, selezionare Aggiungi elemento esistente, selezionare i file da condividere e quindi fare clic su Aggiungi come collegamento. Archiviare i file di codice sorgente in una cartella comune nel file system in cui i progetti collegati possono visualizzarli. E non dimenticare di aggiungerli al controllo del codice sorgente.
- Per il riutilizzo a livello binario, anziché a livello di codice sorgente, vedere Creazione di componenti Windows Runtime in C# e Visual Basic. Sono disponibili anche librerie di classi portabili, che supportano il subset di API .NET disponibili in .NET Framework per Windows 8.1, Windows Phone 8.1 e app di Windows 10 (.NET Core) e .NET Framework completo. I gruppi della libreria di classi portabili sono compatibili con tutte queste piattaforme. Usare Visual Studio per creare un progetto destinato a una libreria di classi portabile. Vedere Sviluppo multipiattaforma con la libreria di classi portabile.
SDK di estensione
La maggior parte delle API di Windows Runtime che l'app Universal 8.1 già chiama vengono implementate nel set di API note come famiglia di dispositivi universali. Tuttavia, alcuni vengono implementati negli SDK di estensione e Visual Studio riconosce solo le API implementate dalla famiglia di dispositivi di destinazione dell'app o da qualsiasi SDK di estensione a cui si è fatto riferimento.
Se vengono visualizzati errori di compilazione relativi a spazi dei nomi o tipi o membri che non sono stati trovati, è probabile che questa sia la causa. Aprire l'argomento dell'API nella documentazione di riferimento dell'API e passare alla sezione Requisiti: che indicherà qual è la famiglia di dispositivi di implementazione. Se non è la famiglia di dispositivi di destinazione, per rendere disponibile l'API per il progetto, è necessario un riferimento all'SDK di estensione per la famiglia di dispositivi.
Fare clic su Progetto>Aggiungi riferimento>Windows Universal>Estensioni e selezionare l'SDK di estensione appropriato. Ad esempio, se le API che si desidera chiamare sono disponibili solo nella famiglia di dispositivi mobili e sono state introdotte nella versione 10.0.x.y, selezionare Estensioni di Windows Mobile per la piattaforma UWP.
Questo aggiungerà il riferimento seguente al file di progetto:
<ItemGroup>
<SDKReference Include="WindowsMobile, Version=10.0.x.y">
<Name>Windows Mobile Extensions for the UWP</Name>
</SDKReference>
</ItemGroup>
Il nome e il numero di versione corrispondono alle cartelle nel percorso installato dell'SDK. Ad esempio, le informazioni precedenti corrispondono a questo nome di cartella:
\Program Files (x86)\Windows Kits\10\Extension SDKs\WindowsMobile\10.0.x.y
A meno che l'app non sia destinata alla famiglia di dispositivi che implementa l'API, si dovrà usare la classe ApiInformation per verificare la presenza dell'API prima di chiamarla (questo è detto codice adattivo). Questa condizione verrà quindi valutata ovunque venga eseguita l'app, ma valuterà true solo nei dispositivi in cui l'API è presente e quindi disponibile per essere chiamata. Usare gli SDK di estensione e il codice adattivo solo dopo aver verificato se esiste un'API universale. Alcuni esempi sono riportati nella sezione seguente.
Vedere anche Manifesto del pacchetto dell'app.
Compilazione condizionale e codice adattivo
Se si usa la compilazione condizionale (con direttive del preprocessore C#) in modo che i file di codice funzionino sia in Windows 8.1 che in Windows Phone 8.1, si può ora esaminare la compilazione condizionale alla luce del lavoro di convergenza svolto in Windows 10. La convergenza significa che, nell'app di Windows 10, alcune condizioni possono essere rimosse completamente. Altre modifiche apportate ai controlli in fase di esecuzione, come illustrato negli esempi seguenti.
Nota Se si desidera supportare Windows 8.1, Windows Phone 8.1 e Windows 10 in un singolo file di codice, è possibile farlo. Se si guarda il progetto di Windows 10 nelle pagine delle proprietà del progetto, si vedrà che il progetto definisce WINDOWS_UAP come simbolo di compilazione condizionale. È quindi possibile usarlo in combinazione con WINDOWS_APP e WINDOWS_PHONE_APP. Questi esempi illustrano il caso più semplice di rimozione della compilazione condizionale da un'app Universal 8.1 e sostituire il codice equivalente per un'app di Windows 10.
Questo primo esempio mostra il modello di utilizzo per l'API PickSingleFileAsync (applicabile solo a Windows 8.1) e l'API PickSingleFileAndContinue (applicabile solo a Windows Phone 8.1).
#if WINDOWS_APP
// Use Windows.Storage.Pickers.FileOpenPicker.PickSingleFileAsync
#else
// Use Windows.Storage.Pickers.FileOpenPicker.PickSingleFileAndContinue
#endif // WINDOWS_APP
Windows 10 converge sull'API PickSingleFileAsync, quindi il codice semplifica le operazioni seguenti:
// Use Windows.Storage.Pickers.FileOpenPicker.PickSingleFileAsync
In questo esempio viene gestito il pulsante Indietro hardware, ma solo in Windows Phone.
#if WINDOWS_PHONE_APP
Windows.Phone.UI.Input.HardwareButtons.BackPressed += this.HardwareButtons_BackPressed;
#endif // WINDOWS_PHONE_APP
...
#if WINDOWS_PHONE_APP
void HardwareButtons_BackPressed(object sender, Windows.Phone.UI.Input.BackPressedEventArgs e)
{
// Handle the event.
}
#endif // WINDOWS_PHONE_APP
In Windows 10, l'evento pulsante Indietro è un concetto universale. I pulsanti Indietro implementati nell'hardware o nel software generano tutti l'evento BackRequested, in modo che sia quello da gestire.
Windows.UI.Core.SystemNavigationManager.GetForCurrentView().BackRequested +=
this.ViewModelLocator_BackRequested;
...
private void ViewModelLocator_BackRequested(object sender, Windows.UI.Core.BackRequestedEventArgs e)
{
// Handle the event.
}
Questo esempio finale è simile al precedente. In questo caso, si gestisce il pulsante della fotocamera hardware, ma ancora una volta, solo nel codice compilato nel pacchetto dell'app di Windows Phone.
#if WINDOWS_PHONE_APP
Windows.Phone.UI.Input.HardwareButtons.CameraPressed += this.HardwareButtons_CameraPressed;
#endif // WINDOWS_PHONE_APP
...
#if WINDOWS_PHONE_APP
void HardwareButtons_CameraPressed(object sender, Windows.Phone.UI.Input.CameraEventArgs e)
{
// Handle the event.
}
#endif // WINDOWS_PHONE_APP
In Windows 10 il pulsante della fotocamera hardware è un concetto particolare per la famiglia di dispositivi mobili. Poiché un pacchetto dell'app verrà eseguito in tutti i dispositivi, la condizione in fase di compilazione viene modificata in una condizione di runtime usando il nome di codice adattivo. A tale scopo, usiamo la classe ApiInformation per eseguire query in fase di esecuzione per la presenza della classe HardwareButtons. HardwareButtons è definito nell'SDK dell'estensione per dispositivi mobili, quindi è necessario aggiungere un riferimento a tale SDK al progetto per la compilazione di questo codice. Si noti, tuttavia, che il gestore verrà eseguito solo in un dispositivo che implementa i tipi definiti nell'SDK dell'estensione per dispositivi mobili ed è la famiglia di dispositivi mobili. Quindi, questo codice è moralmente equivalente al codice Universal 8.1 in quanto è attento solo all'uso di funzionalità presenti, anche se ottiene tale risultato in modo diverso.
// Note: Cache the value instead of querying it more than once.
bool isHardwareButtonsAPIPresent = Windows.Foundation.Metadata.ApiInformation.IsTypePresent
("Windows.Phone.UI.Input.HardwareButtons");
if (isHardwareButtonsAPIPresent)
{
Windows.Phone.UI.Input.HardwareButtons.CameraPressed +=
this.HardwareButtons_CameraPressed;
}
...
private void HardwareButtons_CameraPressed(object sender, Windows.Phone.UI.Input.CameraEventArgs e)
{
// Handle the event.
}
Inoltre, vedere Rilevamento della piattaforma in cui è in esecuzione l'app.
Manifesto del pacchetto dell'app
L'argomento Modifiche apportate a Windows 10 elenca le modifiche apportate al riferimento allo schema del manifesto del pacchetto per Windows 10, inclusi gli elementi aggiunti, rimossi e modificati. Per informazioni di riferimento su tutti gli elementi, gli attributi e i tipi nello schema, vedere Gerarchia degli elementi. Se si sta effettuando la conversione di un'app di Windows Phone Store o se l'app è un aggiornamento a un'app da Windows Phone Store, assicurarsi che l'elemento mp:PhoneIdentity corrisponda a ciò che si trova nel manifesto dell'app precedente (usare gli stessi GUID assegnati all'app dallo Store). In questo modo, gli utenti dell'app che eseguono l'aggiornamento a Windows 10 o Windows 11 riceveranno la nuova app come aggiornamento, non un duplicato. Per altri dettagli, vedere l'argomento di riferimento su mp:PhoneIdentity.
Le impostazioni nel progetto (inclusi i riferimenti agli SDK di estensione) determinano la superficie di attacco dell'API che l'app può chiamare. Tuttavia, il manifesto del pacchetto dell'app è ciò che determina il set effettivo di dispositivi in cui i clienti possono installare l'app dallo Store. Per altre info, vedere esempi in TargetDeviceFamily.
Si può modificare il manifesto del pacchetto dell'app per impostare varie dichiarazioni, funzionalità e altre impostazioni necessarie per alcune funzionalità. È possibile usare l'editor del manifesto del pacchetto dell'app di Visual Studio per modificarlo. Se Esplora soluzioni non viene visualizzato, selezionarlo dal menu Visualizza. Fare doppio clic su Package.appxmanifest. Verrà visualizzata la finestra dell'editor del manifesto. Selezionare la scheda appropriata per apportare modifiche e quindi salvare.
L'argomento successivo è Risoluzione dei problemi.