Como declarar eventos personalizados para evitar bloqueio (Visual Basic)

Há várias circunstâncias em que é importante que um manipulador de eventos não bloqueie manipuladores de eventos subsequentes. Eventos personalizados permitem que o evento chame seus manipuladores de eventos de forma assíncrona.

Por padrão, o campo repositório de backup para uma declaração de evento é um delegado multicast que combina serialmente todos os manipuladores de eventos. Isso significa que, se um manipulador levar muito tempo para ser concluído, ele bloqueará os outros manipuladores até que ele seja concluído. (Manipuladores de eventos bem comportados nunca devem executar operações longas ou potencialmente bloqueadas.)

Em vez de usar a implementação padrão de eventos que o Visual Basic fornece, você pode usar um evento personalizado para executar os manipuladores de eventos de forma assíncrona.

Exemplo

Neste exemplo, o AddHandler acessador adiciona o delegado para cada manipulador do Click evento a um ArrayList armazenado no EventHandlerList campo.

Quando o código aciona o Click evento, o RaiseEvent acessador invoca todos os representantes do manipulador de eventos de forma assíncrona usando o BeginInvoke método. Esse método invoca cada manipulador em um thread de trabalho e retorna imediatamente, portanto, os manipuladores não podem bloquear uns aos outros.

Public NotInheritable Class ReliabilityOptimizedControl
    'Defines a list for storing the delegates
    Private EventHandlerList As New ArrayList

    'Defines the Click event using the custom event syntax.
    'The RaiseEvent always invokes the delegates asynchronously
    Public Custom Event Click As EventHandler
        AddHandler(ByVal value As EventHandler)
            EventHandlerList.Add(value)
        End AddHandler
        RemoveHandler(ByVal value As EventHandler)
            EventHandlerList.Remove(value)
        End RemoveHandler
        RaiseEvent(ByVal sender As Object, ByVal e As EventArgs)
            For Each handler As EventHandler In EventHandlerList
                If handler IsNot Nothing Then
                    handler.BeginInvoke(sender, e, Nothing, Nothing)
                End If
            Next
        End RaiseEvent
    End Event
End Class

Confira também