使用NativeWindow禁用屏幕保护程序

Mic*_*oll 2 c# winforms

我想禁用屏幕保护程序并关闭电源.在这个阶段,没有窗户形式,我可以.因此,我不想使用NativeWindow.

这是我的代码

sealed class ObserverWindow : NativeWindow, IDisposable
{
    internal ObserverWindow()
    {
        this.CreateHandle(new CreateParams()
        {
            Parent= IntPtr.Zero
        });

    }

    public void Dispose()
    {
        DestroyHandle();
    }

    protected override void WndProc(ref Message msg)
    {
        if (msg.Msg == WM_SYSCOMMAND &&
            ((((long)msg.WParam & 0xFFF0) == SC_SCREENSAVE) ||
            ((long)msg.WParam & 0xFFF0) == SC_MONITORPOWER))
        {
            msg.Msg = 0;
            msg.HWnd = IntPtr.Zero;
        }
        base.WndProc(ref msg);
    }
}
Run Code Online (Sandbox Code Playgroud)

问题是,没有使用WM_SYSCOMMAND调用WndProc.实际上,WndProc被称为4次.在最后一次调用时,有msg.Msg == WM_CREATE.

我想我错过了一些创建参数.有人有建议吗?

关心迈克尔

UPDATE

我在非STA线程中运行代码.因此,窗口没有显示任何消息,而不是初始消息.现在我收到了WM_SYSCOMMAND消息.但是当屏幕保护程序激活时,没有消息.

我也尝试用相同的结果覆盖Form的WndProc.但这曾经在Windows XP中运行.Windows 7有变化吗?

操作系统:Windows 7 64位.

正如本问题中的评论所述,只有前景窗口可以取消屏幕保护程序.因此上面的代码无法工作.NativeWindow非常适合接收消息,但不适用于取消屏幕保护程序.对于后者,我推荐这个问题的答案.

Han*_*ant 6

执行此操作的正确方法是告诉Windows您的线程需要激活显示.常用于视频播放器.P /调用SetThreadExecutionState()API函数,传递ES_DISPLAY_REQUIRED.并且ES_SYSTEM_REQUIRED可防止机器自动关闭.访问pinvoke.net获取所需的声明.