簡體   English   中英

.NET 在 UI 線程上引發事件

[英].NET raise event on UI thread

我正在使用SQLDependency類來偵聽 SQL 通知,並且SQLDependency.OnChange事件在與 UI 線程不同的線程上執行。 我的目的是在觸發此事件時更新網格視圖中的數據,以便 SQL 服務器數據庫更改可以立即反映在網格中。

如果我運行LoadData方法將數據重新加載到網格中,則會出現跨線程錯誤:

在此處輸入圖片說明

我創建了一個自定義類來保存所有與 SQLDependency 相關的代碼,並且在我的應用程序中全局聲明了這個類的一個實例。 我在SQLDependency.OnChanged事件中引發的類上有一個事件。 然后在各種不同的表單上處理此事件,以便可以重新加載它們的數據。 但是,因為OnChange事件是在不同的線程上引發的,所以我需要添加邏輯來首先運行:

Delegate Sub ReloadCallback()
Private Sub LoadOnUI()
    If Me.InvokeRequired Then
        Dim d As ReloadCallback = New ReloadCallback(AddressOf LoadOnUI)
        Me.Invoke(d)
    Else
        Invoke(New MethodInvoker(Sub() RefreshData()))
    End If
End Sub

我寧願避免復制此代碼並將其復制到每個處理我的自定義事件的地方。 這個答案幾乎正是我正在尋找的,但我無法弄清楚如何實現所提供的代碼。

邏輯向下,獲取事件的調用列表並獲取其中一個處理程序的線程,然后在該線程上引發事件。 由於我的經驗有限,我無法自己編寫代碼來執行此操作。 任何援助將不勝感激。

目標:在 UI 線程上引發事件,在事件處理程序中沒有重復的額外代碼。

這是一個使用SynchronizationContext的快速示例。

請注意,它假定您是從主 UI 線程創建類,並從構造函數存儲當前上下文:

Public Class Form1

    Private Sub Button1_Click(sender As Object, e As EventArgs) Handles Button1.Click
        Dim d As New Duck("Bob")
        AddHandler d.Quack, AddressOf duck_Quack
        Label1.Text = "Waiting for Quack..."
        d.RaiseThreadedQuack(3)
    End Sub

    Private Sub duck_Quack(source As Duck)
        Label1.Text = "Quack received from: " & source.Name
    End Sub

End Class

Public Class Duck

    Public ReadOnly Property Name() As String
    Private sc As WindowsFormsSynchronizationContext

    Public Sub New(ByVal name As String)
        Me.Name = name
        sc = WindowsFormsSynchronizationContext.Current
    End Sub

    Public Event Quack(ByVal source As Duck)

    Public Sub RaiseThreadedQuack(ByVal delayInSeconds As Integer)
        Dim T As New Threading.Thread(AddressOf ThreadedQuack)
        T.Start(delayInSeconds)
    End Sub

    Private Sub ThreadedQuack(ByVal O As Object)
        System.Threading.Thread.Sleep(TimeSpan.FromSeconds(O).TotalMilliseconds)

        sc.Post(AddressOf RaiseUIQuack, Me)
    End Sub

    Private Sub RaiseUIQuack(ByVal O As Object)
        RaiseEvent Quack(O)
    End Sub

End Class

暫無
暫無

聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.

 
粵ICP備18138465號  © 2020-2024 STACKOOM.COM