From a54b85bfa7507e9124f06e31bf1cfe8c00574233 Mon Sep 17 00:00:00 2001 From: Nikita Tsukanov Date: Sat, 1 Dec 2018 20:17:06 +0300 Subject: [PATCH] A bit more clean method of new window rect calculation --- .../Interop/UnmanagedMethods.cs | 10 ++++ src/Windows/Avalonia.Win32/WindowImpl.cs | 48 +++++++++---------- 2 files changed, 32 insertions(+), 26 deletions(-) diff --git a/src/Windows/Avalonia.Win32/Interop/UnmanagedMethods.cs b/src/Windows/Avalonia.Win32/Interop/UnmanagedMethods.cs index adfbf0cb52..60b56ea580 100644 --- a/src/Windows/Avalonia.Win32/Interop/UnmanagedMethods.cs +++ b/src/Windows/Avalonia.Win32/Interop/UnmanagedMethods.cs @@ -1172,6 +1172,8 @@ namespace Avalonia.Win32.Interop public int right; public int bottom; + public int Width => right - left; + public int Height => bottom - top; public RECT(Rect rect) { left = (int)rect.X; @@ -1179,6 +1181,14 @@ namespace Avalonia.Win32.Interop right = (int)(rect.X + rect.Width); bottom = (int)(rect.Y + rect.Height); } + + public void Offset(POINT pt) + { + left += pt.X; + right += pt.X; + top += pt.Y; + bottom += pt.Y; + } } [StructLayout(LayoutKind.Sequential)] diff --git a/src/Windows/Avalonia.Win32/WindowImpl.cs b/src/Windows/Avalonia.Win32/WindowImpl.cs index 3eeccb368c..1213be1bf0 100644 --- a/src/Windows/Avalonia.Win32/WindowImpl.cs +++ b/src/Windows/Avalonia.Win32/WindowImpl.cs @@ -888,7 +888,7 @@ namespace Avalonia.Win32 private void UpdateWMStyles(Action change) { - var decorated = _decorated; + var oldDecorated = _decorated; var oldThickness = BorderThickness; @@ -912,37 +912,33 @@ namespace Avalonia.Win32 style ^= (WindowStyles.WS_SIZEFRAME); } + GetClientRect(_hwnd, out var oldClientRect); + var oldClientRectOrigin = new UnmanagedMethods.POINT(); + ClientToScreen(_hwnd, ref oldClientRectOrigin); + oldClientRect.Offset(oldClientRectOrigin); + + SetWindowLong(_hwnd, (int)WindowLongParam.GWL_STYLE, (uint)style); UnmanagedMethods.GetWindowRect(_hwnd, out var windowRect); - - if (decorated != _decorated) + bool frameUpdated = false; + if (oldDecorated != _decorated) { - Rect newRect; - + var newRect = oldClientRect; if (_decorated) - { - var thickness = BorderThickness; - - newRect = new Rect( - windowRect.left - thickness.Left, - windowRect.top - thickness.Top, - (windowRect.right - windowRect.left) + (thickness.Left + thickness.Right), - (windowRect.bottom - windowRect.top) + (thickness.Top + thickness.Bottom)); - } - else - { - newRect = new Rect( - windowRect.left + oldThickness.Left, - windowRect.top + oldThickness.Top, - (windowRect.right - windowRect.left) - (oldThickness.Left + oldThickness.Right), - (windowRect.bottom - windowRect.top) - (oldThickness.Top + oldThickness.Bottom)); - } - - UnmanagedMethods.SetWindowPos(_hwnd, IntPtr.Zero, (int)newRect.X, (int)newRect.Y, (int)newRect.Width, - (int)newRect.Height, - UnmanagedMethods.SetWindowPosFlags.SWP_NOZORDER | UnmanagedMethods.SetWindowPosFlags.SWP_NOACTIVATE | SetWindowPosFlags.SWP_FRAMECHANGED); + AdjustWindowRectEx(ref newRect, (uint)style, false, + GetWindowLong(_hwnd, (int)WindowLongParam.GWL_EXSTYLE)); + _changingDecorations = true; + SetWindowPos(_hwnd, IntPtr.Zero, newRect.left, newRect.top, newRect.Width, newRect.Height, + SetWindowPosFlags.SWP_NOZORDER | SetWindowPosFlags.SWP_NOACTIVATE | SetWindowPosFlags.SWP_FRAMECHANGED); + frameUpdated = true; } + + if (!frameUpdated) + SetWindowPos(_hwnd, IntPtr.Zero, 0, 0, 0, 0, + SetWindowPosFlags.SWP_FRAMECHANGED | SetWindowPosFlags.SWP_NOZORDER | + SetWindowPosFlags.SWP_NOACTIVATE + | SetWindowPosFlags.SWP_NOMOVE | SetWindowPosFlags.SWP_NOSIZE); } public void CanResize(bool value)