Detecting resize width vs height

Mugsy's RapSheet 156 Reputation points
2021-10-25T19:45:25.523+00:00

My program lets users resize the form. I maintain the form ratio this way:

Private Sub frmMain_Resize(sender As Object, e As EventArgs) Handles Me.Resize
    dblRatio = Screen.PrimaryScreen.Bounds.Height / Screen.PrimaryScreen.Bounds.Width
    Me.Height = Me.Width * dblRatio
    ' me.width = me.height * dblRatio
End Sub

This works just fine if the user grabs the form from the side or the corners, but I can't do the same if resized from the top or bottom (or vice versa if I comment/uncomment me.height/me.width.)

If I knew how to detect what's being dragged, I could precede each with an "If" so only one or the other is executed.

Ideas? TIA

Windows Forms
Windows Forms
A set of .NET Framework managed libraries for developing graphical user interfaces.
1,821 questions
0 comments No comments
{count} votes

1 answer

Sort by: Most helpful
  1. Castorix31 81,461 Reputation points
    2021-10-25T20:50:17.64+00:00

    A way is to handle WM_SIZING

    Something like this :

    143611-wm-sizing.gif

    Protected Overrides Sub WndProc(ByRef m As Message)  
        If m.Msg = WM_SIZING Then  
            Dim nAspectRatio As Double = Screen.PrimaryScreen.Bounds.Width / Screen.PrimaryScreen.Bounds.Height  
            Dim windowRect, clientRect As RECT  
            GetWindowRect(m.HWnd, windowRect)  
            GetClientRect(m.HWnd, clientRect)  
            Dim nAddX As Integer = (windowRect.right - windowRect.left) - clientRect.right  
            Dim nAddY As Integer = (windowRect.bottom - windowRect.top) - clientRect.bottom  
            Dim rc As RECT = CType(Marshal.PtrToStructure(m.LParam, GetType(RECT)), RECT)  
            If (rc.bottom - rc.top + nAddY <= 200) Then  
                rc.bottom = rc.top + 200 - nAddY - 2  
            End If  
            Select Case CInt(m.WParam)  
                Case WMSZ_LEFT, WMSZ_BOTTOMLEFT, WMSZ_BOTTOMRIGHT, WMSZ_RIGHT  
                    rc.bottom = CInt(rc.top + (CSng((rc.right - rc.left - nAddX)) / nAspectRatio) + nAddY)  
                Case WMSZ_TOPRIGHT, WMSZ_TOP, WMSZ_BOTTOM  
                    rc.right = CInt(rc.left + (CSng((rc.bottom - rc.top - nAddY)) * nAspectRatio) + nAddX)  
                Case WMSZ_TOPLEFT  
                    rc.left = CInt(rc.right - (CSng((rc.bottom - rc.top)) * nAspectRatio) + nAddX)  
            End Select  
            Marshal.StructureToPtr(rc, m.LParam, False)  
            m.Result = CType(1, IntPtr)  
            Return  
        End If  
        MyBase.WndProc(m)  
    End Sub  
    

    with declarations :

    <StructLayout(LayoutKind.Sequential)>  
    Public Structure RECT  
        Dim left As Integer  
        Dim top As Integer  
        Dim right As Integer  
        Dim bottom As Integer  
    End Structure  
      
    <DllImport("User32.dll", SetLastError:=True)>  
    Public Shared Function GetClientRect(hWnd As IntPtr, ByRef lpRect As RECT) As Boolean  
    End Function  
      
    <DllImport("User32.dll", SetLastError:=True)>  
    Public Shared Function GetWindowRect(hWnd As IntPtr, ByRef lpRect As RECT) As Boolean  
    End Function  
      
    Public Const WMSZ_LEFT = 1  
    Public Const WMSZ_RIGHT = 2  
    Public Const WMSZ_TOP = 3  
    Public Const WMSZ_TOPLEFT = 4  
    Public Const WMSZ_TOPRIGHT = 5  
    Public Const WMSZ_BOTTOM = 6  
    Public Const WMSZ_BOTTOMLEFT = 7  
    Public Const WMSZ_BOTTOMRIGHT = 8  
      
    Public Const WM_SIZING = &H214