Pretty simple, I need to resize a few hundred pictureboxes inside a FlowLayoutPanel. In an effort to speed it up, I'm experimenting with Parallel.ForEach
I'm trying to turn this for each loop
For Each p As Control In Me.PanelMain.Controls
p.Size = New Size(GWidth, GHeight)
Next
Into a Parallel.ForEach loop. I'm struggling with the syntax, and online documentation is particularly cryptic this time around. I've gotten this far:
Parallel.ForEach(Of Control)(Me.PanelMain.Controls, Sub(resize)
resize.Size = New Size(GWidth, GHeight)
End Sub
)
This gives an error on compile "System.InvalidCastException: 'Unable to cast object of type 'ControlCollection' to type 'System.Collections.Generic.IEnumerable`1[System.Windows.Forms.Control]'.'" And I really just don't know where to go from here.
ControlCollection
implements IEnumerable
, but not IEnumerable<T>
. IEnumerable<T>
is a type which Parallel.ForEach
expecting.
To cast controls collection to IEnumerable(Of Control) you can use
Dim controls = Me.PanelMain.Controls.Cast(Of Control)()
Parallel.ForEach(controls, Sub(control) control.Size = New Size(GWidth, GHeight))
Note that UI controls can be updated only on the thread they has been created on. So splitting resizing between multiple threads will not work as you expect.
I would reconsider having hundreds of pictureboxes on the form, can user see all pictureboxes at once?
That said, you can try to speed up updating controls by suspending form redrawing after every control resize.
Me.PanelMain.SuspendLayout();
Dim newSize As New Size(GWidth, GHeight)
For Each p As Control In Me.PanelMain.Controls
p.Size = newSize
Next
Me.PanelMain.ResumeLayout();