Advanced Techniques


Data Binding


BindingList is a generic implementation if IBindingList and is very useful for data binding


You can implement sorting on a BindingList by overriding the SupportSortingCore and ISortedCore properties and the ApplySortCore and RemoveSortCode methods.


ApplySortCore method is where you need to provide the actual sorting details
This method takes a PropertyDescriptor object that identifies the list item property to sort by and a ListSortDescription enumeration that indicates whether the list should be sorted in ascending or descending order


Resizing

There are 3 form events related to resizing


Resize - fires when the form is being resized.
ResizeBegin - fires when the mouse is pressed and the resizing is initialized
ResizeEnd - fires when the mouse is released and the resizing has completed.


Me.Size = New System.Drawing.Size(100,100) 


To remove the Resizing handle in the bottom left corner change the SizeGripStyle to Hide


You specify the size and position of both forms and controls by using objects such as Size and Point instead of the scalar properties such as Left, Top , Width and Height.
By default Size and Point are measured in pixels (not twips).


You cannot change the Width and Height of the size object because they are read only. The only way to change it is to assign a new Size object.


FormBorderStyle = SizeableToolWindow

Allowing resizing from all sides
Maximise Box = True - not displayed but allows the user to double click to maximise
Minimise Box = True - not displayed but allows the user to double click to minimise




FormBorderStyle = Sizeable

Allowing resizing only using the grip handle
Maximise Box = True - displayed on windows form
Minimise Box = True - displayed on windows form




This defines the position of the form

Me.Location = New System.Drawing.Point(20, 20) 

This defines the size of the form

Me.Size = New System.Drawing.Size(300,300) 

Move the screen to the upper left corner of the screens working area

Me.DesktopLocation = New Point(0, 0) 

Windows Forms expose a SetBounds method which lets you set both the size and position in one operation

Me.SetBounds(20, 20, 300,300) 

Me.SetDesktopBounds = New Rectangle(10, 10, 10, 10) 

Bounds is a System.Drawing.Rectangle object that represents the external border of the control.
ClientRectangle is the Rectangle object that represents the internal area.
ClientSize is the Size object that represents the dimension of the internal area. This is read-only, although you can obtain the same result by using the SetClientSizeCore method.



Expands the picture box to cover the whole form's client area

PictureBox1.Bounds = Me.ClientRectangle 

This is exactly the same although it will leave a 10 pixel margin near the left and right edges of the picture box and an 8 pixel margin near the top and bottom.

Dim objRectandle As Rectangle = Me.ClientRectangle 
   objRectangle.Inflate(-10. -8)
   PictureBox1.Bounds = objRectangle


Error Handling

Private mobjCOMException As System.Runtime.InteropServices.COMException 
Private mobjException As Exception

Form Load

Private Sub frmMain_Load(ByVal sender As System.Object, _ 
                         ByVal e As System.EventArgs) _
                         Handles MyBase.Load
   Try
      If clsError.ErrorFlag() = True Then Exit Sub



   Catch objCOMException As System.Runtime.InteropServices.COMException
      mobjCOMException = objCOMException
   Catch objException As Exception
      mobjException = objException

   Finally
      If gbDEBUG = True Or _
         ((Not mobjCOMException Is Nothing) Or (Not mobjException Is Nothing)) Then

         Call clsError.Handle("frmMain_Load", msCLASSNAME, _
              "load the form successfully.", _
              mobjCOMException, mobjException)
      End If
   End Try
End Sub

Controls

Private Sub Control_Click(ByVal sender As System.Object, _ 
                          ByVal e As System.EventArgs) _
                          Handles btnOK.Click
   Try
      If gbfrmMainForm_FireEvents = False Then Exit Sub
      If clsError.ErrorFlag() = True Then Exit Sub


   Catch objCOMException As System.Runtime.InteropServices.COMException
      mobjCOMException = objCOMException
   Catch objException As Exception
      mobjException = objException

   Finally
      If gbDEBUG = True Or _
         ((Not mobjCOMException Is Nothing) Or (Not mobjException Is Nothing)) Then

         Call clsError.Handle("Control_Click", msCLASSNAME, _
              "respond to the control successfully.", _
              mobjCOMException, mobjException)
      End If
   End Try
End Sub

OK Button

Private Sub btnOK_Click(ByVal sender As System.Object, _ 
                        ByVal e As System.EventArgs) _
                        Handles btnOK.Click
   Try
      If clsError.ErrorFlag() = True Then Exit Sub



   Catch objCOMException As System.Runtime.InteropServices.COMException
      mobjCOMException = objCOMException
   Catch objException As Exception
      mobjException = objException

   Finally
      If gbDEBUG = True Or _
         ((Not mobjCOMException Is Nothing) Or (Not mobjException Is Nothing)) Then

         Call clsError.Handle("btnOK_Click", msCLASSNAME, _
              "respond to the control successfully.", _
              mobjCOMException, mobjException)
      End If
   End Try
End Sub

Cancel Button

You must always be able to close the form regardless of whether an error has occurred.

Private Sub btnCancel_Click(ByVal sender As System.Object, _ 
                            ByVal e As System.EventArgs) _
                            Handles btnCancel.Click
   Try
'this is the correct method form forms that have been displayed using Frm.ShowDialog (i.e. modal)
'this implicitly calls the Me.Close method so you do not need both
      Me.DialogResult = Windows.Forms.DialogResult.Cancel

'this is the correct method form forms that have been displayed using Frm.Show (i.e. modeless)
      Me.Close

   Catch objCOMException As System.Runtime.InteropServices.COMException
      mobjCOMException = objCOMException
   Catch objException As System.Exception
      mobjException = objException

   Finally
      If gbDEBUG = True Or _
         ((Not mobjCOMException Is Nothing) Or (Not mobjException Is Nothing)) Then

         Call clsError.Handle("btnCancel_Click", msCLASSNAME, _
              "respond to the control successfully.", _
              mobjCOMException, mobjException)
      End If
   End Try
End Sub

Form Close

This is only needed if you are saving any settings even when the dialog box is closed using the X in the corner, such as saving the position of the form.

Private Sub frmMain_Close() 

   Try


   Catch objCOMException As System.Runtime.InteropServices.COMException
      mobjCOMException = objCOMException
   Catch objException As System.Exception
      mobjException = objException

   Finally
      If gbDEBUG = True Or _
         ((Not mobjCOMException Is Nothing) Or (Not mobjException Is Nothing)) Then

      Call clsError.Handle("frmName_Main", msCLASSNAME, _
           "unload the form successfully.", _
           mobjCOMException, mobjException)
      End If
   End Try
End Sub

Detect Keystrokes

It is possible to catch any keystrokes that are made while a Form is displayed by implementing the IMessageFilter interface.
The following code will catch the Excape key on a key down.


Public Class frmMain 
   Inherits System.Windows.Forms.Form

   Implements IMessageFilter

   Private Function PreFilterMessage(ByRef m As Message) As Boolean Implements IMessageFilter.PreFilterMessage
      
   End Function

   Private Sub frmMain_Load(ByVal sender As System.Object, _
                            ByVal e As System.EventArgs) _
                            Handles MyBase.Load

      Application.AddMessageFilter(Me)
   End Sub

End Class

System.Windows.Forms.Keys

System.Windows.Forms.Keys.ShiftKey 
System.Windows.Forms.Keys.ControlKey

Drag and Drop


System.Windows.Forms.DataObject



The Source control is where you are copying/moving from and the Target is where you are moving to.


DoDragDrop Method

Dragging is initiated by calling the DoDragDrop method for the Source control
This takes two parameters
data - specifying the data to pass
aalowdEffects - specifying which operations (copying and/or moving) are allowed
A new DataObject is automatically created


GiveFeedback Event

This in turn raises the GiveFeedback event.
This allows you to display a custom mouse pointer.


AllowDrop Property

Any control which has its AllowDrop property set to True is a potential drop target.


DragEnter Event

As the mouse passes over a control the DragEnter event is raised
The GetDataPresent method is used to make sure that the format of the data is appropriate to the target control and the Effect property is used to display the appropriate mouse pointer.


DragDrop Event

If the user releases the mouse button over the target the DragDrop event is raised
Code in the DragDrop event handler extracts the data from the DataObject and displays it in the target control.



Dragging Files

In this example drag and drop is used to populate a ListBox control with a list of files dragged from Windows Explorer.


To enable drag and drop for a file


Add a ListBox control to a form and set its AllowDrop property to True.

Private Sub ListBox1_DragEnter(ByVal sender As Object, _ 
                               ByVal e As System.Windows.Forms.DragEventArgs) _
                               Handles ListBox1.DragEnter

    If e.Data.GetDataPresent(DataFormats.FileDrop) Then
        e.Effect = DragDropEffects.All
    End If
End Sub

You may notice that the Effect is set to DragDropEffects.All. Because the files themselves are not actually being moved or copied, it does not really matter which AllowedEffects were set by the source, so specifying All means that dropping is enabled for


Private Sub ListBox1_DragDrop(ByVal sender As Object, _ 
                              ByVal e As System.Windows.Forms.DragEventArgs) _
                              Handles ListBox1.DragDrop

    If e.Data.GetDataPresent(DataFormats.FileDrop) Then
        Dim MyFiles() As String
        Dim i As Integer

' Assign the files to an array.
        MyFiles = e.Data.GetData(DataFormats.FileDrop)
' Loop through the array and add the files to the list.
        For i = 0 To MyFiles.Length - 1
            ListBox1.Items.Add(MyFiles(i))
        Next
    End If
End Sub

The FileDrop format contains the full path for each file being dropped. Rather than populating a list, you could just as easily perform other operations on the files — for example, opening them in MDI (multiple-document interface) document windows.


The next example demonstrates a special case for drag and drop: dragging items back and forth between two lists.



Threading


BeginInvoke


EndInvoke




© 2026 Better Solutions Limited. All Rights Reserved. © 2026 Better Solutions Limited TopPrev