5

I would like to be able to control the visibility of GridView columns in the code-behind using a unique identifier that I assign. This way, I can dynamically decide which columns to show and hide, and I don't have to change the code every time I add a new column.

The best way I've thought of to do this is use the HeaderText of columns as unique identifiers, and create a function that loops over all the DataControlField objects in GridView.Columns, searching for the requested HeaderText.

It seems strange to me though that DataControlField objects couldn't have an assignable ID property that could be accessed like GridView.Columns["AssignableID"]. Is there a programmatic reason that DataControlField cannot have an ID property that works this way, or is it just a functionality that doesn't happen to exist?

My question is more about the reason why it doesn't exist than an actual solution to the hiding columns problem, though if someone has a better method for accomplishing this I would appreciate it.

Per request, here is an example of searching by HeaderText:

protected DataControlField GetColumn(GridView grid, string columnName)
{
    foreach (DataControlField column in grid.Columns)
    {
        if (column.HeaderText == columnName)
        {
            return column;
        }
    }
    return null;
}
David
  • 834
  • 1
  • 10
  • 27
  • It's a bit easier to read and comprehend your question if it's split into paragraphs =) I've done that for you, but just an FYI for future reference. – Josh Darnell Jun 07 '12 at 20:23
  • Back on-topic: I assume that you know about the ordinal way of selecting them, correct? Like this: `myGridView.Columns[0].Visible = false;` – Josh Darnell Jun 07 '12 at 20:26
  • It would have been better if you'd have posted sample code to see how you switch visibility of columns based on the HeaderText (althoug i can imagine). That would make your question less abstract. **Edit** @jadarnel27: But i also think that code like that is less readable and more prone to errors than (pseudo): `myGridView.Columns["UserName"].Visible = false;`. Even more when you change the order of columns later. – Tim Schmelter Jun 07 '12 at 20:27
  • Yes, I'm aware of that way, but adding columns in the future causes the hassle of having to change all of the static indexes in the code behind which is what I'd like to avoid. – David Jun 07 '12 at 20:28
  • 1
    @TimSchmelter I was just making sure the OP was aware that there *was* a way at all. I fully agree that the example with a "dictionary-style" lookup is the preferable approach, the numeric indexes would be awful to maintain =) – Josh Darnell Jun 07 '12 at 20:33
  • I was tempted to extend the BoundField class, add an ID property, and create a static function which searches a GridView for the IDs of this extended class, but this seems a bit over the top for something I feel should be much simpler. – David Jun 07 '12 at 20:39
  • 1
    FYI: _Explicitly declared column fields can be used in combination with automatically generated column fields. When both are used, explicitly declared column fields are rendered first, followed by the automatically generated column fields. Automatically generated column fields **are not added to the Columns collection**._ http://msdn.microsoft.com/en-us/library/system.web.ui.webcontrols.gridview.columns.aspx – Tim Schmelter Jun 07 '12 at 20:58

2 Answers2

2

First, I'm right there with you. I also think that code like this

myGridView.Columns[0].Visible = false;

is less readable and more prone to errors than (pseudo-code):

myGridView.Columns["UserName"].Visible = false;

Hence your question why there's no ID property in DataControlField makes sense.

As i've already commented:

Explicitly declared column fields can be used in combination with automatically generated column fields. When both are used, explicitly declared column fields are rendered first, followed by the automatically generated column fields. Automatically generated column fields are not added to the Columns collection.

http://msdn.microsoft.com/en-us/library/system.web.ui.webcontrols.gridview.columns.aspx

I assume that above and the fact that there are different types of DataControlFields like TemplateField, BoundField or ButtonField were the reasons why there's no ID property since it wouldn't be predictable. Some of them are added manually(declaratively or programmatically), others might be added automatically(f.e. the ButtonFields, the ID would be auto generated), some are included in the Columns collection whereas others not and so on.

Tim Schmelter
  • 450,073
  • 74
  • 686
  • 939
  • That makes sense I suppose, though it is still very frustrating. Given the choice, I would probably dismiss the use of GridViews altogether given these types of scenarios in favor of creating the tables yourself using code. However, this isn't really an option when you adopt a large application which uses them everywhere and you don't have the budget to fix them all. – David Jun 11 '12 at 17:57
0

ASP.NET Grid view Columns don't have ID or unique value to access in code.

We can use with index or name.

Eg:

Using Index:

 if(Grid.Columns[0].Visible == true)  
    Grid.Columns[0].Visible = false;

 if(Grid.Columns[0].Visible == false)  
    Grid.Columns[0].Visible = true;

Using Name:

 if(Grid.Columns["ColumnName"].Visible == true)  
    Grid.Columns["ColumnName"].Visible = false;

 if(Grid.Columns["ColumnName"].Visible == false)  
    Grid.Columns["ColumnName"].Visible = true;