<?xml version="1.0" encoding="utf-8"?>
<rss xmlns:atom="https://www.w3.org/2005/Atom" xmlns:sy="https://purl.org/rss/1.0/modules/syndication/" xmlns:dc="https://purl.org/dc/elements/1.1/" xmlns:content="https://purl.org/rss/1.0/modules/content/" xmlns:wfw="https://wellformedweb.org/CommentAPI/" xmlns:slash="https://purl.org/rss/1.0/modules/slash/"
  version="2.0">
  <channel>
    <title>ndelabarre</title>
    <atom:link
      href="https://docs.microsoft.com/archive/blogs/ndelabarre/feed.xml"
      rel="self"
      type="application/rss+xml" />
    <link>https://docs.microsoft.com/archive/blogs/ndelabarre/feed.xml</link>
    <description />
    <lastBuildDate>Wed, 17 Apr 2019 03:24:50 GMT</lastBuildDate>
    <language>en-US</language>
    <sy:updatePeriod>hourly</sy:updatePeriod>
    <sy:updateFrequency>1</sy:updateFrequency>
    <item>
      <title>Les services d’authentification “Azure App Service” évoluent</title>
      <link>https://docs.microsoft.com/archive/blogs/ndelabarre/les-services-dauthentification-azure-app-service-voluent</link>
      <pubDate>Tue, 01 Mar 2016 09:48:51 GMT</pubDate>
      <dc:creator><![CDATA[Nicolas Delabarre]]></dc:creator>
      <guid
        isPermaLink="false">https://blogs.msdn.microsoft.com/ndelabarre/2016/03/01/les-services-dauthentification-azure-app-service-voluent/</guid>
      <description><![CDATA[Pour faire suite à l’excellente série d’articles Implémentation d’une solution fondée sur les Azure...]]></description>
      <content:encoded><![CDATA[<p align="justify">Pour faire suite à l’excellente série d’articles <a href="https://blogs.msdn.com/b/stephgou/archive/2015/08/17/implementation-d-une-solution-fondee-sur-les-azure-app-services.aspx" target="_blank">Implémentation d’une solution fondée sur les Azure App Services</a> écrites par mon collègue Stéphane Goudeau, je vous propose de modifier cette implémentation afin de tirer partie des <a href="https://azure.microsoft.com/en-us/documentation/articles/app-service-api-whats-changed/" target="_blank">derniers</a> avancement d’Azure App Service en matière d’authentification et d’autorisation. Il y a un an, le regroupement des Web Apps, Mobile Apps, API Apps, et Logic Apps dans une solution unifiée dénommée “Azure App Service” permettait de simplifier l’authentification en définissant une <a href="https://github.com/Azure/azure-content/blob/master/articles/app-service/app-service-authentication-overview.md" target="_blank">passerelle d’authentification</a> (App Service Gateway). Un des rôles clef de cette passerelle était de partager le mécanisme d’authentification entre apps et étendre le mécanisme de login aux services mobiles. Néanmoins, une des remontées récurrentes de nos clients était le besoin d’une plus grande flexibilité d’authentification à un niveau applicatif individuel. La fonction <a href="https://azure.microsoft.com/en-us/blog/azure-websites-authentication-authorization/" target="_blank">Authentification/Autorisation</a> initialement accessible uniquement pour les sites web est dorénavant disponible pour les Azure App Service avec le support de nouveaux fournisseurs d’identité, de nouvelles options de login et une plus grande flexibilité dans le contrôle d’accès. Au final on conserve les avantages de la passerelle d’authentification mais avec une granularité plus fine par site (ou app) et une gestion simplifiée depuis le portail Azure. Pour tout nouveau projet, il est donc préférable d’opter pour cette nouvelle fonction d’authentification/autorisation en lieu et place de la passerelle App Service. Cette article vous propose donc de migrer la solution de mon collègue Stéphane initialement basée sur un mécanisme d’authentification AAD via une passerelle intermédiaire vers un système d’authentification AAD plus simple et plus direct. L’architecture générale de la solution finale sera donc très proche de la version originale sans la passerelle intermédiaire :</p>  <p align="justify"><a href="https://msdnshared.blob.core.windows.net/media/MSDNBlogsFS/prod.evol.blogs.msdn.com/CommunityServer.Blogs.Components.WeblogFiles/00/00/01/70/07/metablogapi/8284.image_23D51CEA.png" original-url="https://blogs.msdn.com/cfs-file.ashx/__key/communityserver-blogs-components-weblogfiles/00-00-01-70-07-metablogapi/8284.image_5F00_23D51CEA.png"><img title="image" style="border-top: 0px; border-right: 0px; background-image: none; border-bottom: 0px; padding-top: 0px; padding-left: 0px; border-left: 0px; display: inline; padding-right: 0px" border="0" alt="image" src="https://msdnshared.blob.core.windows.net/media/MSDNBlogsFS/prod.evol.blogs.msdn.com/CommunityServer.Blogs.Components.WeblogFiles/00/00/01/70/07/metablogapi/8004.image_thumb_656F5936.png" original-url="https://blogs.msdn.com/cfs-file.ashx/__key/communityserver-blogs-components-weblogfiles/00-00-01-70-07-metablogapi/8004.image_5F00_thumb_5F00_656F5936.png" width="642" height="366" /></a></p>  <h2>Configuration de l’API App “Doc.Search.API”</h2>  <p>Rendez-vous sur le <a href="https://portal.azure.com/" target="_blank">portail Azure</a> et sélectionnez les paramètres (“All Settings” en anglais) de votre API App : parmi tous les groupes de paramètres disponibles, localisez celui dénommé ‘'Fonctionnalités” (“Features” en anglais) et cliquez sur la fonction “Authentification/Autorisation” :</p>  <p><a href="https://msdnshared.blob.core.windows.net/media/MSDNBlogsFS/prod.evol.blogs.msdn.com/CommunityServer.Blogs.Components.WeblogFiles/00/00/01/70/07/metablogapi/6403.image_68B37B05.png" original-url="https://blogs.msdn.com/cfs-file.ashx/__key/communityserver-blogs-components-weblogfiles/00-00-01-70-07-metablogapi/6403.image_5F00_68B37B05.png"><img title="image" style="border-left-width: 0px; border-right-width: 0px; background-image: none; border-bottom-width: 0px; padding-top: 0px; padding-left: 0px; display: inline; padding-right: 0px; border-top-width: 0px" border="0" alt="image" src="https://msdnshared.blob.core.windows.net/media/MSDNBlogsFS/prod.evol.blogs.msdn.com/CommunityServer.Blogs.Components.WeblogFiles/00/00/01/70/07/metablogapi/4101.image_thumb_67DDA5CC.png" original-url="https://blogs.msdn.com/cfs-file.ashx/__key/communityserver-blogs-components-weblogfiles/00-00-01-70-07-metablogapi/4101.image_5F00_thumb_5F00_67DDA5CC.png" width="706" height="421" /></a></p>  <ul></ul>  <p>Activez l’authentification App Service (commutateur sur “ON”) </p>  <p>Ensuite, la solution initiale étant basée sur une authentification Azure Active Directory, nous continuerons donc à utiliser ce fournisseur : </p>  <ol>   <li>Dans la liste des actions à entreprendre pour toute requête non authentifiée, nous sélectionnons “Login avec Azure Active Directory” car notre application n’autorise l’authentification que via Azure AD. Si toutefois vous souhaitez pouvoir offrir à vos utilisateurs la possibilité de s’authentifier avec différents fournisseurs d’identité, alors vous laisserez la valeur par défaut “Autorise les requêtes (aucune action)”. Cette option offre donc plus de flexibilité pour les applications. </li>    <li>Puis dans la liste des fournisseurs d’authentification supportés, nous opterons pour Azure Active Directory ce qui ouvrira une nouvelle fenêtre où nous sélectionnerons le mode “Express”:&#160; <a href="https://msdnshared.blob.core.windows.net/media/MSDNBlogsFS/prod.evol.blogs.msdn.com/CommunityServer.Blogs.Components.WeblogFiles/00/00/01/70/07/metablogapi/8688.app_service_azure_aad_express_mode_0C@28.png" original-url="https://blogs.msdn.com/cfs-file.ashx/__key/communityserver-blogs-components-weblogfiles/00-00-01-70-07-metablogapi/8688.app_5F00_service_5F00_azure_5F00_aad_5F00_express_5F00_mode_5F00_0C400028.png"><img title="app_service_azure_aad_express_mode" style="border-top: 0px; border-right: 0px; background-image: none; border-bottom: 0px; padding-top: 0px; padding-left: 0px; border-left: 0px; display: inline; padding-right: 0px" border="0" alt="app_service_azure_aad_express_mode" src="https://msdnshared.blob.core.windows.net/media/MSDNBlogsFS/prod.evol.blogs.msdn.com/CommunityServer.Blogs.Components.WeblogFiles/00/00/01/70/07/metablogapi/6457.app_service_azure_aad_express_mode_thumb_0E1055EF.png" original-url="https://blogs.msdn.com/cfs-file.ashx/__key/communityserver-blogs-components-weblogfiles/00-00-01-70-07-metablogapi/6457.app_5F00_service_5F00_azure_5F00_aad_5F00_express_5F00_mode_5F00_thumb_5F00_0E1055EF.png" width="447" height="482" /></a> </li>    <li>Notez que l’application par défaut qui sera enregistrée automatiquement dans Azure AD correspond bien à notre application DocSearchAPI. Si vous cliquez cet élément vous verrez une nouvelle fenêtre :<a href="https://msdnshared.blob.core.windows.net/media/MSDNBlogsFS/prod.evol.blogs.msdn.com/CommunityServer.Blogs.Components.WeblogFiles/00/00/01/70/07/metablogapi/3771.AAD_GUID_2844B7DD.png" original-url="https://blogs.msdn.com/cfs-file.ashx/__key/communityserver-blogs-components-weblogfiles/00-00-01-70-07-metablogapi/3771.AAD_5F00_GUID_5F00_2844B7DD.png"><img title="AAD_GUID" style="border-left-width: 0px; border-right-width: 0px; background-image: none; border-bottom-width: 0px; padding-top: 0px; padding-left: 0px; display: inline; padding-right: 0px; border-top-width: 0px" border="0" alt="AAD_GUID" src="https://msdnshared.blob.core.windows.net/media/MSDNBlogsFS/prod.evol.blogs.msdn.com/CommunityServer.Blogs.Components.WeblogFiles/00/00/01/70/07/metablogapi/1856.AAD_GUID_thumb_1F57B64F.png" original-url="https://blogs.msdn.com/cfs-file.ashx/__key/communityserver-blogs-components-weblogfiles/00-00-01-70-07-metablogapi/1856.AAD_5F00_GUID_5F00_thumb_5F00_1F57B64F.png" width="644" height="424" /></a> </li>    <li>En cliquant sur “OK”, votre application&#160; (dans notre cas “DocSearchAPI”) sera automatiquement enregistrée dans l’annuaire Azure AD par défaut (c’est-à-dire le tenant Azure AD identique à celui que vous utilisez lorsque vous accédez au portail Azure avec votre compte). C’est le mode “Express” </li>    <li>Afin de bien vérifier que votre application a bien été enregistrée dans votre annuaire Azure AD, vous pouvez vous rendre sur <a href="https://manage.windowsazure.com" target="_blank">l’ancien portail Azure</a> :<a href="https://msdnshared.blob.core.windows.net/media/MSDNBlogsFS/prod.evol.blogs.msdn.com/CommunityServer.Blogs.Components.WeblogFiles/00/00/01/70/07/metablogapi/6102.old_azure_portal_AAD_531FACA0.png" original-url="https://blogs.msdn.com/cfs-file.ashx/__key/communityserver-blogs-components-weblogfiles/00-00-01-70-07-metablogapi/6102.old_5F00_azure_5F00_portal_5F00_AAD_5F00_531FACA0.png"><img title="old_azure_portal_AAD" style="border-left-width: 0px; border-right-width: 0px; background-image: none; border-bottom-width: 0px; float: left; padding-top: 0px; padding-left: 0px; display: inline; padding-right: 0px; border-top-width: 0px" border="0" alt="old_azure_portal_AAD" src="https://msdnshared.blob.core.windows.net/media/MSDNBlogsFS/prod.evol.blogs.msdn.com/CommunityServer.Blogs.Components.WeblogFiles/00/00/01/70/07/metablogapi/6567.old_azure_portal_AAD_thumb_199F2D5A.png" original-url="https://blogs.msdn.com/cfs-file.ashx/__key/communityserver-blogs-components-weblogfiles/00-00-01-70-07-metablogapi/6567.old_5F00_azure_5F00_portal_5F00_AAD_5F00_thumb_5F00_199F2D5A.png" width="644" align="left" height="307" /></a> </li>    <li>Sélectionnez ensuite l’onglet “Applications” puis votre application DocSearchAPI :<a href="https://msdnshared.blob.core.windows.net/media/MSDNBlogsFS/prod.evol.blogs.msdn.com/CommunityServer.Blogs.Components.WeblogFiles/00/00/01/70/07/metablogapi/1423.AAD_APP_API_24CB4855.png" original-url="https://blogs.msdn.com/cfs-file.ashx/__key/communityserver-blogs-components-weblogfiles/00-00-01-70-07-metablogapi/1423.AAD_5F00_APP_5F00_API_5F00_24CB4855.png"><img title="AAD_APP_API" style="border-left-width: 0px; border-right-width: 0px; background-image: none; border-bottom-width: 0px; float: left; padding-top: 0px; padding-left: 0px; display: inline; padding-right: 0px; border-top-width: 0px" border="0" alt="AAD_APP_API" src="https://msdnshared.blob.core.windows.net/media/MSDNBlogsFS/prod.evol.blogs.msdn.com/CommunityServer.Blogs.Components.WeblogFiles/00/00/01/70/07/metablogapi/5164.AAD_APP_API_thumb_2F8B305B.png" original-url="https://blogs.msdn.com/cfs-file.ashx/__key/communityserver-blogs-components-weblogfiles/00-00-01-70-07-metablogapi/5164.AAD_5F00_APP_5F00_API_5F00_thumb_5F00_2F8B305B.png" width="644" align="left" height="476" /></a> </li> </ol>  <blockquote>   <p>Vous noterez que le Client ID ci-dessus correspond bien au Client ID accessible à l’étape 3.</p> </blockquote>  <p><u>Remarques</u> :</p>  <ul>   <li>Si vous souhaitez enregistrer votre application dans un autre annuaire Azure AD, c’est tout à fait possible en configurant manuellement une nouvelle application dans l’annuaire Azure AD de votre choix depuis l’ancien portail puis en reportant le Client ID correspondant dans la section “Avancé” de l’étape 2 ci-dessus. Cette configuration manuelle est décrite <a href="https://azure.microsoft.com/en-us/documentation/articles/app-service-mobile-how-to-configure-active-directory-authentication/#advanced" target="_blank">ici</a>. Encore une fois, cette configuration d’authentification est d’une grande flexibilité. </li>    <li>Plus besoin de configurer l’API de passerelle </li> </ul>  <p>&#160;</p>  <p>Prochaine étape : enregistrer l’application Windows 10 UWP “Thot” dans Azure AD</p>  <h2>Enregistrement de l’application Doc.SearchApp dans Azure AD</h2>  <p>Comme nous n’utilisons plus de passerelle, il est indispensable d’enregistrer notre application native Windows 10 dans notre annuaire Azure AD afin qu’elle puisse continuer à accéder à l’API App “Doc.SearchAPI”. Pour cela rien de plus simple :</p>  <ol>   <li>Rendez vous sur <a href="https://manage.windowsazure.com" target="_blank">l’ancien portail Azure</a> </li>    <li>Sélectionnez votre annuaire, puis l’onglet <strong>Applications</strong>. Cliquez alors sur “Ajouter” tout en bas de la page afin de créer un nouvel enregistrement d’application </li>    <li>Optez pour “ajouter une application développée par ma société” :<a href="https://msdnshared.blob.core.windows.net/media/MSDNBlogsFS/prod.evol.blogs.msdn.com/CommunityServer.Blogs.Components.WeblogFiles/00/00/01/70/07/metablogapi/6648.AAD_Register_New_App_17F382E8.png" original-url="https://blogs.msdn.com/cfs-file.ashx/__key/communityserver-blogs-components-weblogfiles/00-00-01-70-07-metablogapi/6648.AAD_5F00_Register_5F00_New_5F00_App_5F00_17F382E8.png"><img title="AAD_Register_New_App" style="border-left-width: 0px; border-right-width: 0px; background-image: none; border-bottom-width: 0px; padding-top: 0px; padding-left: 0px; display: inline; padding-right: 0px; border-top-width: 0px" border="0" alt="AAD_Register_New_App" src="https://msdnshared.blob.core.windows.net/media/MSDNBlogsFS/prod.evol.blogs.msdn.com/CommunityServer.Blogs.Components.WeblogFiles/00/00/01/70/07/metablogapi/1754.AAD_Register_New_App_thumb_09B79AA9.png" original-url="https://blogs.msdn.com/cfs-file.ashx/__key/communityserver-blogs-components-weblogfiles/00-00-01-70-07-metablogapi/1754.AAD_5F00_Register_5F00_New_5F00_App_5F00_thumb_5F00_09B79AA9.png" width="628" height="484" /></a> </li>    <li>Donnez lui un nom, optez pour l’option “Application native” et cliquez sur suivant :<a href="https://msdnshared.blob.core.windows.net/media/MSDNBlogsFS/prod.evol.blogs.msdn.com/CommunityServer.Blogs.Components.WeblogFiles/00/00/01/70/07/metablogapi/7183.AAD_Register_New_App2_5271136D.png" original-url="https://blogs.msdn.com/cfs-file.ashx/__key/communityserver-blogs-components-weblogfiles/00-00-01-70-07-metablogapi/7183.AAD_5F00_Register_5F00_New_5F00_App2_5F00_5271136D.png"><img title="AAD_Register_New_App2" style="border-left-width: 0px; border-right-width: 0px; background-image: none; border-bottom-width: 0px; padding-top: 0px; padding-left: 0px; display: inline; padding-right: 0px; border-top-width: 0px" border="0" alt="AAD_Register_New_App2" src="https://msdnshared.blob.core.windows.net/media/MSDNBlogsFS/prod.evol.blogs.msdn.com/CommunityServer.Blogs.Components.WeblogFiles/00/00/01/70/07/metablogapi/4812.AAD_Register_New_App2_thumb_4B5467A6.png" original-url="https://blogs.msdn.com/cfs-file.ashx/__key/communityserver-blogs-components-weblogfiles/00-00-01-70-07-metablogapi/4812.AAD_5F00_Register_5F00_New_5F00_App2_5F00_thumb_5F00_4B5467A6.png" width="626" height="484" /></a> </li>    <li>Renseignez une URI de redirection (cette URI n’a pas besoin d’être une URI réelle : c’est juste un identifiant qu’il faudra impérativement réutiliser depuis votre application native) puis validez :<a href="https://msdnshared.blob.core.windows.net/media/MSDNBlogsFS/prod.evol.blogs.msdn.com/CommunityServer.Blogs.Components.WeblogFiles/00/00/01/70/07/metablogapi/1200.AAD_Register_New_App3_2D09B0B0.png" original-url="https://blogs.msdn.com/cfs-file.ashx/__key/communityserver-blogs-components-weblogfiles/00-00-01-70-07-metablogapi/1200.AAD_5F00_Register_5F00_New_5F00_App3_5F00_2D09B0B0.png"><img title="AAD_Register_New_App3" style="border-left-width: 0px; border-right-width: 0px; background-image: none; border-bottom-width: 0px; padding-top: 0px; padding-left: 0px; display: inline; padding-right: 0px; border-top-width: 0px" border="0" alt="AAD_Register_New_App3" src="https://msdnshared.blob.core.windows.net/media/MSDNBlogsFS/prod.evol.blogs.msdn.com/CommunityServer.Blogs.Components.WeblogFiles/00/00/01/70/07/metablogapi/0363.AAD_Register_New_App3_thumb_31168F33.png" original-url="https://blogs.msdn.com/cfs-file.ashx/__key/communityserver-blogs-components-weblogfiles/00-00-01-70-07-metablogapi/0363.AAD_5F00_Register_5F00_New_5F00_App3_5F00_thumb_5F00_31168F33.png" width="628" height="484" /></a> </li>    <li>Une fois l’application ajoutée, cliquez sur l’onglet <strong>Configurer</strong> et notez les champs <strong>Client ID</strong> et <strong>Redirect URIs</strong> (cette dernière devant correspondant à ce que vous avez saisi à l’étape 5) que vous reporterez plus tard dans le code de l’application universelle.<a href="https://msdnshared.blob.core.windows.net/media/MSDNBlogsFS/prod.evol.blogs.msdn.com/CommunityServer.Blogs.Components.WeblogFiles/00/00/01/70/07/metablogapi/7750.AAD_Register_New_App4_0EC18A6B.png" original-url="https://blogs.msdn.com/cfs-file.ashx/__key/communityserver-blogs-components-weblogfiles/00-00-01-70-07-metablogapi/7750.AAD_5F00_Register_5F00_New_5F00_App4_5F00_0EC18A6B.png"><img title="AAD_Register_New_App4" style="border-left-width: 0px; border-right-width: 0px; background-image: none; border-bottom-width: 0px; padding-top: 0px; padding-left: 0px; display: inline; padding-right: 0px; border-top-width: 0px" border="0" alt="AAD_Register_New_App4" src="https://msdnshared.blob.core.windows.net/media/MSDNBlogsFS/prod.evol.blogs.msdn.com/CommunityServer.Blogs.Components.WeblogFiles/00/00/01/70/07/metablogapi/2112.AAD_Register_New_App4_thumb_12CE68EE.png" original-url="https://blogs.msdn.com/cfs-file.ashx/__key/communityserver-blogs-components-weblogfiles/00-00-01-70-07-metablogapi/2112.AAD_5F00_Register_5F00_New_5F00_App4_5F00_thumb_5F00_12CE68EE.png" width="644" height="446" /></a> </li>    <li>Sur la même page, scrollez jusqu’en bas de page et cliquez sur le bouton “Ajouter une application” : s’ouvre alors la fenêtre suivante :<a href="https://msdnshared.blob.core.windows.net/media/MSDNBlogsFS/prod.evol.blogs.msdn.com/CommunityServer.Blogs.Components.WeblogFiles/00/00/01/70/07/metablogapi/3482.AAD_Register_New_App5_7FAD3C41.png" original-url="https://blogs.msdn.com/cfs-file.ashx/__key/communityserver-blogs-components-weblogfiles/00-00-01-70-07-metablogapi/3482.AAD_5F00_Register_5F00_New_5F00_App5_5F00_7FAD3C41.png"><img title="AAD_Register_New_App5" style="border-left-width: 0px; border-right-width: 0px; background-image: none; border-bottom-width: 0px; padding-top: 0px; padding-left: 0px; display: inline; padding-right: 0px; border-top-width: 0px" border="0" alt="AAD_Register_New_App5" src="https://msdnshared.blob.core.windows.net/media/MSDNBlogsFS/prod.evol.blogs.msdn.com/CommunityServer.Blogs.Components.WeblogFiles/00/00/01/70/07/metablogapi/4130.AAD_Register_New_App5_thumb_18AB9D38.png" original-url="https://blogs.msdn.com/cfs-file.ashx/__key/communityserver-blogs-components-weblogfiles/00-00-01-70-07-metablogapi/4130.AAD_5F00_Register_5F00_New_5F00_App5_5F00_thumb_5F00_18AB9D38.png" width="627" height="484" /></a> </li>    <li>Dans la fenêtre précédente, sélectionnez l’API App Doc.Search.API (sélectionnez “Affichez toutes les applications” au besoin), cliquez sur l’icône + puis validez </li>    <li>De retour sur la page principale de votre application, vous verrez alors une nouvelle permission accordée à votre application: la permission d’accéder à l’API Doc.Search.API. Attention : par défaut cette permission n’est pas active (le compteur “Delegated Permissions” est à 0) : pour l’activer dérouler la liste et cochez la case “Accès Doc.Search.API). Puis sauvegardez le tout. </li>    <li><a href="https://msdnshared.blob.core.windows.net/media/MSDNBlogsFS/prod.evol.blogs.msdn.com/CommunityServer.Blogs.Components.WeblogFiles/00/00/01/70/07/metablogapi/2538.AAD_Register_New_App6_539-1.png" original-url="https://blogs.msdn.com/cfs-file.ashx/__key/communityserver-blogs-components-weblogfiles/00-00-01-70-07-metablogapi/2538.AAD_5F00_Register_5F00_New_5F00_App6_5F00_5392D001.png"><img title="AAD_Register_New_App6" style="border-left-width: 0px; border-right-width: 0px; background-image: none; border-bottom-width: 0px; float: left; padding-top: 0px; padding-left: 0px; display: inline; padding-right: 0px; border-top-width: 0px" border="0" alt="AAD_Register_New_App6" src="https://msdnshared.blob.core.windows.net/media/MSDNBlogsFS/prod.evol.blogs.msdn.com/CommunityServer.Blogs.Components.WeblogFiles/00/00/01/70/07/metablogapi/1106.AAD_Register_New_App6_thumb_3A2D5D78.png" original-url="https://blogs.msdn.com/cfs-file.ashx/__key/communityserver-blogs-components-weblogfiles/00-00-01-70-07-metablogapi/1106.AAD_5F00_Register_5F00_New_5F00_App6_5F00_thumb_5F00_3A2D5D78.png" width="626" align="left" height="484" /></a> </li> </ol>  <p>&#160;</p>  <p>&#160;</p>  <p>&#160;</p>  <p>&#160;</p>  <p>&#160;</p>  <p>&#160;</p>  <p>&#160;</p>  <p>&#160;</p>  <p>&#160;</p>  <p>&#160;</p>  <p>&#160;</p>  <p>&#160;</p>  <p>Et voilà l’application universelle native est dorénavant autorisée à accéder à l’API app “Doc.Search.API” sous réserve que l’utilisateur soit bien référencé dans l’annuaire Azure AD.</p>  <p>Dernière étape : modifier l’application Windows 10 UWP “Thot” afin d’utiliser la librairie ADAL (Active Directory Authentification Library</p>  <h2>Evolution du code de l’application universelle Thot</h2>  <p>L’application universelle initiale utilisait une librairie dénommée <a href="https://www.nuget.org/packages/Microsoft.Azure.AppService" target="_blank">Microsoft Azure AppService SDK</a>. Cette librairie qui fonctionnait avec l’API de passerelle est aujourd’hui marquée comme obsolète (deprecated en anglais). Il nous faut donc impérativement remplacer ce SDK par une autre librairie nous permettant de réaliser l’authentification de l’utilisateur. C’est là qu’intervient la librairie d’authentification ADAL. Cette librairie a été implémentée <a href="https://github.com/AzureAD" target="_blank">pour différentes plateformes/langages</a> (iOS, Android, Web, Cordova etc). Par conséquent vous avez la possibilité d’appliquer cette solution pour une application native autre que Windows 10.</p>  <ol>   <li>Ajouter une référence à la librairie ADAL dans le projet d’application universelle Doc.Search.App. Pour cela, utiliser le gestionnaire de package nuget :<a href="https://msdnshared.blob.core.windows.net/media/MSDNBlogsFS/prod.evol.blogs.msdn.com/CommunityServer.Blogs.Components.WeblogFiles/00/00/01/70/07/metablogapi/1033.Update_Thot1_34DE76C7.png" original-url="https://blogs.msdn.com/cfs-file.ashx/__key/communityserver-blogs-components-weblogfiles/00-00-01-70-07-metablogapi/1033.Update_5F00_Thot1_5F00_34DE76C7.png"><img title="Update_Thot1" style="border-left-width: 0px; border-right-width: 0px; background-image: none; border-bottom-width: 0px; float: none; padding-top: 0px; padding-left: 0px; margin-left: auto; display: block; padding-right: 0px; border-top-width: 0px; margin-right: auto" border="0" alt="Update_Thot1" src="https://msdnshared.blob.core.windows.net/media/MSDNBlogsFS/prod.evol.blogs.msdn.com/CommunityServer.Blogs.Components.WeblogFiles/00/00/01/70/07/metablogapi/4212.Update_Thot1_thumb_2FFBC30B.png" original-url="https://blogs.msdn.com/cfs-file.ashx/__key/communityserver-blogs-components-weblogfiles/00-00-01-70-07-metablogapi/4212.Update_5F00_Thot1_5F00_thumb_5F00_2FFBC30B.png" width="429" height="484" /></a> </li>    <li>Ensuite voici la liste des fichiers à modifier par rapport au projet initial :      <ul>       <li>MainViewModel.cs </li>        <li>TokenExpiredHandler.cs </li>        <li>ThotSettings.cs </li>     </ul>   </li>    <li><strong>Fichier MainViewModel.cs</strong> : nous allons y définir l’URL du service d’authentification Azure AD, un jeton d’accès (Token)&#160; et nous allons instancier la librairie ADAL (objet AuthenticationContext) :<a href="https://msdnshared.blob.core.windows.net/media/MSDNBlogsFS/prod.evol.blogs.msdn.com/CommunityServer.Blogs.Components.WeblogFiles/00/00/01/70/07/metablogapi/4276.image_5D7F737F.png" original-url="https://blogs.msdn.com/cfs-file.ashx/__key/communityserver-blogs-components-weblogfiles/00-00-01-70-07-metablogapi/4276.image_5F00_5D7F737F.png"><img title="image" style="border-left-width: 0px; border-right-width: 0px; background-image: none; border-bottom-width: 0px; padding-top: 0px; padding-left: 0px; display: inline; padding-right: 0px; border-top-width: 0px" border="0" alt="image" src="https://msdnshared.blob.core.windows.net/media/MSDNBlogsFS/prod.evol.blogs.msdn.com/CommunityServer.Blogs.Components.WeblogFiles/00/00/01/70/07/metablogapi/2480.image_thumb_1C7384CC.png" original-url="https://blogs.msdn.com/cfs-file.ashx/__key/communityserver-blogs-components-weblogfiles/00-00-01-70-07-metablogapi/2480.image_5F00_thumb_5F00_1C7384CC.png" width="572" height="484" /></a> </li>    <li>Notez au passage la mise en commentaire de l’objet IAppServiceClient faisant parti du SDK Azure AppService, aujourd’hui déprécié. </li>    <li>Puis nous allons modifier le délégué de la gestion d’authentification pour déclencher l’authentification Azure AD de l’utilisateur via la méthode ADAL AcquireTokenAsync : en cas de succès nous renvoyons le jeton d’accès qui sera passé dans le header http de toute requête ultérieure :<a href="https://msdnshared.blob.core.windows.net/media/MSDNBlogsFS/prod.evol.blogs.msdn.com/CommunityServer.Blogs.Components.WeblogFiles/00/00/01/70/07/metablogapi/5873.image_402F3D17.png" original-url="https://blogs.msdn.com/cfs-file.ashx/__key/communityserver-blogs-components-weblogfiles/00-00-01-70-07-metablogapi/5873.image_5F00_402F3D17.png"><img title="image" style="border-left-width: 0px; border-right-width: 0px; background-image: none; border-bottom-width: 0px; padding-top: 0px; padding-left: 0px; display: inline; padding-right: 0px; border-top-width: 0px" border="0" alt="image" src="https://msdnshared.blob.core.windows.net/media/MSDNBlogsFS/prod.evol.blogs.msdn.com/CommunityServer.Blogs.Components.WeblogFiles/00/00/01/70/07/metablogapi/5504.image_thumb_503E0BCE.png" original-url="https://blogs.msdn.com/cfs-file.ashx/__key/communityserver-blogs-components-weblogfiles/00-00-01-70-07-metablogapi/5504.image_5F00_thumb_5F00_503E0BCE.png" width="644" height="339" /></a> </li>    <li><strong>Fichier TokenExpiredHandler.cs</strong> : nous allons modifier une seule méthode qui aura la responsabilité d’appeler l’API App en positionnant le jeton d’authentification (récupéré via le délégué d’authentification) dans le header http (propriété “Authorization”) de la requête web :<a href="https://msdnshared.blob.core.windows.net/media/MSDNBlogsFS/prod.evol.blogs.msdn.com/CommunityServer.Blogs.Components.WeblogFiles/00/00/01/70/07/metablogapi/7343.image_7B190091.png" original-url="https://blogs.msdn.com/cfs-file.ashx/__key/communityserver-blogs-components-weblogfiles/00-00-01-70-07-metablogapi/7343.image_5F00_7B190091.png"><img title="image" style="border-left-width: 0px; border-right-width: 0px; background-image: none; border-bottom-width: 0px; padding-top: 0px; padding-left: 0px; display: inline; padding-right: 0px; border-top-width: 0px" border="0" alt="image" src="https://msdnshared.blob.core.windows.net/media/MSDNBlogsFS/prod.evol.blogs.msdn.com/CommunityServer.Blogs.Components.WeblogFiles/00/00/01/70/07/metablogapi/5732.image_thumb_33C63B50.png" original-url="https://blogs.msdn.com/cfs-file.ashx/__key/communityserver-blogs-components-weblogfiles/00-00-01-70-07-metablogapi/5732.image_5F00_thumb_5F00_33C63B50.png" width="644" height="380" /></a> </li>    <li><strong>Fichier ThotSettings.cs</strong> : il contient un certain nombre de constantes correspondant aux identifiants AAD de l’application native (Client ID et Redirect URI), à l’URL de base de l’API App et aux identifiants du fournisseur d’identité AAD (URL d’authentification + identifiant du tenant AAD)<a href="https://msdnshared.blob.core.windows.net/media/MSDNBlogsFS/prod.evol.blogs.msdn.com/CommunityServer.Blogs.Components.WeblogFiles/00/00/01/70/07/metablogapi/3276.image_5781F39B.png" original-url="https://blogs.msdn.com/cfs-file.ashx/__key/communityserver-blogs-components-weblogfiles/00-00-01-70-07-metablogapi/3276.image_5F00_5781F39B.png"><img title="image" style="border-left-width: 0px; border-right-width: 0px; background-image: none; border-bottom-width: 0px; padding-top: 0px; padding-left: 0px; display: inline; padding-right: 0px; border-top-width: 0px" border="0" alt="image" src="https://msdnshared.blob.core.windows.net/media/MSDNBlogsFS/prod.evol.blogs.msdn.com/CommunityServer.Blogs.Components.WeblogFiles/00/00/01/70/07/metablogapi/2870.image_thumb_72BA4C9C.png" original-url="https://blogs.msdn.com/cfs-file.ashx/__key/communityserver-blogs-components-weblogfiles/00-00-01-70-07-metablogapi/2870.image_5F00_thumb_5F00_72BA4C9C.png" width="644" height="189" /></a> </li>    <li>En lançant l’application Thot, il nous est alors demander de nous authentifier avec notre compte Azure AD :<a href="https://msdnshared.blob.core.windows.net/media/MSDNBlogsFS/prod.evol.blogs.msdn.com/CommunityServer.Blogs.Components.WeblogFiles/00/00/01/70/07/metablogapi/7701.DemoThot_304A3B17.png" original-url="https://blogs.msdn.com/cfs-file.ashx/__key/communityserver-blogs-components-weblogfiles/00-00-01-70-07-metablogapi/7701.DemoThot_5F00_304A3B17.png"><img title="DemoThot" style="border-left-width: 0px; border-right-width: 0px; background-image: none; border-bottom-width: 0px; padding-top: 0px; padding-left: 0px; display: inline; padding-right: 0px; border-top-width: 0px" border="0" alt="DemoThot" src="https://msdnshared.blob.core.windows.net/media/MSDNBlogsFS/prod.evol.blogs.msdn.com/CommunityServer.Blogs.Components.WeblogFiles/00/00/01/70/07/metablogapi/6457.DemoThot_thumb_1D290E6B.png" original-url="https://blogs.msdn.com/cfs-file.ashx/__key/communityserver-blogs-components-weblogfiles/00-00-01-70-07-metablogapi/6457.DemoThot_5F00_thumb_5F00_1D290E6B.png" width="644" height="446" /></a> </li>    <li>Une fois authentifié, je peux alors faire une requête de recherche :<img alt="image" src="https://msdnshared.blob.core.windows.net/media/MSDNBlogsFS/prod.evol.blogs.msdn.com/CommunityServer.Blogs.Components.WeblogFiles/00/00/00/75/63/metablogapi/2818.image_thumb_43E5D554.png" original-url="https://blogs.msdn.com/cfs-file.ashx/__key/communityserver-blogs-components-weblogfiles/00-00-00-75-63-metablogapi/2818.image_5F00_thumb_5F00_43E5D554.png" width="640" height="277" /> </li> </ol>  <p>Et voilà : j’espère que cet article vous aura convaincu quant à la grande flexibilité et simplicité de ce nouveau modèle d’authentification des “Azure App Services” qui peut facilement s’appliquer à tout type de plateforme native ou web. En quelques clics + quelques lignes de codes, il est donc très simple de sécuriser l’accès à une API dans un contexte d’entreprise. Maintenant il est temps pour moi de discuter avec Stéphane car le bleu utilisé dans son application me pique un peu les yeux <img class="wlEmoticon wlEmoticon-winkingsmile" style="border-top-style: none; border-left-style: none; border-bottom-style: none; border-right-style: none" alt="Clignement d&#39;œil" src="https://msdnshared.blob.core.windows.net/media/MSDNBlogsFS/prod.evol.blogs.msdn.com/CommunityServer.Blogs.Components.WeblogFiles/00/00/01/70/07/metablogapi/8308.wlEmoticon-winkingsmile_08A64F9E.png" original-url="https://blogs.msdn.com/cfs-file.ashx/__key/communityserver-blogs-components-weblogfiles/00-00-01-70-07-metablogapi/8308.wlEmoticon_2D00_winkingsmile_5F00_08A64F9E.png" /></p>  <p>A bientôt pour de nouveaux articles autour d’Azure et Windows 10</p>]]></content:encoded>
    </item>
    <item>
      <title>Le Windows store pour les entreprises</title>
      <link>https://docs.microsoft.com/archive/blogs/ndelabarre/le-windows-store-pour-les-entreprises</link>
      <pubDate>Thu, 14 Jan 2016 09:37:47 GMT</pubDate>
      <dc:creator><![CDATA[Nicolas Delabarre]]></dc:creator>
      <guid
        isPermaLink="false">https://blogs.msdn.microsoft.com/ndelabarre/2016/01/14/le-windows-store-pour-les-entreprises/</guid>
      <description><![CDATA[Avec l’arrivée de Windows 10, Microsoft propose aux éditeurs de logiciels un nouveau canal de...]]></description>
      <content:encoded><![CDATA[<p align="justify">Avec l’arrivée de Windows 10, Microsoft propose aux éditeurs de logiciels un nouveau canal de distribution de leurs applications : le Windows store pour les entreprises (aussi dénommé « Windows Store for business » dans la langue de Shakespeare). L’objectif de cette plateforme est double :</p>  <p align="justify">1. Faciliter la relation « business » entre un éditeur et ses clients</p>  <p align="justify">2. Proposer aux organisations un moyen simple d’accès à des applications dites « métier » (aussi dénommées « LOB – Line O Business)</p>  <p align="justify">Comment cela fonctionne t-il ? C’est tout l’objectif de cet article <img class="wlEmoticon wlEmoticon-smile" style="border-top-style: none; border-left-style: none; border-bottom-style: none; border-right-style: none" alt="Sourire" src="https://msdnshared.blob.core.windows.net/media/MSDNBlogsFS/prod.evol.blogs.msdn.com/CommunityServer.Blogs.Components.WeblogFiles/00/00/01/70/07/metablogapi/0572.wlEmoticon-smile_235DBE52.png" original-url="https://blogs.msdn.com/cfs-file.ashx/__key/communityserver-blogs-components-weblogfiles/00-00-01-70-07-metablogapi/0572.wlEmoticon_2D00_smile_5F00_235DBE52.png" /></p>  <p><a href="https://msdnshared.blob.core.windows.net/media/MSDNBlogsFS/prod.evol.blogs.msdn.com/CommunityServer.Blogs.Components.WeblogFiles/00/00/01/70/07/metablogapi/8666.Store1_49BFA19D.png" original-url="https://blogs.msdn.com/cfs-file.ashx/__key/communityserver-blogs-components-weblogfiles/00-00-01-70-07-metablogapi/8666.Store1_5F00_49BFA19D.png"><img title="Store1" style="border-left-width: 0px; border-right-width: 0px; background-image: none; border-bottom-width: 0px; padding-top: 0px; padding-left: 0px; display: inline; padding-right: 0px; border-top-width: 0px" border="0" alt="Store1" src="https://msdnshared.blob.core.windows.net/media/MSDNBlogsFS/prod.evol.blogs.msdn.com/CommunityServer.Blogs.Components.WeblogFiles/00/00/01/70/07/metablogapi/8371.Store1_thumb_44734B9D.png" original-url="https://blogs.msdn.com/cfs-file.ashx/__key/communityserver-blogs-components-weblogfiles/00-00-01-70-07-metablogapi/8371.Store1_5F00_thumb_5F00_44734B9D.png" width="688" height="369" /></a></p>  <p align="justify">Ce schéma illustre les différents acteurs impliqués dans la distribution et l’utilisation d’applications modernes ainsi que les plateformes mises en œuvre pour faciliter ces actions.</p>  <h2>Rôles</h2>  <p align="justify">Nous distinguons 3 rôles :</p>  <p align="justify">1. L’éditeur de logiciel (aussi appelé ISV – Independent Software Vendor) dont un des objectifs est de vendre ses logiciels via un store d’application</p>  <p align="justify">2. L’administrateur IT d’une organisation dont un des rôles est de mettre à disposition des employés des logiciels dans le respect des politiques IT (sécurité, licence etc)</p>  <p align="justify">3. Les employés qui utilisent des logiciels depuis une machine (ordinateur, tablette ou smartphone) administrée par l’entreprise</p>  <h2>Point de vue « Employé »</h2>  <p align="justify">Un employé pourra selon les politiques de sécurité IT en vigueur, accéder au magasin public d’applications (Public store) et/ou accéder au magasin privé d’applications (Private Store). </p>  <p align="justify">Les prérequis logiciels et matériels sont les suivants :</p>  <ul>   <li>     <div align="justify">Disposer d’une machine sous Windows 10 (Obligatoire)</div>   </li>    <li>     <div align="justify">Disposer d’un compte Microsoft (MSA) pour accéder au store public [Optionnel]</div>   </li>    <li>     <div align="justify">Disposer d’un compte Azure Active Directory (AD) pour accéder au store privé [Optionnel]</div>   </li> </ul>  <p align="justify">&#160;</p>  <p><a href="https://msdnshared.blob.core.windows.net/media/MSDNBlogsFS/prod.evol.blogs.msdn.com/CommunityServer.Blogs.Components.WeblogFiles/00/00/01/70/07/metablogapi/5164.Store2_221E46D5.png" original-url="https://blogs.msdn.com/cfs-file.ashx/__key/communityserver-blogs-components-weblogfiles/00-00-01-70-07-metablogapi/5164.Store2_5F00_221E46D5.png"><img title="Store2" style="border-left-width: 0px; border-right-width: 0px; background-image: none; border-bottom-width: 0px; float: none; padding-top: 0px; padding-left: 0px; margin-left: auto; display: block; padding-right: 0px; border-top-width: 0px; margin-right: auto" border="0" alt="Store2" src="https://msdnshared.blob.core.windows.net/media/MSDNBlogsFS/prod.evol.blogs.msdn.com/CommunityServer.Blogs.Components.WeblogFiles/00/00/01/70/07/metablogapi/3465.Store2_thumb_760149E3.png" original-url="https://blogs.msdn.com/cfs-file.ashx/__key/communityserver-blogs-components-weblogfiles/00-00-01-70-07-metablogapi/3465.Store2_5F00_thumb_5F00_760149E3.png" width="521" height="551" /></a></p>  <p>L’accès aux applications se fera depuis l’application Store présente nativement aussi bien sur Windows 10 que Windows 10 mobile :</p>  <p><a href="https://msdnshared.blob.core.windows.net/media/MSDNBlogsFS/prod.evol.blogs.msdn.com/CommunityServer.Blogs.Components.WeblogFiles/00/00/01/70/07/metablogapi/6013.Store3_0EFFAADA.png" original-url="https://blogs.msdn.com/cfs-file.ashx/__key/communityserver-blogs-components-weblogfiles/00-00-01-70-07-metablogapi/6013.Store3_5F00_0EFFAADA.png"><img title="Store3" style="border-left-width: 0px; border-right-width: 0px; background-image: none; border-bottom-width: 0px; float: none; padding-top: 0px; padding-left: 0px; margin-left: auto; display: block; padding-right: 0px; border-top-width: 0px; margin-right: auto" border="0" alt="Store3" src="https://msdnshared.blob.core.windows.net/media/MSDNBlogsFS/prod.evol.blogs.msdn.com/CommunityServer.Blogs.Components.WeblogFiles/00/00/01/70/07/metablogapi/3225.Store3_thumb_526A3CED.png" original-url="https://blogs.msdn.com/cfs-file.ashx/__key/communityserver-blogs-components-weblogfiles/00-00-01-70-07-metablogapi/3225.Store3_5F00_thumb_5F00_526A3CED.png" width="657" height="344" /></a></p>  <p>Comme vous pouvez le constater sur l’illustration précédente, l’accès au store privé est bien intégré via la mise à disposition d’un nouvel onglet (ici « DemoZone9.com ») correspondant à l’identifiant unique de son organisation. A noter que ce store privé est accessible uniquement si l’employé est authentifié avec son compte Azure AD.</p>  <p>Et voici à quoi ressemble un store privé (lorsqu’on clique sur « DemoZone.9.com) :</p>  <p><a href="https://msdnshared.blob.core.windows.net/media/MSDNBlogsFS/prod.evol.blogs.msdn.com/CommunityServer.Blogs.Components.WeblogFiles/00/00/01/70/07/metablogapi/4237.Store4_4FC411ED.png" original-url="https://blogs.msdn.com/cfs-file.ashx/__key/communityserver-blogs-components-weblogfiles/00-00-01-70-07-metablogapi/4237.Store4_5F00_4FC411ED.png"><img title="Store4" style="border-left-width: 0px; border-right-width: 0px; background-image: none; border-bottom-width: 0px; padding-top: 0px; padding-left: 0px; display: inline; padding-right: 0px; border-top-width: 0px" border="0" alt="Store4" src="https://msdnshared.blob.core.windows.net/media/MSDNBlogsFS/prod.evol.blogs.msdn.com/CommunityServer.Blogs.Components.WeblogFiles/00/00/01/70/07/metablogapi/3731.Store4_thumb_14733CE0.png" original-url="https://blogs.msdn.com/cfs-file.ashx/__key/communityserver-blogs-components-weblogfiles/00-00-01-70-07-metablogapi/3731.Store4_5F00_thumb_5F00_14733CE0.png" width="687" height="322" /></a></p>  <p>Sont visibles ici deux catégories d’applications :</p>  <p>1. Les applications dites grand public (B2C)</p>  <p>2. Les applications dites « métier » (B2B) aussi appelées « LOB – Line Of Business » identifiables par le libellé « Propriétaire »</p>  <p>Les applications éligibles à la diffusion via le store privé sont :</p>  <ul>   <li>Les applications Windows 10 Universelles (UWP) </li>    <li>Les applications universelles Windows 8 et Windows Phone 8 </li> </ul>  <p>&#160;</p>  <p><u>Remarques</u></p>  <ul>   <li>Le contenu du store privé est défini et contrôlé par l’administrateur IT de l’organisation </li>    <li>L’onglet « DemoZone9.com » est visible et accessible uniquement par les employés de l’organisation </li>    <li>Les utilisateurs doivent s’authentifier avec leur compte Azure AD </li> </ul>  <p>&#160;</p>  <p><u>Démo</u></p>  <p>Vous trouverez <a href="https://1drv.ms/2024c0k" target="_blank">ici</a> une vidéo de démonstration du store privé </p>  <h2>Point de vue « Editeur/Développeur »</h2>  <p>Avec Windows 10 et le store pour les entreprises, un éditeur de logiciels peut désormais gérer le cycle de vie de ses applications métiers depuis l’interface de publication <a href="https://dev.windows.com/" target="_blank">Windows Dev Center</a>.</p>  <p><a href="https://msdnshared.blob.core.windows.net/media/MSDNBlogsFS/prod.evol.blogs.msdn.com/CommunityServer.Blogs.Components.WeblogFiles/00/00/01/70/07/metablogapi/4251.Store5_5679AC21.png" original-url="https://blogs.msdn.com/cfs-file.ashx/__key/communityserver-blogs-components-weblogfiles/00-00-01-70-07-metablogapi/4251.Store5_5F00_5679AC21.png"><img title="Store5" style="border-left-width: 0px; border-right-width: 0px; background-image: none; border-bottom-width: 0px; float: none; padding-top: 0px; padding-left: 0px; margin-left: auto; display: block; padding-right: 0px; border-top-width: 0px; margin-right: auto" border="0" alt="Store5" src="https://msdnshared.blob.core.windows.net/media/MSDNBlogsFS/prod.evol.blogs.msdn.com/CommunityServer.Blogs.Components.WeblogFiles/00/00/01/70/07/metablogapi/1440.Store5_thumb_1160DEEB.png" original-url="https://blogs.msdn.com/cfs-file.ashx/__key/communityserver-blogs-components-weblogfiles/00-00-01-70-07-metablogapi/1440.Store5_5F00_thumb_5F00_1160DEEB.png" width="519" height="551" /></a></p>  <p>Côté prérequis, l’éditeur doit simplement disposer d’un compte de développement Windows, compte individuel ou entreprise. Plus d’infos <a href="https://msdn.microsoft.com/fr-fr/library/windows/apps/jj863494.aspx" target="_blank">ici</a></p>  <p>Lors de la publication d’applications, un éditeur a désormais la possibilité de choisir le mode de gestion et distribution de licence :</p>  <p><a href="https://msdnshared.blob.core.windows.net/media/MSDNBlogsFS/prod.evol.blogs.msdn.com/CommunityServer.Blogs.Components.WeblogFiles/00/00/01/70/07/metablogapi/3531.Store6_1A50712A.png" original-url="https://blogs.msdn.com/cfs-file.ashx/__key/communityserver-blogs-components-weblogfiles/00-00-01-70-07-metablogapi/3531.Store6_5F00_1A50712A.png"><img title="Store6" style="border-left-width: 0px; border-right-width: 0px; background-image: none; border-bottom-width: 0px; padding-top: 0px; padding-left: 0px; display: inline; padding-right: 0px; border-top-width: 0px" border="0" alt="Store6" src="https://msdnshared.blob.core.windows.net/media/MSDNBlogsFS/prod.evol.blogs.msdn.com/CommunityServer.Blogs.Components.WeblogFiles/00/00/01/70/07/metablogapi/0755.Store6_thumb_42EEDD31.png" original-url="https://blogs.msdn.com/cfs-file.ashx/__key/communityserver-blogs-components-weblogfiles/00-00-01-70-07-metablogapi/0755.Store6_5F00_thumb_5F00_42EEDD31.png" width="696" height="258" /></a></p>  <h3>Licence en ligne (Online)</h3>  <p align="justify">C’est le modèle sélectionné par défaut permettant&#160; :</p>  <ol>   <li>     <div align="justify">aux applications d’un éditeur d’être visibles dans le store pour entreprises. </div>   </li>    <li>     <div align="justify">de gérer les licences automatiquement : en effet dans ce mode, la validation de licence est gérée par le Store Microsoft de manière similaire aux applications publiques.</div>   </li> </ol>  <p align="justify">&#160;</p>  <p align="justify">Une conséquence est que les employés d’une organisation ayant fait l’acquisition d’une application en mode online ne pourront y accéder que depuis un équipement (smartphone, tablette ou PC) connecté au store Windows, connexion indispensable pour l’acquisition de l’application et de sa licence associée.&#160; Cela signifie que l’organisation ayant fait l’acquisition ne peut accéder physiquement à l’application et sa licence. Elle pourra toutefois contrôler le déploiement sur son parc.</p>  <h3 align="justify">License hors-ligne (Offline)</h3>  <p>Ce mode n’est pas activé par défaut : les développeurs doivent explicitement cocher l’opt-in correspondant qui permettra aux entreprises clientes de télécharger les licences et applications pour les déployer dans leur infrastructure IT. Quelques conséquences directes liées à ce mode :</p>  <ul>   <li>Aucune connexion au store Windows n’est requise pour la flotte entreprise : autrement dit il est possible d’opérer un mode de déploiement de type side-loading. </li>    <li>La gestion des licences des applications acquises est à charge des entreprises comme pour une gestion de logiciels traditionnelle </li>    <li>L’accès aux applications à licence hors-ligne ne nécessite pas de comptes Azure AD pour les employés </li>    <li>Le déploiement peut être réalisé via des outils de gestion (SCCM, MDM, autres) </li> </ul>  <p>&#160;</p>  <p><u>Remarques</u> </p>  <ul>   <li>Si aucune option de licence n’est sélectionnée, les applications correspondantes seront uniquement disponibles sur le store grand public. </li>    <li>     <div align="justify">Il est possible de sélectionner les deux modes de licence en parallèle</div>   </li> </ul>  <p align="justify">&#160;</p>  <h3 align="justify">Application métier (LOB – Line Of Business)</h3>  <p align="justify">La question en suspens est de savoir comment faire en sorte qu’une application métier ne soit visible que pour un client unique. Comme nous le verrons en troisième partie de cet article (Point de vue de l’administrateur IT d’une organisation), un administrateur IT pourra configurer depuis l’interface du “store entreprises” les éditeurs reconnus officiellement :</p>  <p align="justify"><a href="https://msdnshared.blob.core.windows.net/media/MSDNBlogsFS/prod.evol.blogs.msdn.com/CommunityServer.Blogs.Components.WeblogFiles/00/00/01/70/07/metablogapi/0876.image_24A4263B.png" original-url="https://blogs.msdn.com/cfs-file.ashx/__key/communityserver-blogs-components-weblogfiles/00-00-01-70-07-metablogapi/0876.image_5F00_24A4263B.png"><img title="image" style="border-left-width: 0px; border-right-width: 0px; background-image: none; border-bottom-width: 0px; padding-top: 0px; padding-left: 0px; display: inline; padding-right: 0px; border-top-width: 0px" border="0" alt="image" src="https://msdnshared.blob.core.windows.net/media/MSDNBlogsFS/prod.evol.blogs.msdn.com/CommunityServer.Blogs.Components.WeblogFiles/00/00/01/70/07/metablogapi/2476.image_thumb_1021676E.png" original-url="https://blogs.msdn.com/cfs-file.ashx/__key/communityserver-blogs-components-weblogfiles/00-00-01-70-07-metablogapi/2476.image_5F00_thumb_5F00_1021676E.png" width="744" height="251" /></a></p>  <p align="justify">Une fois que l’administrateur IT vous aura ajouté dans sa liste d’éditeurs de confiance, vous recevrez une demande d’acceptation par email :</p>  <p align="justify"><a href="https://msdnshared.blob.core.windows.net/media/MSDNBlogsFS/prod.evol.blogs.msdn.com/CommunityServer.Blogs.Components.WeblogFiles/00/00/01/70/07/metablogapi/6521.Store8_0B3EB3B2.png" original-url="https://blogs.msdn.com/cfs-file.ashx/__key/communityserver-blogs-components-weblogfiles/00-00-01-70-07-metablogapi/6521.Store8_5F00_0B3EB3B2.png"><img title="Store8" style="border-left-width: 0px; border-right-width: 0px; background-image: none; border-bottom-width: 0px; padding-top: 0px; padding-left: 0px; display: inline; padding-right: 0px; border-top-width: 0px" border="0" alt="Store8" src="https://msdnshared.blob.core.windows.net/media/MSDNBlogsFS/prod.evol.blogs.msdn.com/CommunityServer.Blogs.Components.WeblogFiles/00/00/01/70/07/metablogapi/4314.Store8_thumb_1AE14F74.png" original-url="https://blogs.msdn.com/cfs-file.ashx/__key/communityserver-blogs-components-weblogfiles/00-00-01-70-07-metablogapi/4314.Store8_5F00_thumb_5F00_1AE14F74.png" width="590" height="482" /></a></p>  <p align="justify">En vous rendant sur votre interface de notification …</p>  <p align="justify"><a href="https://msdnshared.blob.core.windows.net/media/MSDNBlogsFS/prod.evol.blogs.msdn.com/CommunityServer.Blogs.Components.WeblogFiles/00/00/01/70/07/metablogapi/3733.Store9_15FE9BB8.png" original-url="https://blogs.msdn.com/cfs-file.ashx/__key/communityserver-blogs-components-weblogfiles/00-00-01-70-07-metablogapi/3733.Store9_5F00_15FE9BB8.png"><img title="Store9" style="border-left-width: 0px; border-right-width: 0px; background-image: none; border-bottom-width: 0px; padding-top: 0px; padding-left: 0px; display: inline; padding-right: 0px; border-top-width: 0px" border="0" alt="Store9" src="https://msdnshared.blob.core.windows.net/media/MSDNBlogsFS/prod.evol.blogs.msdn.com/CommunityServer.Blogs.Components.WeblogFiles/00/00/01/70/07/metablogapi/7571.Store9_thumb_5322573D.png" original-url="https://blogs.msdn.com/cfs-file.ashx/__key/communityserver-blogs-components-weblogfiles/00-00-01-70-07-metablogapi/7571.Store9_5F00_thumb_5F00_5322573D.png" width="717" height="328" /></a></p>  <p align="justify">… vous pourrez alors accepter la demande de mise en relation. Une fois la demande acceptée, vous pourrez soumettre une application métier à destination de l’entreprise pour laquelle vous aurez accepter la mise en relation. Dans la section “Distribution et visibilité”, vous pourrez sélectionner “Distribution métier (LOB)”. Apparaitra alors les comptes clients pour lesquelles vous pourrez publier une application privée :</p>  <p><a href="https://msdnshared.blob.core.windows.net/media/MSDNBlogsFS/prod.evol.blogs.msdn.com/CommunityServer.Blogs.Components.WeblogFiles/00/00/01/70/07/metablogapi/2577.Store10_7C2CF639.png" original-url="https://blogs.msdn.com/cfs-file.ashx/__key/communityserver-blogs-components-weblogfiles/00-00-01-70-07-metablogapi/2577.Store10_5F00_7C2CF639.png"><img title="Store10" style="border-top: 0px; border-right: 0px; background-image: none; border-bottom: 0px; padding-top: 0px; padding-left: 0px; border-left: 0px; display: inline; padding-right: 0px" border="0" alt="Store10" src="https://msdnshared.blob.core.windows.net/media/MSDNBlogsFS/prod.evol.blogs.msdn.com/CommunityServer.Blogs.Components.WeblogFiles/00/00/01/70/07/metablogapi/2273.Store10_thumb_791A9844.png" original-url="https://blogs.msdn.com/cfs-file.ashx/__key/communityserver-blogs-components-weblogfiles/00-00-01-70-07-metablogapi/2273.Store10_5F00_thumb_5F00_791A9844.png" width="716" height="344" /></a></p>  <p><u>Remarques</u></p>  <ul>   <li>il est possible de distribuer la même application LOB à différentes entreprises</li>    <li>Une application LOB est soumise à validation Microsoft. A ce titre elle doit respecter les <a href="https://msdn.microsoft.com/en-us/library/windows/apps/dn764944.aspx" target="_blank">Windows Store Policies</a></li>    <li>La certification est pris en charge par Microsoft</li>    <li>Il est possible de faire un déploiement d’application LOB en mode side-loading</li> </ul>  <p>&#160;</p>  <p><u>Démo</u></p>  <p>Vous trouverez <a href="https://1drv.ms/1ORi4qp" target="_blank">ici</a> une vidéo démontrant la publication d’une application LOB</p>  <h2>Point de vue « Administrateur IT d’une organisation »</h2>  <p align="justify">Jusqu’ici nous avons vu :</p>  <ol>   <li>     <div align="justify">comment un employé d’une organisation pouvait accéder à une application métier depuis un store privé</div>   </li>    <li>     <div align="justify">comment un éditeur de logiciel pouvait vendre et distribuer une application métier à destination d’une organisation</div>   </li> </ol>  <p align="justify">&#160;</p>  <p align="justify">Reste donc à voir comment tout cela est administré au niveau d’une organisation. C’est là qu’intervient le “Windows Store pour les entreprises” qui peut se définir comme un portail web d’administration d’applications accessibles depuis l’url suivante : <a href="https://businessstore.microsoft.com">https://businessstore.microsoft.com</a> </p>  <p><a href="https://msdnshared.blob.core.windows.net/media/MSDNBlogsFS/prod.evol.blogs.msdn.com/CommunityServer.Blogs.Components.WeblogFiles/00/00/01/70/07/metablogapi/4555.image_76746D44.png" original-url="https://blogs.msdn.com/cfs-file.ashx/__key/communityserver-blogs-components-weblogfiles/00-00-01-70-07-metablogapi/4555.image_5F00_76746D44.png"><img title="image" style="border-top: 0px; border-right: 0px; background-image: none; border-bottom: 0px; padding-top: 0px; padding-left: 0px; border-left: 0px; display: inline; padding-right: 0px" border="0" alt="image" src="https://msdnshared.blob.core.windows.net/media/MSDNBlogsFS/prod.evol.blogs.msdn.com/CommunityServer.Blogs.Components.WeblogFiles/00/00/01/70/07/metablogapi/6710.image_thumb_30F1FDCA.png" original-url="https://blogs.msdn.com/cfs-file.ashx/__key/communityserver-blogs-components-weblogfiles/00-00-01-70-07-metablogapi/6710.image_5F00_thumb_5F00_30F1FDCA.png" width="674" height="432" /></a></p>  <p>Le “Windows Store pour les entreprises” permet notamment de :</p>  <ul>   <li>Gérer un catalogue d’applications publiques et/ou privées pour les employés d’une organisation</li>    <li>Faire l’acquisition d’applications en volume de licence</li>    <li>Configurer le mode de distribution/déploiement</li>    <li>Gérer des rôles d’utilisateurs pour l’accès au store pour les entreprises</li> </ul>  <p>&#160;</p>  <h3><a href="https://msdnshared.blob.core.windows.net/media/MSDNBlogsFS/prod.evol.blogs.msdn.com/CommunityServer.Blogs.Components.WeblogFiles/00/00/01/70/07/metablogapi/7651.Store11_4DFAAC92.png" original-url="https://blogs.msdn.com/cfs-file.ashx/__key/communityserver-blogs-components-weblogfiles/00-00-01-70-07-metablogapi/7651.Store11_5F00_4DFAAC92.png"><img title="Store11" style="border-top: 0px; border-right: 0px; background-image: none; border-bottom: 0px; float: none; padding-top: 0px; padding-left: 0px; margin-left: auto; border-left: 0px; display: block; padding-right: 0px; margin-right: auto" border="0" alt="Store11" src="https://msdnshared.blob.core.windows.net/media/MSDNBlogsFS/prod.evol.blogs.msdn.com/CommunityServer.Blogs.Components.WeblogFiles/00/00/01/70/07/metablogapi/1234.Store11_thumb_5E097B49.png" original-url="https://blogs.msdn.com/cfs-file.ashx/__key/communityserver-blogs-components-weblogfiles/00-00-01-70-07-metablogapi/1234.Store11_5F00_thumb_5F00_5E097B49.png" width="553" height="584" /></a></h3>  <p>En prérequis, une organisation devra disposer :</p>  <ul>   <li>d’un compte d’accès au “Windows Store pour Entreprises”</li>    <li>une flotte d’équipements sous Windows 10 (PC, tablette ou smartphone)</li> </ul>  <p>&#160;</p>  <h3>Inscription au “Windows Store pour Entreprises”</h3>  <p>Lorsque vous vous connecterez au “Windows Store pour Entreprises” pour la première fois, on vous demandera soit de vous inscrire soit de vous connecter avec un compte Azure Active Directory <img class="wlEmoticon wlEmoticon-star" style="border-top-style: none; border-left-style: none; border-bottom-style: none; border-right-style: none" alt="Étoile" src="https://msdnshared.blob.core.windows.net/media/MSDNBlogsFS/prod.evol.blogs.msdn.com/CommunityServer.Blogs.Components.WeblogFiles/00/00/01/70/07/metablogapi/8688.wlEmoticon-star_7FF4DDCD.png" original-url="https://blogs.msdn.com/cfs-file.ashx/__key/communityserver-blogs-components-weblogfiles/00-00-01-70-07-metablogapi/8688.wlEmoticon_2D00_star_5F00_7FF4DDCD.png" /> :</p>  <p><a href="https://msdnshared.blob.core.windows.net/media/MSDNBlogsFS/prod.evol.blogs.msdn.com/CommunityServer.Blogs.Components.WeblogFiles/00/00/01/70/07/metablogapi/7522.Store12_5AF71D54.png" original-url="https://blogs.msdn.com/cfs-file.ashx/__key/communityserver-blogs-components-weblogfiles/00-00-01-70-07-metablogapi/7522.Store12_5F00_5AF71D54.png"><img title="Store12" style="border-top: 0px; border-right: 0px; background-image: none; border-bottom: 0px; padding-top: 0px; padding-left: 0px; border-left: 0px; display: inline; padding-right: 0px" border="0" alt="Store12" src="https://msdnshared.blob.core.windows.net/media/MSDNBlogsFS/prod.evol.blogs.msdn.com/CommunityServer.Blogs.Components.WeblogFiles/00/00/01/70/07/metablogapi/2211.Store12_thumb_4A7EAC59.png" original-url="https://blogs.msdn.com/cfs-file.ashx/__key/communityserver-blogs-components-weblogfiles/00-00-01-70-07-metablogapi/2211.Store12_5F00_thumb_5F00_4A7EAC59.png" width="689" height="238" /></a></p>  <p>La procédure complète est très bien documentée <a href="https://technet.microsoft.com/en-us/library/mt621274(v=vs.85).aspx" target="_blank">ici</a> </p>  <p><img class="wlEmoticon wlEmoticon-star" style="border-top-style: none; border-left-style: none; border-bottom-style: none; border-right-style: none" alt="Étoile" src="https://msdnshared.blob.core.windows.net/media/MSDNBlogsFS/prod.evol.blogs.msdn.com/CommunityServer.Blogs.Components.WeblogFiles/00/00/01/70/07/metablogapi/8688.wlEmoticon-star_7FF4DDCD.png" original-url="https://blogs.msdn.com/cfs-file.ashx/__key/communityserver-blogs-components-weblogfiles/00-00-01-70-07-metablogapi/8688.wlEmoticon_2D00_star_5F00_7FF4DDCD.png" /> Si vous possédez un tenant Office365, vous disposez déjà d’un compte Azure AD que vous pouvez réutiliser pour l’accès au Windows Store pour Entreprises.</p>  <h3>Utilisation du Windows Store pour Entreprises</h3>  <p>Voici les différentes actions que vous pouvez réaliser depuis cette interface :</p>  <ul>   <li>Gérer un inventaire d’applications publiques (B2C) et privées (LOB)</li>    <ul>     <li>Faire l’acquisition d’applications B2C et LOB</li>      <li>Gestion de licence (achat, affectation/récupération)</li>   </ul>    <li>Gérer la distribution de ces applications au sein de votre organisation</li>    <ul>     <li>Store privé (mode connecté)</li>      <li>Affectation nominative (mode connecté)</li>      <li>Side-loading</li>   </ul>    <li>Gérer les <u>utilisateurs avancés </u>ayant accès au Windows Store pour Entreprises</li>    <li>Gérer les outils de déploiement d’applications (MDM, SCCM)</li>    <li>Gérer les éditeurs (ISV) d’applications LOB</li> </ul>  <p>&#160;</p>  <p>Voici un exemple d’inventaire d’entreprises :</p>  <p><a href="https://msdnshared.blob.core.windows.net/media/MSDNBlogsFS/prod.evol.blogs.msdn.com/CommunityServer.Blogs.Components.WeblogFiles/00/00/01/70/07/metablogapi/6136.Store14_4AAF5DE9.png" original-url="https://blogs.msdn.com/cfs-file.ashx/__key/communityserver-blogs-components-weblogfiles/00-00-01-70-07-metablogapi/6136.Store14_5F00_4AAF5DE9.png"><img title="Store14" style="border-top: 0px; border-right: 0px; background-image: none; border-bottom: 0px; padding-top: 0px; padding-left: 0px; border-left: 0px; display: inline; padding-right: 0px" border="0" alt="Store14" src="https://msdnshared.blob.core.windows.net/media/MSDNBlogsFS/prod.evol.blogs.msdn.com/CommunityServer.Blogs.Components.WeblogFiles/00/00/01/70/07/metablogapi/4578.Store14_thumb_49591BEF.png" original-url="https://blogs.msdn.com/cfs-file.ashx/__key/communityserver-blogs-components-weblogfiles/00-00-01-70-07-metablogapi/4578.Store14_5F00_thumb_5F00_49591BEF.png" width="754" height="471" /></a></p>          <h4>&#160;</h4>  <h4>Distribution</h4>  <p>La distribution d’applications peut être réalisée selon deux canaux :</p>  <ul>   <li>Via le store privé</li>    <ul>     <li>L’administrateur gère un inventaire ou catalogue d’applications</li>      <li>Les applications de ce catalogue sont visibles uniquement par les employés de l’organisation</li>      <li>Les employés doivent s’authentifier avec leur compte Azure AD</li>      <li>Seules les applications en mode de Licence Online sont accessibles depuis le store privé</li>      <li>A tout moment l’administrateur peut récupérer des licences </li>   </ul>    <li>Distribution Nominative </li>    <ul>     <li>L’administrateur assigne une application à un utilisateur donné</li>      <li>Seules les applications en mode de Licence Online sont accessibles</li>      <li>Les utilisateurs doivent s’authentifier avec leur compte Azure AD</li>      <li>Possibilité de récupérer les licences depuis le portail Windows Store pour entreprises</li>   </ul> </ul>  <p>&#160;</p>  <p>Dans l’exemple ci-dessous, l’application LOB DemoZone9.com est disponible dans le store privé et a été installée par deux employés :</p>  <p><a href="https://msdnshared.blob.core.windows.net/media/MSDNBlogsFS/prod.evol.blogs.msdn.com/CommunityServer.Blogs.Components.WeblogFiles/00/00/01/70/07/metablogapi/2604.Store15_20E64BA9.png" original-url="https://blogs.msdn.com/cfs-file.ashx/__key/communityserver-blogs-components-weblogfiles/00-00-01-70-07-metablogapi/2604.Store15_5F00_20E64BA9.png"><img title="Store15" style="border-top: 0px; border-right: 0px; background-image: none; border-bottom: 0px; padding-top: 0px; padding-left: 0px; border-left: 0px; display: inline; padding-right: 0px" border="0" alt="Store15" src="https://msdnshared.blob.core.windows.net/media/MSDNBlogsFS/prod.evol.blogs.msdn.com/CommunityServer.Blogs.Components.WeblogFiles/00/00/01/70/07/metablogapi/8625.Store15_thumb_50A3F428.png" original-url="https://blogs.msdn.com/cfs-file.ashx/__key/communityserver-blogs-components-weblogfiles/00-00-01-70-07-metablogapi/8625.Store15_5F00_thumb_5F00_50A3F428.png" width="643" height="671" /></a></p>  <p>Dans cet autre exemple, nous pouvons télécharger une application (package, licence et métadonnées) dont la licence est “hors-ligne” :</p>  <p><a href="https://msdnshared.blob.core.windows.net/media/MSDNBlogsFS/prod.evol.blogs.msdn.com/CommunityServer.Blogs.Components.WeblogFiles/00/00/01/70/07/metablogapi/3731.Store16_7FF569B2.png" original-url="https://blogs.msdn.com/cfs-file.ashx/__key/communityserver-blogs-components-weblogfiles/00-00-01-70-07-metablogapi/3731.Store16_5F00_7FF569B2.png"><img title="Store16" style="border-top: 0px; border-right: 0px; background-image: none; border-bottom: 0px; padding-top: 0px; padding-left: 0px; border-left: 0px; display: inline; padding-right: 0px" border="0" alt="Store16" src="https://msdnshared.blob.core.windows.net/media/MSDNBlogsFS/prod.evol.blogs.msdn.com/CommunityServer.Blogs.Components.WeblogFiles/00/00/01/70/07/metablogapi/1512.Store16_thumb_68C9EF34.png" original-url="https://blogs.msdn.com/cfs-file.ashx/__key/communityserver-blogs-components-weblogfiles/00-00-01-70-07-metablogapi/1512.Store16_5F00_thumb_5F00_68C9EF34.png" width="719" height="878" /></a></p>  <h4>Services Windows Store </h4>  <ul>   <li>Le Windows Store pour Entreprises expose une API accessible aux outils de Management (MDM, SSCM )</li>    <li>Permet la synchronisation des applications achetées et leur mise-à-jour</li>    <li>Les Meta-données (App Details, Icons), packages (offline), et Licences (offline) sont synchronisées</li>    <li>Les applications à licence “Offline” sont téléchargeables depuis le portail du Windows Store pour Entreprises </li> </ul>  <p>&#160;</p>  <p>Vous trouverez plus d’information sur cette API <a href="https://msdn.microsoft.com/en-us/library/windows/hardware/mt608307(v=vs.85).aspx" target="_blank">ici</a></p>  <h4>Configuration des outils de Management</h4>  <ul>   <li>Ces outils doivent être enregistrés en temps qu’applications Azure AD</li>    <li>Ces outils doivent également être configurés dans le portail Windows Store pour Entreprises </li>    <li>Azure AD requis pour l’authentification des ces outils auprès des services du Windows Store pour Entreprises </li> </ul>  <p><u></u></p>  <p><u>Démo</u></p>  <p>Vous trouverez <a href="https://1drv.ms/231Zouj" target="_blank">ici</a> une vidéo démontrant l’accès au Windows Store pour Entreprises</p>  <h2>FAQ</h2>  <p><u>Azure Active Directory est-il requis pour utiliser le Windows Store&#160; pour Entreprises ?</u></p>  <ul>   <li>Azure AD est requis pour l’enregistrement au Windows Store pour Entreprises et l’achat d’applications </li>    <ul>     <li>Uniquement pour les IT Pro.</li>   </ul>    <li>Azure AD est requis pour l’installation depuis le store privé. </li>    <ul>     <li>Tous les employés de l’organisation.</li>   </ul>    <li>Azure AD non requis pour les applications installées en mode hors-ligne. </li> </ul>  <p>&#160;</p>  <p><u>Puis-je installer/déployer mes applications sans passer par le store ?</u></p>  <p>Oui : déverrouillage des devices et déploiement d’applications signées par votre organisation est toujours possible. Voir <a href="https://technet.microsoft.com/library/mt269549.aspx" target="_blank">ce lien</a> pour plus d’infos. Néanmoins le store privé présente une alternative possible</p>  <p><u>Ai-je besoin d’un serveur de management pour gérer mes applications ?</u></p>  <p>Non, le cycle de vie des applications peut être géré différemment (par script, DISM ou encore du <a href="https://msdn.microsoft.com/en-us/library/windows/hardware/dn916107(v=vs.85).aspx" target="_blank">provisioning à l’execution</a>)</p>  <h2>Ressources</h2>  <p>Voici un ensemble de liens pour en savoir plus :</p>  <ul>   <li><a href="https://businessstore.microsoft.com/en-us/Store/Apps/" target="_blank">Accès</a> au Windows Store pour Entreprises : </li>    <li>Documentation <a href="https://technet.microsoft.com/en-us/library/mt606938(v=vs.85).aspx" target="_blank">MSDN</a> </li>    <li>Session Ignite 2015 sur le <a href="https://channel9.msdn.com/Events/Ignite/2015/BRK3338" target="_blank">Windows Store pour Entreprises</a> </li> </ul>]]></content:encoded>
    </item>
    <item>
      <title>Gestion de package appx avec les outils en ligne de commande du SDK de développement Windows</title>
      <link>https://docs.microsoft.com/archive/blogs/ndelabarre/gestion-de-package-appx-avec-les-outils-en-ligne-de-commande-du-sdk-de-dveloppement-windows</link>
      <pubDate>Tue, 29 Sep 2015 05:03:41 GMT</pubDate>
      <dc:creator><![CDATA[Nicolas Delabarre]]></dc:creator>
      <guid
        isPermaLink="false">https://blogs.msdn.microsoft.com/ndelabarre/2015/09/29/gestion-de-package-appx-avec-les-outils-en-ligne-de-commande-du-sdk-de-dveloppement-windows/</guid>
      <description><![CDATA[Pour les connaisseurs, vous me direz qu’il est possible d’utiliser le designer de package sous...]]></description>
      <content:encoded><![CDATA[<p>Pour les connaisseurs, vous me direz qu’il est possible d’utiliser le designer de package sous Visual Studio qui est très bien documenté dans la documentation <a href="https://msdn.microsoft.com/en-us/library/hh454036.aspx" target="_blank">MSDN</a>. Et vous avez tout à fait raison. Mais voilà, récemment j’ai été confronté à un bug de Visual Studio 2015 concernant ce fameux designer, bug en cours de correctif. Malheureusement le cycle de développement d’un projet est rarement calé sur le cycle de développement d’un outil. Il faut donc trouver une solution de contournement. </p>  <p>Sans trop rentrer dans les détails de ce bug, je vais quand même vous expliquez comment j’en suis arrivé à devoir générer mon package appx à la main. Il se trouve que le fameux designer de package dont le rôle est de générer un package prêt à être publié sur le Windows Store va modifier à la volée le fichier Package.appxmanifest afin par exemple d’y ajouter des métadonnées. Jusque-là rien de neuf sous le soleil. Le problème est apparu lorsque j’ai souhaité utiliser Cortana et ajouté au fichier manifest l’extension suivante afin de pouvoir lancer mon application depuis Cortana :</p>  <pre style="font-family: consolas; background: white; color: black"><span style="color: blue">&lt;</span><span style="color: #a31515">uap:Extension</span><span style="color: blue">&#160;</span><span style="color: red">Category</span><span style="color: blue">=</span>&quot;<span style="color: blue">windows.personalAssistantLaunch</span>&quot;<span style="color: blue">/&gt;</span></pre>

<p>A chaque fois que je souhaitais créer un package pour le distribuer à un client via le designer de package :</p>

<p><img title="Context menu then click Store-&gt;Create App Packages" alt="Context menu then click Store-&gt;Create App Packages" src="https://i-msdn.sec.s-msft.com/dynimg/IC814382.jpeg" width="603" height="480" /></p>

<p>… l’extension précédente était systématiquement effacer du fichier manifest !!! Plutôt embêtant pour faire valider à mon client une fonctionnalité clef de mon application. Du coup j’ai cherché un moyen de pouvoir générer un package différemment. J’ai pour cela identifié deux scénarios possibles.</p>

<h1><font color="#4bacc6">Scénario 1 : Modifier le package Appx généré par VS2015</font></h1>

<p>Je suis parti du package appx généré par Visual Studio (package contenant le fichier manifest dont l’extension “windows.personalAssistantLaunch” a été effacé par erreur) et j’ai réalisé les actions suivantes :</p>

<ul>
  <li>dézipper le package (en effet un fichier appx n’est qu’un fichier d’archive compressé) </li>

  <li>localiser et éditer le fichier manifest dénommé AppxManifest.xml en y ajoutant la fameuse extension manquante </li>

  <li>rezipper le package </li>

  <li>générer un certificat local de signature de code </li>

  <li>signer le package avec le certificat de signature </li>
</ul>

<p>Pour cela j’ai utilisé les utilitaires disponibles dans le Windows Software Development Kit (SDK) for Windows 10 localisés dans les répertoires suivants :</p>

<p><font face="Courier New">C:\Program Files (x86)\Windows Kits\10\bin\x86</font></p>

<p><font face="Courier New">C:\Program Files (x86)\Windows Kits\10\bin\x64</font></p>

<p><font face="Courier New">C:\Program Files (x86)\Windows Kits\10\bin\arm</font></p>

<p>Dans mon cas je vais générer un fichier appx pour cible desktop (x86). Pensez à modifier votre répertoire si vous souhaitez cibler un jeu d’instructions ARM pour windows phone. Pensez également à ajouter le répertoire “bin” correspondant dans votre variable d’environnement PATH afin de simplifier la saisie de commande. Le répertoire contenant mon fichier appx généré par Visual Studio est le suivant :</p>

<p><a href="https://msdnshared.blob.core.windows.net/media/MSDNBlogsFS/prod.evol.blogs.msdn.com/CommunityServer.Blogs.Components.WeblogFiles/00/00/01/70/07/metablogapi/5875.image_5978CC8E.png" original-url="https://blogs.msdn.com/cfs-file.ashx/__key/communityserver-blogs-components-weblogfiles/00-00-01-70-07-metablogapi/5875.image_5F00_5978CC8E.png"><img title="image" style="border-left-width: 0px; border-right-width: 0px; background-image: none; border-bottom-width: 0px; padding-top: 0px; padding-left: 0px; display: inline; padding-right: 0px; border-top-width: 0px" border="0" alt="image" src="https://msdnshared.blob.core.windows.net/media/MSDNBlogsFS/prod.evol.blogs.msdn.com/CommunityServer.Blogs.Components.WeblogFiles/00/00/01/70/07/metablogapi/6366.image_thumb_3D6A9E54.png" original-url="https://blogs.msdn.com/cfs-file.ashx/__key/communityserver-blogs-components-weblogfiles/00-00-01-70-07-metablogapi/6366.image_5F00_thumb_5F00_3D6A9E54.png" width="642" height="259" /></a></p>

<h3><u>Etape 1 : dézipper le fichier MonAppli_1.0.0.0_x86_Debug.appx</u></h3>

<ul>
  <li>Ouvrez une console en ligne de commande (Touche “Windows” + R puis tapez “cmd” suivi de la touche “Entrée”) </li>

  <li>Déplacez-vous dans le répertoire contenant votre fichier appx généré par Visual Studio </li>

  <li>Dézippez votre fichier appx en tapez la commande suivante : </li>
</ul>

<blockquote>
  <p>&#160;&#160; <font style="background-color: #000000" color="#00ff00" face="Courier New">makeappx.exe unpack /p MonAppli_1.0.0.0_x86_Debug.appx /d .\unpacked /l</font> </p>
</blockquote>

<p>Vous obtenez alors un répertoire “unpack” contenant le fameux fichier manifest à éditer :</p>

<p><a href="https://msdnshared.blob.core.windows.net/media/MSDNBlogsFS/prod.evol.blogs.msdn.com/CommunityServer.Blogs.Components.WeblogFiles/00/00/01/70/07/metablogapi/4265.image_08CCD2CA.png" original-url="https://blogs.msdn.com/cfs-file.ashx/__key/communityserver-blogs-components-weblogfiles/00-00-01-70-07-metablogapi/4265.image_5F00_08CCD2CA.png"><img title="image" style="border-left-width: 0px; border-right-width: 0px; background-image: none; border-bottom-width: 0px; padding-top: 0px; padding-left: 0px; display: inline; padding-right: 0px; border-top-width: 0px" border="0" alt="image" src="https://msdnshared.blob.core.windows.net/media/MSDNBlogsFS/prod.evol.blogs.msdn.com/CommunityServer.Blogs.Components.WeblogFiles/00/00/01/70/07/metablogapi/1460.image_thumb_6A821BD3.png" original-url="https://blogs.msdn.com/cfs-file.ashx/__key/communityserver-blogs-components-weblogfiles/00-00-01-70-07-metablogapi/1460.image_5F00_thumb_5F00_6A821BD3.png" width="642" height="283" /></a></p>

<h3><u>Etape 2 : rezipper le fichier MonAppli_1.0.0.0_x86_Debug.appx en modifiant son nom</u></h3>

<p>Ouvrez le fichier AppxManifest.xml avec un éditeur de texte et mémorisez la valeur de l’attribut “Publisher” dans la section suivante : </p>

<pre style="font-family: consolas; background: white; color: black"><span style="color: blue">&#160; &lt;</span><span style="color: #a31515">Identity</span>
<span style="color: blue">&#160;&#160;&#160; </span><span style="color: red">Name</span><span style="color: blue">=</span>&quot;<span style="color: blue">f786839b-6b88-4374-8865-cf7628099bbc</span>&quot;
<span style="color: blue">&#160;&#160;&#160; </span><span style="color: red">Publisher</span><span style="color: blue">=</span>&quot;<span style="color: blue">CN=myname</span>&quot;
<span style="color: blue">&#160;&#160;&#160; </span><span style="color: red">Version</span><span style="color: blue">=</span>&quot;<span style="color: blue">1.0.0.0</span>&quot;<span style="color: blue"> /&gt;</span></pre>

<p>Ce nom correspond à votre nom d’éditeur de logiciel et nous en aurons besoin ultérieurement pour la génération de certificat numérique. </p>

<p>Un fois le fichier manifest modifié, je vais pouvoir rezipper le fichier appx en tapant la ligne de commande suivante :</p>

<p><font style="background-color: #000000" color="#00ff00" face="Courier New">makeappx.exe pack /d .\unpacked /p MonAppli_1.0.0.0_x86_Debug_UPDATED.appx /l</font></p>

<p>Et voici le nouveau fichier appx :</p>

<p><a href="https://msdnshared.blob.core.windows.net/media/MSDNBlogsFS/prod.evol.blogs.msdn.com/CommunityServer.Blogs.Components.WeblogFiles/00/00/01/70/07/metablogapi/2086.image_47C0E416.png" original-url="https://blogs.msdn.com/cfs-file.ashx/__key/communityserver-blogs-components-weblogfiles/00-00-01-70-07-metablogapi/2086.image_5F00_47C0E416.png"><img title="image" style="border-left-width: 0px; border-right-width: 0px; background-image: none; border-bottom-width: 0px; padding-top: 0px; padding-left: 0px; display: inline; padding-right: 0px; border-top-width: 0px" border="0" alt="image" src="https://msdnshared.blob.core.windows.net/media/MSDNBlogsFS/prod.evol.blogs.msdn.com/CommunityServer.Blogs.Components.WeblogFiles/00/00/01/70/07/metablogapi/3125.image_thumb_19D6220F.png" original-url="https://blogs.msdn.com/cfs-file.ashx/__key/communityserver-blogs-components-weblogfiles/00-00-01-70-07-metablogapi/3125.image_5F00_thumb_5F00_19D6220F.png" width="642" height="291" /></a></p>

<p>Au passage vous pouvez effacer le répertoire “unpack”.</p>

<h3><u>Etape 3 : générer un certificat de signature de code auto-signé et une clef privée</u></h3>

<p>Et oui … les applications ne peuvent pas s’installer aussi facilement : elles doivent être signées numériquement. Pour cela il est nécessaire de générer un certificat numérique. Si vous regardez bien la capture d’écran précédente, vous y trouverez un fichier certificat d’extension “.cer” qui&#160; a été initialement généré par Visual Studio lors de la création du package. Malheureusement nous ne pouvons pas le réutiliser car nous ne connaissons pas le mot de passe de la clef privée associée à ce certificat et utilisée pour la signature. Nous allons donc en créer un nouveau. Donc je vous invite à effacer le fichier MonAppli_1.0.0.0_x86_Debug.cer. Ensuite je vous invite à taper la commande suivante :</p>

<p><font style="background-color: #000000" color="#00ff00" face="Courier New">makecert.exe -sv MyCertificatePrivate.pvk -n &quot;CN=myname&quot; /h 0 /eku &quot;1.3.6.1.5.5.7.3.3,1.3.6.1.4.1.311.10.3.13&quot; MyCertificate.cer -a sha256 -r</font> 

  <br /></p>

<p>Cette commande va générer deux fichiers :</p>

<ul>
  <li>Une clef privée stockée dans un fichier d’extension “.pvk” </li>

  <li>Un certificat numérique de signature stockée dans un fichier d’extension “.cer” </li>
</ul>

<p>Comme vous l’avez remarqué, l’exécution de cette commande a affiché successivement deux boites de dialogue suivante :</p>

<p><a href="https://msdnshared.blob.core.windows.net/media/MSDNBlogsFS/prod.evol.blogs.msdn.com/CommunityServer.Blogs.Components.WeblogFiles/00/00/01/70/07/metablogapi/7026.image_0F3AE55E.png" original-url="https://blogs.msdn.com/cfs-file.ashx/__key/communityserver-blogs-components-weblogfiles/00-00-01-70-07-metablogapi/7026.image_5F00_0F3AE55E.png"><img title="image" style="border-left-width: 0px; border-right-width: 0px; background-image: none; border-bottom-width: 0px; padding-top: 0px; padding-left: 0px; display: inline; padding-right: 0px; border-top-width: 0px" border="0" alt="image" src="https://msdnshared.blob.core.windows.net/media/MSDNBlogsFS/prod.evol.blogs.msdn.com/CommunityServer.Blogs.Components.WeblogFiles/00/00/01/70/07/metablogapi/5270.image_thumb_7C85EBA6.png" original-url="https://blogs.msdn.com/cfs-file.ashx/__key/communityserver-blogs-components-weblogfiles/00-00-01-70-07-metablogapi/5270.image_5F00_thumb_5F00_7C85EBA6.png" width="242" height="174" /></a></p>

<p>puis</p>

<p><a href="https://msdnshared.blob.core.windows.net/media/MSDNBlogsFS/prod.evol.blogs.msdn.com/CommunityServer.Blogs.Components.WeblogFiles/00/00/01/70/07/metablogapi/3632.image_65C6A41D.png" original-url="https://blogs.msdn.com/cfs-file.ashx/__key/communityserver-blogs-components-weblogfiles/00-00-01-70-07-metablogapi/3632.image_5F00_65C6A41D.png"><img title="image" style="border-left-width: 0px; border-right-width: 0px; background-image: none; border-bottom-width: 0px; padding-top: 0px; padding-left: 0px; display: inline; padding-right: 0px; border-top-width: 0px" border="0" alt="image" src="https://msdnshared.blob.core.windows.net/media/MSDNBlogsFS/prod.evol.blogs.msdn.com/CommunityServer.Blogs.Components.WeblogFiles/00/00/01/70/07/metablogapi/8546.image_thumb_081E3997.png" original-url="https://blogs.msdn.com/cfs-file.ashx/__key/communityserver-blogs-components-weblogfiles/00-00-01-70-07-metablogapi/8546.image_5F00_thumb_5F00_081E3997.png" width="242" height="166" /></a></p>

<p>Toute clef privée est en effet protégée par un mot de passe (pensez à le mémoriser car il vous sera redemandé à l’étape suivante).</p>

<h3><u>Etape 4 : convertir le certificat et la clef privée en un unique fichier “pfx”</u></h3>

<p>Afin de signer le fichier appx, nous avons besoin d’un fichier de type “Personal Information Exchange” (format PKCS#12) dont l’extension est “.pfx”. Pour cela nous allons utiliser un autre utilitaire dénommé “pvk2pfx.exe”. Toujours dans la même console, tapez la commande suivante :</p>

<p><font style="background-color: #000000" color="#00ff00" face="Courier New">pvk2pfx.exe -pvk MyCertificatePrivate.pvk -spc MyCertificate.cer -pfx MyCertificate.pfx</font></p>

<p>Au passage notez qu’il vous sera demandé de saisir le mot de passe protégeant la clef privée, mot de passe défini lors de l’étape précédente :</p>

<p><a href="https://msdnshared.blob.core.windows.net/media/MSDNBlogsFS/prod.evol.blogs.msdn.com/CommunityServer.Blogs.Components.WeblogFiles/00/00/01/70/07/metablogapi/7178.image_15844C9D.png" original-url="https://blogs.msdn.com/cfs-file.ashx/__key/communityserver-blogs-components-weblogfiles/00-00-01-70-07-metablogapi/7178.image_5F00_15844C9D.png"><img title="image" style="border-left-width: 0px; border-right-width: 0px; background-image: none; border-bottom-width: 0px; padding-top: 0px; padding-left: 0px; display: inline; padding-right: 0px; border-top-width: 0px" border="0" alt="image" src="https://msdnshared.blob.core.windows.net/media/MSDNBlogsFS/prod.evol.blogs.msdn.com/CommunityServer.Blogs.Components.WeblogFiles/00/00/01/70/07/metablogapi/1586.image_thumb_10A198E1.png" original-url="https://blogs.msdn.com/cfs-file.ashx/__key/communityserver-blogs-components-weblogfiles/00-00-01-70-07-metablogapi/1586.image_5F00_thumb_5F00_10A198E1.png" width="242" height="165" /></a></p>

<p>Voilà nous avons dorénavant notre fichier pfx et nous sommes prêt à signer notre fichier appx :</p>

<p><a href="https://msdnshared.blob.core.windows.net/media/MSDNBlogsFS/prod.evol.blogs.msdn.com/CommunityServer.Blogs.Components.WeblogFiles/00/00/01/70/07/metablogapi/4544.image_39AC37DD.png" original-url="https://blogs.msdn.com/cfs-file.ashx/__key/communityserver-blogs-components-weblogfiles/00-00-01-70-07-metablogapi/4544.image_5F00_39AC37DD.png"><img title="image" style="border-left-width: 0px; border-right-width: 0px; background-image: none; border-bottom-width: 0px; padding-top: 0px; padding-left: 0px; display: inline; padding-right: 0px; border-top-width: 0px" border="0" alt="image" src="https://msdnshared.blob.core.windows.net/media/MSDNBlogsFS/prod.evol.blogs.msdn.com/CommunityServer.Blogs.Components.WeblogFiles/00/00/01/70/07/metablogapi/0676.image_thumb_04A2395E.png" original-url="https://blogs.msdn.com/cfs-file.ashx/__key/communityserver-blogs-components-weblogfiles/00-00-01-70-07-metablogapi/0676.image_5F00_thumb_5F00_04A2395E.png" width="642" height="212" /></a></p>

<h3><u>Etape 5 : signer le package appx</u></h3>

<p>Pour ce faire, vous allez taper la ligne de commande suivante :</p>

<p><font style="background-color: #000000" color="#00ff00" face="Courier New">signtool.exe sign /a /v /fd SHA256 /f MyCertificate.pfx MonAppli_1.0.0.0_x86_Debug_UPDATED.appx</font></p>

<p>Et voilà : dorénavant vous pouvez envoyer votre package appx fraichement générer. Avant d’envoyer le script powershell d’installation, pensez à effacer le fichier appx original. </p>

<p>Ce premier scénario a donc couvert les différentes étapes pour modifier un package appx initialement généré par VS2015. Cela est pratique dans certains cas pour diffuser une version “Debug” en mode “side-loading”. Néanmoins il y a un problème majeur : vous ne pouvez pas publier&#160; sur le store un tel package en mode Release. En effet depuis VS2015 le mode Release inclut un mode de compilation .NET Natif afin d’optimiser les performances de votre application. Et malheureusement il n’est pas possible de publier sur le store un package appx précompilé en .NET natif. Vous aurez le message d’erreur suivant :</p>

<p><a href="https://msdnshared.blob.core.windows.net/media/MSDNBlogsFS/prod.evol.blogs.msdn.com/CommunityServer.Blogs.Components.WeblogFiles/00/00/01/70/07/metablogapi/0005.image_5AC1C528.png" original-url="https://blogs.msdn.com/cfs-file.ashx/__key/communityserver-blogs-components-weblogfiles/00-00-01-70-07-metablogapi/0005.image_5F00_5AC1C528.png"><img title="image" style="border-left-width: 0px; border-right-width: 0px; background-image: none; border-bottom-width: 0px; padding-top: 0px; padding-left: 0px; display: inline; padding-right: 0px; border-top-width: 0px" border="0" alt="image" src="https://msdnshared.blob.core.windows.net/media/MSDNBlogsFS/prod.evol.blogs.msdn.com/CommunityServer.Blogs.Components.WeblogFiles/00/00/01/70/07/metablogapi/7510.image_thumb_2A9A7A65.png" original-url="https://blogs.msdn.com/cfs-file.ashx/__key/communityserver-blogs-components-weblogfiles/00-00-01-70-07-metablogapi/7510.image_5F00_thumb_5F00_2A9A7A65.png" width="642" height="75" /></a></p>

<p>Nous touchons ici les limites de ce premier scénario. Heureusement il existe une seconde approche : utilisez MSBuild</p>

<h1><font color="#4bacc6">Scénario 2 : Générer un package appx avec MSBuild</font></h1>

<p>A la différence du premier scénario, nous génèrerons ici le package “from scratch”. Cette génération est réalisée en trois temps :</p>

<ul>
  <li>Associer votre application avec le store Windows </li>

  <li>Editer votre fichier Package.appxmanifest notamment pour définir le numéro de version (optionnelle) </li>

  <li>Générer votre package en utilisant MsBuild </li>
</ul>

<h3><u>Etape 1 : Associer votre application avec le store</u></h3>

<p>Depuis Visual Studio, sélectionnez votre projet et cliquez sur le bouton droit de la souris pour afficher le menu contextuel. Puis sélectionnez le menu “Store” puis “Associate App With Store” :</p>

<p><a href="https://msdnshared.blob.core.windows.net/media/MSDNBlogsFS/prod.evol.blogs.msdn.com/CommunityServer.Blogs.Components.WeblogFiles/00/00/01/70/07/metablogapi/6064.image_7353F329.png" original-url="https://blogs.msdn.com/cfs-file.ashx/__key/communityserver-blogs-components-weblogfiles/00-00-01-70-07-metablogapi/6064.image_5F00_7353F329.png"><img title="image" style="border-left-width: 0px; border-right-width: 0px; background-image: none; border-bottom-width: 0px; padding-top: 0px; padding-left: 0px; display: inline; padding-right: 0px; border-top-width: 0px" border="0" alt="image" src="https://msdnshared.blob.core.windows.net/media/MSDNBlogsFS/prod.evol.blogs.msdn.com/CommunityServer.Blogs.Components.WeblogFiles/00/00/01/70/07/metablogapi/0537.image_thumb_105CA1F2.png" original-url="https://blogs.msdn.com/cfs-file.ashx/__key/communityserver-blogs-components-weblogfiles/00-00-01-70-07-metablogapi/0537.image_5F00_thumb_5F00_105CA1F2.png" width="642" height="381" /></a></p>

<p>Cette phase nécessite de vous authentifier avec votre compte développeur. Vous pourrez alors sélectionner un nom d’application. Cette association avec le store aura pour conséquence la récupération de deux fichiers qui seront utilisés par la procédure de build pour générer et signer vos différents packages :</p>

<ul>
  <li>Package.StoreAssociation.xml </li>

  <li>MonAppli_StoreKey.pfx </li>
</ul>

<p><u></u></p>

<h3><u>Etape 2 : Editer votre fichier Package.appxmanifest (Optionnelle)</u></h3>

<p>Cette étape est complètement optionnelle et spécifique à mon besoin d’ajouter une extension pour Cortana. Par ailleurs vous pouvez y définir le numéro de version de votre application (attribut <font color="#ff0000" face="Courier New">Version</font> de la balise <font face="Courier New">&lt;Identity&gt;</font>). Vous pouvez passer directement à l’étape suivante.</p>

<h3><u>Etape 3 : Générer votre package en utilisant MsBuild</u></h3>

<p>Ouvrez une console en ligne Visual Studio, c’est-à-dire une console paramétrée avec les variables d’environnements nécessaire à l’utilisation de MsBuild. Pour cela, rendez-vous dans le répertoire suivant :</p>

<p><font face="Courier New">C:\Program Files (x86)\Microsoft Visual Studio 14.0\Common7\Tools</font></p>

<p>Ensuite ouvrez le batch file <font face="Courier New">VsDevCmd.bat</font> puis lancez la commande suivante :</p>

<p><font face="Courier New"><font style="background-color: #000000" color="#00ff00">MSBuild .\MonAppli.csproj /p:Configuration=Release;AppxBundle=Always;AppxBundlePlatforms=&quot;x86|x64&quot; </font></font></p>

<p><font face="Courier New"><font style="background-color: #000000" color="#00ff00">/p:BuildAppxUploadPackageForUap=true</font> 

    <br /></font></p>

<p>Cette commande aura pour effet :</p>

<ul>
  <li>de compiler votre projet en mode Release </li>

  <li>de générer un package de type bundle </li>

  <li>de cibler les plateformes x86 et x64 (noter la présence du caractère ‘|’ permettant de lister différentes plateformes cibles dans une même commande)</li>
</ul>

<p>Au final vous obtiendrez un fichier <font face="Courier New">MonAppli_1.0.0.0_x86_x64_bundle.appxupload</font> que vous pourrez directement charger sur l’interface de publication Dev Center.</p>

<h1><font color="#4bacc6">Conclusion</font></h1>

<p>En résumé, cet article a exposé deux approches pour générer un package sans utiliser le designer de package intégré à Visual Studio :</p>

<ul>
  <li>La première méthode pour faire du side-loading de package sans utiliser le designer de Visual Studio </li>

  <li>La seconde méthode pour générer un package de production, bien utile dès qu’on souhaite scripter la procédure de build d’une application Windows store </li>
</ul>

<h1><font color="#4bacc6">Références</font></h1>

<p><a href="https://msdn.microsoft.com/en-us/library/hh454036.aspx" target="_blank"><font color="#0000ff">Packager une application Windows 10 Universelle</font></a></p>

<p><a href="https://msdn.microsoft.com/fr-fr/library/windows/desktop/jj835832(v=vs.85).aspx" target="_blank"><font color="#0000ff">Comment créer un certificat de signature de package</font></a></p>

<p><a href="https://msdn.microsoft.com/fr-fr/library/windows/desktop/hh446767(v=vs.85).aspx" target="_blank"><font color="#0000ff">Créer un package avec MakeAppx</font></a></p>]]></content:encoded>
    </item>
    <item>
      <title>Unity et les APIs Windows / Windows Phone</title>
      <link>https://docs.microsoft.com/archive/blogs/ndelabarre/unity-et-les-apis-windows-windows-phone</link>
      <pubDate>Fri, 19 Jun 2015 03:16:25 GMT</pubDate>
      <dc:creator><![CDATA[Nicolas Delabarre]]></dc:creator>
      <guid
        isPermaLink="false">https://blogs.msdn.microsoft.com/ndelabarre/2015/06/19/unity-et-les-apis-windows-windows-phone/</guid>
      <description><![CDATA[Imaginons que vous souhaitiez utiliser des APIs spécifiques à la plateforme WinRT (Windows et...]]></description>
      <content:encoded><![CDATA[<p>Imaginons que vous souhaitiez utiliser des APIs spécifiques à la plateforme WinRT (Windows et Windows Phone) qui ne sont pas disponibles de base dans le framework Unity. Par exemple votre jeu pourrait proposer à l’utilisateur de commenter et noter votre application simplement en le redirigeant vers le store Windows. Vous pourriez également proposer à l’utilisateur de choisir son avatar à partir&#160; de sa galerie photo de son téléphone. Cet article vous présente deux méthodes pour utiliser des APIs WinRT depuis votre application unity :</p>  <ul>   <li>L’utilisation de directives de compilation </li>    <li>La création de plugins </li> </ul>  <p>&#160;</p>  <h3>Pré-requis </h3>  <ul>   <li>Unity 4.6 ou supérieure </li>    <li>PC sous Windows 8.1 </li>    <li>Visual Studio 2013 Community Edition (gratuit) </li>    <li>Visual Studio 2013 Tool for Unity (optionnel) </li>    <li>Un téléphone sous Windows Phone 8.1 (optionnel car on peut utiliser l’émulateur WP8.1) </li> </ul>  <p>Dans la suite de cet article, nous exporterons notre application Unity vers la plateforme “Universal 8.1” </p>  <p>&#160;</p>  <h1>Directives de compilation</h1>  <p>La force d’Unity est de pouvoir cibler différentes plateformes avec un code unique bâti sur un framework unifié. Néanmoins il existe des situations où le code doit être adapté aux spécificités des plateformes. Pour palier ce problème, Unity fournit aux développeurs <a href="https://docs.unity3d.com/Manual/PlatformDependentCompilation.html">des directives de compilation prédéfinies</a> :</p>  <p>&#160;</p>  <p><a href="https://msdnshared.blob.core.windows.net/media/MSDNBlogsFS/prod.evol.blogs.msdn.com/CommunityServer.Blogs.Components.WeblogFiles/00/00/01/70/07/metablogapi/1768.compilation_directives_18EC955E.png" original-url="https://blogs.msdn.com/cfs-file.ashx/__key/communityserver-blogs-components-weblogfiles/00-00-01-70-07-metablogapi/1768.compilation_5F00_directives_5F00_18EC955E.png"><img title="compilation_directives" style="border-top: 0px; border-right: 0px; background-image: none; border-bottom: 0px; padding-top: 0px; padding-left: 0px; border-left: 0px; display: inline; padding-right: 0px" border="0" alt="compilation_directives" src="https://msdnshared.blob.core.windows.net/media/MSDNBlogsFS/prod.evol.blogs.msdn.com/CommunityServer.Blogs.Components.WeblogFiles/00/00/01/70/07/metablogapi/4237.compilation_directives_thumb_0734ACE6.png" original-url="https://blogs.msdn.com/cfs-file.ashx/__key/communityserver-blogs-components-weblogfiles/00-00-01-70-07-metablogapi/4237.compilation_5F00_directives_5F00_thumb_5F00_0734ACE6.png" width="1206" height="579" /></a></p>  <p align="justify">Parmi ces directives, voici celles que nous allons utiliser :</p>  <ul>   <li>     <div align="justify">NETFX_CORE : à utiliser dès lors qu’on souhaite appeler une API Windows Runtime depuis un script Unity. A noter que le code inclus dans un tel bloc est ignoré par l’éditeur Unity : en plus de l’utilisation des APIs WinRT, c’est un moyen pratique pour utiliser des spécificités du framework .NET 4.5 </div>   </li>    <li>     <div align="justify">UNITY_METRO : à utiliser dès lors qu’on souhaite utiliser une API Windows Runtime commune à Windows 8.1 et Windows Phone 8.1 </div>   </li>    <li>     <div align="justify">UNITY_METRO_8_1 : à utiliser dès lors qu’on souhaite utiliser une API Windows Runtime spécifique à Windows 8.1 (et non supportée par Windows Phone 8.1) ou implémenter un comportement spécifique à Windows comme par exemple l’accès à la Charm barre. </div>   </li>    <li>     <div align="justify">UNITY_WP_8_1 : à utiliser dès lors qu’on souhaite utiliser une API Windows Runtime spécifique à Windows Phone 8.1 (et non supportée par Windows 8.1) ou implémenter un comportement spécifique à Windows Phone comme par exemple la gestion du bouton “Retour” </div>   </li> </ul>  <p align="justify"><u>Remarque</u> : contrairement à NETFX_CORE, les directives UNITY_METRO, UNITY_METRO_8_1 et UNITY_WP_8_1 sont actives dans l’éditeur Unity dès que vous sélectionner “Windows store” comme plateforme cible dans la boite de dialogue d’exportation.</p>  <p align="justify">A titre d’illustration, je vous propose donc d’implémenter un code d’exemple ultra simple : mon application Unity va afficher un Canvas avec un bouton ; lorsqu’on cliquera sur le bouton, l’application ouvrira une boite de dialogue native de la plateforme Windows avec un message texte. Bien que très basique d’un point de vue fonctionnelle, cet exemple va couvrir un certain nombre d’aspects clés pour comprendre la manière dont un script Unity peut interagir avec l’OS.</p>  <p align="justify">La première étape consiste donc à créer un projet Unity (en y important le plugin Visual Studio Tools for Unity) :</p>  <ul>   <li>     <div align="justify">une scène principale dénommée “Main” </div>   </li>    <li>     <div align="justify">Un script c# dénommé <strong>MessageBox.cs</strong> et attaché à la caméra principale. J’y ai défini une méthode dénommée <strong>OnMessageBoxClick</strong> pour gérer le clic bouton </div>   </li>    <li>     <div align="justify">Un canvas contenant un bouton dont le gestionnaire de clics est initialisé avec la méthode OnMessageBoxClick </div>   </li> </ul>  <p align="justify">&#160;</p>  <p><a href="https://msdnshared.blob.core.windows.net/media/MSDNBlogsFS/prod.evol.blogs.msdn.com/CommunityServer.Blogs.Components.WeblogFiles/00/00/01/70/07/metablogapi/1781.Unity_MessageBox_79F5D5E5.png" original-url="https://blogs.msdn.com/cfs-file.ashx/__key/communityserver-blogs-components-weblogfiles/00-00-01-70-07-metablogapi/1781.Unity_5F00_MessageBox_5F00_79F5D5E5.png"><img title="Unity_MessageBox" style="border-top: 0px; border-right: 0px; background-image: none; border-bottom: 0px; padding-top: 0px; padding-left: 0px; border-left: 0px; display: inline; padding-right: 0px" border="0" alt="Unity_MessageBox" src="https://msdnshared.blob.core.windows.net/media/MSDNBlogsFS/prod.evol.blogs.msdn.com/CommunityServer.Blogs.Components.WeblogFiles/00/00/01/70/07/metablogapi/7853.Unity_MessageBox_thumb_07809441.png" original-url="https://blogs.msdn.com/cfs-file.ashx/__key/communityserver-blogs-components-weblogfiles/00-00-01-70-07-metablogapi/7853.Unity_5F00_MessageBox_5F00_thumb_5F00_07809441.png" width="823" height="774" /></a></p>  <p>Parlons maintenant du script C# associé :</p>  <h4>1. <u>Configuré sous Visual Studio avant exportation</u> :</h4>  <div id="scid:9ce6104f-a9aa-4a17-a79f-3a39532ebf7c:9c0c893a-1348-4fb5-b915-181578460cee" class="wlWriterEditableSmartContent" style="float: none; padding-bottom: 0px; padding-top: 0px; padding-left: 0px; margin: 0px; display: inline; padding-right: 0px"> <div style="border: #000080 1px solid; color: #000; font-family: 'Courier New', Courier, Monospace; font-size: 10pt"> <div style="background: #000080; color: #fff; font-family: Verdana, Tahoma, Arial, sans-serif; font-weight: bold; padding: 2px 5px">Code Snippet</div> <div style="background: #ddd; overflow: auto"> <ol start="1" style="background: #ffffff; margin: 0 0 0 2.5em; padding: 0 0 0 5px;"> <li><span style="background:#ffffff;color:#0000ff">using</span><span style="background:#ffffff;color:#000000"> UnityEngine;</span></li> <li style="background: #f3f3f3"><span style="background:#ffffff;color:#0000ff">using</span><span style="background:#ffffff;color:#000000"> System.Collections;</span></li> <li>&nbsp;</li> <li style="background: #f3f3f3"><span style="background:#ffffff;color:#0000ff">#if</span><span style="background:#ffffff;color:#000000"> NETFX_CORE</span></li> <li><span style="background:#ffffff;color:#808080">using System;</span></li> <li style="background: #f3f3f3"><span style="background:#ffffff;color:#808080">using Windows.UI.Popups;</span></li> <li><span style="background:#ffffff;color:#808080">using Windows.UI.Core;</span></li> <li style="background: #f3f3f3"><span style="background:#ffffff;color:#808080">using System.Threading.Tasks;</span></li> <li><span style="background:#ffffff;color:#808080">using Windows.ApplicationModel.Core;</span></li> <li style="background: #f3f3f3"><span style="background:#ffffff;color:#0000ff">#endif</span></li> <li>&nbsp;</li> <li style="background: #f3f3f3"><span style="background:#ffffff;color:#0000ff">public</span><span style="background:#ffffff;color:#000000"> </span><span style="background:#ffffff;color:#0000ff">class</span><span style="background:#ffffff;color:#000000"> </span><span style="background:#ffffff;color:#2b91af">MessageBox</span><span style="background:#ffffff;color:#000000"> : </span><span style="background:#ffffff;color:#2b91af">MonoBehaviour</span><span style="background:#ffffff;color:#000000"> {</span></li> <li>&nbsp;</li> <li style="background: #f3f3f3">    <span style="background:#ffffff;color:#0000ff">#if</span><span style="background:#ffffff;color:#000000"> NETFX_CORE</span></li> <li>        <span style="background:#ffffff;color:#808080">public void OnMessageBoxClick()</span></li> <li style="background: #f3f3f3">        <span style="background:#ffffff;color:#808080">{        </span></li> <li>            <span style="background:#ffffff;color:#808080">showMessageDialogAsync(&quot;Hello from WinRT !&quot;);        </span></li> <li style="background: #f3f3f3">        <span style="background:#ffffff;color:#808080">}</span></li> <li>&nbsp;</li> <li style="background: #f3f3f3">        <span style="background:#ffffff;color:#808080">async void showMessageDialogAsync(string message)</span></li> <li>        <span style="background:#ffffff;color:#808080">{</span></li> <li style="background: #f3f3f3">            <span style="background:#ffffff;color:#808080">await CoreApplication.MainView.CoreWindow.Dispatcher.RunAsync(CoreDispatcherPriority.Normal, async () =&gt;</span></li> <li>            <span style="background:#ffffff;color:#808080">{</span></li> <li style="background: #f3f3f3">                <span style="background:#ffffff;color:#808080">MessageDialog messageBox = new MessageDialog(message);</span></li> <li>                <span style="background:#ffffff;color:#808080">await messageBox.ShowAsync();</span></li> <li style="background: #f3f3f3">            <span style="background:#ffffff;color:#808080">});</span></li> <li>        <span style="background:#ffffff;color:#808080">}</span></li> <li style="background: #f3f3f3">&nbsp;</li> <li>    <span style="background:#ffffff;color:#0000ff">#else</span></li> <li style="background: #f3f3f3">        <span style="background:#ffffff;color:#000000"></span><span style="background:#ffffff;color:#0000ff">public</span><span style="background:#ffffff;color:#000000"> </span><span style="background:#ffffff;color:#0000ff">void</span><span style="background:#ffffff;color:#000000"> OnMessageBoxClick()</span></li> <li>        <span style="background:#ffffff;color:#000000">{</span></li> <li style="background: #f3f3f3">            <span style="background:#ffffff;color:#000000"></span><span style="background:#ffffff;color:#2b91af">Debug</span><span style="background:#ffffff;color:#000000">.Log(</span><span style="background:#ffffff;color:#a31515">&quot;Hello from Unity Player&quot;</span><span style="background:#ffffff;color:#000000">);</span></li> <li>        <span style="background:#ffffff;color:#000000">}</span></li> <li style="background: #f3f3f3">    <span style="background:#ffffff;color:#0000ff">#endif</span></li> </ol> </div> </div> </div>  <p>Comme vous pouvez le constater, tout ce qui est encadré par la directive NETFX_CORE est ignoré par l’éditeur Unity (code grisé). Le gestionnaire de clic ne fait qu’afficher une trace dans la console Unity. </p>  <h4>2. <u>Configuré sous Visual Studio après exportation “Universal 8.1”</u> :</h4>  <div id="scid:9ce6104f-a9aa-4a17-a79f-3a39532ebf7c:cee73e67-2f1a-48ad-876c-5fdf98d42756" class="wlWriterEditableSmartContent" style="float: none; padding-bottom: 0px; padding-top: 0px; padding-left: 0px; margin: 0px; display: inline; padding-right: 0px"> <div style="border: #000080 1px solid; color: #000; font-family: 'Courier New', Courier, Monospace; font-size: 10pt"> <div style="background: #000080; color: #fff; font-family: Verdana, Tahoma, Arial, sans-serif; font-weight: bold; padding: 2px 5px">Code Snippet</div> <div style="background: #ddd; overflow: auto"> <ol start="1" style="background: #ffffff; margin: 0 0 0 2.5em; padding: 0 0 0 5px;"> <li><span style="background:#ffffff;color:#0000ff">using</span><span style="background:#ffffff;color:#000000"> UnityEngine;</span></li> <li style="background: #f3f3f3"><span style="background:#ffffff;color:#0000ff">using</span><span style="background:#ffffff;color:#000000"> System.Collections;</span></li> <li>&nbsp;</li> <li style="background: #f3f3f3"><span style="background:#ffffff;color:#0000ff">#if</span><span style="background:#ffffff;color:#000000"> NETFX_CORE</span></li> <li><span style="background:#ffffff;color:#0000ff">using</span><span style="background:#ffffff;color:#000000"> System;</span></li> <li style="background: #f3f3f3"><span style="background:#ffffff;color:#0000ff">using</span><span style="background:#ffffff;color:#000000"> Windows.UI.Popups;</span></li> <li><span style="background:#ffffff;color:#0000ff">using</span><span style="background:#ffffff;color:#000000"> Windows.UI.Core;</span></li> <li style="background: #f3f3f3"><span style="background:#ffffff;color:#0000ff">using</span><span style="background:#ffffff;color:#000000"> System.Threading.Tasks;</span></li> <li><span style="background:#ffffff;color:#0000ff">using</span><span style="background:#ffffff;color:#000000"> Windows.ApplicationModel.Core;</span></li> <li style="background: #f3f3f3"><span style="background:#ffffff;color:#0000ff">#endif</span></li> <li>&nbsp;</li> <li style="background: #f3f3f3"><span style="background:#ffffff;color:#0000ff">public</span><span style="background:#ffffff;color:#000000"> </span><span style="background:#ffffff;color:#0000ff">class</span><span style="background:#ffffff;color:#000000"> </span><span style="background:#ffffff;color:#2b91af">MessageBox</span><span style="background:#ffffff;color:#000000"> : </span><span style="background:#ffffff;color:#2b91af">MonoBehaviour</span><span style="background:#ffffff;color:#000000"> {</span></li> <li>&nbsp;</li> <li style="background: #f3f3f3">    <span style="background:#ffffff;color:#0000ff">#if</span><span style="background:#ffffff;color:#000000"> NETFX_CORE</span></li> <li>        <span style="background:#ffffff;color:#000000"></span><span style="background:#ffffff;color:#0000ff">public</span><span style="background:#ffffff;color:#000000"> </span><span style="background:#ffffff;color:#0000ff">void</span><span style="background:#ffffff;color:#000000"> OnMessageBoxClick()</span></li> <li style="background: #f3f3f3">        <span style="background:#ffffff;color:#000000">{        </span></li> <li>            <span style="background:#ffffff;color:#000000">showMessageDialogAsync(</span><span style="background:#ffffff;color:#a31515">&quot;Hello from WinRT !&quot;</span><span style="background:#ffffff;color:#000000">);        </span></li> <li style="background: #f3f3f3">        <span style="background:#ffffff;color:#000000">}</span></li> <li>&nbsp;</li> <li style="background: #f3f3f3">        <span style="background:#ffffff;color:#000000"></span><span style="background:#ffffff;color:#0000ff">async</span><span style="background:#ffffff;color:#000000"> </span><span style="background:#ffffff;color:#0000ff">void</span><span style="background:#ffffff;color:#000000"> showMessageDialogAsync(</span><span style="background:#ffffff;color:#0000ff">string</span><span style="background:#ffffff;color:#000000"> message)</span></li> <li>        <span style="background:#ffffff;color:#000000">{</span></li> <li style="background: #f3f3f3">            <span style="background:#ffffff;color:#000000"></span><span style="background:#ffffff;color:#0000ff">await</span><span style="background:#ffffff;color:#000000"> </span><span style="background:#ffffff;color:#2b91af">CoreApplication</span><span style="background:#ffffff;color:#000000">.MainView.CoreWindow.Dispatcher.RunAsync(</span><span style="background:#ffffff;color:#2b91af">CoreDispatcherPriority</span><span style="background:#ffffff;color:#000000">.Normal, </span><span style="background:#ffffff;color:#0000ff">async</span><span style="background:#ffffff;color:#000000"> () =&gt;</span></li> <li>            <span style="background:#ffffff;color:#000000">{</span></li> <li style="background: #f3f3f3">                <span style="background:#ffffff;color:#000000"></span><span style="background:#ffffff;color:#2b91af">MessageDialog</span><span style="background:#ffffff;color:#000000"> messageBox = </span><span style="background:#ffffff;color:#0000ff">new</span><span style="background:#ffffff;color:#000000"> </span><span style="background:#ffffff;color:#2b91af">MessageDialog</span><span style="background:#ffffff;color:#000000">(message);</span></li> <li>                <span style="background:#ffffff;color:#000000"></span><span style="background:#ffffff;color:#0000ff">await</span><span style="background:#ffffff;color:#000000"> messageBox.ShowAsync();</span></li> <li style="background: #f3f3f3">            <span style="background:#ffffff;color:#000000">});</span></li> <li>        <span style="background:#ffffff;color:#000000">}</span></li> <li style="background: #f3f3f3">&nbsp;</li> <li>    <span style="background:#ffffff;color:#0000ff">#else</span></li> <li style="background: #f3f3f3">        <span style="background:#ffffff;color:#808080">public void OnMessageBoxClick()</span></li> <li>        <span style="background:#ffffff;color:#808080">{</span></li> <li style="background: #f3f3f3">            <span style="background:#ffffff;color:#808080">Debug.Log(&quot;Hello from Unity Player&quot;);</span></li> <li>        <span style="background:#ffffff;color:#808080">}</span></li> <li style="background: #f3f3f3">    <span style="background:#ffffff;color:#0000ff">#endif</span></li> <li><span style="background:#ffffff;color:#000000">}</span></li> </ol> </div> </div> </div>  <p>Cette fois le code encadré par la directive NETFX_CORE est bien actif et pour cause : dans votre projet exporté sous Visual Studio, lorsque vous sélectionnez dans l’explorateur de solutions le projet “MessageBox.Windows” ou “MessageBox.Windows Phone” et affichez les propriétés du projet (onglet Build), vous verrez parmi les directives de compilation actives la directive NETFX_CORE :</p>  <p><a href="https://msdnshared.blob.core.windows.net/media/MSDNBlogsFS/prod.evol.blogs.msdn.com/CommunityServer.Blogs.Components.WeblogFiles/00/00/01/70/07/metablogapi/3515.NETFX_CORE_37CF1B0A.png" original-url="https://blogs.msdn.com/cfs-file.ashx/__key/communityserver-blogs-components-weblogfiles/00-00-01-70-07-metablogapi/3515.NETFX_5F00_CORE_5F00_37CF1B0A.png"><img title="NETFX_CORE" style="border-top: 0px; border-right: 0px; background-image: none; border-bottom: 0px; padding-top: 0px; padding-left: 0px; border-left: 0px; display: inline; padding-right: 0px" border="0" alt="NETFX_CORE" src="https://msdnshared.blob.core.windows.net/media/MSDNBlogsFS/prod.evol.blogs.msdn.com/CommunityServer.Blogs.Components.WeblogFiles/00/00/01/70/07/metablogapi/8306.NETFX_CORE_thumb_1BC0ECD0.png" original-url="https://blogs.msdn.com/cfs-file.ashx/__key/communityserver-blogs-components-weblogfiles/00-00-01-70-07-metablogapi/8306.NETFX_5F00_CORE_5F00_thumb_5F00_1BC0ECD0.png" width="646" height="369" /></a></p>  <p align="justify">Il est temps de disséquer le code : la classe WinRT pour afficher une boite de dialogue native est MessageDialog. Un de ces constructeurs est ici appelé avec en paramètre le message texte passé sous forme de chaine de caractères. Puis la méthode ShowAsync est appelée selon le pattern Await/Async. Ce qui est notable (et qui ne vous aura sans doute pas échappé) c’est le fait que ce bloc de code est inclus dans une lambda expression asynchrone, elle-même passée en paramètre d’un appel à la méthode <strong><font face="Courier New">CoreApplication.MainView.CoreWindow.Dispatcher.RunAsync</font></strong> : cela signifie que l’affichage de la boite de dialogue est délégué au thread graphique (UI) de la fenêtre principale de l’application ; c’est une obligation imposée par le modèle de threading des applications WinRT dès lors qu’on interagit avec l’interface graphique. Logiquement vous pourriez croire que le script Unity s’exécute déjà dans ce thread graphique et que cette délégation est inutile … et bien non, détrompez vous : le script Unity s’exécute dans un background thread (encore appelé worker thread). D’ailleurs Unity a défini des méthodes spécifiques Windows pour gérer ce changement de contexte dans la classe <a href="https://docs.unity3d.com/ScriptReference/WSA.Application.html" target="_blank">UnityEngine.WSA.Application</a> :</p>  <p><a href="https://msdnshared.blob.core.windows.net/media/MSDNBlogsFS/prod.evol.blogs.msdn.com/CommunityServer.Blogs.Components.WeblogFiles/00/00/01/70/07/metablogapi/1665.WSA.Thread_5AB78ECD.png" original-url="https://blogs.msdn.com/cfs-file.ashx/__key/communityserver-blogs-components-weblogfiles/00-00-01-70-07-metablogapi/1665.WSA.Thread_5F00_5AB78ECD.png"><img title="WSA.Thread" style="border-top: 0px; border-right: 0px; background-image: none; border-bottom: 0px; padding-top: 0px; padding-left: 0px; border-left: 0px; display: inline; padding-right: 0px" border="0" alt="WSA.Thread" src="https://msdnshared.blob.core.windows.net/media/MSDNBlogsFS/prod.evol.blogs.msdn.com/CommunityServer.Blogs.Components.WeblogFiles/00/00/01/70/07/metablogapi/3782.WSA.Thread_thumb_532EB011.png" original-url="https://blogs.msdn.com/cfs-file.ashx/__key/communityserver-blogs-components-weblogfiles/00-00-01-70-07-metablogapi/3782.WSA.Thread_5F00_thumb_5F00_532EB011.png" width="507" height="486" /></a></p>  <p>Je pourrais donc réécrire mon code ainsi :</p>  <div id="scid:9ce6104f-a9aa-4a17-a79f-3a39532ebf7c:1ae8fd65-8534-4a65-b6e1-dde3ba5e6841" class="wlWriterEditableSmartContent" style="float: none; padding-bottom: 0px; padding-top: 0px; padding-left: 0px; margin: 0px; display: inline; padding-right: 0px"> <div style="border: #000080 1px solid; color: #000; font-family: 'Courier New', Courier, Monospace; font-size: 10pt"> <div style="background: #000080; color: #fff; font-family: Verdana, Tahoma, Arial, sans-serif; font-weight: bold; padding: 2px 5px">Code Snippet</div> <div style="background: #ddd; max-height: 300px; overflow: auto"> <ol start="1" style="background: #ffffff; margin: 0 0 0 2.5em; padding: 0 0 0 5px;"> <li><span style="background:#ffffff;color:#000000"></span><span style="background:#ffffff;color:#0000ff">async</span><span style="background:#ffffff;color:#000000"> </span><span style="background:#ffffff;color:#0000ff">void</span><span style="background:#ffffff;color:#000000"> showMessageDialogAsync(</span><span style="background:#ffffff;color:#0000ff">string</span><span style="background:#ffffff;color:#000000"> message)</span></li> <li style="background: #f3f3f3"><span style="background:#ffffff;color:#000000">{</span></li> <li>    <span style="background:#ffffff;color:#000000">UnityEngine.WSA.</span><span style="background:#ffffff;color:#2b91af">Application</span><span style="background:#ffffff;color:#000000">.InvokeOnUIThread( </span><span style="background:#ffffff;color:#0000ff">async</span><span style="background:#ffffff;color:#000000"> () =&gt;</span></li> <li style="background: #f3f3f3">    <span style="background:#ffffff;color:#000000">{</span></li> <li>&nbsp;</li> <li style="background: #f3f3f3">        <span style="background:#ffffff;color:#000000"></span><span style="background:#ffffff;color:#2b91af">MessageDialog</span><span style="background:#ffffff;color:#000000"> messageBox = </span><span style="background:#ffffff;color:#0000ff">new</span><span style="background:#ffffff;color:#000000"> </span><span style="background:#ffffff;color:#2b91af">MessageDialog</span><span style="background:#ffffff;color:#000000">(message);</span></li> <li>        <span style="background:#ffffff;color:#000000"></span><span style="background:#ffffff;color:#0000ff">await</span><span style="background:#ffffff;color:#000000"> messageBox.ShowAsync();</span></li> <li style="background: #f3f3f3">    <span style="background:#ffffff;color:#000000">}, </span></li> <li>    <span style="background:#ffffff;color:#000000"></span><span style="background:#ffffff;color:#0000ff">false</span><span style="background:#ffffff;color:#000000">);</span></li> <li style="background: #f3f3f3"><span style="background:#ffffff;color:#000000">}</span></li> </ol> </div> </div> </div>  <p>Cela fonctionnerait tout aussi bien ; c’est à vous de choisir en fonction de vos préférences. L’avantage de la méthode <strong><font face="Courier New">InvokeOnUIThread</font></strong> est qu’elle peut être appelée directement depuis un script Unity en dehors de tout bloc NETFX_CORE. Vous aurez également remarqué que l’exemple ci-dessous n’utilise qu’une seule directive NETFX_CORE. Dans quel cas de figure utiliser UNITY_METRO_8_1 ou UNITY_WP_8_1 ? La réponse est double : </p>  <p>&#160;</p>  <p><strong>Réponse 1</strong> : 90% des APIs pour Windows et Windows Phone sont communes.</p>  <p><a href="https://msdnshared.blob.core.windows.net/media/MSDNBlogsFS/prod.evol.blogs.msdn.com/CommunityServer.Blogs.Components.WeblogFiles/00/00/01/70/07/metablogapi/2860.convergenceControls01_424C9CD2.jpg" original-url="https://blogs.msdn.com/cfs-file.ashx/__key/communityserver-blogs-components-weblogfiles/00-00-01-70-07-metablogapi/2860.convergenceControls01_5F00_424C9CD2.jpg"><img title="convergenceControls01" style="border-top: 0px; border-right: 0px; background-image: none; border-bottom: 0px; padding-top: 0px; padding-left: 0px; border-left: 0px; display: inline; padding-right: 0px" border="0" alt="convergenceControls01" src="https://msdnshared.blob.core.windows.net/media/MSDNBlogsFS/prod.evol.blogs.msdn.com/CommunityServer.Blogs.Components.WeblogFiles/00/00/01/70/07/metablogapi/4405.convergenceControls01_thumb_24FC666A.jpg" original-url="https://blogs.msdn.com/cfs-file.ashx/__key/communityserver-blogs-components-weblogfiles/00-00-01-70-07-metablogapi/4405.convergenceControls01_5F00_thumb_5F00_24FC666A.jpg" width="646" height="354" /></a></p>  <p>Pour utiliser les 10% restants (parties bleue et rose), il faudra donc utiliser ces directives. Je peux vous donner un exemple concret : imaginez que vous souhaitiez rediriger votre utilisateur vers l’application Store native afin de l’inciter à noter votre application. Bien que l’API soit identique pour Windows et Windows Phone, le format de l’URI utilisé en paramètre d’entrée est différent entre les deux store (“package family name” pour windows et “application ID” pour windows phone) :</p>  <p>&#160;</p>  <div id="scid:9ce6104f-a9aa-4a17-a79f-3a39532ebf7c:4523c242-1067-4a83-baf0-31cca6165321" class="wlWriterEditableSmartContent" style="float: none; padding-bottom: 0px; padding-top: 0px; padding-left: 0px; margin: 0px; display: inline; padding-right: 0px"> <div style="border: #000080 1px solid; color: #000; font-family: 'Courier New', Courier, Monospace; font-size: 10pt"> <div style="background: #000080; color: #fff; font-family: Verdana, Tahoma, Arial, sans-serif; font-weight: bold; padding: 2px 5px">Code Snippet</div> <div style="background: #ddd; overflow: auto"> <ol start="1" style="background: #ffffff; margin: 0 0 0 2.5em; padding: 0 0 0 5px;"> <li><span style="background:#ffffff;color:#0000ff">#if</span><span style="background:#ffffff;color:#000000"> NETFX_CORE</span></li> <li style="background: #f3f3f3">        <span style="background:#ffffff;color:#000000"></span><span style="background:#ffffff;color:#0000ff">public</span><span style="background:#ffffff;color:#000000"> </span><span style="background:#ffffff;color:#0000ff">void</span><span style="background:#ffffff;color:#000000"> OnStoreReviewClick()</span></li> <li>        <span style="background:#ffffff;color:#000000">{</span></li> <li style="background: #f3f3f3">            <span style="background:#ffffff;color:#0000ff">#if</span><span style="background:#ffffff;color:#000000"> UNITY_METRO_8_1</span></li> <li>                <span style="background:#ffffff;color:#000000">showStoreReviewPageAsync(</span><span style="background:#ffffff;color:#a31515">&quot;ms-windows-store:Review?PFN={0}&quot;</span><span style="background:#ffffff;color:#000000">, </span><span style="background:#ffffff;color:#a31515">&quot;com.microsoft.app.contoso&quot;</span><span style="background:#ffffff;color:#000000">);</span></li> <li style="background: #f3f3f3">            <span style="background:#ffffff;color:#0000ff">#elif</span><span style="background:#ffffff;color:#000000"> UNITY_WP_8_1</span></li> <li>                <span style="background:#ffffff;color:#808080">showStoreReviewPageAsync(&quot;ms-windows-store:reviewapp?appid={0}&quot;, &quot;ad543082-80ec-45bb-aa02-ffe7f4182ba8&quot;);</span></li> <li style="background: #f3f3f3">            <span style="background:#ffffff;color:#0000ff">#endif</span></li> <li>        <span style="background:#ffffff;color:#000000">}</span></li> <li style="background: #f3f3f3">&nbsp;</li> <li>        <span style="background:#ffffff;color:#000000"></span><span style="background:#ffffff;color:#0000ff">private</span><span style="background:#ffffff;color:#000000"> </span><span style="background:#ffffff;color:#0000ff">async</span><span style="background:#ffffff;color:#000000"> </span><span style="background:#ffffff;color:#0000ff">void</span><span style="background:#ffffff;color:#000000"> showStoreReviewPageAsync(</span><span style="background:#ffffff;color:#0000ff">string</span><span style="background:#ffffff;color:#000000"> prefix, </span><span style="background:#ffffff;color:#0000ff">string</span><span style="background:#ffffff;color:#000000"> data)</span></li> <li style="background: #f3f3f3">        <span style="background:#ffffff;color:#000000">{</span></li> <li>            <span style="background:#ffffff;color:#000000"></span><span style="background:#ffffff;color:#0000ff">await</span><span style="background:#ffffff;color:#000000"> </span><span style="background:#ffffff;color:#2b91af">CoreApplication</span><span style="background:#ffffff;color:#000000">.MainView.CoreWindow.Dispatcher.RunAsync(</span><span style="background:#ffffff;color:#2b91af">CoreDispatcherPriority</span><span style="background:#ffffff;color:#000000">.Normal, </span><span style="background:#ffffff;color:#0000ff">async</span><span style="background:#ffffff;color:#000000"> () =&gt;</span></li> <li style="background: #f3f3f3">            <span style="background:#ffffff;color:#000000">{</span></li> <li>                <span style="background:#ffffff;color:#000000"></span><span style="background:#ffffff;color:#0000ff">var</span><span style="background:#ffffff;color:#000000"> uri = </span><span style="background:#ffffff;color:#0000ff">new</span><span style="background:#ffffff;color:#000000"> </span><span style="background:#ffffff;color:#2b91af">Uri</span><span style="background:#ffffff;color:#000000">(</span><span style="background:#ffffff;color:#0000ff">string</span><span style="background:#ffffff;color:#000000">.Format(prefix, data));</span></li> <li style="background: #f3f3f3">                <span style="background:#ffffff;color:#000000"></span><span style="background:#ffffff;color:#0000ff">await</span><span style="background:#ffffff;color:#000000"> Windows.System.</span><span style="background:#ffffff;color:#2b91af">Launcher</span><span style="background:#ffffff;color:#000000">.LaunchUriAsync(uri);</span></li> <li>            <span style="background:#ffffff;color:#000000">});</span></li> <li style="background: #f3f3f3">        <span style="background:#ffffff;color:#000000">}</span></li> <li><span style="background:#ffffff;color:#0000ff">#endif</span></li> </ol> </div> </div> </div>  <p>Bien sûr avec l’arrivée de Windows 10, ce code deviendra obsolète. En attendant, cela reste une implémentation efficace. </p>  <p><strong>Réponse 2</strong> : pour gérer le bouton “Retour” présent sur Windows Phone mais absent sur Windows. En général, lorsque l’utilisateur active la touche “Retour”, soit il le fait lorsqu’il navigue dans des menus (dans ce cas il faut afficher le menu précédent ou quitter le jeu), soit il l’actionne en plein jeu (dans ce cas, il faut mettre le jeu en pause). Sous Unity, le bouton “Retour” est mappé sur la touche “ESC”. Par conséquent voici un exemple de code basique gérant la touche retour uniquement pour Windows Phone :</p>  <div id="scid:9ce6104f-a9aa-4a17-a79f-3a39532ebf7c:fcc18c2e-6690-47cb-b479-e50155b563b6" class="wlWriterEditableSmartContent" style="float: none; padding-bottom: 0px; padding-top: 0px; padding-left: 0px; margin: 0px; display: inline; padding-right: 0px"> <div style="border: #000080 1px solid; color: #000; font-family: 'Courier New', Courier, Monospace; font-size: 10pt"> <div style="background: #000080; color: #fff; font-family: Verdana, Tahoma, Arial, sans-serif; font-weight: bold; padding: 2px 5px">Code Snippet</div> <div style="background: #ddd; overflow: auto"> <ol start="1" style="background: #ffffff; margin: 0 0 0 2.5em; padding: 0 0 0 5px;"> <li><span style="background:#ffffff;color:#0000ff">void</span><span style="background:#ffffff;color:#000000"> Update()</span></li> <li style="background: #f3f3f3">    <span style="background:#ffffff;color:#000000">{</span></li> <li>        <span style="background:#ffffff;color:#0000ff">#if</span><span style="background:#ffffff;color:#000000"> UNITY_WP_8_1</span></li> <li style="background: #f3f3f3">            <span style="background:#ffffff;color:#000000"></span><span style="background:#ffffff;color:#0000ff">if</span><span style="background:#ffffff;color:#000000"> (</span><span style="background:#ffffff;color:#2b91af">Input</span><span style="background:#ffffff;color:#000000">.GetKeyDown(</span><span style="background:#ffffff;color:#2b91af">KeyCode</span><span style="background:#ffffff;color:#000000">.Escape))</span></li> <li>            <span style="background:#ffffff;color:#000000">{</span></li> <li style="background: #f3f3f3">                <span style="background:#ffffff;color:#000000"></span><span style="background:#ffffff;color:#2b91af">Application</span><span style="background:#ffffff;color:#000000">.Quit();</span></li> <li>            <span style="background:#ffffff;color:#000000">}</span></li> <li style="background: #f3f3f3">        <span style="background:#ffffff;color:#0000ff">#endif</span></li> <li>    <span style="background:#ffffff;color:#000000">}</span></li> </ol> </div> </div> </div>  <p>&#160;</p>  <h1>Les Plugins</h1>  <p>Utiliser des directives de compilations c’est bien mais cela peut rendre le code difficilement maintenable ou lisible. Une alternative possible est de définir une librairie (DLL) contenant tous les appels dépendants de la plateforme. Dans cette seconde partie de l’article, je vous propose donc de définir une telle librairie ou plutôt deux librairies :</p>  <ul>   <li>Une librairie dénommée “MyPlugin.dll” dans laquelle je vais définir la méthode permettant d’afficher une boite de dialogue native (au sens natif à la plateforme Windows) </li>    <li>Une seconde librairie ayant le même nom “MyPlugin.dll” et contenant la même interface mais avec une implémentation vide (on parle alors de “Stub” ou coquille vide). Pourquoi ? Tout simplement pour permettre à votre jeu de s’exécuter dans le player de l’éditeur Unity. Du coup l’appel aux APIs plateformes ne se fera que dans un contexte d’exécution plateforme. </li> </ul>  <h2>Création du plugin</h2>  <p>Nous allons donc créer un plugin sous forme de DLL universelle ciblant Windows 8.1 et Windows Phone 8.1. </p>  <p>Pour commencer je vais créer un nouveau projet sous VS2013&#160; : dénommé “MyPlugin” de type <strong>Visual C# –&gt; Store App –&gt; Universal App –&gt; Class Library (Portable for Universal Apps) :</strong></p>  <p><a href="https://msdnshared.blob.core.windows.net/media/MSDNBlogsFS/prod.evol.blogs.msdn.com/CommunityServer.Blogs.Components.WeblogFiles/00/00/01/70/07/metablogapi/0181.image6_3FCB1D27.png" original-url="https://blogs.msdn.com/cfs-file.ashx/__key/communityserver-blogs-components-weblogfiles/00-00-01-70-07-metablogapi/0181.image6_5F00_3FCB1D27.png"><img title="image" style="border-top: 0px; border-right: 0px; background-image: none; border-bottom: 0px; padding-top: 0px; padding-left: 0px; border-left: 0px; display: inline; padding-right: 0px" border="0" alt="image" src="https://msdnshared.blob.core.windows.net/media/MSDNBlogsFS/prod.evol.blogs.msdn.com/CommunityServer.Blogs.Components.WeblogFiles/00/00/01/70/07/metablogapi/1563.image6_thumb_2DA701BA.png" original-url="https://blogs.msdn.com/cfs-file.ashx/__key/communityserver-blogs-components-weblogfiles/00-00-01-70-07-metablogapi/1563.image6_5F00_thumb_5F00_2DA701BA.png" width="646" height="448" /></a></p>  <ol>   <li>Je choisis la catégorie de template <strong>Visual C# –&gt; Store App –&gt; Universal App </strong></li>    <li>Je veille à ce que la version de mon plugin soit basée sur le <strong>framework .NET 4.5.1</strong> afin de pouvoir utiliser dans mon plugin la dernière version .NET compatible avec les plateformes Windows 8.1 / Windows Phone 8.1 </li>    <li>Puis je sélectionne <strong>Class Library (Portable for Universal Apps)</strong> ce qui me permettra de créer une librairie sous forme de DLL utilisable à la fois sur Windows et sur Windows Phone </li>    <li>Je définis un nom de projet pour ma librairie : <strong>UniversalPlugin</strong> </li>    <li>Enfin je nomme ma solution MyPlugins et je valide la création en cliquant sur le bouton “OK” </li> </ol>  <p>&#160;</p>  <p>Visual Studio va alors créer la structure de fichiers suivante (capture sous de l’explorateur de fichiers sous Windows ) :</p>  <p><a href="https://msdnshared.blob.core.windows.net/media/MSDNBlogsFS/prod.evol.blogs.msdn.com/CommunityServer.Blogs.Components.WeblogFiles/00/00/01/70/07/metablogapi/6204.image10_4CEEC9EF.png" original-url="https://blogs.msdn.com/cfs-file.ashx/__key/communityserver-blogs-components-weblogfiles/00-00-01-70-07-metablogapi/6204.image10_5F00_4CEEC9EF.png"><img title="image" style="border-top: 0px; border-right: 0px; background-image: none; border-bottom: 0px; padding-top: 0px; padding-left: 0px; border-left: 0px; display: inline; padding-right: 0px" border="0" alt="image" src="https://msdnshared.blob.core.windows.net/media/MSDNBlogsFS/prod.evol.blogs.msdn.com/CommunityServer.Blogs.Components.WeblogFiles/00/00/01/70/07/metablogapi/2867.image10_thumb_07D5FCB9.png" original-url="https://blogs.msdn.com/cfs-file.ashx/__key/communityserver-blogs-components-weblogfiles/00-00-01-70-07-metablogapi/2867.image10_5F00_thumb_5F00_07D5FCB9.png" width="646" height="280" /></a></p>  <p>Et la structure de projet logique suivante (capture de l’explorateur de solution sous Visual Studio) :</p>  <p><a href="https://msdnshared.blob.core.windows.net/media/MSDNBlogsFS/prod.evol.blogs.msdn.com/CommunityServer.Blogs.Components.WeblogFiles/00/00/01/70/07/metablogapi/4477.image14_0289A6B9.png" original-url="https://blogs.msdn.com/cfs-file.ashx/__key/communityserver-blogs-components-weblogfiles/00-00-01-70-07-metablogapi/4477.image14_5F00_0289A6B9.png"><img title="image" style="border-top: 0px; border-right: 0px; background-image: none; border-bottom: 0px; padding-top: 0px; padding-left: 0px; border-left: 0px; display: inline; padding-right: 0px" border="0" alt="image" src="https://msdnshared.blob.core.windows.net/media/MSDNBlogsFS/prod.evol.blogs.msdn.com/CommunityServer.Blogs.Components.WeblogFiles/00/00/01/70/07/metablogapi/5751.image14_thumb_59156578.png" original-url="https://blogs.msdn.com/cfs-file.ashx/__key/communityserver-blogs-components-weblogfiles/00-00-01-70-07-metablogapi/5751.image14_5F00_thumb_5F00_59156578.png" width="646" height="323" /></a></p>  <p>Par défaut VS2013 a crée une classe unique dénommée Class1 définie dans le fichier correspondant Class1.cs. Je vous propose d’effacer ce fichier (sélectionnez le projet “UniversalPlugin” depuis l’explorateur de solution Visual Studio et ouvrez le menu contextuel en cliquant sur le bouton droit de la souris, puis sélectionnez “Effacer”). Nous allons créer une interface qui va définir les méthodes publiques du plugins qui seront accessibles depuis vos scripts Unity : pour cela je vous invite à ré-affichez le menu contextuel du projet “UniversalPlugin” sous Visual Studio et sélectionnez “Ajouter&#160; / Nouvel élément” :</p>  <p><a href="https://msdnshared.blob.core.windows.net/media/MSDNBlogsFS/prod.evol.blogs.msdn.com/CommunityServer.Blogs.Components.WeblogFiles/00/00/01/70/07/metablogapi/6786.image18_1A45FF81.png" original-url="https://blogs.msdn.com/cfs-file.ashx/__key/communityserver-blogs-components-weblogfiles/00-00-01-70-07-metablogapi/6786.image18_5F00_1A45FF81.png"><img title="image" style="border-top: 0px; border-right: 0px; background-image: none; border-bottom: 0px; padding-top: 0px; padding-left: 0px; border-left: 0px; display: inline; padding-right: 0px" border="0" alt="image" src="https://msdnshared.blob.core.windows.net/media/MSDNBlogsFS/prod.evol.blogs.msdn.com/CommunityServer.Blogs.Components.WeblogFiles/00/00/01/70/07/metablogapi/7140.image18_thumb_5CDD4D0C.png" original-url="https://blogs.msdn.com/cfs-file.ashx/__key/communityserver-blogs-components-weblogfiles/00-00-01-70-07-metablogapi/7140.image18_5F00_thumb_5F00_5CDD4D0C.png" width="646" height="448" /></a></p>  <ol>   <li>Je sélectionne une interface </li>    <li>… que je nomme IUniversalPlugin.cs (par convention il est intéressant de commencer tout nom d’interface par un “i” majuscule : cela permet en un clin d’œil d’identifier les interfaces de leur implémentation. </li>    <li>Cliquer sur le bouton “Ajout / Add” </li> </ol>  <p>Nous allons ensuite modifier le fichier IUniversalPlugin.cs pour définir deux méthodes permettant d’afficher une boite de dialogue native :</p>  <div id="scid:9ce6104f-a9aa-4a17-a79f-3a39532ebf7c:cec9039b-75ad-4f98-aa1d-20954be3d1dc" class="wlWriterEditableSmartContent" style="float: none; padding-bottom: 0px; padding-top: 0px; padding-left: 0px; margin: 0px; display: inline; padding-right: 0px"> <div style="border: #000080 1px solid; color: #000; font-family: 'Courier New', Courier, Monospace; font-size: 10pt"> <div style="background: #000080; color: #fff; font-family: Verdana, Tahoma, Arial, sans-serif; font-weight: bold; padding: 2px 5px">Code Snippet</div> <div style="background: #ddd; overflow: auto"> <ol start="1" style="background: #ffffff; margin: 0 0 0 2.5em; padding: 0 0 0 5px;"> <li><span style="background:#ffffff;color:#0000ff">using</span><span style="background:#ffffff;color:#000000"> System;</span></li> <li style="background: #f3f3f3"><span style="background:#ffffff;color:#0000ff">using</span><span style="background:#ffffff;color:#000000"> System.Collections.Generic;</span></li> <li><span style="background:#ffffff;color:#0000ff">using</span><span style="background:#ffffff;color:#000000"> System.Linq;</span></li> <li style="background: #f3f3f3"><span style="background:#ffffff;color:#0000ff">using</span><span style="background:#ffffff;color:#000000"> System.Text;</span></li> <li>&nbsp;</li> <li style="background: #f3f3f3"><span style="background:#ffffff;color:#0000ff">namespace</span><span style="background:#ffffff;color:#000000"> MyPlugins</span></li> <li><span style="background:#ffffff;color:#000000">{</span></li> <li style="background: #f3f3f3">    <span style="background:#ffffff;color:#000000"></span><span style="background:#ffffff;color:#008000">/*</span></li> <li>     <span style="background:#ffffff;color:#008000">*   Define unity plugin interfaces for accessing APIs common to both Windows 8.1 and Windows Phone 8.1</span></li> <li style="background: #f3f3f3">     <span style="background:#ffffff;color:#008000">*/</span></li> <li>    <span style="background:#ffffff;color:#000000"></span><span style="background:#ffffff;color:#0000ff">public</span><span style="background:#ffffff;color:#000000"> </span><span style="background:#ffffff;color:#0000ff">interface</span><span style="background:#ffffff;color:#000000"> </span><span style="background:#ffffff;color:#2b91af">IUniversalPlugin</span></li> <li style="background: #f3f3f3">    <span style="background:#ffffff;color:#000000">{</span></li> <li>        <span style="background:#ffffff;color:#000000"></span><span style="background:#ffffff;color:#008000">// Prompt a native dialog box with a message</span></li> <li style="background: #f3f3f3">        <span style="background:#ffffff;color:#000000"></span><span style="background:#ffffff;color:#0000ff">void</span><span style="background:#ffffff;color:#000000"> ShowMessageDialog(</span><span style="background:#ffffff;color:#0000ff">string</span><span style="background:#ffffff;color:#000000"> message);</span></li> <li>&nbsp;</li> <li style="background: #f3f3f3">        <span style="background:#ffffff;color:#000000"></span><span style="background:#ffffff;color:#008000">// Prompt a native dialog box with a message and a title</span></li> <li>        <span style="background:#ffffff;color:#000000"></span><span style="background:#ffffff;color:#0000ff">void</span><span style="background:#ffffff;color:#000000"> ShowMessageDialog(</span><span style="background:#ffffff;color:#0000ff">string</span><span style="background:#ffffff;color:#000000"> message, </span><span style="background:#ffffff;color:#0000ff">string</span><span style="background:#ffffff;color:#000000"> title);</span></li> <li style="background: #f3f3f3">    <span style="background:#ffffff;color:#000000">}</span></li> <li><span style="background:#ffffff;color:#000000">}</span></li> </ol> </div> </div> </div>  <p>Pensez à bien rendre cette interface publique. Reste à implémenter ces deux méthodes. Pour ce faire je vais créer une nouvelle classe dénommée UniversalPlugin dans un nouveau fichier UniversalPlugin.cs. Comment ? Très simple : dans la fenêtre d’explorateur de solution Visual Studio, sélectionnez le projet UniversalPlugin et cliquez sur le bouton droit de la souris. Dans le menu contextuel, sélectionnez “Ajouter / Classe” :</p>  <p><a href="https://msdnshared.blob.core.windows.net/media/MSDNBlogsFS/prod.evol.blogs.msdn.com/CommunityServer.Blogs.Components.WeblogFiles/00/00/01/70/07/metablogapi/1004.image23_21AE92A3.png" original-url="https://blogs.msdn.com/cfs-file.ashx/__key/communityserver-blogs-components-weblogfiles/00-00-01-70-07-metablogapi/1004.image23_5F00_21AE92A3.png"><img title="image" style="border-top: 0px; border-right: 0px; background-image: none; border-bottom: 0px; padding-top: 0px; padding-left: 0px; border-left: 0px; display: inline; padding-right: 0px" border="0" alt="image" src="https://msdnshared.blob.core.windows.net/media/MSDNBlogsFS/prod.evol.blogs.msdn.com/CommunityServer.Blogs.Components.WeblogFiles/00/00/01/70/07/metablogapi/4834.image23_thumb_4D8698A5.png" original-url="https://blogs.msdn.com/cfs-file.ashx/__key/communityserver-blogs-components-weblogfiles/00-00-01-70-07-metablogapi/4834.image23_5F00_thumb_5F00_4D8698A5.png" width="646" height="448" /></a></p>  <ol>   <li>Par défaut, Classe est sélectionnée … ne changez rien </li>    <li>Puis nommez le fichier UniversalPlugin.cs : le fichier contiendra alors la définition (vide) de la classe UniversalPlugin </li> </ol>  <p>Ensuit nous allons modifier ce fichier UniversalPlugin.cs ainsi :</p>  <div id="scid:9ce6104f-a9aa-4a17-a79f-3a39532ebf7c:7344f35c-3985-4c81-92e3-9b4f2bf67495" class="wlWriterEditableSmartContent" style="float: none; padding-bottom: 0px; padding-top: 0px; padding-left: 0px; margin: 0px; display: inline; padding-right: 0px"> <div style="border: #000080 1px solid; color: #000; font-family: 'Courier New', Courier, Monospace; font-size: 10pt"> <div style="background: #000080; color: #fff; font-family: Verdana, Tahoma, Arial, sans-serif; font-weight: bold; padding: 2px 5px">Code Snippet</div> <div style="background: #ddd; overflow: auto"> <ol start="1" style="background: #ffffff; margin: 0 0 0 2.5em; padding: 0 0 0 5px;"> <li><span style="background:#ffffff;color:#0000ff">using</span><span style="background:#ffffff;color:#000000"> System;</span></li> <li style="background: #f3f3f3"><span style="background:#ffffff;color:#0000ff">using</span><span style="background:#ffffff;color:#000000"> System.Collections.Generic;</span></li> <li><span style="background:#ffffff;color:#0000ff">using</span><span style="background:#ffffff;color:#000000"> System.Linq;</span></li> <li style="background: #f3f3f3"><span style="background:#ffffff;color:#0000ff">using</span><span style="background:#ffffff;color:#000000"> System.Text;</span></li> <li><span style="background:#ffffff;color:#0000ff">using</span><span style="background:#ffffff;color:#000000"> System.Threading.Tasks;</span></li> <li style="background: #f3f3f3">&nbsp;</li> <li><span style="background:#ffffff;color:#0000ff">using</span><span style="background:#ffffff;color:#000000"> Windows.ApplicationModel.Core;</span></li> <li style="background: #f3f3f3"><span style="background:#ffffff;color:#0000ff">using</span><span style="background:#ffffff;color:#000000"> Windows.UI.Core;</span></li> <li><span style="background:#ffffff;color:#0000ff">using</span><span style="background:#ffffff;color:#000000"> Windows.UI.Popups;</span></li> <li style="background: #f3f3f3">&nbsp;</li> <li><span style="background:#ffffff;color:#0000ff">namespace</span><span style="background:#ffffff;color:#000000"> MyPlugins</span></li> <li style="background: #f3f3f3"><span style="background:#ffffff;color:#000000">{</span></li> <li>    <span style="background:#ffffff;color:#000000"></span><span style="background:#ffffff;color:#0000ff">public</span><span style="background:#ffffff;color:#000000"> </span><span style="background:#ffffff;color:#0000ff">class</span><span style="background:#ffffff;color:#000000"> </span><span style="background:#ffffff;color:#2b91af">UniversalPlugin</span><span style="background:#ffffff;color:#000000"> : </span><span style="background:#ffffff;color:#2b91af">IUniversalPlugin</span></li> <li style="background: #f3f3f3">    <span style="background:#ffffff;color:#000000">{</span></li> <li>        <span style="background:#ffffff;color:#000000"></span><span style="background:#ffffff;color:#008000">// Singleton pattern</span></li> <li style="background: #f3f3f3">        <span style="background:#ffffff;color:#000000"></span><span style="background:#ffffff;color:#0000ff">private</span><span style="background:#ffffff;color:#000000"> </span><span style="background:#ffffff;color:#0000ff">static</span><span style="background:#ffffff;color:#000000"> </span><span style="background:#ffffff;color:#0000ff">readonly</span><span style="background:#ffffff;color:#000000"> </span><span style="background:#ffffff;color:#2b91af">IUniversalPlugin</span><span style="background:#ffffff;color:#000000"> iinstance = </span><span style="background:#ffffff;color:#0000ff">new</span><span style="background:#ffffff;color:#000000"> </span><span style="background:#ffffff;color:#2b91af">UniversalPlugin</span><span style="background:#ffffff;color:#000000">();</span></li> <li>        <span style="background:#ffffff;color:#000000"></span><span style="background:#ffffff;color:#0000ff">public</span><span style="background:#ffffff;color:#000000"> </span><span style="background:#ffffff;color:#0000ff">static</span><span style="background:#ffffff;color:#000000"> </span><span style="background:#ffffff;color:#2b91af">IUniversalPlugin</span><span style="background:#ffffff;color:#000000"> IInstance</span></li> <li style="background: #f3f3f3">        <span style="background:#ffffff;color:#000000">{</span></li> <li>            <span style="background:#ffffff;color:#000000"></span><span style="background:#ffffff;color:#0000ff">get</span></li> <li style="background: #f3f3f3">            <span style="background:#ffffff;color:#000000">{</span></li> <li>                <span style="background:#ffffff;color:#000000"></span><span style="background:#ffffff;color:#0000ff">return</span><span style="background:#ffffff;color:#000000"> iinstance;</span></li> <li style="background: #f3f3f3">            <span style="background:#ffffff;color:#000000">}</span></li> <li>        <span style="background:#ffffff;color:#000000">}</span></li> <li style="background: #f3f3f3">&nbsp;</li> <li>        <span style="background:#ffffff;color:#000000"></span><span style="background:#ffffff;color:#008000">// Implementation of the first public method of IUniversalPlugin</span></li> <li style="background: #f3f3f3">        <span style="background:#ffffff;color:#000000"></span><span style="background:#ffffff;color:#0000ff">public</span><span style="background:#ffffff;color:#000000"> </span><span style="background:#ffffff;color:#0000ff">void</span><span style="background:#ffffff;color:#000000"> ShowMessageDialog(</span><span style="background:#ffffff;color:#0000ff">string</span><span style="background:#ffffff;color:#000000"> message)</span></li> <li>        <span style="background:#ffffff;color:#000000">{</span></li> <li style="background: #f3f3f3">            <span style="background:#ffffff;color:#000000">showMessageDialogAsyncPriv(message, </span><span style="background:#ffffff;color:#0000ff">null</span><span style="background:#ffffff;color:#000000">);</span></li> <li>        <span style="background:#ffffff;color:#000000">}</span></li> <li style="background: #f3f3f3">&nbsp;</li> <li>        <span style="background:#ffffff;color:#000000"></span><span style="background:#ffffff;color:#008000">// Implementation of the second public method of IUniversalPlugin</span></li> <li style="background: #f3f3f3">        <span style="background:#ffffff;color:#000000"></span><span style="background:#ffffff;color:#0000ff">public</span><span style="background:#ffffff;color:#000000"> </span><span style="background:#ffffff;color:#0000ff">void</span><span style="background:#ffffff;color:#000000"> ShowMessageDialog(</span><span style="background:#ffffff;color:#0000ff">string</span><span style="background:#ffffff;color:#000000"> message, </span><span style="background:#ffffff;color:#0000ff">string</span><span style="background:#ffffff;color:#000000"> title)</span></li> <li>        <span style="background:#ffffff;color:#000000">{</span></li> <li style="background: #f3f3f3">            <span style="background:#ffffff;color:#000000">showMessageDialogAsyncPriv(message, title);</span></li> <li>        <span style="background:#ffffff;color:#000000">}</span></li> <li style="background: #f3f3f3">&nbsp;</li> <li>        <span style="background:#ffffff;color:#000000"></span><span style="background:#ffffff;color:#008000">// Both public implementation of IUniversalPlugin rely on the following common private method</span></li> <li style="background: #f3f3f3">        <span style="background:#ffffff;color:#000000"></span><span style="background:#ffffff;color:#0000ff">private</span><span style="background:#ffffff;color:#000000"> </span><span style="background:#ffffff;color:#0000ff">async</span><span style="background:#ffffff;color:#000000"> </span><span style="background:#ffffff;color:#0000ff">void</span><span style="background:#ffffff;color:#000000"> showMessageDialogAsyncPriv(</span><span style="background:#ffffff;color:#0000ff">string</span><span style="background:#ffffff;color:#000000"> message, </span><span style="background:#ffffff;color:#0000ff">string</span><span style="background:#ffffff;color:#000000"> title)</span></li> <li>        <span style="background:#ffffff;color:#000000">{</span></li> <li style="background: #f3f3f3">            <span style="background:#ffffff;color:#000000"></span><span style="background:#ffffff;color:#008000">// Request the execution of the lambda expression argument to be done by the UI thread from the current worker thread</span></li> <li>            <span style="background:#ffffff;color:#000000"></span><span style="background:#ffffff;color:#0000ff">await</span><span style="background:#ffffff;color:#000000"> </span><span style="background:#ffffff;color:#2b91af">CoreApplication</span><span style="background:#ffffff;color:#000000">.MainView.CoreWindow.Dispatcher.RunAsync(</span><span style="background:#ffffff;color:#2b91af">CoreDispatcherPriority</span><span style="background:#ffffff;color:#000000">.Normal, </span><span style="background:#ffffff;color:#0000ff">async</span><span style="background:#ffffff;color:#000000"> () =&gt;</span></li> <li style="background: #f3f3f3">            <span style="background:#ffffff;color:#000000">{</span></li> <li>                <span style="background:#ffffff;color:#000000"></span><span style="background:#ffffff;color:#2b91af">MessageDialog</span><span style="background:#ffffff;color:#000000"> messageBox;</span></li> <li style="background: #f3f3f3">&nbsp;</li> <li>                <span style="background:#ffffff;color:#000000"></span><span style="background:#ffffff;color:#0000ff">if</span><span style="background:#ffffff;color:#000000"> (title != </span><span style="background:#ffffff;color:#0000ff">null</span><span style="background:#ffffff;color:#000000">) messageBox = </span><span style="background:#ffffff;color:#0000ff">new</span><span style="background:#ffffff;color:#000000"> </span><span style="background:#ffffff;color:#2b91af">MessageDialog</span><span style="background:#ffffff;color:#000000">(message, title);</span></li> <li style="background: #f3f3f3">                <span style="background:#ffffff;color:#000000"></span><span style="background:#ffffff;color:#0000ff">else</span></li> <li>                    <span style="background:#ffffff;color:#000000">messageBox = </span><span style="background:#ffffff;color:#0000ff">new</span><span style="background:#ffffff;color:#000000"> </span><span style="background:#ffffff;color:#2b91af">MessageDialog</span><span style="background:#ffffff;color:#000000">(message);</span></li> <li style="background: #f3f3f3">&nbsp;</li> <li>                <span style="background:#ffffff;color:#000000"></span><span style="background:#ffffff;color:#008000">// Display the message box</span></li> <li style="background: #f3f3f3">                <span style="background:#ffffff;color:#000000"></span><span style="background:#ffffff;color:#0000ff">await</span><span style="background:#ffffff;color:#000000"> messageBox.ShowAsync();</span></li> <li>            <span style="background:#ffffff;color:#000000">});</span></li> <li style="background: #f3f3f3">        <span style="background:#ffffff;color:#000000">}</span></li> <li>    <span style="background:#ffffff;color:#000000">}</span></li> <li style="background: #f3f3f3"><span style="background:#ffffff;color:#000000">}</span></li> </ol> </div> </div> </div>  <p align="justify">Première remarque : j’ai renommé l’espace de nom initial “UniversalPlugin” en “MyPlugins” de manière à distinguer l’espace de nom des classes qu’il contient. Pour cela j’ai sélectionné avec le curseur de souris l’espace de nom initial, UniversalPlugin et j’ai cliqué sur le bouton droit et choisi le menu “Refactor –&gt; Rename” : cela permet de modifier le nom d’espace dans la globalité du projet (au niveau de la DLL et de tous les fichiers de code).</p>  <p align="justify">Ensuite, afin d’optimiser l’utilisation de la classe UniversalPlugin, nous utilisons le pattern classique de “Singleton” ce qui permet de ré-utiliser la même instance pour différents appels. Un appel à la méthode d’affichage d’une boite de dialogue natif se fera donc ainsi :</p>  <p align="justify"><font face="Courier New">UniversalPlugin.IInstance.ShowMessageDialog(“Hello from WinRT”);</font></p>  <p align="justify">&#160;</p>  <p align="justify">La méthode <font face="Courier New">showMessageDialogAsyncPriv </font>mérite quelques explications : l’affichage d’une boite de dialogue sous Windows/Windows Phone requiert l’exécution dans le contexte du thread graphique (encore appelé thread UI). Or par défaut, une application Unity s’exécute dans un thread applicatif (encore appelé worker thread). Par conséquent la méthode CoreApplication.MainView.CoreWindow.Dispatcher.RunAsync permet de demander l’exécution du code asynchrone inclus dans la lambda expression passée en second paramètre. Si vous appelez directement la méthode messageBox.ShowAsync, votre application se terminera brutalement suite à une levée d’exception système. Lorsque nous compilons le projet “UniversalPlugin”, une DLL dénommée UniversalPlugin.dll sera générée dans le répertoire MyPlugins\UniversalPlugin\bin\Debug (ou MyPlugins\UniversalPlugin\bin\Release). Comme je le mentionnais en début de paragraphe sur les plugins : la création de cette librairie est nécessaire mais pas suffisante. En effet si vous utilisez directement cette librairie depuis vos scripts Unity, ces derniers ne compileront pas du fait de l’utilisation d’API .NET WinRT (à moins d’utiliser une directive de type NETFX_CORE … mais dans ce cas on perd tout l’intérêt d’utiliser un plugin). Il faut donc définir une seconde librairie reprenant les mêmes méthodes de la première librairie mais en y implémentant des méthodes vides (classiquement appelées Stub). C’est donc ce que nous allons voir maintenant.</p>  <p align="justify">Depuis l’explorateur de solutions sous Visual Studio, sélectionnez la solution “MyPlugins” puis afficher le menu contextuel (souris bouton droit) et choisissez le menu “Ajouter / Nouveau Projet” :</p>  <p><a href="https://msdnshared.blob.core.windows.net/media/MSDNBlogsFS/prod.evol.blogs.msdn.com/CommunityServer.Blogs.Components.WeblogFiles/00/00/01/70/07/metablogapi/7563.image_1DF02C2C.png" original-url="https://blogs.msdn.com/cfs-file.ashx/__key/communityserver-blogs-components-weblogfiles/00-00-01-70-07-metablogapi/7563.image_5F00_1DF02C2C.png"><img title="image" style="border-top: 0px; border-right: 0px; background-image: none; border-bottom: 0px; padding-top: 0px; padding-left: 0px; border-left: 0px; display: inline; padding-right: 0px" border="0" alt="image" src="https://msdnshared.blob.core.windows.net/media/MSDNBlogsFS/prod.evol.blogs.msdn.com/CommunityServer.Blogs.Components.WeblogFiles/00/00/01/70/07/metablogapi/0068.image_thumb_48862A00.png" original-url="https://blogs.msdn.com/cfs-file.ashx/__key/communityserver-blogs-components-weblogfiles/00-00-01-70-07-metablogapi/0068.image_5F00_thumb_5F00_48862A00.png" width="646" height="448" /></a></p>  <ol>   <ol>     <li>       <div>Je choisis la catégorie de template <strong>Visual C# –&gt; Windows Desktop</strong></div>     </li>      <li>       <div>Je veille à ce que la version de mon plugin soit basée sur le <strong>framework .NET 3.5 (et non .NET 4.5.1)</strong> car Unity s’appuie sur Mono (dont implémentation Open Source de .NET est équivalent à la version 3.5) </div>     </li>      <li>       <div>Puis je sélectionne <strong>Class Library (Portable for Universal Apps)</strong> ce qui me permettra de créer une librairie sous forme de DLL utilisable à la fois sur Windows et sur Windows Phone </div>     </li>      <li>       <div>Je définis un nom de projet pour ma librairie Stub : <strong>UniversalPlugin.Stub</strong> </div>     </li>      <li>       <div>Enfin je conserve le chemin de destination par défaut (qui correspond à mon répertoire de travail) et je valide la création en cliquant sur le bouton “OK”</div>     </li>   </ol> </ol>  <p>Visual Studio va alors créer la structure de fichiers suivante (capture sous de l’explorateur de fichiers sous Windows ) :</p>  <p><a href="https://msdnshared.blob.core.windows.net/media/MSDNBlogsFS/prod.evol.blogs.msdn.com/CommunityServer.Blogs.Components.WeblogFiles/00/00/01/70/07/metablogapi/4774.image31_36CBB0D7.png" original-url="https://blogs.msdn.com/cfs-file.ashx/__key/communityserver-blogs-components-weblogfiles/00-00-01-70-07-metablogapi/4774.image31_5F00_36CBB0D7.png"><img title="image" style="border-top: 0px; border-right: 0px; background-image: none; border-bottom: 0px; padding-top: 0px; padding-left: 0px; border-left: 0px; display: inline; padding-right: 0px" border="0" alt="image" src="https://msdnshared.blob.core.windows.net/media/MSDNBlogsFS/prod.evol.blogs.msdn.com/CommunityServer.Blogs.Components.WeblogFiles/00/00/01/70/07/metablogapi/8311.image31_thumb_466E4C99.png" original-url="https://blogs.msdn.com/cfs-file.ashx/__key/communityserver-blogs-components-weblogfiles/00-00-01-70-07-metablogapi/8311.image31_5F00_thumb_5F00_466E4C99.png" width="646" height="324" /></a></p>  <p>Et la structure de projet logique suivante (capture de l’explorateur de solution sous Visual Studio) :</p>  <p><a href="https://msdnshared.blob.core.windows.net/media/MSDNBlogsFS/prod.evol.blogs.msdn.com/CommunityServer.Blogs.Components.WeblogFiles/00/00/01/70/07/metablogapi/3808.image36_70DF9F18.png" original-url="https://blogs.msdn.com/cfs-file.ashx/__key/communityserver-blogs-components-weblogfiles/00-00-01-70-07-metablogapi/3808.image36_5F00_70DF9F18.png"><img title="image" style="border-top: 0px; border-right: 0px; background-image: none; border-bottom: 0px; padding-top: 0px; padding-left: 0px; border-left: 0px; display: inline; padding-right: 0px" border="0" alt="image" src="https://msdnshared.blob.core.windows.net/media/MSDNBlogsFS/prod.evol.blogs.msdn.com/CommunityServer.Blogs.Components.WeblogFiles/00/00/01/70/07/metablogapi/7041.image36_thumb_6E397418.png" original-url="https://blogs.msdn.com/cfs-file.ashx/__key/communityserver-blogs-components-weblogfiles/00-00-01-70-07-metablogapi/7041.image36_5F00_thumb_5F00_6E397418.png" width="646" height="436" /></a></p>  <p>Dorénavant nous avons deux projets dans notre solution MyPlugins :</p>  <ul>   <li>UniversalPlugin </li>    <li>UniversalPlugin.Stub </li> </ul>  <p>Si vous ouvrez le fichier Class1.cs créé par défaut, vous verrez que la classe appartient à l’espace de nom (namespace en anglais) UniversalPlugin.Stub : c’est un problème car l’objectif du stub est de rendre les choses transparentes pour Unity lorsque vous exécuterez votre code depuis l’éditeur. Par conséquent il faut modifier cet espace de nom pour qu’il soit identique à l’espace de nom de la première librairie à savoir MyPlugins. Pour cela, sélectionnez le projet “UniversalPlugin.Stub” depuis Visual Studio, cliquez sur le bouton droit de souris et cliquez sur le menu “Propriétés” :</p>  <p><a href="https://msdnshared.blob.core.windows.net/media/MSDNBlogsFS/prod.evol.blogs.msdn.com/CommunityServer.Blogs.Components.WeblogFiles/00/00/01/70/07/metablogapi/0131.image40_313A63E8.png" original-url="https://blogs.msdn.com/cfs-file.ashx/__key/communityserver-blogs-components-weblogfiles/00-00-01-70-07-metablogapi/0131.image40_5F00_313A63E8.png"><img title="image" style="border-top: 0px; border-right: 0px; background-image: none; border-bottom: 0px; padding-top: 0px; padding-left: 0px; border-left: 0px; display: inline; padding-right: 0px" border="0" alt="image" src="https://msdnshared.blob.core.windows.net/media/MSDNBlogsFS/prod.evol.blogs.msdn.com/CommunityServer.Blogs.Components.WeblogFiles/00/00/01/70/07/metablogapi/1121.image40_thumb_22FE7BA9.png" original-url="https://blogs.msdn.com/cfs-file.ashx/__key/communityserver-blogs-components-weblogfiles/00-00-01-70-07-metablogapi/1121.image40_5F00_thumb_5F00_22FE7BA9.png" width="646" height="410" /></a></p>  <ul>   <li>Renommer le nom de l’assembly en <strong>UniversalPlugin</strong> afin que le fichier DLL du stub soit identique au nom de fichier DLL de la première librairie </li>    <li>Renommer le nom d’espace par défaut en <strong>MyPlugins</strong> </li>    <li>Sauvegarder les propriétés du projet (combinaison de touches CTRL + S) </li> </ul>  <p>Je vous propose ensuite d’effacer le fichier Class1.cs (sélectionnez le projet “UniversalPlugin.Stub” depuis l’explorateur de solution Visual Studio et ouvrez le menu contextuel en cliquant sur le bouton droit de la souris, puis sélectionnez “Effacer”). Maintenant nous allons ajouter une classe (ou plutôt un lien symbolique)&#160; du projet UniversalPlugin (donc déjà existante) dans le projet UniversalPlugin.Stub : il s’agit de l’interface IUniversalPlugin ; pour cela sélectionnez le projet UniversalPlugin.Stub, puis afficher le menu contextuel et choisissez “Ajouter / Elément existant” :</p>  <p><a href="https://msdnshared.blob.core.windows.net/media/MSDNBlogsFS/prod.evol.blogs.msdn.com/CommunityServer.Blogs.Components.WeblogFiles/00/00/01/70/07/metablogapi/7367.image45_28DE40A4.png" original-url="https://blogs.msdn.com/cfs-file.ashx/__key/communityserver-blogs-components-weblogfiles/00-00-01-70-07-metablogapi/7367.image45_5F00_28DE40A4.png"><img title="image" style="border-top: 0px; border-right: 0px; background-image: none; border-bottom: 0px; padding-top: 0px; padding-left: 0px; border-left: 0px; display: inline; padding-right: 0px" border="0" alt="image" src="https://msdnshared.blob.core.windows.net/media/MSDNBlogsFS/prod.evol.blogs.msdn.com/CommunityServer.Blogs.Components.WeblogFiles/00/00/01/70/07/metablogapi/3718.image45_thumb_07ED5EAE.png" original-url="https://blogs.msdn.com/cfs-file.ashx/__key/communityserver-blogs-components-weblogfiles/00-00-01-70-07-metablogapi/3718.image45_5F00_thumb_5F00_07ED5EAE.png" width="646" height="432" /></a></p>  <ol>   <li>Modifiez le répertoire sélectionné par défaut (UniversalPlugin.Stub) afin de parcourir le répertoire UniversalPlugin </li>    <li>Sélectionnez le fichier d’interface IUniversalPlugin.cs </li>    <li>Cliquez sur le bouton “Ajouter comme lien” de manière à créer une référence à ce fichier dans votre projet courant UniversalPlugin.Stub </li> </ol>  <p>Notez la petite flèche sur l’icone du fichier IUniversalPlugin.cs de votre projet UniversalPlugin.Stub :</p>  <p><a href="https://msdnshared.blob.core.windows.net/media/MSDNBlogsFS/prod.evol.blogs.msdn.com/CommunityServer.Blogs.Components.WeblogFiles/00/00/01/70/07/metablogapi/2287.image49_71BC64BD.png" original-url="https://blogs.msdn.com/cfs-file.ashx/__key/communityserver-blogs-components-weblogfiles/00-00-01-70-07-metablogapi/2287.image49_5F00_71BC64BD.png"><img title="image" style="border-top: 0px; border-right: 0px; background-image: none; border-bottom: 0px; padding-top: 0px; padding-left: 0px; border-left: 0px; display: inline; padding-right: 0px" border="0" alt="image" src="https://msdnshared.blob.core.windows.net/media/MSDNBlogsFS/prod.evol.blogs.msdn.com/CommunityServer.Blogs.Components.WeblogFiles/00/00/01/70/07/metablogapi/1464.image49_thumb_63ECAF73.png" original-url="https://blogs.msdn.com/cfs-file.ashx/__key/communityserver-blogs-components-weblogfiles/00-00-01-70-07-metablogapi/1464.image49_5F00_thumb_5F00_63ECAF73.png" width="646" height="453" /></a></p>  <p>&#160;</p>  <p>Nous avons créé un lien symbolique qui permet de simplifier la maintenance de l’interface du plugin : si nous voulons ajouter une nouvelle méthode, inutile de modifier deux fichiers avec le risque d’erreur que cela peut induire. Reste maintenant à définir la partie Stub, ce qui est très simple : sélectionnez le projet UniversalPlugin.Stub, puis afficher le menu contextuel et choisissez “Ajouter / Elément existant” :</p>  <p><a href="https://msdnshared.blob.core.windows.net/media/MSDNBlogsFS/prod.evol.blogs.msdn.com/CommunityServer.Blogs.Components.WeblogFiles/00/00/01/70/07/metablogapi/3823.image53_3DAF777D.png" original-url="https://blogs.msdn.com/cfs-file.ashx/__key/communityserver-blogs-components-weblogfiles/00-00-01-70-07-metablogapi/3823.image53_5F00_3DAF777D.png"><img title="image" style="border-top: 0px; border-right: 0px; background-image: none; border-bottom: 0px; padding-top: 0px; padding-left: 0px; border-left: 0px; display: inline; padding-right: 0px" border="0" alt="image" src="https://msdnshared.blob.core.windows.net/media/MSDNBlogsFS/prod.evol.blogs.msdn.com/CommunityServer.Blogs.Components.WeblogFiles/00/00/01/70/07/metablogapi/2766.image53_thumb_3C6D6F4F.png" original-url="https://blogs.msdn.com/cfs-file.ashx/__key/communityserver-blogs-components-weblogfiles/00-00-01-70-07-metablogapi/2766.image53_5F00_thumb_5F00_3C6D6F4F.png" width="646" height="409" /></a></p>  <ul>   <ol>     <li>Modifiez le répertoire sélectionné par défaut (UniversalPlugin.Stub) afin de parcourir le répertoire UniversalPlugin </li>      <li>Sélectionnez le fichier d’interface UniversalPlugin.cs (sans le “i” majuscule cette fois) </li>      <li>Cliquez sur le bouton “Ajouter” de manière à créer une copie de ce fichier dans votre projet courant UniversalPlugin.Stub <!--EndFragment--></li>   </ol> </ul>  <p>Modifier votre fichier UniversalPlugin.cs fraichement dupliqué :</p>  <div id="scid:9ce6104f-a9aa-4a17-a79f-3a39532ebf7c:f55f00b3-5acf-4992-8db0-831ed6f2a148" class="wlWriterEditableSmartContent" style="float: none; padding-bottom: 0px; padding-top: 0px; padding-left: 0px; margin: 0px; display: inline; padding-right: 0px"> <div style="border: #000080 1px solid; color: #000; font-family: 'Courier New', Courier, Monospace; font-size: 10pt"> <div style="background: #000080; color: #fff; font-family: Verdana, Tahoma, Arial, sans-serif; font-weight: bold; padding: 2px 5px">Code Snippet</div> <div style="background: #ddd; overflow: auto"> <ol start="1" style="background: #ffffff; margin: 0 0 0 2.5em; padding: 0 0 0 5px;"> <li><span style="background:#ffffff;color:#0000ff">using</span><span style="background:#ffffff;color:#000000"> System;</span></li> <li style="background: #f3f3f3"><span style="background:#ffffff;color:#0000ff">using</span><span style="background:#ffffff;color:#000000"> System.Collections.Generic;</span></li> <li><span style="background:#ffffff;color:#0000ff">using</span><span style="background:#ffffff;color:#000000"> System.Linq;</span></li> <li style="background: #f3f3f3"><span style="background:#ffffff;color:#0000ff">using</span><span style="background:#ffffff;color:#000000"> System.Text;</span></li> <li>&nbsp;</li> <li style="background: #f3f3f3">&nbsp;</li> <li><span style="background:#ffffff;color:#0000ff">namespace</span><span style="background:#ffffff;color:#000000"> MyPlugins</span></li> <li style="background: #f3f3f3"><span style="background:#ffffff;color:#000000">{</span></li> <li>    <span style="background:#ffffff;color:#000000"></span><span style="background:#ffffff;color:#0000ff">public</span><span style="background:#ffffff;color:#000000"> </span><span style="background:#ffffff;color:#0000ff">class</span><span style="background:#ffffff;color:#000000"> </span><span style="background:#ffffff;color:#2b91af">UniversalPlugin</span><span style="background:#ffffff;color:#000000"> : </span><span style="background:#ffffff;color:#2b91af">IUniversalPlugin</span></li> <li style="background: #f3f3f3">    <span style="background:#ffffff;color:#000000">{</span></li> <li>        <span style="background:#ffffff;color:#000000"></span><span style="background:#ffffff;color:#008000">// Singleton pattern</span></li> <li style="background: #f3f3f3">        <span style="background:#ffffff;color:#000000"></span><span style="background:#ffffff;color:#0000ff">private</span><span style="background:#ffffff;color:#000000"> </span><span style="background:#ffffff;color:#0000ff">static</span><span style="background:#ffffff;color:#000000"> </span><span style="background:#ffffff;color:#0000ff">readonly</span><span style="background:#ffffff;color:#000000"> </span><span style="background:#ffffff;color:#2b91af">IUniversalPlugin</span><span style="background:#ffffff;color:#000000"> iinstance = </span><span style="background:#ffffff;color:#0000ff">new</span><span style="background:#ffffff;color:#000000"> </span><span style="background:#ffffff;color:#2b91af">UniversalPlugin</span><span style="background:#ffffff;color:#000000">();</span></li> <li>        <span style="background:#ffffff;color:#000000"></span><span style="background:#ffffff;color:#0000ff">public</span><span style="background:#ffffff;color:#000000"> </span><span style="background:#ffffff;color:#0000ff">static</span><span style="background:#ffffff;color:#000000"> </span><span style="background:#ffffff;color:#2b91af">IUniversalPlugin</span><span style="background:#ffffff;color:#000000"> IInstance</span></li> <li style="background: #f3f3f3">        <span style="background:#ffffff;color:#000000">{</span></li> <li>            <span style="background:#ffffff;color:#000000"></span><span style="background:#ffffff;color:#0000ff">get</span></li> <li style="background: #f3f3f3">            <span style="background:#ffffff;color:#000000">{</span></li> <li>                <span style="background:#ffffff;color:#000000"></span><span style="background:#ffffff;color:#0000ff">return</span><span style="background:#ffffff;color:#000000"> iinstance;</span></li> <li style="background: #f3f3f3">            <span style="background:#ffffff;color:#000000">}</span></li> <li>        <span style="background:#ffffff;color:#000000">}</span></li> <li style="background: #f3f3f3">&nbsp;</li> <li>        <span style="background:#ffffff;color:#000000"></span><span style="background:#ffffff;color:#008000">// Implementation of the first public method of IUniversalPlugin</span></li> <li style="background: #f3f3f3">        <span style="background:#ffffff;color:#000000"></span><span style="background:#ffffff;color:#0000ff">public</span><span style="background:#ffffff;color:#000000"> </span><span style="background:#ffffff;color:#0000ff">void</span><span style="background:#ffffff;color:#000000"> ShowMessageDialog(</span><span style="background:#ffffff;color:#0000ff">string</span><span style="background:#ffffff;color:#000000"> message)</span></li> <li>        <span style="background:#ffffff;color:#000000">{</span></li> <li style="background: #f3f3f3">            <span style="background:#ffffff;color:#000000"></span></li> <li>        <span style="background:#ffffff;color:#000000">}</span></li> <li style="background: #f3f3f3">&nbsp;</li> <li>        <span style="background:#ffffff;color:#000000"></span><span style="background:#ffffff;color:#008000">// Implementation of the second public method of IUniversalPlugin</span></li> <li style="background: #f3f3f3">        <span style="background:#ffffff;color:#000000"></span><span style="background:#ffffff;color:#0000ff">public</span><span style="background:#ffffff;color:#000000"> </span><span style="background:#ffffff;color:#0000ff">void</span><span style="background:#ffffff;color:#000000"> ShowMessageDialog(</span><span style="background:#ffffff;color:#0000ff">string</span><span style="background:#ffffff;color:#000000"> message, </span><span style="background:#ffffff;color:#0000ff">string</span><span style="background:#ffffff;color:#000000"> title)</span></li> <li>        <span style="background:#ffffff;color:#000000">{</span></li> <li style="background: #f3f3f3">            <span style="background:#ffffff;color:#000000"></span></li> <li>        <span style="background:#ffffff;color:#000000">}        </span></li> <li style="background: #f3f3f3">    <span style="background:#ffffff;color:#000000">}</span></li> <li><span style="background:#ffffff;color:#000000">}</span></li> </ol> </div> </div> </div>  <p>Comme vous le constatez, j’ai vidé le contenu des méthodes ShowMessageDialog et j’ai effacé la méthode <font face="Courier New">showMessageDialogAsyncPriv.</font>Compilez maintenant votre projet UniversalPlugin.Stub et vous obtiendrez la fameuse seconde librairie portant le même nom que la première “UniversalPlugin.dll”</p>  <h2>Utilisation du plugin</h2>  <p>Maintenant je vous propose de reprendre l’application Unity utilisée dans la première partie de cet article. Avant d’ouvrir le projet sous Unity il est important de déployer les fichiers DLL (plugin et stub). Dans un premier nous allons les déployer à la main via l’explorateur de fichier. Ultérieurement je vous montrerai comment créer un fichier de déploiement (fichier d’extension .unitypackage) ou package qu’il sera alors possible d’importer depuis Unity. Voici la structure classique de fichier de notre projet Unity initial dénommé MessageBox :</p>  <p><a href="https://msdnshared.blob.core.windows.net/media/MSDNBlogsFS/prod.evol.blogs.msdn.com/CommunityServer.Blogs.Components.WeblogFiles/00/00/01/70/07/metablogapi/8561.image_6D91CB51.png" original-url="https://blogs.msdn.com/cfs-file.ashx/__key/communityserver-blogs-components-weblogfiles/00-00-01-70-07-metablogapi/8561.image_5F00_6D91CB51.png"><img title="image" style="border-top: 0px; border-right: 0px; background-image: none; border-bottom: 0px; padding-top: 0px; padding-left: 0px; border-left: 0px; display: inline; padding-right: 0px" border="0" alt="image" src="https://msdnshared.blob.core.windows.net/media/MSDNBlogsFS/prod.evol.blogs.msdn.com/CommunityServer.Blogs.Components.WeblogFiles/00/00/01/70/07/metablogapi/4670.image_thumb_51EFD00C.png" original-url="https://blogs.msdn.com/cfs-file.ashx/__key/communityserver-blogs-components-weblogfiles/00-00-01-70-07-metablogapi/4670.image_5F00_thumb_5F00_51EFD00C.png" width="646" height="394" /></a></p>  <p>&#160;</p>  <p>Dans le répertoire “Assets” je vais créer un sous-répertoire dénommé “Plugins” : ATTENTION l’orthographe de ce répertoire est importante ; si vous oubliez le “s’” à la fin, l’éditeur ne saura pas localisez vos DLLs et vous ne pourrez pas exporter votre jeu. Une fois ce répertoire Plugins créé, vous allez :</p>  <ol>   <li>y copier <u>la librairie Stub</u> de votre plugin </li>    <li>y créer un répertoire dénommé “Metro” et copier dans ce nouveau répertoire la librairie de votre plugin </li> </ol>  <p>Maintenant nous pouvons ouvrir le projet Unity et éditer le fichier script Unity dénommé MessageBox.cs ainsi :</p>  <div id="scid:9ce6104f-a9aa-4a17-a79f-3a39532ebf7c:a1295961-ea86-4db7-8b0f-f15dc2e03ba8" class="wlWriterEditableSmartContent" style="float: none; padding-bottom: 0px; padding-top: 0px; padding-left: 0px; margin: 0px; display: inline; padding-right: 0px"> <div style="border: #000080 1px solid; color: #000; font-family: 'Courier New', Courier, Monospace; font-size: 10pt"> <div style="background: #000080; color: #fff; font-family: Verdana, Tahoma, Arial, sans-serif; font-weight: bold; padding: 2px 5px">Code Snippet</div> <div style="background: #ddd; overflow: auto"> <ol start="1" style="background: #ffffff; margin: 0 0 0 2.5em; padding: 0 0 0 5px;"> <li><span style="background:#ffffff;color:#0000ff">using</span><span style="background:#ffffff;color:#000000"> UnityEngine;</span></li> <li style="background: #f3f3f3"><span style="background:#ffffff;color:#0000ff">using</span><span style="background:#ffffff;color:#000000"> System.Collections;</span></li> <li>&nbsp;</li> <li style="background: #f3f3f3"><span style="background:#ffffff;color:#0000ff">using</span><span style="background:#ffffff;color:#000000"> MyPlugins;</span></li> <li>&nbsp;</li> <li style="background: #f3f3f3"><span style="background:#ffffff;color:#0000ff">public</span><span style="background:#ffffff;color:#000000"> </span><span style="background:#ffffff;color:#0000ff">class</span><span style="background:#ffffff;color:#000000"> </span><span style="background:#ffffff;color:#2b91af">MessageBox</span><span style="background:#ffffff;color:#000000"> : </span><span style="background:#ffffff;color:#2b91af">MonoBehaviour</span></li> <li><span style="background:#ffffff;color:#000000">{</span></li> <li style="background: #f3f3f3">    <span style="background:#ffffff;color:#000000"></span><span style="background:#ffffff;color:#0000ff">void</span><span style="background:#ffffff;color:#000000"> Update()</span></li> <li>    <span style="background:#ffffff;color:#000000">{</span></li> <li style="background: #f3f3f3">        <span style="background:#ffffff;color:#0000ff">#if</span><span style="background:#ffffff;color:#000000"> UNITY_WP_8_1</span></li> <li>            <span style="background:#ffffff;color:#808080">if (Input.GetKeyDown(KeyCode.Escape))</span></li> <li style="background: #f3f3f3">            <span style="background:#ffffff;color:#808080">{</span></li> <li>                <span style="background:#ffffff;color:#808080">Application.Quit();</span></li> <li style="background: #f3f3f3">            <span style="background:#ffffff;color:#808080">}</span></li> <li>        <span style="background:#ffffff;color:#0000ff">#endif</span></li> <li style="background: #f3f3f3">    <span style="background:#ffffff;color:#000000">}</span></li> <li>&nbsp;</li> <li style="background: #f3f3f3">    <span style="background:#ffffff;color:#000000"></span><span style="background:#ffffff;color:#0000ff">public</span><span style="background:#ffffff;color:#000000"> </span><span style="background:#ffffff;color:#0000ff">void</span><span style="background:#ffffff;color:#000000"> OnMessageBoxClick()</span></li> <li>    <span style="background:#ffffff;color:#000000">{</span></li> <li style="background: #f3f3f3">        <span style="background:#ffffff;color:#000000"></span><span style="background:#ffffff;color:#2b91af">UniversalPlugin</span><span style="background:#ffffff;color:#000000">.IInstance.ShowMessageDialog(</span><span style="background:#ffffff;color:#a31515">&quot;Hello from WinRT platform&quot;</span><span style="background:#ffffff;color:#000000">, </span><span style="background:#ffffff;color:#a31515">&quot;Native Dialog&quot;</span><span style="background:#ffffff;color:#000000">);    </span></li> <li>    <span style="background:#ffffff;color:#000000">} </span></li> <li style="background: #f3f3f3">&nbsp;</li> <li><span style="background:#ffffff;color:#000000">}</span></li> </ol> </div> </div> </div>  <p>Notez deux choses :</p>  <ol>   <li>L’inclusion de l’espace de nom “MyPlugins” </li>    <li>La modification du gestionnaire de clic OnMessageBoxClick avec l’appel à notre plugin. </li> </ol>  <p>&#160;</p>  <p>Si maintenant vous exécutez votre application depuis l’éditeur Unity et que vous cliquez sur le bouton MessageBox, rien ne se passe et c’est normal puisque la méthode ShowMessageDialog appelée est celle du stub dont l’implémentation est vide. Pour finir je vous invite à exporter votre jeu en application universelle 8.1. Si l’exportation réussie, Unity va ouvrir l’explorateur de fichier contenant votre projet Visual Studio :</p>  <p><a href="https://msdnshared.blob.core.windows.net/media/MSDNBlogsFS/prod.evol.blogs.msdn.com/CommunityServer.Blogs.Components.WeblogFiles/00/00/01/70/07/metablogapi/6266.image_79B866DA.png" original-url="https://blogs.msdn.com/cfs-file.ashx/__key/communityserver-blogs-components-weblogfiles/00-00-01-70-07-metablogapi/6266.image_5F00_79B866DA.png"><img title="image" style="border-top: 0px; border-right: 0px; background-image: none; border-bottom: 0px; padding-top: 0px; padding-left: 0px; border-left: 0px; display: inline; padding-right: 0px" border="0" alt="image" src="https://msdnshared.blob.core.windows.net/media/MSDNBlogsFS/prod.evol.blogs.msdn.com/CommunityServer.Blogs.Components.WeblogFiles/00/00/01/70/07/metablogapi/5504.image_thumb_29760F5A.png" original-url="https://blogs.msdn.com/cfs-file.ashx/__key/communityserver-blogs-components-weblogfiles/00-00-01-70-07-metablogapi/5504.image_5F00_thumb_5F00_29760F5A.png" width="646" height="364" /></a></p>  <p>Ouvrez le fichier MessageBox.sln avec Visual Studio 2013 puis sélectionnez le projet MessageBox.Windows (Windows 8.1) et cliquer sur le bouton “Local Machine’'” après vous êtes assurés que l’architecture processeur soit bien “x86” :</p>  <p><a href="https://msdnshared.blob.core.windows.net/media/MSDNBlogsFS/prod.evol.blogs.msdn.com/CommunityServer.Blogs.Components.WeblogFiles/00/00/01/70/07/metablogapi/4786.image_0A55832B.png" original-url="https://blogs.msdn.com/cfs-file.ashx/__key/communityserver-blogs-components-weblogfiles/00-00-01-70-07-metablogapi/4786.image_5F00_0A55832B.png"><img title="image" style="border-top: 0px; border-right: 0px; background-image: none; border-bottom: 0px; padding-top: 0px; padding-left: 0px; border-left: 0px; display: inline; padding-right: 0px" border="0" alt="image" src="https://msdnshared.blob.core.windows.net/media/MSDNBlogsFS/prod.evol.blogs.msdn.com/CommunityServer.Blogs.Components.WeblogFiles/00/00/01/70/07/metablogapi/8461.image_thumb_6E4754F0.png" original-url="https://blogs.msdn.com/cfs-file.ashx/__key/communityserver-blogs-components-weblogfiles/00-00-01-70-07-metablogapi/8461.image_5F00_thumb_5F00_6E4754F0.png" width="646" height="463" /></a></p>  <p>A l’exécution, cliquez sur l’unique bouton “Display MessageBox” du Canvas Unity :</p>  <p><a href="https://msdnshared.blob.core.windows.net/media/MSDNBlogsFS/prod.evol.blogs.msdn.com/CommunityServer.Blogs.Components.WeblogFiles/00/00/01/70/07/metablogapi/8306.image_1F020EAF.png" original-url="https://blogs.msdn.com/cfs-file.ashx/__key/communityserver-blogs-components-weblogfiles/00-00-01-70-07-metablogapi/8306.image_5F00_1F020EAF.png"><img title="image" style="border-top: 0px; border-right: 0px; background-image: none; border-bottom: 0px; padding-top: 0px; padding-left: 0px; border-left: 0px; display: inline; padding-right: 0px" border="0" alt="image" src="https://msdnshared.blob.core.windows.net/media/MSDNBlogsFS/prod.evol.blogs.msdn.com/CommunityServer.Blogs.Components.WeblogFiles/00/00/01/70/07/metablogapi/7245.image_thumb_67BB8773.png" original-url="https://blogs.msdn.com/cfs-file.ashx/__key/communityserver-blogs-components-weblogfiles/00-00-01-70-07-metablogapi/7245.image_5F00_thumb_5F00_67BB8773.png" width="646" height="366" /></a></p>  <p>Et voilà ….</p>  <p><u>Note</u> : vous pouvez également tester l’application en version Windows Phone 8.1 car notre plugin est universel.</p>  <h2>Déploiement du plugin</h2>  <p>Comme vous l’avez constaté, le déploiement manuel de votre plugin est un peu fastidieux et on a vite fait de s’emmêler les pinceaux entre la DLL du plugin et sa version Stub portant le même nom. Pour palier se problème, nous allons créer un petit script (batch file) tout simple :</p>  <div id="scid:9ce6104f-a9aa-4a17-a79f-3a39532ebf7c:5def5aba-bc3c-4a9e-8aad-207e88d9d7c2" class="wlWriterEditableSmartContent" style="float: none; padding-bottom: 0px; padding-top: 0px; padding-left: 0px; margin: 0px; display: inline; padding-right: 0px"> <div style="border: #000080 1px solid; color: #000; font-family: 'Courier New', Courier, Monospace; font-size: 10pt"> <div style="background: #000080; color: #fff; font-family: Verdana, Tahoma, Arial, sans-serif; font-weight: bold; padding: 2px 5px">Code Snippet</div> <div style="background: #ddd; overflow: auto"> <ol start="1" style="background: #ffffff; margin: 0 0 0 2.5em; padding: 0 0 0 5px;"> <li><span style="background:#ffffff;color:#000000">@echo off</span></li> <li style="background: #f3f3f3">&nbsp;</li> <li><span style="background:#ffffff;color:#000000">REM Visual Studio project directory for DLLs</span></li> <li style="background: #f3f3f3"><span style="background:#ffffff;color:#000000">SET UNIVERSAL_PLUGIN_DLL=.&#92;UniversalPlugin</span></li> <li><span style="background:#ffffff;color:#000000"> </span></li> <li style="background: #f3f3f3"><span style="background:#ffffff;color:#000000">REM Unity directory structure</span></li> <li><span style="background:#ffffff;color:#000000">SET UNITY_PROJECT_DIR=%1</span></li> <li style="background: #f3f3f3"><span style="background:#ffffff;color:#000000">SET PLUGIN_DIR=%UNITY_PROJECT_DIR%&#92;Assets&#92;Plugins&#92;\par SET METRO_DIR=%PLUGIN_DIR%&#92;Metro&#92;\par </span></li> <li><span style="background:#ffffff;color:#000000">IF %1.==. GOTO ERROR1</span></li> <li style="background: #f3f3f3">&nbsp;</li> <li><span style="background:#ffffff;color:#000000">echo  %UNITY_PROJECT_DIR%</span></li> <li style="background: #f3f3f3"><span style="background:#ffffff;color:#000000">echo  %PLUGIN_DIR%</span></li> <li><span style="background:#ffffff;color:#000000">echo  %METRO_DIR%</span></li> <li style="background: #f3f3f3">&nbsp;</li> <li><span style="background:#ffffff;color:#000000">IF not exist %PLUGIN_DIR% (mkdir %PLUGIN_DIR%)</span></li> <li style="background: #f3f3f3"><span style="background:#ffffff;color:#000000">IF not exist %METRO_DIR% (mkdir %METRO_DIR%)</span></li> <li>&nbsp;</li> <li style="background: #f3f3f3"><span style="background:#ffffff;color:#000000">xcopy %UNIVERSAL_PLUGIN_DLL%.Stub&#92;bin&#92;Release&#92;*.dll  %PLUGIN_DIR% /Y</span></li> <li><span style="background:#ffffff;color:#000000">xcopy %UNIVERSAL_PLUGIN_DLL%&#92;bin&#92;Release&#92;*.dll  %METRO_DIR% /Y</span></li> <li style="background: #f3f3f3">&nbsp;</li> <li><span style="background:#ffffff;color:#000000">GOTO Success</span></li> <li style="background: #f3f3f3">&nbsp;</li> <li><span style="background:#ffffff;color:#000000">:ERROR1</span></li> <li style="background: #f3f3f3">  <span style="background:#ffffff;color:#000000">ECHO Unity project folder is missing !!</span></li> <li>  <span style="background:#ffffff;color:#000000">GOTO End</span></li> <li style="background: #f3f3f3">&nbsp;</li> <li><span style="background:#ffffff;color:#000000">:Success</span></li> <li style="background: #f3f3f3">  <span style="background:#ffffff;color:#000000">ECHO DLL files have been copied with success !</span></li> <li>  <span style="background:#ffffff;color:#000000"></span></li> <li style="background: #f3f3f3"><span style="background:#ffffff;color:#000000">:End</span></li> <li><span style="background:#ffffff;color:#000000">pause</span></li> </ol> </div> </div> </div>  <p>&#160;</p>  <p>Pour le tester :</p>  <ol>   <li>Copiez le fichier deploy.bat ci-dessous dans le répertoire de votre solution Visual Studio utilisée pour créer votre plugin. Dans mon cas il s’agit du répertoire suivant : C:\work\dev\wp\unity\MyPlugins </li>    <li>Ouvrez une invite de commande et placez-vous dans ce même répertoire puis exécutez la commande suivante : </li> </ol>  <blockquote>   <p><strong><font size="3" face="Courier New">deploy C:\work\dev\unity\MessageBox</font></strong></p> </blockquote>  <p>Vous obtenez alors la sortie suivante :</p>  <p><a href="https://msdnshared.blob.core.windows.net/media/MSDNBlogsFS/prod.evol.blogs.msdn.com/CommunityServer.Blogs.Components.WeblogFiles/00/00/01/70/07/metablogapi/8272.image_5BB9973F.png" original-url="https://blogs.msdn.com/cfs-file.ashx/__key/communityserver-blogs-components-weblogfiles/00-00-01-70-07-metablogapi/8272.image_5F00_5BB9973F.png"><img title="image" style="border-top: 0px; border-right: 0px; background-image: none; border-bottom: 0px; padding-top: 0px; padding-left: 0px; border-left: 0px; display: inline; padding-right: 0px" border="0" alt="image" src="https://msdnshared.blob.core.windows.net/media/MSDNBlogsFS/prod.evol.blogs.msdn.com/CommunityServer.Blogs.Components.WeblogFiles/00/00/01/70/07/metablogapi/8233.image_thumb_4DE9E1F5.png" original-url="https://blogs.msdn.com/cfs-file.ashx/__key/communityserver-blogs-components-weblogfiles/00-00-01-70-07-metablogapi/8233.image_5F00_thumb_5F00_4DE9E1F5.png" width="646" height="424" /></a></p>  <p>Notez que mon fichier batch déploie uniquement les fichiers DLLs en mode release. </p>  <h2>Distribution du plugin</h2>  <p>Sachez que vous pouvez distribuer votre plugin sur l’asset store de Unity en version gratuite ou payante. Pour distribuer votre plugin via l’asset store de Unity ou autre site web, il vous faudra packager votre plugin dans un fichier d’extension “.unitypackage”, ce qui permettra aux utilisateurs de l’importer directement depuis Unity. Pour cela il faut utiliser l’exécutable Unity en mode scripté et créer au moins un projet Unity utilisant votre plugin (dans notre cas il s’agit du projet MessageBox). Voici la commande à saisir :</p>  <p><a href="https://msdnshared.blob.core.windows.net/media/MSDNBlogsFS/prod.evol.blogs.msdn.com/CommunityServer.Blogs.Components.WeblogFiles/00/00/01/70/07/metablogapi/0172.image_5AE652B7.png" original-url="https://blogs.msdn.com/cfs-file.ashx/__key/communityserver-blogs-components-weblogfiles/00-00-01-70-07-metablogapi/0172.image_5F00_5AE652B7.png"><img title="image" style="border-top: 0px; border-right: 0px; background-image: none; border-bottom: 0px; padding-top: 0px; padding-left: 0px; border-left: 0px; display: inline; padding-right: 0px" border="0" alt="image" src="https://msdnshared.blob.core.windows.net/media/MSDNBlogsFS/prod.evol.blogs.msdn.com/CommunityServer.Blogs.Components.WeblogFiles/00/00/01/70/07/metablogapi/5811.image_thumb_239FCB7C.png" original-url="https://blogs.msdn.com/cfs-file.ashx/__key/communityserver-blogs-components-weblogfiles/00-00-01-70-07-metablogapi/5811.image_5F00_thumb_5F00_239FCB7C.png" width="646" height="424" /></a></p>  <ul>   <li>l’option –batchmode permet d’utiliser Unity sans ouvrir l’éditeur </li>    <li>l’option –projectPatch indique le répertoire du projet Unity (ici notre projet test MessageBox) </li>    <li>l’option –exportPackage indique le répertoire contenant notre plugin </li>    <li>Et à la fin nous indiquons le nom du package personnalisé, MyPlugins.unitypackage, qui sera généré à la racine du répertoire MessageBox </li> </ul>  <p>Une fois le package généré, d’autres développeurs pourront l’utiliser via Unity en sélectionnant le menu Assets / Import Assets / Custom Package. S’ouvrira alors la fenêtre Unity suivante :</p>  <p><a href="https://msdnshared.blob.core.windows.net/media/MSDNBlogsFS/prod.evol.blogs.msdn.com/CommunityServer.Blogs.Components.WeblogFiles/00/00/01/70/07/metablogapi/4784.image_27ACA9FF.png" original-url="https://blogs.msdn.com/cfs-file.ashx/__key/communityserver-blogs-components-weblogfiles/00-00-01-70-07-metablogapi/4784.image_5F00_27ACA9FF.png"><img title="image" style="border-top: 0px; border-right: 0px; background-image: none; border-bottom: 0px; padding-top: 0px; padding-left: 0px; border-left: 0px; display: inline; padding-right: 0px" border="0" alt="image" src="https://msdnshared.blob.core.windows.net/media/MSDNBlogsFS/prod.evol.blogs.msdn.com/CommunityServer.Blogs.Components.WeblogFiles/00/00/01/70/07/metablogapi/5635.image_thumb_1DE74287.png" original-url="https://blogs.msdn.com/cfs-file.ashx/__key/communityserver-blogs-components-weblogfiles/00-00-01-70-07-metablogapi/5635.image_5F00_thumb_5F00_1DE74287.png" width="458" height="486" /></a></p>  <p>&#160;</p>  <h2></h2>  <h1>Conclusion</h1>  <p>Voilà … l’utilisation des APIs Windows/Windows Phone 8.1 depuis vos scripts Unity n’ont plus de secrets pour vous ou presque. Vous pouvez téléchargez librement les exemples de codes détaillées dans ce article <a href="https://1drv.ms/1Cyshi8" target="_blank">ici</a></p>]]></content:encoded>
    </item>
    <item>
      <title>Utiliser Visual Studio avec Unity</title>
      <link>https://docs.microsoft.com/archive/blogs/ndelabarre/utiliser-visual-studio-avec-unity</link>
      <pubDate>Tue, 28 Apr 2015 07:43:24 GMT</pubDate>
      <dc:creator><![CDATA[Nicolas Delabarre]]></dc:creator>
      <guid
        isPermaLink="false">https://blogs.msdn.microsoft.com/ndelabarre/2015/04/28/utiliser-visual-studio-avec-unity/</guid>
      <description><![CDATA[Par défaut, Unity propose l’installation et l’utilisation d’un éditeur de développement (IDE)...]]></description>
      <content:encoded><![CDATA[<p align="justify">Par défaut, Unity propose l’installation et l’utilisation d’un éditeur de développement (IDE) dénommé MonoDevelop. Ce dernier fournit les briques de base indispensables pour le développement de code : compilation, débogage, auto-completion,&#160; documentation des APIs Unity, coloration syntaxique, synchronisation avec l’éditeur Unity. L’objet de ce billet n’est pas de rentrer dans une sempiternelle polémique afin savoir si tel ou tel IDE est meilleur que tel autre. Non mais voilà, lorsqu’on est habitué à utiliser Visual Studio, tout autre IDE peut paraître déroutant&#160; :-)</p>  <p align="justify">Aussi je vais vous montrer dans cet article comment utiliser Visual Studio pour développer votre code Unity. Je pars sur le principe que vous possédez :</p>  <ul>   <li>     <div align="justify">Un PC tournant sous Windows 7/8/8.1 </div>   </li>    <li>     <div align="justify">Une version récente (2013 ou plus) de <a href="https://www.visualstudio.com/fr-fr/downloads#d-express-windows-8?CR_CC=200395106" target="_blank">Visual Studio</a> (Community &amp; Express, Pro, Premium ou Ultimate) </div>   </li>    <li>     <div align="justify">Unity (version 4.x ou 5.x) </div>   </li> </ul>  <p align="justify">&#160;</p>  <p align="justify">Sachez également que la version gratuite (Community &amp; Express) de Visual Studio est compatible avec Unity : aucune excuse pour ne pas essayer. </p>  <p align="justify">L’utilisation de Visual Studio avec Unity nécessite l’installation d’un plugin initialement développé par la société SyntaxTree et qui a fait l’objet d’un rachat il y a <a href="https://syntaxtree.com/" target="_blank">bientôt un an</a> par Microsoft. </p>  <p><a href="https://msdnshared.blob.core.windows.net/media/MSDNBlogsFS/prod.evol.blogs.msdn.com/CommunityServer.Blogs.Components.WeblogFiles/00/00/01/70/07/metablogapi/0317.image_0CCBC69E.png" original-url="https://blogs.msdn.com/cfs-file.ashx/__key/communityserver-blogs-components-weblogfiles/00-00-01-70-07-metablogapi/0317.image_5F00_0CCBC69E.png"><img title="image" style="border-left-width: 0px; border-right-width: 0px; border-bottom-width: 0px; display: inline; border-top-width: 0px" border="0" alt="image" src="https://msdnshared.blob.core.windows.net/media/MSDNBlogsFS/prod.evol.blogs.msdn.com/CommunityServer.Blogs.Components.WeblogFiles/00/00/01/70/07/metablogapi/5543.image_thumb_43A8AB95.png" original-url="https://blogs.msdn.com/cfs-file.ashx/__key/communityserver-blogs-components-weblogfiles/00-00-01-70-07-metablogapi/5543.image_5F00_thumb_5F00_43A8AB95.png" width="244" height="55" /></a> </p>  <h1>Installation</h1>  <p>Ce plugin est accessible en libre téléchargement depuis le site officiel <a title="https://unityvs.com/" href="https://unityvs.com/">https://unityvs.com/</a></p>  <p></p>  <p>Cliquez sur “Visual Studio 2013 Tools for Unity” comme indiqué ci-dessous :</p>  <p><a href="https://msdnshared.blob.core.windows.net/media/MSDNBlogsFS/prod.evol.blogs.msdn.com/CommunityServer.Blogs.Components.WeblogFiles/00/00/01/70/07/metablogapi/5468.image_4C983DD4.png" original-url="https://blogs.msdn.com/cfs-file.ashx/__key/communityserver-blogs-components-weblogfiles/00-00-01-70-07-metablogapi/5468.image_5F00_4C983DD4.png"><img title="image" style="border-left-width: 0px; border-right-width: 0px; border-bottom-width: 0px; display: inline; border-top-width: 0px" border="0" alt="image" src="https://msdnshared.blob.core.windows.net/media/MSDNBlogsFS/prod.evol.blogs.msdn.com/CommunityServer.Blogs.Components.WeblogFiles/00/00/01/70/07/metablogapi/4745.image_thumb_433F0951.png" original-url="https://blogs.msdn.com/cfs-file.ashx/__key/communityserver-blogs-components-weblogfiles/00-00-01-70-07-metablogapi/4745.image_5F00_thumb_5F00_433F0951.png" width="626" height="258" /></a> </p>  <p>Vous arriverez alors sur une page intermédiaire permettant de démarrer le téléchargement du fichier <strong>Visual Studio 2013 Tools for Unity.msi </strong>:</p>  <p><a href="https://msdnshared.blob.core.windows.net/media/MSDNBlogsFS/prod.evol.blogs.msdn.com/CommunityServer.Blogs.Components.WeblogFiles/00/00/01/70/07/metablogapi/6825.image_24F4525B.png" original-url="https://blogs.msdn.com/cfs-file.ashx/__key/communityserver-blogs-components-weblogfiles/00-00-01-70-07-metablogapi/6825.image_5F00_24F4525B.png"><img title="image" style="border-left-width: 0px; border-right-width: 0px; border-bottom-width: 0px; display: inline; border-top-width: 0px" border="0" alt="image" src="https://msdnshared.blob.core.windows.net/media/MSDNBlogsFS/prod.evol.blogs.msdn.com/CommunityServer.Blogs.Components.WeblogFiles/00/00/01/70/07/metablogapi/0005.image_thumb_09525716.png" original-url="https://blogs.msdn.com/cfs-file.ashx/__key/communityserver-blogs-components-weblogfiles/00-00-01-70-07-metablogapi/0005.image_5F00_thumb_5F00_09525716.png" width="630" height="299" /></a> </p>  <p>Une fois téléchargé, lancez l’installation du plugin en double-cliquant le fichier msi (assurez vous d’avoir fermé Unity au préalable). Le répertoire d’installation proposé par défaut est le suivant : <em>C:\Program Files (x86)\Microsoft Visual Studio Tools for Unity\2013</em> . Vous pouvez bien sûr choisir un autre répertoire.</p>  <h1>Configuration</h1>  <p>L’étape suivante consiste à créer un nouveau projet sous Unity puis à importer le plugin via le menu <strong>Import Package / Visual Studio 2013 Tools</strong> comme indiqué sur la capture ci-dessous :</p>  <p><a href="https://msdnshared.blob.core.windows.net/media/MSDNBlogsFS/prod.evol.blogs.msdn.com/CommunityServer.Blogs.Components.WeblogFiles/00/00/01/70/07/metablogapi/0451.image_3FC30918.png" original-url="https://blogs.msdn.com/cfs-file.ashx/__key/communityserver-blogs-components-weblogfiles/00-00-01-70-07-metablogapi/0451.image_5F00_3FC30918.png"><img title="image" style="border-left-width: 0px; border-right-width: 0px; border-bottom-width: 0px; display: inline; border-top-width: 0px" border="0" alt="image" src="https://msdnshared.blob.core.windows.net/media/MSDNBlogsFS/prod.evol.blogs.msdn.com/CommunityServer.Blogs.Components.WeblogFiles/00/00/01/70/07/metablogapi/4188.image_thumb_7633BB1A.png" original-url="https://blogs.msdn.com/cfs-file.ashx/__key/communityserver-blogs-components-weblogfiles/00-00-01-70-07-metablogapi/4188.image_5F00_thumb_5F00_7633BB1A.png" width="694" height="378" /></a> </p>  <p align="justify"><u>Note</u> : si vous utilisez Unity 5.x, le sous menu “Visual Studio 2013 Tools” n’est pas présent. Pas de panique : il faut simplement sélectionner le sous menu <strong>Custom Package …</strong> et localisez le fichier <em><strong>Visual Studio 2013 Tools.unitypackage</strong> </em>disponible dans le répertoire d’installation du plugin ( <em>C:\Program Files (x86)\Microsoft Visual Studio Tools for Unity\2013</em> dans mon cas).</p>  <p>S’affiche alors la boite de dialogue suivante :</p>  <p><a href="https://msdnshared.blob.core.windows.net/media/MSDNBlogsFS/prod.evol.blogs.msdn.com/CommunityServer.Blogs.Components.WeblogFiles/00/00/01/70/07/metablogapi/2061.image_2CA46D1D.png" original-url="https://blogs.msdn.com/cfs-file.ashx/__key/communityserver-blogs-components-weblogfiles/00-00-01-70-07-metablogapi/2061.image_5F00_2CA46D1D.png"><img title="image" style="border-left-width: 0px; border-right-width: 0px; border-bottom-width: 0px; display: inline; border-top-width: 0px" border="0" alt="image" src="https://msdnshared.blob.core.windows.net/media/MSDNBlogsFS/prod.evol.blogs.msdn.com/CommunityServer.Blogs.Components.WeblogFiles/00/00/01/70/07/metablogapi/1348.image_thumb_3BDAD5EA.png" original-url="https://blogs.msdn.com/cfs-file.ashx/__key/communityserver-blogs-components-weblogfiles/00-00-01-70-07-metablogapi/1348.image_5F00_thumb_5F00_3BDAD5EA.png" width="399" height="424" /></a> </p>  <p>Laissez tout sélectionné par défaut et cliquez sur le bouton <strong>Import. </strong>Une fois importé, deux changements significatifs apparaissent dans l’éditeur Unity :</p>  <p><a href="https://msdnshared.blob.core.windows.net/media/MSDNBlogsFS/prod.evol.blogs.msdn.com/CommunityServer.Blogs.Components.WeblogFiles/00/00/01/70/07/metablogapi/3463.image_796AC464.png" original-url="https://blogs.msdn.com/cfs-file.ashx/__key/communityserver-blogs-components-weblogfiles/00-00-01-70-07-metablogapi/3463.image_5F00_796AC464.png"><img title="image" style="border-left-width: 0px; border-right-width: 0px; border-bottom-width: 0px; display: inline; border-top-width: 0px" border="0" alt="image" src="https://msdnshared.blob.core.windows.net/media/MSDNBlogsFS/prod.evol.blogs.msdn.com/CommunityServer.Blogs.Components.WeblogFiles/00/00/01/70/07/metablogapi/1346.image_thumb_08A12D32.png" original-url="https://blogs.msdn.com/cfs-file.ashx/__key/communityserver-blogs-components-weblogfiles/00-00-01-70-07-metablogapi/1346.image_5F00_thumb_5F00_08A12D32.png" width="696" height="387" /></a> </p>  <ul>   <li>Un nouveau menu dénommé <strong>Visual Studio Tools</strong> permettant de générer le projet Visual Studio ainsi que de paramétrer le plugin </li>    <li>Un nouveau sous-répertoire dénommé <strong>UnityVS</strong> dans le répertoire de base Assets : il contient toute la plomberie pour faire le bridge entre l’éditeur Unity et Visual Studio (synchro, déboguage etc) </li> </ul>  <p>&#160;</p>  <p><u>Note</u> : si vous vous rendez dans le menu <strong>Edit / Préférences</strong> et que vous sélectionnez l’onglet <strong>External Tools</strong>, vous noterez que l’éditeur par défaut MonoDevelop a été remplacé par UnityVS comme indiqué ci-dessous :</p>  <p><a href="https://msdnshared.blob.core.windows.net/media/MSDNBlogsFS/prod.evol.blogs.msdn.com/CommunityServer.Blogs.Components.WeblogFiles/00/00/01/70/07/metablogapi/1106.unity_prefs_5AB66B2A.png" original-url="https://blogs.msdn.com/cfs-file.ashx/__key/communityserver-blogs-components-weblogfiles/00-00-01-70-07-metablogapi/1106.unity_5F00_prefs_5F00_5AB66B2A.png"><img title="unity_prefs" style="border-left-width: 0px; border-right-width: 0px; border-bottom-width: 0px; display: inline; border-top-width: 0px" border="0" alt="unity_prefs" src="https://msdnshared.blob.core.windows.net/media/MSDNBlogsFS/prod.evol.blogs.msdn.com/CommunityServer.Blogs.Components.WeblogFiles/00/00/01/70/07/metablogapi/0121.unity_prefs_thumb_63A5FD69.png" original-url="https://blogs.msdn.com/cfs-file.ashx/__key/communityserver-blogs-components-weblogfiles/00-00-01-70-07-metablogapi/0121.unity_5F00_prefs_5F00_thumb_5F00_63A5FD69.png" width="496" height="422" /></a> </p>  <p></p>  <p>Votre environnement est maintenant prêt.</p>  <h1>Utilisation</h1>  <p align="justify">Dorénavant vous pouvez créer vos scripts C# depuis Unity. Lorsque vous double-cliquez sur un script Unity, cela ouvre automatiquement le projet Visual Studio sur le script sélectionné. Notez par ailleurs qu’il y a une synchronisation automatique entre l’éditeur Unity et Visual Studio : ajoutez un nouveau script sous Unity et retrouvez-le automatiquement sous le projet Visual Studio correspondant sans avoir besoin de relancer Visual Studio.</p>  <h3>IntelliSense</h3>  <p align="justify">Vous retrouvez bien sûr les fonctions d’aide contextuelle/auto-completion IntelliSense adaptée aux APIs Unity :</p>  <p align="justify"><a href="https://msdnshared.blob.core.windows.net/media/MSDNBlogsFS/prod.evol.blogs.msdn.com/CommunityServer.Blogs.Components.WeblogFiles/00/00/01/70/07/metablogapi/3201.image_176DF3BB.png" original-url="https://blogs.msdn.com/cfs-file.ashx/__key/communityserver-blogs-components-weblogfiles/00-00-01-70-07-metablogapi/3201.image_5F00_176DF3BB.png"><img title="image" style="border-left-width: 0px; border-right-width: 0px; border-bottom-width: 0px; display: inline; border-top-width: 0px" border="0" alt="image" src="https://msdnshared.blob.core.windows.net/media/MSDNBlogsFS/prod.evol.blogs.msdn.com/CommunityServer.Blogs.Components.WeblogFiles/00/00/01/70/07/metablogapi/1184.image_thumb_7BCBF875.png" original-url="https://blogs.msdn.com/cfs-file.ashx/__key/communityserver-blogs-components-weblogfiles/00-00-01-70-07-metablogapi/1184.image_5F00_thumb_5F00_7BCBF875.png" width="684" height="392" /></a> </p>  <h3>Debug</h3>  <p align="justify">L’étape suivante consiste à déboguer vos scripts depuis Visual Studio tout en exécutant votre scène depuis Unity. Voici la procédure :</p>  <ul>   <li>     <div align="justify">Ouvrez votre projet sous Visual Studio et positionnez un point d’arrêt (dans mon exemple, je positionne un point d’arrêt dans la méthode start() de mon unique script <em>Main.cs</em> rattaché à la caméra principale).</div>   </li>    <li>     <div align="justify">Connectez Visual Studio à l’instance d’Unity contenant votre scène à déboguer : pour cela localisez dans la partie inférieure droite de Visual Studio, une petite icône représentant une prise. S’ouvre alors une boite de dialogue listant les instances ouvertes d’Unity&#160; et leur projet associé :</div>   </li> </ul>  <p align="justify">&#160;</p>  <p align="justify"><a href="https://msdnshared.blob.core.windows.net/media/MSDNBlogsFS/prod.evol.blogs.msdn.com/CommunityServer.Blogs.Components.WeblogFiles/00/00/01/70/07/metablogapi/2021.ConnectVSToUnity_1FF3E3B6.png" original-url="https://blogs.msdn.com/cfs-file.ashx/__key/communityserver-blogs-components-weblogfiles/00-00-01-70-07-metablogapi/2021.ConnectVSToUnity_5F00_1FF3E3B6.png"><img title="ConnectVSToUnity" style="border-left-width: 0px; border-right-width: 0px; border-bottom-width: 0px; display: inline; border-top-width: 0px" border="0" alt="ConnectVSToUnity" src="https://msdnshared.blob.core.windows.net/media/MSDNBlogsFS/prod.evol.blogs.msdn.com/CommunityServer.Blogs.Components.WeblogFiles/00/00/01/70/07/metablogapi/8802.ConnectVSToUnity_thumb_61FA52F7.png" original-url="https://blogs.msdn.com/cfs-file.ashx/__key/communityserver-blogs-components-weblogfiles/00-00-01-70-07-metablogapi/8802.ConnectVSToUnity_5F00_thumb_5F00_61FA52F7.png" width="444" height="250" /></a> </p>  <p>Sélectionnez votre instance et validez le bouton OK. </p>  <ul>   <li>Puis,&#160; toujours dans Visual Studio, cliquez sur le bouton <strong>Attach to Unity</strong> : Visual Studio lance alors le mode Debug et attend. </li> </ul>  <p></p>  <p></p>  <p><a href="https://msdnshared.blob.core.windows.net/media/MSDNBlogsFS/prod.evol.blogs.msdn.com/CommunityServer.Blogs.Components.WeblogFiles/00/00/01/70/07/metablogapi/8420.image_35DD5606.png" original-url="https://blogs.msdn.com/cfs-file.ashx/__key/communityserver-blogs-components-weblogfiles/00-00-01-70-07-metablogapi/8420.image_5F00_35DD5606.png"><img title="image" style="border-left-width: 0px; border-right-width: 0px; border-bottom-width: 0px; display: inline; border-top-width: 0px" border="0" alt="image" src="https://msdnshared.blob.core.windows.net/media/MSDNBlogsFS/prod.evol.blogs.msdn.com/CommunityServer.Blogs.Components.WeblogFiles/00/00/01/70/07/metablogapi/0842.image_thumb_61247DBE.png" original-url="https://blogs.msdn.com/cfs-file.ashx/__key/communityserver-blogs-components-weblogfiles/00-00-01-70-07-metablogapi/0842.image_5F00_thumb_5F00_61247DBE.png" width="591" height="139" /></a> </p>  <ul>   <li>Retournez dans Unity et lancez le player sur la scène correspondante. Dans mon exemple, Visual Studio va breaker dès le démarrage : </li> </ul>  <p>&#160;</p>  <p><a href="https://msdnshared.blob.core.windows.net/media/MSDNBlogsFS/prod.evol.blogs.msdn.com/CommunityServer.Blogs.Components.WeblogFiles/00/00/01/70/07/metablogapi/3022.image_17952FC1.png" original-url="https://blogs.msdn.com/cfs-file.ashx/__key/communityserver-blogs-components-weblogfiles/00-00-01-70-07-metablogapi/3022.image_5F00_17952FC1.png"><img title="image" style="border-left-width: 0px; border-right-width: 0px; border-bottom-width: 0px; display: inline; border-top-width: 0px" border="0" alt="image" src="https://msdnshared.blob.core.windows.net/media/MSDNBlogsFS/prod.evol.blogs.msdn.com/CommunityServer.Blogs.Components.WeblogFiles/00/00/01/70/07/metablogapi/1234.image_thumb_14EF04C1.png" original-url="https://blogs.msdn.com/cfs-file.ashx/__key/communityserver-blogs-components-weblogfiles/00-00-01-70-07-metablogapi/1234.image_5F00_thumb_5F00_14EF04C1.png" width="699" height="616" /></a> </p>  <p></p>  <p></p>  <h3>Aide en ligne</h3>  <p align="justify">Autre fonctionnalité intéressante : accéder à la documentation en ligne des APIs Unity depuis Visual Studio, et ce, de manière contextuelle. Pour cela rien de plus simple : SyntaxTree a mappé l’appel de l’aide en ligne sur le raccourci clavier CTRL+H. Par exemple si je positionne mon curseur sur la classe <strong>MonoBehavior</strong> dans mon script Main.cs et que je tape ce raccourci clavier, j’obtiens la documentation de la classe <strong>MonoBehavior</strong> :</p>  <p><a href="https://msdnshared.blob.core.windows.net/media/MSDNBlogsFS/prod.evol.blogs.msdn.com/CommunityServer.Blogs.Components.WeblogFiles/00/00/01/70/07/metablogapi/8117.CallDocumentationFromVS_3916F001.png" original-url="https://blogs.msdn.com/cfs-file.ashx/__key/communityserver-blogs-components-weblogfiles/00-00-01-70-07-metablogapi/8117.CallDocumentationFromVS_5F00_3916F001.png"><img title="CallDocumentationFromVS" style="border-left-width: 0px; border-right-width: 0px; border-bottom-width: 0px; display: inline; border-top-width: 0px" border="0" alt="CallDocumentationFromVS" src="https://msdnshared.blob.core.windows.net/media/MSDNBlogsFS/prod.evol.blogs.msdn.com/CommunityServer.Blogs.Components.WeblogFiles/00/00/01/70/07/metablogapi/5342.CallDocumentationFromVS_thumb_5D3EDB41.png" original-url="https://blogs.msdn.com/cfs-file.ashx/__key/communityserver-blogs-components-weblogfiles/00-00-01-70-07-metablogapi/5342.CallDocumentationFromVS_5F00_thumb_5F00_5D3EDB41.png" width="700" height="381" /></a> </p>  <p>Si vous souhaitez mapper la documentation en ligne sur un autre raccourci clavier, aucun problème : sélectionnez le menu <strong>Tools / Options</strong> puis cliquez sur l’élément <strong>Keyboard</strong> ; dans le champ “Show commands containing”, saisissez le mot unity et sélectionnez la commande <strong>Help.UnityAPIReference :</strong></p>  <p><a href="https://msdnshared.blob.core.windows.net/media/MSDNBlogsFS/prod.evol.blogs.msdn.com/CommunityServer.Blogs.Components.WeblogFiles/00/00/01/70/07/metablogapi/0160.CustomHelpCommand_537973C9.png" original-url="https://blogs.msdn.com/cfs-file.ashx/__key/communityserver-blogs-components-weblogfiles/00-00-01-70-07-metablogapi/0160.CustomHelpCommand_5F00_537973C9.png"><img title="CustomHelpCommand" style="border-left-width: 0px; border-right-width: 0px; border-bottom-width: 0px; display: inline; border-top-width: 0px" border="0" alt="CustomHelpCommand" src="https://msdnshared.blob.core.windows.net/media/MSDNBlogsFS/prod.evol.blogs.msdn.com/CommunityServer.Blogs.Components.WeblogFiles/00/00/01/70/07/metablogapi/8053.CustomHelpCommand_thumb_74F8A358.png" original-url="https://blogs.msdn.com/cfs-file.ashx/__key/communityserver-blogs-components-weblogfiles/00-00-01-70-07-metablogapi/8053.CustomHelpCommand_5F00_thumb_5F00_74F8A358.png" width="693" height="406" /></a> </p>  <p>Vous pouvez alors sélectionner un autre raccourci clavier dans la liste <strong>Shortcuts for selected command</strong>.</p>  <h1>Conclusion</h1>  <p>Voilà j’espère que cet article vous aura donné un bon aperçu de l’utilisation de Visual Studio pour coder et déboguer vos scripts Unity. Pour aller plus loin je vous invite à consulter la <a href="https://unityvs.com/documentation/" target="_blank">documentation en ligne</a> où vous apprendrez par exemple à déboguer des DLLs externes.</p>]]></content:encoded>
    </item>
    <item>
      <title>Exporter un projet Unity pour les plateformes Windows 8.1 / Windows Phone 8.1</title>
      <link>https://docs.microsoft.com/archive/blogs/ndelabarre/exporter-un-projet-unity-pour-les-plateformes-windows-8-1-windows-phone-8-1</link>
      <pubDate>Sun, 12 Apr 2015 08:33:57 GMT</pubDate>
      <dc:creator><![CDATA[Nicolas Delabarre]]></dc:creator>
      <guid
        isPermaLink="false">https://blogs.msdn.microsoft.com/ndelabarre/2015/04/12/exporter-un-projet-unity-pour-les-plateformes-windows-8-1-windows-phone-8-1/</guid>
      <description><![CDATA[&#160;  Si vous lisez cet article dans le but d’apprendre comment exporter son projet Unity sur...]]></description>
      <content:encoded><![CDATA[<p>&#160;</p>  <p align="justify">Si vous lisez cet article dans le but d’apprendre comment exporter son projet Unity sur Windows 8.1 / Windows Phone 8.1, vous êtes au bon endroit. Afin de rendre cette session d’apprentissage plus efficace, je vous recommande de manipuler en parallèle : cela permet de mémoriser plus facilement les différentes étapes. </p>  <h1>Pré requis logiciels</h1>  <p align="justify">Il est nécessaire d’utiliser la configuration logicielle minimale suivante :</p>  <ul>   <li>     <div align="justify"><strong>Windows 8.1 Pro</strong>. Bien qu’il soit possible d’utiliser une version non professionnelle de Windows 8.1, il est préférable d’utiliser une version Pro afin de bénéficier d’Hyper-V, la technologie Microsoft de virtualisation cliente, nécessaire pour l’utilisation de l’émulateur Windows Phone. Si vous disposez d’un téléphone Windows Phone 8.1 ou si vous ciblez uniquement la plateforme Windows 8.1, une version non professionnelle fera l’affaire. A noter que si vous êtes sur MAC, il est possible&#160; de <a href="https://msdn.microsoft.com/fr-fr/library/windows/apps/jj945492.aspx" target="_blank">virtualiser un environnement de développement Windows 8.1</a> via des outils de virtualisation tels que Bootcamp, Parallels ou encore VMware. </div>   </li>    <li>     <div align="justify"><strong>Visual Studio 2013</strong>. L’outil de développement intégré qui permet notamment de générer et packager vos applications Windows et Windows Phone au format exigé pour une publication sur le store de Microsoft. Les versions Express et Community peuvent être téléchargées et installées gratuitement depuis ce <a href="https://dev.windows.com/fr-fr " target="_blank">lien</a>. A noter que l’installation de cet outil intègre également les SDKs Windows Phone et Windows. </div>   </li>    <li>     <div align="justify"><strong>Unity</strong>. Afin de pouvoir exporter vos projets pour les plateformes Windows 8.1 / Windows Phone 8.1, il est nécessaire d’installer une version supérieure à la version 4.3. A l’heure où je rédige cet article, la dernière version <a href="https://unity3d.com/unity/download" target="_blank">téléchargeable</a> est la version 5.0 </div>   </li> </ul>  <h1>Unity et l’exportation</h1>  <p>L’éditeur d’Unity permet d’exporter votre projet sur différentes platformes Microsoft. Lorsque vous êtes dans l’éditeur Unity, sélectionnez dans le menu “File” le sous menu dénommé “Build Settings” (ou tapez la combinaison clavier CTRL + SHIFT + B si vous êtes du genre <em>keyboard fanatic</em>):</p>  <p><a href="https://msdnshared.blob.core.windows.net/media/MSDNBlogsFS/prod.evol.blogs.msdn.com/CommunityServer.Blogs.Components.WeblogFiles/00/00/01/70/07/metablogapi/4606.BuildSettingsMenu_2C4FB6A8.png" original-url="https://blogs.msdn.com/cfs-file.ashx/__key/communityserver-blogs-components-weblogfiles/00-00-01-70-07-metablogapi/4606.BuildSettingsMenu_5F00_2C4FB6A8.png"><img title="BuildSettingsMenu" style="border-left-width: 0px; border-right-width: 0px; border-bottom-width: 0px; display: inline; border-top-width: 0px" border="0" alt="BuildSettingsMenu" src="https://msdnshared.blob.core.windows.net/media/MSDNBlogsFS/prod.evol.blogs.msdn.com/CommunityServer.Blogs.Components.WeblogFiles/00/00/01/70/07/metablogapi/4162.BuildSettingsMenu_thumb_7DF8C1AB.png" original-url="https://blogs.msdn.com/cfs-file.ashx/__key/communityserver-blogs-components-weblogfiles/00-00-01-70-07-metablogapi/4162.BuildSettingsMenu_5F00_thumb_5F00_7DF8C1AB.png" width="583" height="484" /></a> </p>  <p>S’ouvre alors une boite de dialogue listant toutes les plateformes d’exportation supportées :</p>  <p><a href="https://msdnshared.blob.core.windows.net/media/MSDNBlogsFS/prod.evol.blogs.msdn.com/CommunityServer.Blogs.Components.WeblogFiles/00/00/01/70/07/metablogapi/7144.BuildSettingsDialog_5ACB56F9.png" original-url="https://blogs.msdn.com/cfs-file.ashx/__key/communityserver-blogs-components-weblogfiles/00-00-01-70-07-metablogapi/7144.BuildSettingsDialog_5F00_5ACB56F9.png"><img title="BuildSettingsDialog" style="border-left-width: 0px; border-right-width: 0px; border-bottom-width: 0px; display: inline; border-top-width: 0px" border="0" alt="BuildSettingsDialog" src="https://msdnshared.blob.core.windows.net/media/MSDNBlogsFS/prod.evol.blogs.msdn.com/CommunityServer.Blogs.Components.WeblogFiles/00/00/01/70/07/metablogapi/5050.BuildSettingsDialog_thumb_73C9B7EF.png" original-url="https://blogs.msdn.com/cfs-file.ashx/__key/communityserver-blogs-components-weblogfiles/00-00-01-70-07-metablogapi/5050.BuildSettingsDialog_5F00_thumb_5F00_73C9B7EF.png" width="426" height="484" /></a></p>  <p align="justify">Lors du tout premier lancement, la liste “Scenes In Build” est vide et la plateforme d’exportation par défaut est “PC, Mac &amp; Linux Standalone”. La première étape consiste à ajouter des scènes dans notre binaire. Si vous avez déjà crée un projet, vous disposez forcément d’au moins une scène (fichier d’extension “.unity”). Je vous invite donc à cliquer sur le bouton “Add Current” afin de sélectionner un ou plusieurs fichiers “.unity”. Ensuite il convient de sélectionner une plateforme. Dans notre cas, nous allons sélectionner la <strong>plateforme “Windows Store”</strong> et cliquer sur le bouton “Switch Platform”. Peut-être pensez-vous intérieurement : </p>  <ul>   <li>     <div align="justify">Question : “Oui mais pourquoi ne pas sélectionner PC ?”</div>   </li>    <li>     <div align="justify">Réponse : tout simplement parce qu’un binaire ciblant la plateforme PC, même s’il peut s’exécuter sur Windows 8.1, ne pourra pas être distribué sur Windows Store : en effet à ce jour seules les applications modernes peuvent être publiées sur le Windows Store</div>   </li> </ul>  <p align="justify">&#160;</p>  <ul>   <li>     <div align="justify">Question : “Et Windows Phone 8 ? Si je choisis cette option, je pourrai exécuter mon application sur Windows Phone 8.1, non ?</div>   </li>    <li>     <div align="justify">Réponse : Oui c’est vrai MAIS votre application sera identifiée comme une application Windows Phone Silverlight et non comme une application universelle WinRT. Du coup il vous faudra gérer deux exports en parallèle, l’un pour Windows et l’autre pour Windows Phone. Par ailleurs comme Windows 10 fait la part belle aux <a href="https://www.microsoftvirtualacademy.com/training-courses/a-developers-guide-to-windows-10-preview" target="_blank">développements d’applications universelles</a> (UAP), vos maintenances d’applications futurs n’en seront que simplifiées si vous faîtes ce choix dès aujourd’hui .&#160; </div>   </li> </ul>  <p>&#160;</p>  <p>Nous obtenons alors la boite de dialogue suivante :</p>  <p><a href="https://msdnshared.blob.core.windows.net/media/MSDNBlogsFS/prod.evol.blogs.msdn.com/CommunityServer.Blogs.Components.WeblogFiles/00/00/01/70/07/metablogapi/0131.BuildSettingsDialogWindowsStore_62E513FF.png" original-url="https://blogs.msdn.com/cfs-file.ashx/__key/communityserver-blogs-components-weblogfiles/00-00-01-70-07-metablogapi/0131.BuildSettingsDialogWindowsStore_5F00_62E513FF.png"><img title="BuildSettingsDialogWindowsStore" style="border-left-width: 0px; border-right-width: 0px; border-bottom-width: 0px; display: inline; border-top-width: 0px" border="0" alt="BuildSettingsDialogWindowsStore" src="https://msdnshared.blob.core.windows.net/media/MSDNBlogsFS/prod.evol.blogs.msdn.com/CommunityServer.Blogs.Components.WeblogFiles/00/00/01/70/07/metablogapi/3113.BuildSettingsDialogWindowsStore_thumb_66F1F282.png" original-url="https://blogs.msdn.com/cfs-file.ashx/__key/communityserver-blogs-components-weblogfiles/00-00-01-70-07-metablogapi/3113.BuildSettingsDialogWindowsStore_5F00_thumb_5F00_66F1F282.png" width="429" height="484" /></a> </p>  <p><u>Remarques</u> :</p>  <ul>   <li>     <div align="justify">J’ai choisi comme type <strong>“XAML C# Solutions”</strong>. J’aurai pu choisir “XAML C++ Solutions”. C’est une affaire de goût mais pas que ! En effet l’avantage du C# est que je peux débuguer mes scripts unity C# depuis Visual Studio. C’est bien pratique.</div>   </li>    <li>     <div align="justify">Ensuite j’ai sélectionné le<strong> SDK dénommé “Universal 8.1”</strong> afin de générer une unique solution Visual Studio permettant d’adresser à la fois Windows 8.1 et Windows Phone 8.1. D’autres choix sont possibles :</div>      <ul>       <li>         <div align="justify">8.0 pour adresser uniquement Windows 8.0</div>       </li>        <li>         <div align="justify">8.1 pour adresser uniquement Windows 8.1</div>       </li>        <li>         <div align="justify">Phone 8.1 pour adresser uniquement Windows Phone 8.1 (RT)</div>       </li>     </ul>   </li>    <li>     <div align="justify">Enfin j’ai coché “Unity C# Projects” afin de pouvoir débuguer sous Visual Studio</div>   </li> </ul>  <p>&#160;</p>  <p>Avant d’exporter ma scène, je clique sur le bouton “Player Settings” afin de définir des métadonnées (nom d’application, icones, splashscreen etc). S’affiche alors la fenêtre “Inspector” pointant sur l’onglet de plateforme “Windows Store” (icône verte) :</p>  <p><a href="https://msdnshared.blob.core.windows.net/media/MSDNBlogsFS/prod.evol.blogs.msdn.com/CommunityServer.Blogs.Components.WeblogFiles/00/00/01/70/07/metablogapi/1018.PlayerSettingsInspector_58B60A43.png" original-url="https://blogs.msdn.com/cfs-file.ashx/__key/communityserver-blogs-components-weblogfiles/00-00-01-70-07-metablogapi/1018.PlayerSettingsInspector_5F00_58B60A43.png"><img title="PlayerSettingsInspector" style="border-left-width: 0px; border-right-width: 0px; border-bottom-width: 0px; display: inline; border-top-width: 0px" border="0" alt="PlayerSettingsInspector" src="https://msdnshared.blob.core.windows.net/media/MSDNBlogsFS/prod.evol.blogs.msdn.com/CommunityServer.Blogs.Components.WeblogFiles/00/00/01/70/07/metablogapi/4276.PlayerSettingsInspector_thumb_5CC2E8C6.png" original-url="https://blogs.msdn.com/cfs-file.ashx/__key/communityserver-blogs-components-weblogfiles/00-00-01-70-07-metablogapi/4276.PlayerSettingsInspector_5F00_thumb_5F00_5CC2E8C6.png" width="407" height="484" /></a> </p>  <p align="justify">Je ne vais pas énumérer tous les paramètres car ils sont nombreux. Sachez néanmoins que tous les paramètres configurés ici sont modifiables dans Visual Studio après exportation. Par exemple si vous cliquez sur “Icon”, vous pourrez définir les différentes icônes (ou tuile dans le jargon des app Windows store) depuis Unity et vous les retrouverez dans le répertoire “Assets” de votre solution Visual Studio. Idem pour les autres métadonnées comme le nom de l’application, la version, les splashscreens etc. </p>  <p align="justify">Il est temps de cliquer sur le bouton “Build” de la fenêtre “Player Settings”. Une fois le répertoire de sortie sélectionné (personnellement j’ai l’habitude de créer un répertoire “Build” puis un répertoire reprenant le nom de la plateforme cible e.g. ./Build/Universal8.1/ ), Unity démarre la génération du projet Visual Studio :</p>  <p><a href="https://msdnshared.blob.core.windows.net/media/MSDNBlogsFS/prod.evol.blogs.msdn.com/CommunityServer.Blogs.Components.WeblogFiles/00/00/01/70/07/metablogapi/8738.Building_3CAA6CBA.png" original-url="https://blogs.msdn.com/cfs-file.ashx/__key/communityserver-blogs-components-weblogfiles/00-00-01-70-07-metablogapi/8738.Building_5F00_3CAA6CBA.png"><img title="Building" style="border-left-width: 0px; border-right-width: 0px; border-bottom-width: 0px; display: inline; border-top-width: 0px" border="0" alt="Building" src="https://msdnshared.blob.core.windows.net/media/MSDNBlogsFS/prod.evol.blogs.msdn.com/CommunityServer.Blogs.Components.WeblogFiles/00/00/01/70/07/metablogapi/3482.Building_thumb_0563E57F.png" original-url="https://blogs.msdn.com/cfs-file.ashx/__key/communityserver-blogs-components-weblogfiles/00-00-01-70-07-metablogapi/3482.Building_5F00_thumb_5F00_0563E57F.png" width="357" height="81" /></a> </p>  <p align="justify">Si vos scripts Unity contiennent des erreurs de compilation ou font référence à des plugins mal compilés, la génération échouera avec un message d’erreur associé. Si par contre la génération réussit, Unity ouvre alors l’explorateur de fichier pointant sur le projet Visual Studio fraichement crée :</p>  <p><a href="https://msdnshared.blob.core.windows.net/media/MSDNBlogsFS/prod.evol.blogs.msdn.com/CommunityServer.Blogs.Components.WeblogFiles/00/00/01/70/07/metablogapi/0724.BuildFolder_15068141.png" original-url="https://blogs.msdn.com/cfs-file.ashx/__key/communityserver-blogs-components-weblogfiles/00-00-01-70-07-metablogapi/0724.BuildFolder_5F00_15068141.png"><img title="BuildFolder" style="border-left-width: 0px; border-right-width: 0px; border-bottom-width: 0px; display: inline; border-top-width: 0px" border="0" alt="BuildFolder" src="https://msdnshared.blob.core.windows.net/media/MSDNBlogsFS/prod.evol.blogs.msdn.com/CommunityServer.Blogs.Components.WeblogFiles/00/00/01/70/07/metablogapi/6433.BuildFolder_thumb_06CA9902.png" original-url="https://blogs.msdn.com/cfs-file.ashx/__key/communityserver-blogs-components-weblogfiles/00-00-01-70-07-metablogapi/6433.BuildFolder_5F00_thumb_5F00_06CA9902.png" width="636" height="484" /></a> </p>  <h1>Une fois sous Visual Studio</h1>  <p>Ouvrez le projet généré (fichier d’extension “.sln”) avec Visual Studio soit en double-cliquant ce fichier depuis l’explorateur, soit en sélectionnant le menu “Ouvrir Projet” depuis Visual Studio. Une fois ouvert, intéressons-nous à la fenêtre “Explorateur de solutions” :</p>  <p><a href="https://msdnshared.blob.core.windows.net/media/MSDNBlogsFS/prod.evol.blogs.msdn.com/CommunityServer.Blogs.Components.WeblogFiles/00/00/01/70/07/metablogapi/1602.SolutionExplorer_43822192.png" original-url="https://blogs.msdn.com/cfs-file.ashx/__key/communityserver-blogs-components-weblogfiles/00-00-01-70-07-metablogapi/1602.SolutionExplorer_5F00_43822192.png"><img title="SolutionExplorer" style="border-left-width: 0px; border-right-width: 0px; border-bottom-width: 0px; display: inline; border-top-width: 0px" border="0" alt="SolutionExplorer" src="https://msdnshared.blob.core.windows.net/media/MSDNBlogsFS/prod.evol.blogs.msdn.com/CommunityServer.Blogs.Components.WeblogFiles/00/00/01/70/07/metablogapi/2161.SolutionExplorer_thumb_43187F4E.png" original-url="https://blogs.msdn.com/cfs-file.ashx/__key/communityserver-blogs-components-weblogfiles/00-00-01-70-07-metablogapi/2161.SolutionExplorer_5F00_thumb_5F00_43187F4E.png" width="531" height="484" /></a> </p>  <p align="justify">Ne fuyez pas !!!! Il y a beaucoup de fichiers mais en réalité seuls quelques uns vont retenir notre attention.&#160; Tout d’abord, il faut repérer le projet actif … facile son nom est en caractères gras : <strong>“New Unity Project.Windows (Windows 8.1)”</strong>. Visual Studio est sympa : il vous indique le nom de la plateforme active ciblée (ici Windows 8.1). <em>“Quoi ?”</em> allez-vous me dire ; <em>“Je pensais qu’en exportant en “Universal 8.1” j’obtiendrais une unique solution Visual Studio ?”</em> Pas tout à fait mais presque : vous obtenez bien une unique solution Visual Studio contenant plusieurs projets dont les principaux sont :</p>  <ul>   <li>     <div align="justify">New Unity Project.Windows (Windows 8.1)</div>   </li>    <li>     <div align="justify">New Unity Project.WindowsPhone (Windows Phone 8.1)</div>   </li> </ul>  <p align="justify">&#160;</p>  <p align="justify"><a href="https://msdnshared.blob.core.windows.net/media/MSDNBlogsFS/prod.evol.blogs.msdn.com/CommunityServer.Blogs.Components.WeblogFiles/00/00/01/70/07/metablogapi/5661.ProjetVisualStudio_0DA24DDA.png" original-url="https://blogs.msdn.com/cfs-file.ashx/__key/communityserver-blogs-components-weblogfiles/00-00-01-70-07-metablogapi/5661.ProjetVisualStudio_5F00_0DA24DDA.png"><img title="ProjetVisualStudio" style="border-left-width: 0px; border-right-width: 0px; border-bottom-width: 0px; display: inline; border-top-width: 0px" border="0" alt="ProjetVisualStudio" src="https://msdnshared.blob.core.windows.net/media/MSDNBlogsFS/prod.evol.blogs.msdn.com/CommunityServer.Blogs.Components.WeblogFiles/00/00/01/70/07/metablogapi/4064.ProjetVisualStudio_thumb_21BDFB14.png" original-url="https://blogs.msdn.com/cfs-file.ashx/__key/communityserver-blogs-components-weblogfiles/00-00-01-70-07-metablogapi/4064.ProjetVisualStudio_5F00_thumb_5F00_21BDFB14.png" width="644" height="370" /></a> </p>  <p align="justify">Pour compiler/exécuter/packager la version Windows ou la version Windows Phone, il vous faudra activer l’un de ces deux projets, le projet Windows étant le projet activé par défaut. Ensuite vous pouvez accéder/éditer/débuguer vos scripts unity (fichier main.cs dans mon exemple ci-dessus) qui sont accessibles dans le répertoire “Assets” des deux projets Assembly-CSharp-metro-vs2013 (Windows 8.1) et Assembly-CSharp-windows-phone-8.1 (Windows Phone 8.1). A noter que ces scripts sont des liens pointant vers les fichiers physiques du projet unity : ils n’ont pas été dupliqués ce qui est une approche plutôt intelligente car cela permet de travailler de manière synchrone sur les deux éditeurs en parallèle (bien sûr, dès qu’on modifie une scène unity il est nécessaire de ré-exporter vers Visual Studio, mais cela n’écrase pas les scripts unity). </p>  <p align="justify">Pour l’exécution sur Windows 8.1, pensez à sélectionner “x86” comme type de plateforme cible avant de lancer une exécution, sinon vous aurez une erreur (ARM est en effet positionné par défaut) :</p>  <p align="justify"><a href="https://msdnshared.blob.core.windows.net/media/MSDNBlogsFS/prod.evol.blogs.msdn.com/CommunityServer.Blogs.Components.WeblogFiles/00/00/01/70/07/metablogapi/8132.x86_19C8E963.png" original-url="https://blogs.msdn.com/cfs-file.ashx/__key/communityserver-blogs-components-weblogfiles/00-00-01-70-07-metablogapi/8132.x86_5F00_19C8E963.png"><img title="x86" style="border-left-width: 0px; border-right-width: 0px; border-bottom-width: 0px; display: inline; border-top-width: 0px" border="0" alt="x86" src="https://msdnshared.blob.core.windows.net/media/MSDNBlogsFS/prod.evol.blogs.msdn.com/CommunityServer.Blogs.Components.WeblogFiles/00/00/01/70/07/metablogapi/0652.x86_thumb_4267556A.png" original-url="https://blogs.msdn.com/cfs-file.ashx/__key/communityserver-blogs-components-weblogfiles/00-00-01-70-07-metablogapi/0652.x86_5F00_thumb_5F00_4267556A.png" width="395" height="213" /></a> </p>  <p align="justify">Pour l’exécution sur Windows Phone 8.1, vous avez le choix entre l’exécution sur émulateur (avec différentes résolutions) ou sur téléphone réel connecté en USB :</p>  <p align="justify"><a href="https://msdnshared.blob.core.windows.net/media/MSDNBlogsFS/prod.evol.blogs.msdn.com/CommunityServer.Blogs.Components.WeblogFiles/00/00/01/70/07/metablogapi/4331.arm_224ED95E.png" original-url="https://blogs.msdn.com/cfs-file.ashx/__key/communityserver-blogs-components-weblogfiles/00-00-01-70-07-metablogapi/4331.arm_5F00_224ED95E.png"><img title="arm" style="border-left-width: 0px; border-right-width: 0px; border-bottom-width: 0px; display: inline; border-top-width: 0px" border="0" alt="arm" src="https://msdnshared.blob.core.windows.net/media/MSDNBlogsFS/prod.evol.blogs.msdn.com/CommunityServer.Blogs.Components.WeblogFiles/00/00/01/70/07/metablogapi/8103.arm_thumb_48471A65.png" original-url="https://blogs.msdn.com/cfs-file.ashx/__key/communityserver-blogs-components-weblogfiles/00-00-01-70-07-metablogapi/8103.arm_5F00_thumb_5F00_48471A65.png" width="508" height="275" /></a> </p>  <p align="justify"><strong><u>Important</u></strong> : pour tester votre application sur un téléphone réel vous devez absolument débloquer votre téléphone afin de le basculer en mode développeur. Pour cela il est nécessaire de :</p>  <ul>   <li>     <div align="justify">Créer un <a href="https://www.microsoft.com/fr-fr/account/default.aspx " target="_blank">compte Microsoft</a> (équivalent d’un compte iTunes ou Gmail) : c’est facile et gratuit</div>   </li>    <li>     <div align="justify">Créer un <a href="https://dev.windows.com/fr-fr" target="_blank">compte développeur Microsoft</a> : les frais d’inscription sont uniques pour les 2 stores de $19 (14€) pour 1 individu, $99 (75€) pour une entreprise, gratuit pour les étudiants via le programme DreamSpark. Un compte permet de débloquer jusqu’à 3 téléphones</div>   </li>    <li>     <div align="justify">Débloquer son téléphone via l’utilitaire <a href="https://msdn.microsoft.com/en-us/library/windows/apps/ff769508%28v=vs.105%29.aspx" target="_blank">“Windows Phone Developer Registration”</a> inclus dans le sdk</div>   </li> </ul>  <p align="justify">&#160;</p>  <h1>A savoir</h1>  <p align="justify">Unity a défini des directives de compilation qui vous permettront de différencier des comportements de code selon que vous cibliez Windows 8.1 ou Windows Phone 8.1. Pourquoi ? Par exemple pour détecter les touches de clavier sous Windows ou encore tester la touche “Retour” uniquement disponible sous Windows Phone 8.1. Ces deux directives sont les suivantes :</p>  <ul>   <li>     <div align="justify">UNITY_WP_8_1 : Windows phone 8.1 only</div>   </li>    <li>     <div align="justify">UNITY_METRO_8_1 : Windows 8.1 only</div>   </li> </ul>  <p align="justify">&#160;</p>  <p align="justify">Voici un exemple de code tout simple permettant d’afficher un menu pause lorsque l’utilisateur appuie sur le bouton “Retour”. </p>    <div style="border: #000080 1px solid; color: #000; font-family: Consolas, 'Courier New', Courier, Monospace; font-size: 10pt"> <div style="background: #000080; color: #fff; font-family: Verdana, Tahoma, Arial, sans-serif; font-weight: bold; padding: 2px 5px">Code Snippet</div> <div style="background: #ffffff; color: #000000; max-height: 400px; overflow: auto"> <ol start="16" style="background: #ffffff; margin: 0 0 0 3em; padding: 0 0 0 5px;"> <li><span style="color:#008000">// Update is called once per frame</span></li> <li style="background: #f3f3f3"><span style="background:#ffffff;color:#000000"></span><span style="color:#0000ff">void</span> Update () {</li> <li>&nbsp;</li> <li style="background: #f3f3f3"><span style="color:#0000ff">#if</span> UNITY_WP_8_1</li> <li>&#160;&#160;&#160;&#160;<span style="color:#0000ff">while</span>(Input.GetKeyDown(KeyCode.Escape))</li> <li style="background: #f3f3f3">&#160;&#160;&#160;&#160;{</li> <li>&#160;&#160;&#160;&#160;&#160;&#160;&#160;&#160;pauseMenuEnabled = !pauseMenuEnabled;</li> <li style="background: #f3f3f3">&nbsp;</li> <li>&#160;&#160;&#160;&#160;&#160;&#160;&#160;&#160;<span style="color:#008000">// Display Pause menu when Back key is getting pressed</span></li> <li style="background: #f3f3f3">&#160;&#160;&#160;&#160;&#160;&#160;&#160;&#160;<span style="color:#0000ff">if</span> (pauseMenuEnabled)</li> <li>&#160;&#160;&#160;&#160;&#160;&#160;&#160;&#160;{</li> <li style="background: #f3f3f3">&#160;&#160;&#160;&#160;&#160;&#160;&#160;&#160;&#160;&#160;&#160;&#160;PauseGame();</li> <li>&#160;&#160;&#160;&#160;&#160;&#160;&#160;&#160;}</li> <li style="background: #f3f3f3">&#160;&#160;&#160;&#160;&#160;&#160;&#160;&#160;<span style="color:#0000ff">else</span></li> <li>&#160;&#160;&#160;&#160;&#160;&#160;&#160;&#160;{</li> <li style="background: #f3f3f3">&#160;&#160;&#160;&#160;&#160;&#160;&#160;&#160;&#160;&#160;&#160;&#160;ResumeGame();</li> <li>&#160;&#160;&#160;&#160;&#160;&#160;&#160;&#160;}</li> <li style="background: #f3f3f3">&#160;&#160;&#160;&#160;}</li> <li><span style="color:#0000ff">#endif</span></li> <li style="background: #f3f3f3"><span style="background:#ffffff;color:#000000">}</span></li> </ol> </div> </div>    <p>&#160;</p>  <p>La gestion du bouton “Retour” est mappé sur la touche clavier “ESC”. Ce code sera ignoré pour la compilation ciblant Windows 8.1</p>  <h1>Conclusion</h1>  <p>L’export d’un projet Unity sur les plateformes Windows et Windows Store est simple à mettre en œuvre. Vous avez déjà des jeux Unity ciblant iOS et Android ? Alors n’hésitez pas à faire le test :-) Dans le prochain article je détaillerai l’utilisation du plugin UnityVS permettant d’utiliser l’IDE Visual Studio en lieu et place de l’éditeur par défaut MonoDevelop. </p>]]></content:encoded>
    </item>
  </channel>
</rss>