Reputation: 549
I have a panel with about six controls on the panel. I wanted to remove the controls from the panel and finally did so with MyPanel.Clear(). But before that I tried the following code that runs from a button click:
For Each b As Control In MyItem.MyPanel.Controls
MyItem.MyPanel.Controls.Remove(b)
Next
I would click the button and watch it, as well as the MyItem.MyPanel.Controls.Count in debug. As it went through, the count would reduce: to 5 to 4 to 3, then it would exit. If I clicked the button again it would remove two more, then the last one on the third click, so they all fit the bill and were all removed without changing anything. Why did it take three clicks? I'm obviously missing something simple here, I think, but I don't know what it is, and I'd really like to understand it. If I had to remove specific controls, it looks like I would have had a problem.
Upvotes: 2
Views: 135
Reputation: 652
I ran into this issue myself and its odd it even lets you do it as you're modifying the collection in the loop you are referring to.This should be a better method.
If you like to remove them based on type
For i = Panel1.Controls.Count - 1 To 0 Step -1
If TypeOf Panel1.Controls(i) Is Label Then
Panel1.Controls.Remove(Panel1.Controls(i))
End If
Next
Upvotes: 2
Reputation: 1857
What is happening is that you are deleting the controls starting from the first position and moving to the last. If the list has 6 records and you start deleting them like you are, programatically you are saying:
remove(0)
remove(1)
...
remove(5)
While you are doing that, the list is getting smaller. Once you delete the first item it drops from 6 positions to 5, then 4, then 3, etc. So midway through your code it tries to remove item at location 3 (4th item), but since you already removed 3 items, the list's size only contains 3 items and that position does not exist.
To properly remove them all, you would have to start at the back of the list and move to the front.
Perhaps something like:
For i As Integer = (MyItem.MyPanel.Controls.Count- 1) To 0 Step -1
MyItem.mypanel.Controls(i).Dispose()
Next
Upvotes: 0
Reputation: 26048
Odd that VB.NET even lets you do this, but essentially what you are doing is editing the collection you are iterating through. To better understand, pretend you are using a regular for loop from 1 to 6, at the first iteration you are removing object 1, leaving you with 5 objects, making the old number 2 object the first. The next iteration you remove the 2nd thing, which used to be the third, and so on. Most languages this is a run-time error.
Upvotes: 2