I have a Windows Form with 3 variables declared as my own User Controls, a BackGroundWorker, 1 panel and 3 buttons
Dim uc1 As DocumentTab
Dim uc2 As HomeScreen
Dim uc3 As StylePage
These User controls are initialized from the BackGroundWorker.DoWork().
New DocumentTabuc1 =
uc2 =
New HomeScreenuc3 =
New StylePageThe Click Events of the buttons calls this method to add the specified user control to the panel. Keep in mind that this method is always executed from the UI Thread.
Private Sub AddControlToTab(ByVal cCTL As Control, ByVal Panel As Control)
With cCTLPanel.SuspendLayout()
Panel.Controls.Clear()
New System.Drawing.Point(0, 0).BackColor = System.Drawing.Color.Transparent
.Dock = System.Windows.Forms.DockStyle.Fill
.Location =
.TabIndex = 0
End WithPanel.Controls.Add(cCTL)
Panel.ResumeLayout()
End SubCross-thread operation not valid: Control '' accessed from a thread other than the thread it was created on.
I only get the Cross-Thread error when adding uc1 which is of type DocumentTab.
Is it possible or even good practice to do what I'm doing (Initialize User Controls from a Thread other than the UI)
By the way this form is only a test since the real form will have 30+ UserControls and Initializing all of them could take a few seconds and thus my need to do it from a seperate thread to keep the UI responsive.

Cross-thread Exception with UserControl Initialized from BackGroundWorker
hanagomi
I've modified the AddControlToTab method to be thread safe. However the line in yellow always returns False although the control was initialized from the Worker thread while this method is always ran on the UI thread. Do I need to implement some Interface in my UserControl so that InvokeRequired returns the proper value
Private Sub AddControlToTab(ByVal cCTL As Control, ByVal Panel As Control) If cCTL.InvokeRequired Then Dim d As New AddControlCallback(AddressOf AddControlToTab) Me.Invoke(d, New Object() {cCTL, Panel}) Else With cCTL New System.Drawing.Point(0, 0).TabIndex = 0
End WithPanel.Controls.Add(cCTL)
Panel.ResumeLayout()
End If End SubAndyMcBal
It's because you created the controls in the DoWork event, which is on a different thread than the UI. Generally, you should create the controls in the initializer or form_load event, and do your data access in the DoWork event; binding the controls in the Completed event.
You don’t really need to worry about a large number of controls slowing your down your form. As an experiment, create an empty form and add a few thousand textboxes, then run it. You'll see the form gets created pretty quickly. Most forms delays are caused when one tries to retrieve data from the database on the same thread as the UI.
Matthijs Koopman
winprock
well not exactly. you cannot access a control from another thread which it did not create, it should go to the original thread that created that control.
To access it, you need to invoke it. Here is an example without using the background worker
http://forums.microsoft.com/MSDN/ShowPost.aspx PostID=689966&SiteID=1
backgroundworker example:
http://msdn2.microsoft.com/en-us/library/system.componentmodel.backgroundworker.aspx
HMote
I continue to get the Cross-Threaded exception.
Let me try to explain better since I think you may have gotten confused by last post...
The method AddControlToTab is ALWAYS executed on the UI Thread. Therefore the line
should ALAWAYS return TRUE because the User Control cCTL is ALWAYS initialized/created from the Worker thread.
Ravie14