从BackgroundWorker中的异步操作进行线程安全调用

时间:2016-02-25 22:30:00

标签: vb.net multithreading interface freeze bass.dll

我在BackgroundWorker中有一些代码可以帮助我防止在Bass连接到audiostream时冻结界面:

Private Sub WorkerConnectToStream_DoWork(sender As Object, e As System.ComponentModel.DoWorkEventArgs) Handles WorkerConnectToStream.DoWork
    Bass.BASS_StreamFree(StreamNumber)
    StreamNumber = Bass.BASS_StreamCreateURL(StreamAddr, 0, BASSFlag.BASS_STREAM_STATUS, _downloadProc_, Me.Handle)
    If StreamNumber <> 0 Then
        Bass.BASS_ChannelPlay(StreamNumber, True)
    End If
End Sub

但是我得到:InvalidOperationException,消息“控制控件名称是从创建它的线程以外的线程访问的”。如果我将CheckForIllegalCrossThreadCalls属性设置为false或我从Debug文件夹启动我的程序,那么一切正常,但这不是最好的解决方案。

如果我使用:

invoke(sub()
    StreamNumber = Bass.BASS_StreamCreateURL(StreamAddr, 0, BASSFlag.BASS_STREAM_STATUS, _downloadProc_, Me.Handle)
end sub)

然后此消息消失,但我的表单界面冻结。 我怎么解决这个问题? 非常感谢! 我很抱歉我的英语不好。

1 个答案:

答案 0 :(得分:0)

问题是你的DoWork在后​​台线程上运行但是在主线程上调用了一个控件。控件无法做到这一点。您需要在ReportProgress内引发Dowork等事件,传递数据并在那里更新您的控件。这就是BGW的意义所在。它允许您与控件交互,而无需编写大量代码来管理线程。

如果您对某些内容使用某些控件并且此控件位于窗体上,请尝试在BG线程上实例化它并仅在内存中使用它。我记得,我做过类似的事情并且有效。