1

OK..ここに問題があります

いくつかのボタンアイテムを追加できるコントロールコンテナを含むメインUIフォームがあります。また、listnerを起動するbackgroundworkerオブジェクトもあります。リスターイベントが発生したら、メインUIフォームのそのコントロールコンテナーにボタンを作成したいと思います。そのコンテナに新しいコントロールアイテムを追加しようとするまで、すべてが正常に機能しているようです。次の例外が発生します

「クロススレッド操作が無効です:コントロール'RadMagnifier_AcceptReject'は、作成されたスレッド以外のスレッドからアクセスされました。」

コードは次のように流れます

Private Sub Mainform_Load(ByVal sender As System.Object, ByVal e As System.EventArgs) Handles MyBase.Load
    Me.SessionTableAdapter.Fill(Me.BCSSDataSet1.Session)
    FormatColumns()
    Me.BackgroundWorker2.RunWorkerAsync()
End Sub

Private Sub BackgroundWorker2_DoWork(ByVal sender As Object, ByVal e As System.ComponentModel.DoWorkEventArgs) Handles BackgroundWorker2.DoWork
    Notifications()
End Sub


Private Sub Notifications()
    'Start listing for events when event is fired try to add a button to a controls container on the UI thread, and that when i get the problem
End Sub
4

5 に答える 5

2

すべての UI 操作を RunWorkerCompleted メソッドに移動したと仮定すると、バグのように見えます。

http://connect.microsoft.com/VisualStudio/feedback/ViewFeedback.aspx?FeedbackID=116930 http://thedatafarm.com/devlifeblog/archive/2005/12/21/39532.aspx

防弾(疑似コード)を使用することをお勧めします:

if(control.InvokeRequired)
  control.Invoke(Action);
else
  Action()
于 2009-05-22T13:24:48.430 に答える
1

UI スレッド以外のスレッドから UI 要素を更新することはできません。

ボタン追加コードを RunWorkerCompleted イベントに追加します。これは UI スレッドで発生するためです。DoWork イベントは、UI スレッドではなくスレッド プール スレッドで実行されます。

于 2013-02-09T13:52:01.617 に答える
0

Control.BeginInvokeを使用して、フォーム上でバックグラウンドスレッドから呼び出し、デリゲートを渡して新しいボタンを追加できます。

于 2009-02-14T21:24:42.463 に答える
0

UI スレッドで実行されるため、 RunWorkerCompletedイベントを使用する必要があります。DoWork イベントからフォームにコントロールを追加することは、この関数がメイン フォームを作成したスレッドとは異なるスレッドで実行されるため、正しくありません。

Private Sub Form1_Load(ByVal sender As System.Object, ByVal e As System.EventArgs) Handles MyBase.Load
    Me.BackgroundWorker1.RunWorkerAsync()
End Sub

Private Sub BackgroundWorker1_DoWork(ByVal sender As System.Object, ByVal e As System.ComponentModel.DoWorkEventArgs) Handles BackgroundWorker1.DoWork
    Thread.Sleep(1000)
    'Do not modify the UI here!!!
End Sub

Private Sub BackgroundWorker1_RunWorkerCompleted(ByVal sender As System.Object, ByVal e As System.ComponentModel.RunWorkerCompletedEventArgs) Handles BackgroundWorker1.RunWorkerCompleted
    Me.Controls.Add(New Button())
End Sub
于 2009-01-22T19:40:45.100 に答える
0

うーん..通知プロシージャを RunworkerCompleted イベントに移動すると、同じエラーが発生します。通知手順は新しいボタンを作成する前にイベントが発生するのを待つため、ボタンを RunworkerCompleted イベントに直接追加することはできません。

これはより明確な例です

Private Sub Notifications() 新しい NotificationEngine() として NotificationObj を暗くする

    ' register a handler to listen for receive events
    AddHandler Noification.ReceiveCompleted, AddressOf NotificationReceive

    ' start the notification processor
    NotificationObj.Start()

End Sub

そして、新しいボタンを作成してメイン フォームのコントロール コンテナに追加すると、NotificationReceive イベントが発生します。

于 2009-01-22T20:32:59.893 に答える