Datagrid columns using AutoGenerate via the autoGenColumnsArray private member array collection (ref

  • Thread starter Thread starter Jason Coyne Gaijin42
  • Start date Start date
J

Jason Coyne Gaijin42

I have seen several people looking for a way to access the Columns
collection when using the AutoGenerate = true option. Some
people have gotten so far as to find the private autoGenColumnsArray
that has the information, but we as developers have no way to access
this information.

I have come up with a solution for the problem, (as I am sure many
others have) using reflection. Here is some sample code that will
print out the auto generated column names from a datagrid.

As stated, this code uses reflection. Reflection is slow. It might not
also be allowed depending on your system's security settings. Also, if
MS changes the internal structure of the DataGrid, this might break.
(We are breaking encapsulation)

Provided, is a function that will generically allow you to get the
value of any private member of a class using reflection.

Sorry about the formatting, I dont know a good way to format code for
usenet. Visual Studio should clean up the code just find for you tho.

<code>
DataGrid dg = new DataGrid();
dg.DataSource =new DataTable();// (Run some query or whatnot here)
dg.DataBind

ArrayList AutoGeneratedColumns
= (ArrayList) GetPrivateField(dg,"autoGenColumnsArray") ;

if (AutoGeneratedColumns!= null)
foreach (DataGridColumn CurrentColumn in AutoGeneratedColumns)
{
Response.Write(CurrentColumn.HeaderText);
}


public static object GetPrivateField(object PassedObject, string
FieldName)
{

object Field=null;

if (PassedObject == null)
throw new ArgumentNullException("PassedObject"
,"PassedObject must be an instantiated object.");

if (FieldName == null || FieldName.Trim() == "")
throw new ArgumentOutOfRangeException("FieldName"
,"Fieldname must be a non empty string.");

Type ObjectType = PassedObject.GetType();
System.Reflection.FieldInfo PrivateField =
ObjectType.GetField(FieldName
,System.Reflection.BindingFlags.Instance
| System.Reflection.BindingFlags.NonPublic
| System.Reflection.BindingFlags.Public
| System.Reflection.BindingFlags.IgnoreCase);

if (PrivateField == null)
throw new ArgumentOutOfRangeException("FieldName"
, ObjectType.FullName + " does not have a field : " + FieldName +
".");

Field = PrivateField.GetValue(PassedObject);
return Field;
}
</code>
 
With autogen=true, why not simply add to the Table you are binding to. This
can be extended quite efficiently in XML or in the ADO.NET objects. When
autogen=false, you need to explicitly expand the DataGrid, as well.

--
Gregory A. Beamer
MVP; MCP: +I, SE, SD, DBA

***************************************************************
Think outside the box!
***************************************************************
 
The purpose of the code was not to change the columns collection, but
to iterate through it.

In my particular case, I was writing a utility that would take any
datagrid, and output an excel worksheet that contained the contents of
that datagrid. I could get all the data fine, by looping through the
Items collection, but to get the column headings, I looped through the
columns array. However for autogenerated columns, they did not exist
in the columns array, only in the autogencolumnsarray and there is no
way to access that. So I wrote a way to access that.

It was possible to iterate through the underlying DataSource object,
but the code was rather clunky. The autoGenColumns array was much
cleaner.
 
Back
Top