0

I have a view where some labels and textboxes are generated once the user clicks on a button. When generating I pass the name as "dynamic_something" and it gets added

enter image description here

TextBox textBox = new TextBox();
textBox.Name = "dynamic_something";
this.Controls.Add(textBox);

When the user clicks on another button I want to remove all the generated fields. I loop through all the controls and find the controls with dynamic at the start and remove but all fields doesn't get removed.

foreach (Control currentControl in this.Controls)
{

     if ((currentControl).Name.StartsWith("dynamic"))
     {
       Controls.Remove(currentControl);
     }

}

enter image description here

How can I fix this?

T.S.
  • 18,195
  • 11
  • 58
  • 78
Rasheen Ruwisha
  • 135
  • 3
  • 10
  • 2
    1) Don't try to remove an object from a collection that you're iterating in a `foreach` loop. Use a backwards `for` loop 2) Dispose of the Control (`currentControl.Dispose();`, here), don't use `Collection.Remove(Control)`. Disposing of the Control also removes it from the collection. – Jimi Nov 26 '19 at 18:06
  • @Jimi In the initial loop I added the controls to a list and using another loop I removed it using the Dispose(). And it worked perfectly. Thanks! Could you add this as the answer so I can accept it. – Rasheen Ruwisha Nov 26 '19 at 18:13
  • It's a duplicate of (the not enough well-known) [Removing dynamically created controls in C#](https://stackoverflow.com/a/2014427/7444103). – Jimi Nov 26 '19 at 18:19

1 Answers1

0

You can't remove items from collection you iterating. You can use while loop for this, or LINQ:

var f = new Form();
f.Controls.Add(new Label() { Name = "x1" });
f.Controls.Add(new Label() { Name = "y" }); 
f.Controls.Add(new Label() { Name = "x2" });
f.Controls
    .Cast<Control>()
    .Where(c => c.Name.StartsWith("x")).ToList()
    .ForEach(c => f.Controls.Remove(c));
Debug.Assert(f.Controls.Count == 1);

That works because you do not iterate mutating collection.

T.S.
  • 18,195
  • 11
  • 58
  • 78