Programmazione con gli SDK di estensione

Per comprendere in che modo Windows 10 consente all'app piattaforma UWP (Universal Windows Platform) (UWP) di indirizzare in modo più efficace diverse classi di dispositivi, questo argomento illustra i concetti seguenti.

  • Famiglia di dispositivi
  • SDK dell'estensione
  • Contratto API

Viene anche illustrato come usarli nella programmazione.

Video: Introduzione alle famiglie di dispositivi e UWP

 

Famiglie di dispositivi e famiglia di dispositivi di destinazione dell'app

Una famiglia di dispositivi identifica le API, le caratteristiche di sistema e i comportamenti che è possibile prevedere in una classe di dispositivi.

famiglie di dispositivi

Una famiglia di dispositivi è la base di un sistema operativo (OS). Ad esempio, i PC e i tablet eseguono un'edizione desktop del sistema operativo e si basano sulla famiglia di dispositivi Desktop. I dispositivi IoT eseguono un'edizione IoT del sistema operativo, basata sulla famiglia di dispositivi IoT.

Ogni famiglia di dispositivi figlio aggiunge le proprie API alle API ereditate dalla famiglia di dispositivi universali. L'unione risultante delle API in una famiglia di dispositivi figlio è garantita che sia presente in un sistema operativo basato su tale famiglia di dispositivi e quindi su ogni dispositivo che esegue tale sistema operativo.

La decisione su quale famiglia di dispositivi (o famiglie) la tua app sarà di destinazione è la tua. Questa decisione incide sulla tua app in modo rilevante, perché Determina

  • le famiglie di dispositivi offerti dall'app per l'installazione da Microsoft Store (e di conseguenza i fattori di modulo da considerare quando si progetta l'interfaccia utente dell'app) e
  • il set specifico di API che è possibile basarsi su un dispositivo che esegue l'app (il dispositivo host).

Facendo affidamento sul fatto di essere presenti, è possibile chiamare queste API senza prima dover verificare se sono presenti nel dispositivo host. La famiglia di dispositivi di destinazione fornisce tale garanzia (garanzie diverse per famiglie di dispositivi diverse).

Configurare la famiglia di dispositivi di destinazione

Nel file di origine del manifesto del pacchetto dell'app (il file), l'elemento Package.appxmanifestTargetDeviceFamily ha un attributo Name . Il valore di tale attributo è il nome della famiglia di dispositivi destinata all'app. I valori seguenti sono validi.

  • Windows.Desktop
  • Windows.Holographic
  • Windows.IoT
  • Windows.Mobile
  • Windows.Team
  • Windows.Universal
  • Windows.Xbox

Per impostazione predefinita, l'app UWP è destinata alla famiglia di dispositivi universali Windows.Universal , ovvero Microsoft Visual Studio specifica per TargetDeviceFamily. Ciò significa che l'app può essere installata in tutti i dispositivi Windows 10 e che è possibile basarsi su un set di API di grandi dimensioni presente nel dispositivo host. Un'app come quella deve avere un'interfaccia utente altamente adattiva e funzionalità di input complete, perché può essere eseguita in un'ampia gamma di dispositivi. Vedere Visualizzare l'anteprima dell'interfaccia utente in dimensioni diverse dello schermo più avanti in questo argomento.

Se si desidera limitare le famiglie di dispositivi offerti dall'app per l'installazione da Microsoft Store, è possibile scegliere di destinazione una famiglia di dispositivi diversa, ad esempio la famiglia di dispositivi Desktop () o la famiglia di dispositivi IoT (Windows.DesktopWindows.IoT). Naturalmente, ci saranno meno dispositivi che possono ospitare l'app, ma sarà possibile basarsi su un set più ampio di API presenti in tali dispositivi (che sarà il set nella famiglia di dispositivi universali, più il set nella famiglia di dispositivi di destinazione). Un'app come quella in genere deve essere solo moderatamente adattiva; può essere in qualche modo specializzato nelle funzionalità di interfaccia utente e input, perché può essere eseguito solo in un tipo specifico di dispositivo.

Suggerimento

Ma puoi anche avere il meglio di entrambi i mondi. È possibile configurare l'app per l'esecuzione in tutti i dispositivi Windows 10 e accedere anche alle funzionalità specializzate di determinate famiglie di dispositivi quando si trova che si sta eseguendo su uno. Questo scenario migliore di entrambi i mondi richiede un po' di lavoro aggiuntivo e verranno illustrati gli specifici di questo argomento.

Configurare la versione della famiglia di dispositivi di destinazione

Le API vengono aggiunte a Windows nel tempo, quindi un'altra dimensione per scegliere una famiglia di dispositivi sta decidendo quale versione (o versioni) è di destinazione. Alcuni tipi di progetto in Visual Studio dispongono di una pagina delle proprietà in cui è possibile configurare le versioni della piattaforma di destinazione. Tuttavia, per tutti i tipi di progetto è possibile configurare le versioni della piattaforma di destinazione direttamente nel file di progetto.

Ecco un esempio che mostra le proprietà pertinenti in un file di progetto.

<!-- MyProject.Xxxproj -->
<PropertyGroup Label="Globals">
    ...
    <WindowsTargetPlatformVersion>10.0.19041.0</WindowsTargetPlatformVersion>
    <WindowsTargetPlatformMinVersion>10.0.17134.0</WindowsTargetPlatformMinVersion>
    ...
</PropertyGroup>

In fase di compilazione, questi valori (insieme al valore di TargetDeviceFamily@Name da Package.appxmanifest) vengono copiati AppxManifest.xml nel file generato nella cartella di output del progetto. Ecco un esempio.

<!-- AppxManifest.xml -->
<Dependencies>
    <TargetDeviceFamily Name="Windows.Universal"
        MaxVersionTested="10.0.19041.0"
        MinVersion="10.0.17134.0" />
    ...
</Dependencies>

MaxVersionTested specifica la versione massima della famiglia di dispositivi in cui l'app è destinata a cui è stata testata. MinVersion specifica la versione minima della famiglia di dispositivi destinata all'app. Per altre informazioni, vedere TargetDeviceFamily.

Importante

È consigliabile configurare questi numeri di versione tramite le pagine delle proprietà del progetto di Visual Studio o i valori di WindowsTargetPlatformVersion e WindowsTargetPlatformMinVersion nel file di progetto. Non modificare AppxManifest.xml, perché la compilazione sovrascrive il file. E non modificare gli attributi MinVersion e MaxVersionTested dell'elemento TargetDeviceFamily nel file di origine manifesto del pacchetto dell'app (il Package.appxmanifest file), perché questi valori vengono ignorati.

SDK di estensione e come farvi riferimento

Se nel progetto di Visual Studio si modifica la destinazione dalla famiglia di dispositivi universali ad altre famiglie di dispositivi, è necessario aggiungere un riferimento all'SDK di estensione corrispondente alla famiglia di dispositivi. Ciò rende disponibili le API in tale famiglia di dispositivi per il progetto.

Se, ad esempio, si usa la famiglia di dispositivi IoT, quindi , con il nodo del progetto selezionato in Esplora soluzioni, fare clic su Progetto>Aggiungi riferimento...>Windows> universaleEstensioni e selezionare la versione appropriata delle estensioni windows IoT per la piattaforma UWP. Ad esempio, se l'API IoT più recente che si vuole chiamare è stata introdotta nella versione 10.0.17134.0, selezionare tale versione.

Selezionare l'SDK dell'estensione IoT

Questo è il modo in cui tale riferimento verrà visualizzato nel file di progetto.

<ItemGroup>
    <SDKReference Include="WindowsIoT, Version=10.0.17134.0" />
</ItemGroup>

Il nome e il numero della versione corrispondono a quelli delle cartelle in cui è installato l'SDK. Ad esempio, le informazioni precedenti corrispondono alla cartella denominata

\Program Files (x86)\Windows Kits\10\Extension SDKs\WindowsIoT\10.0.17134.0

Altri SDK di estensione includono estensioni desktop Windows per la piattaforma UWP, le estensioni di Windows Mobile per la piattaforma UWP e le estensioni del team di Windows perla piattaforma UWP.

Se si lascia l'app destinata alla famiglia di dispositivi universali, è comunque possibile aggiungere un riferimento a uno o più SDK di estensione. Fare riferimento agli SDK di estensione che contengono le API aggiuntive che si desidera chiamare. Tenere presente la famiglia di dispositivi universali, quindi queste sono le uniche API che è possibile fare affidamento su come essere presenti. Per le API a cui si fa riferimento gli SDK di estensione, è necessario verificare che siano presenti nel dispositivo host in fase di esecuzione prima di chiamarli (altri dettagli nella sezione Scrittura del codice più avanti in questo argomento). Naturalmente, non è necessario eseguire tale test per le API nella famiglia di dispositivi universali. Questo è lo scenario migliore di entrambi i mondi menzionati nella sezione precedente.

Usando un SDK di estensione, è possibile indirizzare le API univoche di una famiglia specifica di dispositivi e quindi accedere alle proprie funzionalità specializzate. È possibile eseguire questa operazione se si punta alla famiglia di dispositivi corrispondente o meno.

Contratti API e come cercarli

Le API in una famiglia di dispositivi vengono suddivise in gruppi noti come contratti API. Quando viene rilasciata una nuova versione di una famiglia di dispositivi, tale nuova versione rappresenta essenzialmente la raccolta di nuove versioni di tutti i contratti API appartenenti alla famiglia di dispositivi.

Ad esempio, il contratto API denominato Windows.Foundation.UniversalApiContract è stato alla versione 6.0 quando è stato fornito con la versione 10.0.17134.0 della famiglia di dispositivi universali. Ma lo stesso contratto era alla versione 10.0 quando è stato fornito con la versione 10.0.19041.0 della stessa famiglia di dispositivi.

Cercare il contratto API per un'API WinRT

Vediamo come cercare il nome e il numero di versione del contratto API per qualsiasi API Windows Runtime API specificata. Nella sezione Scrittura del codice più avanti in questo argomento si vedrà perché e come usare tali informazioni.

Come primo esempio, si userà il metodo StorageFolder.TryGetChangeTracker . Nella sezione dei requisiti di Windows 10 di tale argomento è possibile notare che StorageFolder.TryGetChangeTracker è stato introdotto per la prima volta con la versione 6.0 di Windows.Foundation.UniversalApiContract.

Si esaminerà quindi l'argomento per il metodo StorageFolder.TryGetItemAsync . In questo argomento non è presente alcuna sezione dei requisiti Windows 10. Esaminare invece l'argomento per la classe StorageFolder stessa. La sezione dei requisiti di Windows 10 contiene la risposta. Poiché l'argomento StorageFolder.TryGetItemAsync non dice alcuna differenza, è possibile concludere che condivide i requisiti con la classe padre. Quindi StorageFolder.TryGetItemAsync è stato introdotto per la prima volta con la versione 1.0 di Windows.Foundation.UniversalApiContract.

Come scegliere una famiglia di dispositivi di destinazione

Ecco alcune considerazioni utili per decidere quale famiglia di dispositivi assegnare. Per altre informazioni, vedere TargetDeviceFamily.

Ottimizzare la copertura dell'app

Per raggiungere l'intervallo massimo di tipi di dispositivi con l'app e di conseguenza per usarlo su più dispositivi possibile, l'app deve indirizzare la famiglia di dispositivi universali. In particolare, come abbiamo visto, si punta a una serie di versioni della famiglia di dispositivi universali.

Limitare l'app a un tipo di dispositivo

È possibile che l'app non venga eseguita su un'ampia gamma di fattori di modulo del dispositivo; forse è specializzato per un PC desktop o per una console Xbox. In questo caso, è possibile scegliere di destinazione una delle famiglie di dispositivi figlio.

Limitare l'app a un subset di tutti i dispositivi possibili

Anziché indirizzare la famiglia di dispositivi universali o la destinazione di una delle famiglie di dispositivi figlio, è invece possibile indirizzare due o più famiglie di dispositivi figlio. La destinazione di Desktop e dispositivi mobili può essere utile per l'app. O Desktop e Team. O Desktop, Mobile e Team e così via.

Escludere il supporto per una determinata versione di una famiglia di dispositivi

In rari casi, è possibile che l'app venga eseguita ovunque , ad eccezione dei dispositivi con una determinata versione di una determinata famiglia di dispositivi. Ad esempio, si supponga che l'app sia destinata alla versione 10.0.x.0 della famiglia di dispositivi universali. Quando la versione del sistema operativo cambia in futuro, ad esempio 10.0.x.2, a quel punto, è possibile specificare che l'app viene eseguita ovunque tranne la versione 10.0.x.1 di Xbox indirizzando l'app a 10.0.x.0 di Universal e 10.0.x.2 di Xbox. La tua app non sarà quindi disponibile per il set di versioni della famiglia di dispositivi appartenenti alla versione di Xbox 10.0.x.1 (inclusa) e precedenti.

Scrittura del codice

Gran parte del codice sarà universale nel senso che eseguirà lo stesso modo in ogni dispositivo. Tuttavia, per il codice personalizzato per una determinata famiglia di dispositivi, sarà possibile usare il codice adattivo. Si considerino questi diversi casi.

Chiamare un'API implementata dalla famiglia di dispositivi di destinazione

Ogni volta che si vuole chiamare un'API in un'app UWP, si vuole sapere se l'API viene implementata dalla famiglia di dispositivi destinata all'app. Visual Studio IntelliSense mostra le API nella famiglia di dispositivi universali e le API disponibili per qualsiasi SDK di estensione a cui si fa riferimento.

La documentazione di riferimento dell'API Windows Runtime indica quale famiglia di dispositivi fa parte di un'API. Se si cerca l'argomento di riferimento dell'API per un'API Windows Runtime e si cerca la sezione dei requisiti di Windows 10, si vedrà cosa è la famiglia di dispositivi di implementazione e quale versione di tale famiglia di dispositivi viene visualizzata prima nell'API. Se non sono presenti Windows 10 requisiti, vedere la classe proprietaria del membro e visualizzare le informazioni nella sezione requisiti Windows 10. Queste informazioni verranno applicate anche al membro.

Chiamare un'API non implementata dalla famiglia di dispositivi di destinazione

Esistono casi in cui si vuole chiamare un'API in un SDK di estensione a cui si è fatto riferimento, ma tale API non fa parte della famiglia di dispositivi destinata.

Ad esempio, potrebbe essere destinato alla famiglia di dispositivi universali, ma esiste un'API desktop che si vuole chiamare ogni volta che l'app è in esecuzione in un dispositivo desktop.

Oppure l'app può supportare le versioni iniziali di una famiglia di dispositivi, ma è disponibile un'API che si vuole chiamare solo in versioni molto recenti della stessa famiglia di dispositivi.

In casi come quelli, è possibile scegliere di scrivere codice adattivo in modo che sia possibile chiamare tali API in modo sicuro. La sezione successiva illustra come.

Scrivere codice adattivo usando ApiInformation

Esistono due passaggi coinvolti nell'uso del codice adattivo per chiamare un'API in modo condizionale. Il primo passaggio consiste nel rendere l'API disponibile per il progetto. A tale scopo, aggiungere un riferimento all'SDK di estensione che rappresenta la famiglia di dispositivi proprietaria dell'API.

Il secondo passaggio consiste nell'usare la classe ApiInformation in una condizione nel codice per testare la presenza dell'API che si vuole chiamare. Questa condizione viene valutata ovunque e ogni volta che viene eseguita l'app. Ma restituisce true solo nei dispositivi in cui l'API è presente e quindi disponibile per chiamare.

Se si vuole chiamare solo un numero ridotto di API, è possibile usare il metodo ApiInformation.IsTypePresent come questo.

// Cache the value, instead of querying it multiple times.
bool isHardwareButtonsAPIPresent =
    Windows.Foundation.Metadata.ApiInformation.IsTypePresent("Windows.Phone.UI.Input.HardwareButtons");

if (isHardwareButtonsAPIPresent)
{
    Windows.Phone.UI.Input.HardwareButtons.CameraPressed += HardwareButtons_CameraPressed;
}

In questo caso, la presenza della classe HardwareButtons implica la presenza dell'evento CameraPressed , perché la classe e il membro hanno le stesse informazioni sui requisiti. Ma in tempo, i nuovi membri verranno aggiunti alle classi già introdotte e tali membri saranno introdotti in seguito nei numeri di versione. In questi casi, invece di usare IsTypePresent, puoi verificare la presenza di singoli membri con IsEventPresent, IsMethodPresent, IsPropertyPresent e metodi simili. Ecco un esempio.

bool isHardwareButtons_CameraPressedAPIPresent =
    Windows.Foundation.Metadata.ApiInformation.IsEventPresent
        ("Windows.Phone.UI.Input.HardwareButtons", "CameraPressed");

Come sappiamo, il set di API all'interno di una famiglia di dispositivi è ulteriormente suddiviso in suddivisioni in suddivisioni note come contratti API. Puoi verificare la presenza di un contratto API usando il metodo ApiInformation.IsApiContractPresent. Questo è un modo efficiente per eseguire una singola condizione per conoscere la presenza o altrimenti di un numero elevato di API che appartengono alla stessa versione di un contratto API.

Per informazioni su come determinare il contratto API che ha prima introdotto le API di interesse, vedere la sezione Ricerca del contratto API per un'API WinRT in precedenza in questo argomento.

Dopo aver ottenuto queste informazioni, è possibile collegarla al codice adattivo. Ad esempio, se il nome del contratto API è Windows.Devices.Scanners.ScannerDeviceContract, e i relativi numeri di versione principale e secondaria sono rispettivamente 1 e 0, la condizione sarà simile all'esempio seguente.

bool isWindows_Devices_Scanners_ScannerDeviceContract_1_0Present =
    Windows.Foundation.Metadata.ApiInformation.IsApiContractPresent
        ("Windows.Devices.Scanners.ScannerDeviceContract", 1, 0);

Visualizzare l'anteprima dell'interfaccia utente in diverse dimensioni dello schermo

È consigliabile ottimizzare la copertura dell'app. Ma anche se si fa riferimento a un solo tipo di fattore di forma del dispositivo, probabilmente ci saranno dimensioni diverse dello schermo in cui l'app potrebbe venire visualizzata.

Quando si è pronti per visualizzare l'aspetto e l'aspetto dell'app in una determinata dimensione dello schermo, usare la barra degli strumenti di anteprima del dispositivo in Visual Studio per visualizzare in anteprima l'interfaccia utente in un dispositivo mobile di piccole o medie dimensioni, in un PC o in uno schermo tv di grandi dimensioni. In questo modo, se sono state usate le funzionalità di layout adattive di XAML (vedere Layout adattivi con stati visivi e trigger di stato), è anche possibile testare tale funzionalità.

barra degli strumenti di anteprima del dispositivo in Visual Studio 2015

Non è necessario prendere una decisione in anticipo su ogni tipo di dispositivo supportato. È possibile aggiungere una dimensione aggiuntiva del dispositivo al progetto in qualsiasi momento.

Vedi anche