How to use single and multicast delegates in Visual Basic .NET or in Visual Basic 2005 (322188)



The information in this article applies to:

  • Microsoft Visual Basic 2005
  • Microsoft Visual Basic .NET (2003)
  • Microsoft Visual Basic .NET (2002)

This article was previously published under Q322188

SUMMARY

This step-by-step article demonstrates how to use single and multicast delegates.

This article includes three delegate examples:
  • One single delegate example includes a delegate in an object that is called from a Windows Form.
  • The other single delegate example includes a delegate on a form that can be invoked from a class.
  • The multicast delegate example builds an additional instance of the form delegate and demonstrates how to create a multicast delegate that includes both of the form callbacks.
If you are new to delegates, the examples in this article are what were previously known as "callbacks." Delegates are type safe function pointers that integrate the ability to call multiple methods serially and support the calling of static methods and instance methods (native function pointers can only target static methods). The delegate functions in this example are very basic. Their function is to change the background color of a picture box.

The Visual Basic .NET or Visual Basic 2005 sample in this article includes a form with two text boxes and three command buttons. Button1 demonstrates a class delegate that can be called from the form. Button2 demonstrates the opposite scenario; the delegate resides on the form and is called from the class. Button2 also demonstrates that a delegate can be passed to another entity. Button3 creates a multicast delegate that includes two form methods. When the delegate is executed, the delegate calls both of the form methods.

back to the top

Build a Delegate from a Class

This example builds a delegate in a class. An instance of the delegate is created on the form so that the class method that is specified in the delegate can be called from the form.

This example is not particularly practical because you can use a standard class method to get the same functionality. This example is offered here as a demonstration of how to establish this type of delegate.
'Define the delegate in the class.
Delegate Function ClassCallback() As Color

'Create an instance of the delegate on the form,
'and specify the use of the changeColor method.
Dim c As New ClassCallback(AddressOf cbox.changeColor)

'Call the delegate function (changeColor).
Me.TextBox1.BackColor = c.Invoke
				
back to the top

Build a Delegate from a Form

This example creates a delegate on a form that can be passed to the class (as opposed to the first example in which the delegate is not passed). The class can then call the specified method through the delegate.
'Declare the delegate.
Public Delegate Sub FormCallBack()

'Create an instance of the delegate.
Dim fc As New FormCallBack(AddressOf toggleColor)

'Pass the delegate to the class.
cbox.setCallback(fc)

'Accept the delegate in the class, and invoke the method.
Public Sub setCallback(ByVal fc As FormCallBack)
   fc()
End Sub
				
back to the top

Build a Multicast Delegate from a Form

This example creates an additional instance of the delegate on the form to demonstrate how to build a multicast delegate. A multicast delegate can call more than one method. In this case, the delegate includes two methods.
'Create an instance of the delegate.
Dim fc1 As New FormCallBack(AddressOf toggleColor)

'Create a second instance of the delegate.
Dim fc2 As New FormCallBack(AddressOf toggleOtherColor)

'Create a multicast delegate.
Dim fc As FormCallBack = _
             CType(System.Delegate.Combine(fc1, fc2), FormCallBack)

'Pass the delegate to the class.
'Note that this does not require any changes to the class method.
cbox.setCallback(fc)
				
back to the top

Build the Visual Basic .NET or Visual Basic 2005 Sample

  1. Follow these steps to create a new Windows Application project in Visual Basic .NET or in Visual Basic 2005:
    1. Start Microsoft Visual Studio .NET or Microsoft Visual Studio 2005.
    2. On the File menu, point to New, and then click Open.
    3. Click Visual Basic Projects under Project Types, and then click Windows Application under Templates. By default, Form1 is created.

      Note In Visual Studio 2005, click Visual Basic under Project Types.
  2. In Solution Explorer, right-click Form1.vb, and then click View Code. Replace the code in the form with the following code:
    Namespace delegateExample
      Public Delegate Sub FormCallBack()
    
      Public Class Form1
        Inherits System.Windows.Forms.Form
    
    #Region " Windows Form Designer generated code "
    
        Public Sub New()
          MyBase.New()
    
          'This call is required by the Windows Form Designer.
          InitializeComponent()
    
          'Add any initialization after the InitializeComponent() call
    
        End Sub
    
        'Form overrides dispose to clean up the component list.
        Protected Overloads Overrides Sub Dispose(ByVal disposing As Boolean)
          If disposing Then
            If Not (components Is Nothing) Then
              components.Dispose()
            End If
          End If
          MyBase.Dispose(disposing)
        End Sub
    
        'Required by the Windows Form Designer
        Private components As System.ComponentModel.IContainer
    
        'NOTE: The following procedure is required by the Windows Form Designer
        'It can be modified using the Windows Form Designer.  
        'Do not modify it using the code editor.
        Friend WithEvents TextBox1 As System.Windows.Forms.TextBox
        Friend WithEvents TextBox2 As System.Windows.Forms.TextBox
        Friend WithEvents Button1 As System.Windows.Forms.Button
        Friend WithEvents Button2 As System.Windows.Forms.Button
        Friend WithEvents Button3 As System.Windows.Forms.Button
        <System.Diagnostics.DebuggerStepThrough()> Private Sub InitializeComponent()
          Me.TextBox1 = New System.Windows.Forms.TextBox()
          Me.TextBox2 = New System.Windows.Forms.TextBox()
          Me.Button1 = New System.Windows.Forms.Button()
          Me.Button2 = New System.Windows.Forms.Button()
          Me.Button3 = New System.Windows.Forms.Button()
          Me.SuspendLayout()
          '
          'TextBox1
          '
          Me.TextBox1.Location = New System.Drawing.Point(16, 16)
          Me.TextBox1.Multiline = True
          Me.TextBox1.Name = "TextBox1"
          Me.TextBox1.Size = New System.Drawing.Size(64, 96)
          Me.TextBox1.TabIndex = 0
          Me.TextBox1.Text = ""
          Me.TextBox1.TextAlign = System.Windows.Forms.HorizontalAlignment.Center
          '
          'TextBox2
          '
          Me.TextBox2.Location = New System.Drawing.Point(104, 16)
          Me.TextBox2.Multiline = True
          Me.TextBox2.Name = "TextBox2"
          Me.TextBox2.Size = New System.Drawing.Size(64, 96)
          Me.TextBox2.TabIndex = 3
          Me.TextBox2.Text = ""
          '
          'Button1
          '
          Me.Button1.Location = New System.Drawing.Point(16, 136)
          Me.Button1.Name = "Button1"
          Me.Button1.Size = New System.Drawing.Size(64, 56)
          Me.Button1.TabIndex = 1
          Me.Button1.Text = "Delegate in Object"
          '
          'Button2
          '
          Me.Button2.Location = New System.Drawing.Point(104, 136)
          Me.Button2.Name = "Button2"
          Me.Button2.Size = New System.Drawing.Size(64, 56)
          Me.Button2.TabIndex = 4
          Me.Button2.Text = "Delegate in Form"
          '
          'Button3
          '
          Me.Button3.Location = New System.Drawing.Point(192, 64)
          Me.Button3.Name = "Button3"
          Me.Button3.Size = New System.Drawing.Size(75, 128)
          Me.Button3.TabIndex = 5
          Me.Button3.Text = "Multicast Delegate"
          '
          'Form1
          '
          Me.AutoScaleBaseSize = New System.Drawing.Size(5, 13)
          Me.ClientSize = New System.Drawing.Size(292, 266)
          Me.Controls.AddRange(New System.Windows.Forms.Control() {Me.Button3, Me.Button2, Me.Button1, Me.TextBox2, Me.TextBox1})
          Me.Name = "Form1"
          Me.Text = "Form1"
          Me.ResumeLayout(False)
    
        End Sub
    
    #End Region
    
        Private toggle As Boolean = False
        Private othertoggle As Boolean = False
        Private cbox As ColorBox
    
        Private Sub Form1_Load(ByVal sender As System.Object, ByVal e As System.EventArgs) Handles MyBase.Load
          cbox = New ColorBox()
        End Sub
    
        Private Sub Button1_Click(ByVal sender As System.Object, ByVal e As System.EventArgs) Handles Button1.Click
          Dim c As New ClassCallback(AddressOf cbox.changeColor)
          Me.TextBox1.BackColor = c.Invoke
        End Sub
    
        Public Sub toggleColor()
          toggle = Not toggle
          If toggle = True Then
            Me.TextBox2.BackColor = Color.Red
          Else
            Me.TextBox2.BackColor = Color.Goldenrod
          End If
        End Sub
    
        Public Sub toggleOtherColor()
          othertoggle = Not othertoggle
          If othertoggle = True Then
            Me.TextBox1.BackColor = Color.Red
          Else
            Me.TextBox1.BackColor = Color.Goldenrod
          End If
        End Sub
    
        Private Sub Button2_Click(ByVal sender As System.Object, ByVal e As System.EventArgs) Handles Button2.Click
          Dim fc As New FormCallBack(AddressOf toggleColor)
          cbox.setCallback(fc)
        End Sub
    
        Private Sub Button3_Click(ByVal sender As System.Object, ByVal e As System.EventArgs) Handles Button3.Click
          'Create an instance of the delegate.
          Dim fc1 As New FormCallBack(AddressOf toggleColor)
          'Create a second instance of the delegate.
          Dim fc2 As New FormCallBack(AddressOf toggleOtherColor)
          'Create a multicast delegate.
          Dim fc As FormCallBack = _
              CType(System.Delegate.Combine(fc1, fc2), FormCallBack)
          'Pass the delegate to the class.
          'Note that this does not require any changes to the class method.
          cbox.setCallback(fc)
        End Sub
      End Class
    End Namespace
    					
    Note The code should be changed in Visual Basic 2005. If you create a new form that is named Form1 in Visual Basic 2005, you will have a Form1.vb file for your code and a Form1.Designer.vb file that contains the automatically generated part. The Windows Forms Designer uses the partial keyword to divide the implementation of Form1 into two separate files. This prevents the designer-emitted code from being interspersed with your code. For more information about the Visual Basic 2005 language enhancements, visit the following Microsoft Web site:For more information about partial classes and the Windows Forms Designer, visit the following Microsoft Web site:
  3. In Solution Explorer, right-click the project name, and then click Properties.
  4. In the Startup Object list, click delegateExample.Form1, and then click OK.
  5. On the Project menu, click Add Class to add a class to the project.
  6. Replace the code in the class with the following code:
    Namespace delegateExample
      Delegate Function ClassCallback() As Color
    
      Public Class ColorBox
    
        ' Boolean flag is used to toggle colors.
        Private toggle As Boolean = True
    
        ' Method that is provided to the form for use in the callback.
        Public Function changeColor() As Color
          toggle = Not toggle
          If toggle = True Then
            Return Color.Red
          Else
            Return Color.Goldenrod
          End If
        End Function
    
        'Accept the delegate in the class, and invoke the method.
        Public Sub setCallback(ByVal fc As FormCallBack)
          fc()
        End Sub
    
      End Class
    End Namespace
    					
  7. Run the project. Click the buttons. Notice that the delegate methods are called to toggle the colors of the text boxes.
back to the top

Modification Type:MinorLast Reviewed:10/3/2006
Keywords:kbvs2005swept kbvs2005applies kbHOWTOmaster KB322188 kbAudDeveloper