Search code examples
vb.netformsresizesetbounds

Animating form resize in VB.NET


I have a form positioned slightly above the taskbar/system tray in the bottom right corner of my desktop window. It's sort of like a pop-up notification. The notification itself looks great, but there's a button on it which resizes the form up, animating the sizing in increments of 5px whilst keeping it's position relative to the bottom-right corner of the screen.

The problem with this is that it doesn't look very smooth. Adjusting Me.Width resizes from the left so you have to then move the form to the left with Me.Left to compensate. Me.SetBounds just seems to be a wrapper for setting those properties anyway.

Is there anything I can do to have the form smoothly (or at least appear to) resize outwards from the left of the form?


Solution

  • ETA: You can actually do this using SetBounds, as SetBounds will delegate to SetBoundsCore which, in turn will invoke SetWindowPos. So SetBounds will internally really set all bounds at once and the window manager will redraw the window only after all properties are set.


    Another option would be to import the MoveWindow function and use that instead. It produces a smooth animation here, as it can set size and position simultaneously before telling the window manager to redraw the window.

    My test code looked like this (converted from C# via IL to VB with help from Reflector):

    Private button1 As Button
    Private components As IContainer = Nothing
    Private tm As Timer = New Timer
    
    Private Sub Form1_Load(ByVal sender As Object, ByVal e As EventArgs)
        MyBase.Left = (Screen.PrimaryScreen.WorkingArea.Width - MyBase.Width)
        MyBase.Top = (Screen.PrimaryScreen.WorkingArea.Height - MyBase.Height)
        Me.tm.Enabled = False
        Me.tm.Interval = 20
        AddHandler Me.tm.Tick, Function 
            If (MyBase.Width < 500) Then
                Form1.MoveWindow(MyBase.Handle, (MyBase.Left - 5), (MyBase.Top - 5), (MyBase.Width + 5), (MyBase.Height + 5), True)
            Else
                Me.tm.Enabled = False
            End If
        End Function
    End Sub
    
    <DllImport("user32.dll", SetLastError:=True)> _
    Friend Shared Function MoveWindow(ByVal hWnd As IntPtr, ByVal X As Integer, ByVal Y As Integer, ByVal nWidth As Integer, ByVal nHeight As Integer, ByVal bRepaint As Boolean) As Boolean
    End Function