本文介绍了使用事件来更新后台工作人员与另一个类的UI的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

我正在尝试使用事件来更新来自其他类的后台工作者的文本框.

I’m trying to use events to update a textbox from a background worker from a different class.

此SO帖子,除了我使用的是VB.NET.我正在尝试通过@ sa_ddam213实施第二个建议的解决方案.

It is the same problem as mentioned in this SO post, except I'm using VB.NET. I'm trying to implement the 2nd suggested solution by @sa_ddam213.

我收到一个错误:跨线程操作无效:控制'txtResult'是从创建该线程的线程之外的其他线程访问的."

I’m getting an error: "Cross-thread operation not valid: Control 'txtResult' accessed from a thread other than the thread it was created on."

这是我的代码:

Public Class DataProcessor
    Public Delegate Sub ProgressUpdate(ByVal value As String)
    Public Event OnProgressUpdate As ProgressUpdate

    Private Sub PushStatusToUser(ByVal status As String)
        RaiseEvent OnProgressUpdate(status)
    End Sub

    Public Sub ProcessAllFiles(ByVal userData As UserData)
        'Do the work
    End Sub
End Class

Public Class MainForm
    Private bw As New BackgroundWorker
    Private dp As New DataProcessor

    Private Sub bw_DoWork(ByVal sender As Object, ByVal e As DoWorkEventArgs)
        Dim worker As BackgroundWorker = CType(sender, BackgroundWorker)

        If bw.CancellationPending = True Then
            e.Cancel = True
        Else
            dp.ProcessAllFiles(CType(e.Argument, UserData))
        End If
    End Sub

    Private Sub dp_OnProgressUpdate(ByVal status As String)
        txtResult.Text = status
    End Sub

    Private Sub MainForm_Load(sender As Object, e As EventArgs) Handles MyBase.Load
        bw.WorkerReportsProgress = True
        bw.WorkerSupportsCancellation = True
        AddHandler bw.DoWork, AddressOf bw_DoWork
        AddHandler bw.ProgressChanged, AddressOf bw_ProgressChanged
        AddHandler bw.RunWorkerCompleted, AddressOf bw_RunWorkerCompleted

        AddHandler dp.OnProgressUpdate, AddressOf dp_OnProgressUpdate
    End Sub
End Class

谢谢!

推荐答案

该事件仍然来自与UI不同的线程.您需要将唤醒任务委派回UI.我不检查InvokeRequired,因为我知道它来自工作线程.

The event still comes from a different thread than the UI. You need to delegate the woke back to the UI. I don't check InvokeRequired because I know it is from the worker thread.

Me是以下形式,调用要求将处理将数据带到UI线程的委托.在这里,我的Delegate Sub是lambda Sub,而不是使用常规的Sub例程-更简单的设计.

Me is the form, Invoke asks for the delegate that will handle the work of bring the data to the UI thread. Here my Delegate Sub is a lambda Sub instead of using a normal Sub routine - simpler design.

Private Sub dp_OnProgressUpdate(ByVal status As String)
   'invoke the UI thread to access the control
   'this is a lambda sub
   Me.Invoke(Sub
               'safe to access the form or controls in here
               txtResult.Text = status
             End Sub)
 End Sub

这篇关于使用事件来更新后台工作人员与另一个类的UI的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持!

10-29 04:44