Link to home
Start Free TrialLog in
Avatar of Veljean
Veljean

asked on

Value of cell in gridview is empty (using RowDataBound event)

Hi
I would like to retrieve the value of a cell in  my gridview, but all the text values are always empty!

Im using the following code:

But always the line of "e.Row.Cells[y].Text" returns an empty string... what im doing wrong?
protected void GridView1_RowDataBound(object sender, GridViewRowEventArgs e)
    {

        switch (e.Row.RowType)
        {
            case DataControlRowType.Header:
                
                columnCount = e.Row.Cells.Count;
                for (int x = 0; x < columnCount; x++)
                {
                    dtData.Columns.Add(e.Row.Cells[x].Text);
                }
                break;

            case DataControlRowType.DataRow:

                DataRow drItem = dtData.NewRow();
                for (int y = 0; y < columnCount; y++)
                {
                    drItem[y] = e.Row.Cells[y].Text;
                }
                dtData.Rows.Add(drItem);
                break;

            default:
                dsData.Tables.Add(dtData);
                Session["gv"] = dsData;
                break;

        }
    }

Open in new window

Avatar of Daniel Van Der Werken
Daniel Van Der Werken
Flag of United States of America image

The event RowDataBound is where you grab the data from a dataset presented in the ASPX page and fill the gridview with that data.  Therefore, I would expect something like this:

-- get the Data passed in via the event arg e as e.Row.DataItem cast appropriately.
-- set the gridview display cell using e.Row.Cells to take in the value you get from e.Row.DataItem.

More or less...  There are plenty of examples how to do this specifically on the web.

Therefore, on the event, RowDataBound, your initial values for the cells in the gridview are indeed string.Empty or null as you fill the gridview here.  You don't retrieve data from it.

Where you get the data is on the new event you'd set up in the RowDataBound event.

Here's what I'd do for a very simple datasource object where the e.Row.DataItem is actually just a string value:

In my aspx I have the ObjectDataSource setup like this.  Note this could be a SQLDataSoruce, but I used an Object because I actually created bogus data for a prototype I was making:

      <asp:ObjectDataSource ID="_prvODSCompanies"
                            runat="server"
                            SelectMethod="_pubGetCompanyNames"
                            TypeName="Namespace.DummyFilesClass"  >
      </asp:ObjectDataSource>

and my gridview is this:

         <asp:GridView ID="_prvGridViewCompanies"
                       runat="server"
                       AutoGenerateColumns="false"
                       CssClass="gvgrid"
                       Width="250"
                       DataSourceID="_prvODSCompanies">
            <Columns>
               <asp:TemplateField HeaderText="Select" HeaderStyle-ForeColor="Black">
                  <ItemTemplate></ItemTemplate>
               </asp:TemplateField>            
               <asp:TemplateField HeaderText="Delete" HeaderStyle-ForeColor="Black">
                  <ItemTemplate></ItemTemplate>
               </asp:TemplateField>            
               <asp:TemplateField HeaderText="Edit" HeaderStyle-ForeColor="Black">
                  <ItemTemplate></ItemTemplate>
               </asp:TemplateField>            
               <asp:TemplateField HeaderText="Company Name" HeaderStyle-ForeColor="Black">
                  <ItemTemplate></ItemTemplate>
               </asp:TemplateField>
            </Columns>
         </asp:GridView>

Note that I set this up such that I have four"empty" columns with headers.  I don't want the grid view to automatically fill these in for me because I'm going to do that myself in the RowDataBound event.

In the code behind I do this:

        void _prvGridViewCompanies_RowDataBound( object sender, GridViewRowEventArgs e )
        {
            if ( e.Row.RowType == DataControlRowType.DataRow )
            {
                CheckBox cb = new CheckBox();
                e.Row.Cells[ 0 ].Controls.Add( cb );   // matches the "select" column

                ImageButton delIconButton = new ImageButton();
                delIconButton.ImageUrl = "~/images/delete_redx_small.png";
                e.Row.Cells[ 1 ].Controls.Add( delIconButton );  // matches the delete column

                ImageButton edIconButton = new ImageButton();
                edIconButton.ImageUrl = "~/images/pencil_image.png";
                e.Row.Cells[ 2 ].Controls.Add( edIconButton );  // matches the edit column

                LinkButton linkButton = new LinkButton();
                linkButton.Text = e.Row.DataItem.ToString();  // this is simple because my datasource is a List<string>
                linkButton.Click += new EventHandler( linkButton_Click );
                e.Row.Cells[ 3 ].Controls.Add( linkButton );  // matches the "company name" column
            }
        }

I could have added events for all of the buttons I made, but I didn't because I was lazy and just setting this up for demo purposes for myself only, but note that I did add a new event handler for the link button I created here.

All I have to do now is set up the event:

        void linkButton_Click( object sender, EventArgs e )
        {
            LinkButton lb = ( LinkButton )sender;
            string lbText = lb.Text;
        }

Actually, clicking on the link doesn't do anything except for set lbText to the value I clicked on in the gridview, but that's good enough for me if I set my breakpoint there and look at the value to confirm I got what I expected.

I hope this helps.




Avatar of Veljean
Veljean

ASKER

Thanks Dan7el, you put me in the right direction...
 Using a expression like this:

 string strColumn = DataBinder.Eval(e.Row.DataItem,"Column1").ToString();

I was able to read the value of the cell I wanted.

Only one more tip please, since I have more than 45 columns is tedious for me to reference one by one, it exists a method to dynamically get the name of the columns from e.Row.DataItem?

something like this?

 
for (int y = 0; y < columnCount; y++)
                {
                  
                    string strColumna = e.Row.DataItem.ColumnName[y]; //Obviously this is incorrect
                    drItem[y] = DataBinder.Eval(e.Row.DataItem, strColumna).ToString();



                }

Open in new window

ASKER CERTIFIED SOLUTION
Avatar of Daniel Van Der Werken
Daniel Van Der Werken
Flag of United States of America image

Link to home
membership
This solution is only available to members.
To access this solution, you must be a member of Experts Exchange.
Start Free Trial