Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

How can I dynamically clear all controls in a user control?

Is it possible to dynamically (and generically) clear the state of all of a user control's child controls? (e.g., all of its TextBoxes, DropDrownLists, RadioButtons, DataGrids, Repeaters, etc -- basically anything that has ViewState)

I'm trying to avoid doing something like this:

foreach (Control c in myUserControl.Controls)
{
    if (c is TextBox)
    {
        TextBox tb = (TextBox)c;
        tb.Text = "";
    }
    else if (c is DropDownList)
    {
        DropDownList ddl = (DropDownList)c;
        ddl.SelectedIndex = -1;
    }
    else if (c is DataGrid)
    {
        DataGrid dg = (DataGrid)c;
        dg.Controls.Clear();
    }

    // etc.

}

I'm looking for something like this:

foreach (Control c in myUserControl.Controls)
    c.Clear();

...but obviously that doesn't exist. Is there any easy way to accomplish this dynamically/generically?

like image 539
Michael Avatar asked May 19 '10 18:05

Michael


2 Answers

I was going to suggest a solution similar to Task's except (as sixlettervariables points out) we need to implement it as 1 extension method and essentailly switch on the precise type of the control passed in (i.e. copy your logic that you posted in your question).

public static class ControlExtensions
{
    public static void Clear( this Control c )
    {
        if(c == null) {
            throw new ArgumentNullException("c");
        }
        if (c is TextBox)
        {
            TextBox tb = (TextBox)c;
            tb.Text = "";
        }
        else if (c is DropDownList)
        {
            DropDownList ddl = (DropDownList)c;
            ddl.SelectedIndex = -1;
        }
        else if (c is DataGrid)
        {
            DataGrid dg = (DataGrid)c;
            dg.Controls.Clear();
        }
        // etc....
    }
}

It is not particularly elegent looking method but your code in your page/control is now the more succinct

foreach (Control c in myUserControl.Controls) {
    c.Clear();
}

and you can of course now call control.Clear() anywhere else in you code.

like image 59
Chris Fewtrell Avatar answered Sep 16 '22 16:09

Chris Fewtrell


You can do

foreach (Control c in myUserControl.Controls) {
    myUserControl.Controls.Remove(c);
}

Because Controls is just a list, you can call Remove() on it, passing it what you want to remove.

EDIT: Oh I'm sorry, I didn't read it correctly. I don't know of a way to do this, maybe someone here who is good with Reflection could make it where you could do like

foreach (Control c in myUserControl.Controls) {
    c = new c.Type.GetConstructor().Invoke();
}

or something, to turn it into a freshly made component.

like image 27
Nilbert Avatar answered Sep 20 '22 16:09

Nilbert