2014-10-09 6 views
5

Ich möchte alle Energiesparpläne in Ihrem Computer mit C# abrufen.Windows-Energiesparpläne/-schemata in C# abrufen (mit WinAPI)

Ich dachte Sie die API PowerEnumerate Funktion in irgendeiner Weise zu verwenden, möglicherweise in der Lage:

DWORD WINAPI PowerEnumerate(
    _In_opt_ HKEY RootPowerKey, 
    _In_opt_ const GUID *SchemeGuid, 
    _In_opt_ const GUID *SubGroupOfPowerSettingsGuid, 
    _In_  POWER_DATA_ACCESSOR AccessFlags, 
    _In_  ULONG Index, 
    _Out_opt_ UCHAR *Buffer, 
    _Inout_ DWORD *BufferSize 
); 

Aber ich habe keine Ahnung, wie man wie ich weiß nicht, C. wirklich So .. kann Wie Ich mag es, alle verfügbaren Energiesparpläne aufzuzählen und eine Liste von ihnen zu erstellen. Ich möchte dann auf jede Energiespar-GUID und ihren "benutzerfreundlichen Namen" zugreifen können.

Also .. Wenn jemand, der gut in der WinAPI von C# ist, wer helfen möchte, wäre das toll - oder wenn jemand eine bessere Lösung hat. Ich habe wirklich versucht, eine gute Antwort darauf zu finden, aber es scheint keine zu geben. Ich denke, das würde vielen Menschen helfen.

Kann mir jemand dabei helfen?

Antwort

6

Dies sollte es tun:

using System; 
using System.Linq; 
using System.Reflection; 
using System.Runtime.InteropServices; 
using System.Collections.Generic; 

public class Program 
{ 
    [DllImport("PowrProf.dll")] 
    public static extern UInt32 PowerEnumerate(IntPtr RootPowerKey, IntPtr SchemeGuid, IntPtr SubGroupOfPowerSettingGuid, UInt32 AcessFlags, UInt32 Index, ref Guid Buffer, ref UInt32 BufferSize); 

    [DllImport("PowrProf.dll")] 
    public static extern UInt32 PowerReadFriendlyName(IntPtr RootPowerKey, ref Guid SchemeGuid, IntPtr SubGroupOfPowerSettingGuid, IntPtr PowerSettingGuid, IntPtr Buffer, ref UInt32 BufferSize); 

    public enum AccessFlags : uint 
    { 
     ACCESS_SCHEME = 16, 
     ACCESS_SUBGROUP = 17, 
     ACCESS_INDIVIDUAL_SETTING = 18 
    } 

    private static string ReadFriendlyName(Guid schemeGuid) 
    { 
     uint sizeName = 1024; 
     IntPtr pSizeName = Marshal.AllocHGlobal((int)sizeName); 

     string friendlyName; 

     try 
     { 
      PowerReadFriendlyName(IntPtr.Zero, ref schemeGuid, IntPtr.Zero, IntPtr.Zero, pSizeName, ref sizeName); 
      friendlyName = Marshal.PtrToStringUni(pSizeName); 
     } 
     finally 
     { 
      Marshal.FreeHGlobal(pSizeName); 
     } 

     return friendlyName; 
    } 

    public static IEnumerable<Guid> GetAll() 
    { 
     var schemeGuid = Guid.Empty; 

     uint sizeSchemeGuid = (uint)Marshal.SizeOf(typeof(Guid)); 
     uint schemeIndex = 0; 

     while (PowerEnumerate(IntPtr.Zero, IntPtr.Zero, IntPtr.Zero, (uint)AccessFlags.ACCESS_SCHEME, schemeIndex, ref schemeGuid, ref sizeSchemeGuid) == 0) 
     { 
      yield return schemeGuid; 
      schemeIndex++; 
     } 
    } 

    public static void Main() 
    { 
     var guidPlans = GetAll(); 

     foreach (Guid guidPlan in guidPlans) 
     { 
      Console.WriteLine(ReadFriendlyName(guidPlan)); 
     } 
    } 
} 

Sie können dieses Programm als Administrator zu Sicherheitszwecken laufen müssen.

+0

Funktioniert genau wie ich wollte! Vielen Dank!! Wenn du Zeit hast, wäre es nett, wenn du dich mit einem Tutorial verbinden könntest, wo ich selbst lernen könnte, wie ich diese Art von Sachen mache. Noch einmal Danke! – CrashproofCode

+0

Blech ... Verwenden Sie C++/CLI anstelle von P/Invoke. Jedem sein eigenes ... –