关闭显示器电源SendMessage函数调用方法

2019-07-13 23:05发布

当然在台式机上,直接关闭显示器电源即可。
在笔记本上,利用键盘的FN快捷键,只能关闭屏幕背光,
不能关掉主板给屏幕的信号输出。仔细看仍然会看到暗淡的桌面。

在桌面显示属性的“电源管理”里面,我们可以调整电源方案,
设置计算机在X分钟后关闭监视器,硬盘,待机。等等。。。

命令行为:
powercfg /change "电源方案名称" /moniter-timeout-ac 1

这个比较麻烦,还需知道当前使用的电源方案。

不过,windows为我们提供了一个API。可以实现即时关闭监视器。


LRESULT WINAPI SendMessage(
__in HWND hWnd,
__in UINT Msg,
__in WPARAM wParam,
__in LPARAM lParam
);

详见:http://msdn.microsoft.com/en-us/library/ms644950(VS.85).aspx

此API在平台调用中,如下签名:

 //C# Signature:
 [DllImport("user32.dll", CharSet = CharSet.Auto)]
 static extern IntPtr SendMessage(IntPtr hWnd, UInt32 Msg, IntPtr wParam, IntPtr lParam);
此方法的各个参数类型有一些重载,一般还是建议用IntPtr,否则,在64位平台OR其它情况下可能会崩溃~

我们需要传给Msg 一个系统消息,即:WM_SYSCOMMAND
然后是附加信息,比如屏幕保护:SC_SCREENSAVE,监视器电源:SC_MONITORPOWER
WM_SYSCOMMAND有如下取值:

enum SysCommands : int
{
SC_SIZE = 0xF000,
SC_MOVE = 0xF010,
SC_MINIMIZE = 0xF020,
SC_MAXIMIZE = 0xF030,
SC_NEXTWINDOW = 0xF040,
SC_PREVWINDOW = 0xF050,
SC_CLOSE = 0xF060,
SC_VSCROLL = 0xF070,
SC_HSCROLL = 0xF080,
SC_MOUSEMENU = 0xF090,
SC_KEYMENU = 0xF100,
SC_ARRANGE = 0xF110,
SC_RESTORE = 0xF120,
SC_TASKLIST = 0xF130,
SC_SCREENSAVE = 0xF140,
SC_HOTKEY = 0xF150,
//#if(WINVER >= 0x0400) //Win95
SC_DEFAULT = 0xF160,
SC_MONITORPOWER = 0xF170,
SC_CONTEXTHELP = 0xF180,
SC_SEPARATOR = 0xF00F,
//#endif /* WINVER >= 0x0400 */

//#if(WINVER >= 0x0600) //Vista
SCF_ISSECURE = 0x00000001,
//#endif /* WINVER >= 0x0600 */

/*
* Obsolete names
*/
SC_ICON = SC_MINIMIZE,
SC_ZOOM = SC_MAXIMIZE,
}
于是有了下面的调用:

 private const uint WM_SYSCOMMAND = 0x0112;
 private const uint SC_MONITORPOWER = 0xF170;
 //关闭
 SendMessage(this.Handle,WM_SYSCOMMAND , (IntPtr)SC_MONITORPOWER,2);
 //打开
 SendMessage(this.Handle,WM_SYSCOMMAND , (IntPtr)SC_MONITORPOWER,-1);

 希望大家在工作之余,可以为社会做点小小的贡献~