vb.net - 进度条和代码位置的多线程(vb.net)?

标签 vb.net multithreading progress-bar backgroundworker invokerequired

我无法从另一个线程更新进度条。 我确实以最简单的方式让它运行了,但是清理代码让我卡住了。

我的测试代码看起来像网上所有与 backgroundworker 和 BeginInvoke 相关的示例。

FormP 是 Progressbar-Form。 这有效:

Public Class Form1
Private Delegate Sub delegate_ProgressUpdate(ByVal paramValue As Integer,
  ByVal paramMax As Integer)

Private Sub Button1_Click(sender As System.Object,
  e As System.EventArgs) Handles Button1.Click
    ' Test 01:
    ' Show Progressbar via BGW
    ' All functions are within Form1
    Dim bgw As New BackgroundWorker()
    AddHandler bgw.DoWork, AddressOf BGW_Sample01_DoWork

    FormP.Show(Me)
    bgw.RunWorkerAsync()
End Sub

Private Sub invokeMe_ProgressUpdate(ByVal paramValue As Integer, ByVal paramMax As Integer)
    FormP.ProgressBar1.Maximum = paramMax
    FormP.ProgressBar1.Value = paramValue
    FormP.ProgressBar1.Update()
End Sub

Private Sub BGW_Sample01_DoWork(sender As Object, e As System.ComponentModel.DoWorkEventArgs)
    For i As Integer = 1 To 10
        Threading.Thread.Sleep(500) ' Test delay
        Me.BeginInvoke(New delegate_ProgressUpdate(AddressOf invokeMe_ProgressUpdate),
                       i, 10)
    Next
    MessageBox.Show("Fertig")
End Sub

如果我试图让封装在 FormP 中的东西更有序地工作,那是行不通的。

Private Sub Button2_Click(sender As System.Object, e As System.EventArgs) Handles Button2.Click
    Dim bgw As New BackgroundWorker
    AddHandler bgw.DoWork, AddressOf BGW_Sample02_DoWork
    FormP.Show(Me)
    bgw.RunWorkerAsync()
End Sub

Private Sub BGW_Sample02_DoWork(sender As Object, e As System.ComponentModel.DoWorkEventArgs)
    For i As Integer = 1 To 10
        Threading.Thread.Sleep(500)
        FormP.SetProgress(i, 10)
    Next
    MessageBox.Show("Fertig")
End Sub


' ########## FormP #################

Public Class FormP

Private Delegate Sub delegate_ProgressUpdate(ByVal value As Integer, ByVal maximum As Integer)

Public Sub SetProgress(ByVal paramValue As Integer, ByVal paramMaximum As Integer)
    If Me.InvokeRequired Then
        Me.Invoke(New delegate_ProgressUpdate(AddressOf Me.SetProgress), paramValue, paramMaximum)
    Else
        Me.ProgressBar1.Maximum = paramMaximum
        Me.ProgressBar1.Value = paramValue
        Me.ProgressBar1.Update()
    End If
End Sub

End Class

FormP 不会卡住,但 UI 不会更新。 实际上 Me.InvokeRequired 是错误的,我认为这是我开始错过一些重要部分的地方。 我在这里尝试了 Form1.InvokeRequired,但它也是错误的。 我的理解是:这里的调用线程是bgw线程,不管这个线程调用的代码是在哪个类中... 好像不是吧?

感谢您的任何想法。

最佳答案

最终起作用的是:

Private frmP As FormP

Private Sub Button2_Click(sender As System.Object, e As System.EventArgs) Handles Button2.Click
    Dim bgw As New BackgroundWorker
    If Me.frmP IsNot Nothing AndAlso Me.frmP.Visible Then Return
    Me.frmP = New FormP
    Me.frmP.Show(Me)
    AddHandler bgw.DoWork, AddressOf BGW_Sample02_DoWork
    bgw.RunWorkerAsync(New Object() {Me.frmP})
End Sub

Private Sub BGW_Sample02_DoWork(sender As Object, e As System.ComponentModel.DoWorkEventArgs)
    Dim objFrmP As FormP = DirectCast(e.Argument(0), FormP)
    For i As Integer = 1 To 10
        objFrmP.setProgress(i, 10)
        Threading.Thread.Sleep(500)
    Next
    MessageBox.Show("Finished")
End Sub

FormP 中的 Progress-Dialog-Code:

Public Sub setProgress(paramValue As Integer, paramMaximum As Integer)
    If Me.InvokeRequired Then
        ' defining a delegate type is not really necessary
        Me.Invoke(Sub() Me.setProgress(paramValue, paramMaximum))
    Else
        Me.ProgressBar1.Maximum = paramMaximum
        Me.ProgressBar1.Value = paramValue
        Me.ProgressBar1.Update()
    End If
End Sub

关于vb.net - 进度条和代码位置的多线程(vb.net)?,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/12533412/

相关文章:

delphi - 在 Vista Aero 上禁用进度条动画

vb.net - 调用 InvokeRequired 和 Invoke 的简洁方法

vb.net - 尝试读取或写入 protected 内存。这通常表明其他内存已损坏

c# - wpf中的多列自动搜索用户控件

java - 在 Java 中的多线程进程中更新 boolean 值

python - 在 Python 中,以 currentThread() 为键的字典会导致内存泄漏吗?

.net - 如何通过反射检索字符串并将其升序连接

java - 动态加载 GridPane 时显示 ProgressBar

python - 从另一个运行 FTP 下载的线程更新 PyQt 进度

delphi - 不兼容的类型:“TDownloadProgressEvent”和“过程”