Comment détecter si mon application est en cours d’exécution sur Windows 10

Je recherche un moyen de détecter si mon application C # s’exécute sous Windows 10.

J’avais espéré que Environment.OSVersion ferait l’affaire, mais cela semble renvoyer une Version de 6.3.9600.0 sur Windows 8.1 et Windows 10.

D’autres solutions telles que celle -ci ne semblent pas non plus distinguer Windows 8 de Windows 10.

Aucune suggestion?


Pourquoi ai-je besoin de faire ça?

Parce que j’utilise un contrôle WinForms WebBrowser pour héberger une page OAuth qui se bloque et se grave dans les anciennes versions d’IE (mon application se connecte au compte Nest d’ un utilisateur …).

Par défaut, le contrôle WebBrowser émule IE7. À l’aide d’une clé de registre, vous pouvez lui indiquer d’émuler la dernière version d’IE installée sur le PC hôte. Toutefois, la valeur qui fonctionnait jusqu’à Windows 8.1 (et les versions préliminaires de Windows 10) ne fonctionne pas dans la version finale de Windows 10.

Si vous regardez le registre, vous trouverez le nom de l’environnement:

 HKEY_LOCAL_MACHINE\SOFTWARE\Microsoft\Windows NT\CurrentVersion\ProductName 

Par exemple, mon nom de produit est Windows 10 Home :

Enregistrement

Avec ce code, vous obtenez si Windows 10:

  static bool IsWindows10() { var reg = Registry.LocalMachine.OpenSubKey(@"SOFTWARE\Microsoft\Windows NT\CurrentVersion"); ssortingng productName = (ssortingng)reg.GetValue("ProductName"); return productName.StartsWith("Windows 10"); } 

Remarque: ajoutez à l’ using Microsoft.Win32; à vos utilisations.

Réponse

Utilisez Environment.OSVersion et ajoutez un fichier manifeste d’application avec les élémentssupportés pertinents non commentés.

append par exemple ceci sous

               

Raison

Je n’aime pas la réponse de @Mitat Koyuncu, car il utilise le registre inutilement et, comme indiqué dans les commentaires, utilise une parsing non fiable des chaînes.

De plus, je n’aime pas la réponse de @sstan parce qu’il utilise du code tiers et qu’il a de toute façon besoin du manifeste d’application.

De MSDN :

Windows 10: VerifyVersionInfo renvoie false lorsqu’il est appelé par des applications ne disposant pas d’un manifeste de compatibilité pour Windows 8.1 ou Windows 10 si le paramètre lpVersionInfo est défini pour spécifier Windows 8.1 ou Windows 10, même si la version actuelle du système d’exploitation est Windows 8.1 ou Windows 10. Plus précisément, VerifyVersionInfo a le comportement suivant:

• Si l’application n’a pas de manifeste, VerifyVersionInfo se comporte comme si la version du système d’exploitation était Windows 8 (6.2).

• Si l’application possède un manifeste contenant le GUID correspondant à Windows 8.1, VerifyVersionInfo se comporte comme si la version du système d’exploitation était Windows 8.1 (6.3).

• Si l’application possède un manifeste contenant le GUID correspondant à Windows 10, VerifyVersionInfo se comporte comme si la version du système d’exploitation était Windows 10 (10.0).

La raison en est que VerifyVersionInfo est obsolète dans Windows 10.

J’ai testé sur Windows 10 et effectivement Environment.OSVersion fonctionne exactement comme prévu lorsque app.Manifest contient le GUID approprié comme ci-dessus. C’est très probablement pour cette raison qu’ils n’ont pas changé ni n’ont déconseillé de le faire à partir de .Net Framework.

Sous le capot, Environment.OSVersion utilise la fonction GetVersionEx , obsolète. La documentation met en garde sur le comportement que vous avez observé:

Les applications non manifestées pour Windows 8.1 ou Windows 10 renverront la valeur de version de Windows 8 OS (6.2).

La documentation recommande ensuite:

Identifier le système d’exploitation actuel n’est généralement pas le meilleur moyen de déterminer si une fonctionnalité particulière du système d’exploitation est présente. En effet, de nouvelles fonctionnalités peuvent être ajoutées au système d’exploitation dans une DLL redissortingbuable. Plutôt que d’utiliser GetVersionEx pour déterminer la plate-forme du système d’exploitation ou le numéro de version, testez la présence de la fonctionnalité elle-même.

Si la recommandation ci-dessus ne convient pas à votre cas et que vous souhaitez réellement vérifier la version actuelle du système d’exploitation, la documentation fournit également un indice à ce sujet:

Pour comparer la version actuelle du système à une version requirejse, utilisez la fonction VerifyVersionInfo au lieu d’utiliser GetVersionEx pour effectuer la comparaison vous-même.

L’article suivant a publié une solution de travail utilisant la fonction VerifyVersionInfo : Version Helper API for .NET .

Compte tenu de l’auteur de cet article, l’extrait de code suivant devrait vous fournir le comportement que vous recherchez:

 public class Program { static void Main(ssortingng[] args) { Console.WriteLine(IsWindowsVersionOrGreater(6, 3, 0)); // Plug in appropriate values. } [StructLayout(LayoutKind.Sequential)] struct OsVersionInfoEx { public uint OSVersionInfoSize; public uint MajorVersion; public uint MinorVersion; public uint BuildNumber; public uint PlatformId; [MarshalAs(UnmanagedType.ByValTStr, SizeConst = 128)] public ssortingng CSDVersion; public ushort ServicePackMajor; public ushort ServicePackMinor; public ushort SuiteMask; public byte ProductType; public byte Reserved; } [DllImport("kernel32.dll")] static extern ulong VerSetConditionMask(ulong dwlConditionMask, uint dwTypeBitMask, byte dwConditionMask); [DllImport("kernel32.dll")] static extern bool VerifyVersionInfo( [In] ref OsVersionInfoEx lpVersionInfo, uint dwTypeMask, ulong dwlConditionMask); static bool IsWindowsVersionOrGreater( uint majorVersion, uint minorVersion, ushort servicePackMajor) { OsVersionInfoEx osvi = new OsVersionInfoEx(); osvi.OSVersionInfoSize = (uint)Marshal.SizeOf(osvi); osvi.MajorVersion = majorVersion; osvi.MinorVersion = minorVersion; osvi.ServicePackMajor = servicePackMajor; // These constants initialized with corresponding definitions in // winnt.h (part of Windows SDK) const uint VER_MINORVERSION = 0x0000001; const uint VER_MAJORVERSION = 0x0000002; const uint VER_SERVICEPACKMAJOR = 0x0000020; const byte VER_GREATER_EQUAL = 3; ulong versionOrGreaterMask = VerSetConditionMask( VerSetConditionMask( VerSetConditionMask( 0, VER_MAJORVERSION, VER_GREATER_EQUAL), VER_MINORVERSION, VER_GREATER_EQUAL), VER_SERVICEPACKMAJOR, VER_GREATER_EQUAL); uint versionOrGreaterTypeMask = VER_MAJORVERSION | VER_MINORVERSION | VER_SERVICEPACKMAJOR; return VerifyVersionInfo(ref osvi, versionOrGreaterTypeMask, versionOrGreaterMask); } } 

Avertissement: je n’ai pas encore Windows 10, je n’ai donc pas testé le code sous Windows 10.

Je suggère d’utiliser le registre pour trouver les valeurs que vous voulez. Microsoft a modifié la manière dont Windows 10 est répertorié dans le registre. Le code doit donc s’adapter à cette situation.

Voici le code que j’utilise, qui identifie correctement Windows 10:

 namespace Inspection { ///  /// Static class that adds convenient methods for getting information on the running computers basic hardware and os setup. ///  public static class ComputerInfo { ///  /// Returns the Windows major version number for this computer. ///  public static uint WinMajorVersion { get { dynamic major; // The 'CurrentMajorVersionNumber' ssortingng value in the CurrentVersion key is new for Windows 10, // and will most likely (hopefully) be there for some time before MS decides to change this - again... if (TryGetRegistryKey(@"SOFTWARE\Microsoft\Windows NT\CurrentVersion", "CurrentMajorVersionNumber", out major)) { return (uint) major; } // When the 'CurrentMajorVersionNumber' value is not present we fallback to reading the previous key used for this: 'CurrentVersion' dynamic version; if (!TryGetRegistryKey(@"SOFTWARE\Microsoft\Windows NT\CurrentVersion", "CurrentVersion", out version)) return 0; var versionParts = ((ssortingng) version).Split('.'); if (versionParts.Length != 2) return 0; uint majorAsUInt; return uint.TryParse(versionParts[0], out majorAsUInt) ? majorAsUInt : 0; } } ///  /// Returns the Windows minor version number for this computer. ///  public static uint WinMinorVersion { get { dynamic minor; // The 'CurrentMinorVersionNumber' ssortingng value in the CurrentVersion key is new for Windows 10, // and will most likely (hopefully) be there for some time before MS decides to change this - again... if (TryGetRegistryKey(@"SOFTWARE\Microsoft\Windows NT\CurrentVersion", "CurrentMinorVersionNumber", out minor)) { return (uint) minor; } // When the 'CurrentMinorVersionNumber' value is not present we fallback to reading the previous key used for this: 'CurrentVersion' dynamic version; if (!TryGetRegistryKey(@"SOFTWARE\Microsoft\Windows NT\CurrentVersion", "CurrentVersion", out version)) return 0; var versionParts = ((ssortingng) version).Split('.'); if (versionParts.Length != 2) return 0; uint minorAsUInt; return uint.TryParse(versionParts[1], out minorAsUInt) ? minorAsUInt : 0; } } ///  /// Returns whether or not the current computer is a server or not. ///  public static uint IsServer { get { dynamic installationType; if (TryGetRegistryKey(@"SOFTWARE\Microsoft\Windows NT\CurrentVersion", "InstallationType", out installationType)) { return (uint) (installationType.Equals("Client") ? 0 : 1); } return 0; } } private static bool TryGetRegistryKey(ssortingng path, ssortingng key, out dynamic value) { value = null; try { var rk = Registry.LocalMachine.OpenSubKey(path); if (rk == null) return false; value = rk.GetValue(key); return value != null; } catch { return false; } } } } 

Avez-vous essayé ci-dessous? [Vous devez append une référence à Microsoft.VisulaBasic dll]

 new Microsoft.VisualBasic.Devices.ComputerInfo().OSFullName 

Sur ma machine cela donne, Microsoft Windows 7 Ultimate

Ne pouvez-vous pas utiliser les fonctions Version Helper? https://msdn.microsoft.com/en-us/library/windows/desktop/dn424972(v=vs.85).aspx

IsWindows10OrGreater

Indique si la version actuelle du système d’exploitation correspond ou est supérieure à la version de Windows 10. Pour Windows 10, IsWindows10OrGreater renvoie false, à moins que l’application ne contienne un manifeste contenant une section de compatibilité contenant le GUID désignant Windows 10.

et ajoutez les GUID: https://msdn.microsoft.com/en-ca/library/windows/desktop/dn481241(v=vs.85).aspx

Essaye celui-là:

 ssortingng subKey = @"SOFTWARE\Wow6432Node\Microsoft\Windows NT\CurrentVersion"; Microsoft.Win32.RegistryKey key = Microsoft.Win32.Registry.LocalMachine; Microsoft.Win32.RegistryKey skey = key.OpenSubKey(subKey); ssortingng name = skey.GetValue("ProductName").ToSsortingng(); 

et alors vous pouvez simplement utiliser une clause if:

 if(name.Contains("Windows 10")) { //... procedures } else { //... procedures }