How do I prevent Window resizing when the Workstation is Locked then Unlocked?

大兔子大兔子 提交于 2019-12-03 16:53:05

Before the window is resized, the application will get a WM_WINDOWPOSCHANGING message from Windows. You can intercept that message and change the parameters, forcing the window to stay put. You need to be careful, because you'll get the same message when the user is trying to move or resize the window. Probably when it's maximized or minimized, too.

Edit: You can use the WTSRegisterSessionNotification function to get additional messages. The messages are intended for fast user switching, but the lock screen is implemented in Windows as a system session.

Leif Carlsen

A similar question has an answer that allows you to restore window size in a .net application after the session is unlocked.

Someone asked essentially the same question on SuperUser, but from your user's perspective: How can I stop big windows from resizing when I lock my workstation?

ChrisF

I tried the solution given in the question referenced by Leif and found that the SessionSwitchReason.SessionUnlock event seemed to be fired after the computer had been locked rather than before. This meant that the window size and location had already been reset, so the resize failed.

Therefore, I had to find another way of storing the current size and location before the computer was locked. The only thing I could see to do was to subscribe to the ResizeEnd for Winforms applications and update the "pre-lock" size and location there.

I haven't been able to get it working for WPF applications yet, because WPF doesn't have the equivalent of ResizeEnd (or I haven't found it yet) and subscribing to SizeChanged and LocationChanged isn't good enough as these are fired when the computer is locked as well overwriting the size and location.

In the end I had to hook into the Windows ExitSizeMove event to save the current size and position. Details of how to hook into this event can be found here:

private const int WM_EXITSIZEMOVE = 0x232;

private void Window_Loaded(object sender, RoutedEventArgs e)
{
    HwndSource source = HwndSource.FromHwnd(new WindowInteropHelper(this).Handle);
    source.AddHook(new HwndSourceHook(WndProc));
}

private IntPtr WndProc(IntPtr hwnd, int msg,
                       IntPtr wParam, IntPtr lParam, ref bool handled)
{
    if (msg == WM_EXITSIZEMOVE)
    {
        // save location and size of window

        handled = true;
    }

    return IntPtr.Zero;
}
易学教程内所有资源均来自网络或用户发布的内容,如有违反法律规定的内容欢迎反馈
该文章没有解决你所遇到的问题?点击提问,说说你的问题,让更多的人一起探讨吧!