Net获取windows显示适配器、监视器信息
先了解一个概念
在.net 中如何获取屏幕监视器的详情。主要有如下四种方法:
1 显示适配器-设备的硬件ID和状态标志等信息
[DllImport("user32.dll")] private static extern bool EnumDisplayDevices(string lpDevice, uint iDevNum, ref DISPLAY_DEVICE lpDisplayDevice, uint dwFlags); [StructLayout(LayoutKind.Sequential, CharSet = CharSet.Ansi)] private struct DISPLAY_DEVICE { public int cb; [MarshalAs(UnmanagedType.ByValTStr, SizeConst = 32)] public string DeviceName; [MarshalAs(UnmanagedType.ByValTStr, SizeConst = 128)] public string DeviceString; public uint StateFlags; [MarshalAs(UnmanagedType.ByValTStr, SizeConst = 128)] public string DeviceID; [MarshalAs(UnmanagedType.ByValTStr, SizeConst = 128)] public string DeviceKey; } /// <summary> /// 显示设备的硬件ID和状态标志 /// </summary> public static void GetMonitorHardwareIDs() { DISPLAY_DEVICE displayDevice = new DISPLAY_DEVICE(); displayDevice.cb = Marshal.SizeOf(displayDevice); for (int i = 0; EnumDisplayDevices(null, (uint)i, ref displayDevice, 0); i++) { Debug.WriteLine($"=========== EnumDisplay {i}"); Debug.WriteLine("Device Name: " + displayDevice.DeviceName); Debug.WriteLine("Device DeviceString: " + displayDevice.DeviceString); Debug.WriteLine("Device StateFlags: " + displayDevice.StateFlags); Debug.WriteLine("Device ID: " + displayDevice.DeviceID); Debug.WriteLine("Device DeviceKey: " + displayDevice.DeviceKey); Debug.WriteLine("======================"); displayDevice.cb = Marshal.SizeOf(displayDevice); } }
查看时候,需要删选Device StateFlags: 0 的设备
2 屏幕的布局和工作区域信息,.net中使用此屏幕的index作为屏幕的编号
/// <summary> /// 屏幕的布局和工作区域信息 /// </summary> private void PrintAllScreensInfo() { for (int i = 0; i < System.Windows.Forms.Screen.AllScreens.Length; i++) { Debug.WriteLine($"=========== AllScreens {i}"); Debug.WriteLine("Device Name: " + System.Windows.Forms.Screen.AllScreens[i].DeviceName); Debug.WriteLine("Bounds: " + System.Windows.Forms.Screen.AllScreens[i].Bounds); Debug.WriteLine("Working Area: " + System.Windows.Forms.Screen.AllScreens[i].WorkingArea); Debug.WriteLine("Primary Screen: " + System.Windows.Forms.Screen.AllScreens[i].Primary); Debug.WriteLine("BitsPerPixel: " + System.Windows.Forms.Screen.AllScreens[i].BitsPerPixel); Debug.WriteLine(System.Windows.Forms.Screen.AllScreens[i].ToString()); Debug.WriteLine("======================"); } }
3 监视器-详细属性,如制造商、型号、屏幕尺寸等信息
注意:获取的信息可能不准确,并非所有显示器都会提供完整的WMI信息。例如,一些较旧的或非标准的显示器可能不支持通过WMI报告其制造商、类型或分辨率等详细信息。
/// <summary> /// 显示器的详细属性,如制造商、型号、屏幕尺寸 /// </summary> private void GetMonitorDetails() { // 创建一个ManagementObjectSearcher对象,用于查询WMI数据 ManagementObjectSearcher searcher = new ManagementObjectSearcher("SELECT * FROM Win32_DesktopMonitor"); // 遍历查询结果,获取每个显示器的信息 int i = 0; foreach (ManagementObject obj in searcher.Get()) { Debug.WriteLine($"=========== Win32_DesktopMonitor {i++}"); Debug.WriteLine("Caption: {0}", obj["Caption"]); // 显示器名称 Debug.WriteLine("Name: {0}", obj["Name"]); Debug.WriteLine("Device ID: {0}", obj["DeviceID"]); // 显示器的PnP设备ID Debug.WriteLine("PNPDeviceID: {0}", obj["PNPDeviceID"]); Debug.WriteLine("DisplayType: {0}", obj["DisplayType"]); Debug.WriteLine("MonitorManufacturer: {0}", obj["MonitorManufacturer"]); Debug.WriteLine("MonitorType: {0}", obj["MonitorType"]); // 显示器的状态 Debug.WriteLine("Status: {0}", obj["Status"]); // 显示器的屏幕高度 Debug.WriteLine("Screen Height: {0}", obj["ScreenHeight"]); // 显示器的屏幕宽度 Debug.WriteLine("Screen Width: {0}", obj["ScreenWidth"]); // 显示器的描述 Debug.WriteLine("Description: {0}", obj["Description"]); Debug.WriteLine("SystemCreationClassName: {0}", obj["SystemCreationClassName"]); Debug.WriteLine("======================"); } }
补充: cmd : wmic path win32_pnpentity get DeviceID, Name 获取设备信息 。PNPDeviceID 是 Windows 操作系统中用于唯一标识硬件设备的字符串。PNP 是 Plug and Play(即插即用)的缩写,它是一种标准,允许操作系统自动检测并配置硬件设备,而无需用户进行手动设置。
4 通过SharpDX.DXGI,获取所有监视器的信息。
var adapter = new Factory1().GetAdapter1(0); int outputCount = adapter.GetOutputCount(); Console.WriteLine($"Total outputs: {outputCount}"); for (int i = 0; i < outputCount; i++) { Output output = adapter.GetOutput(i); var bounds = output.Description.DesktopBounds; Debug.WriteLine($"=========== Adapter_Output {i}"); Debug.WriteLine($"DeviceName: {output.Description.DeviceName}"); Debug.WriteLine($"position: {bounds.Left} {bounds.Top} {bounds.Right} {bounds.Bottom}"); Debug.WriteLine($"bounds: {Math.Abs(bounds.Right- bounds.Left)} {Math.Abs(bounds.Bottom - bounds.Top)} "); Debug.WriteLine($"IsAttachedToDesktop: {output.Description.IsAttachedToDesktop}"); Debug.WriteLine($"MonitorHandle: {output.Description.MonitorHandle}"); Debug.WriteLine($"======================"); } adapter.Dispose();
总结使用场景:识别显示器的硬件ID,结合上面四中,最后通过第四种获取 屏幕索引,然后传入屏幕索引,使用DX截图获取屏幕图像,详见https://www.cnblogs.com/terryK/p/18585945