At runtime, how to add new Headers and Items to the Repeater control.

Here's the deal. I have an orders page called Orders.aspx which contains a Repeaters control with Header and Items Templates. Under one condition, my columns need to change; I actually need to remove one or two columns and add three columns. The bottom line is that I would like to AVOID creating a completely new page just for this specific change in display.

I have successfully manipulated the header columns of the Header Template, but my Item Template is causing me lots of grief.

For my header template I can make Visible/Invisible with no problem ( as follows ) :

        if (e.Item.ItemType == ListItemType.Header)
            HtmlTableRow trheader = (HtmlTableRow)e.Item.FindControl("trHeaders");

            HtmlTableCell tdExec_Spot = (HtmlTableCell) e.Item.FindControl("tdExec_Spot");
            HtmlTableCell tdExec_Date = (HtmlTableCell)e.Item.FindControl("tdExec_Date");
            HtmlTableCell tdVal_Date = (HtmlTableCell)e.Item.FindControl("tdVal_Date");
            HtmlTableCell tdStatus = (HtmlTableCell)e.Item.FindControl("tdStatus");
            if (false)
                tdExec_Spot.Visible = (CurTabView == enTabViews.Executed ? true : false);   // visible to True
                tdExec_Date.Visible = (CurTabView == enTabViews.Executed ? true : false);   // visible to True
                tdVal_Date.Visible = (CurTabView == enTabViews.Executed ? true : false);     // visible to True
                tdStatus.Visible = (CurTabView == enTabViews.Executed ? false : true);         // make status column false

For the three Item Template controls I need to add at runtime, I've two two ways:
1) Add the three Label controls in my aspx , but make visible by default. Then at runtime make them Visible. Seems easy.
    PROBLEM: Asp seems to insert <TD> cells even when my Labels are false, so all Table Cells to the right are shifted to the right. This makes the display very messy and confusing.

2) A more difficult approach is to add them programatically. I can do this but these three Table Cells are added all the way out to the right. I need to specify their exact location in the row (under the specific header tdExec_Spot/tdExec_Date/tdVal_Date headers that I made visible above).
  Here's my code for creating these controls at runtime :

protected void Repeater1_ItemDataBound(object sender, RepeaterItemEventArgs e)
        HtmlTableRow tr = (HtmlTableRow)e.Item.FindControl("trTagOrder");

        if (tr != null)
         if (CurTabView == enTabViews.Executed)
            {   // add the execution rate, date and value date to Executed page.
                HiddenField hidExec_Spot = (HiddenField)tr.FindControl("hidExec_Spot");
                HiddenField hidExec_Date = (HiddenField)tr.FindControl("hidExec_Date");
                HiddenField hidVal_Date = (HiddenField)tr.FindControl("hidVal_Date");                

                string lcCellId = " ";
                foreach (HtmlTableCell cell in tr.Cells)   // My attempt here is to add the Label controls to the right of the User column ( lcCellId == "tdUser" )
                    lcCellId = cell.ID;
                    if (lcCellId == "tdUser"){
                        Label lblExec_Rate = new Label();
                        lblExec_Rate.Text = hidExec_Spot.Value;
                        HtmlTableCell htmlCell = new HtmlTableCell();
                        htmlCell.ID = "tdExec_Rate";
                        htmlCell.Align = "left";
                        htmlCell.Width = "50px";

                        // Add Exec_Date and Val_Date here !!!
                        Label lblExec_Date = new Label();
                        lblExec_Date.Text = hidExec_Date.Value;
                        lblExec_Date.Width = 200;
                        HtmlTableCell htmlCell2 = new HtmlTableCell();
                        htmlCell2.ID = "tdExec_Date";
                        htmlCell2.Align = "left";
                        htmlCell2.Width = "50px";

                        Label lblVal_Date = new Label();
                        lblVal_Date.Text = hidVal_Date.Value;
                        HtmlTableCell htmlCell3 = new HtmlTableCell();
                        htmlCell3.Align = "left";  
                        htmlCell3.Width = "50px";

 I've posted two gif images to my personal site ( to show you the good and bad display I'm referring to.

The first display shows my nicely formatted page (for example, note how the Ticket/User/Status/Type columns line up nicely with the values below it):


In this version, I've removed the Status column and have added "Exec Rate", "Execution Date&Time", and "Value Date" columns as shown here :


Notice how those three column headers are the last three; however, the data below it is skewed to the right. For example, the rate of "114.5 " should fall below the "Exec Rate" column, then comes the DateTime field, then the short date field. However, they're all shifted.

Again, I'd like to avoid creating a complete new page just for this one display change. I'd like it to be a smart program and code it at runtime if I can make it clean.

Bob Mazzo
New York

Who is Participating?
Closed, points refunded.
Experts Exchange Moderator
jgroetchAuthor Commented:
After ripping my hair out since yesterday, I might have finally figured this out.
If I go back to my first, more simplified approach of adding the labels to the aspx design page, then the trick appears to be adding an ID property to each <TD> tag, then do a FindControl() to get access to that <TD> at runtime as follows :

ASPX PAGE (Repeater control Item Template):

    <tr align="center" id="trTagOrder" style="font:Arial; font-weight:bold; font-variant:normal; color:Black;" runat="server" > 
    <td id="tdExec_Rate" visible="false" style="text-align:left;width:50px" ><!-- the following three col's only displayed on Executed tab -->  
          <asp:Label ID="lblExec_Rate" Text='<% #Eval("exec_spot") %>' Visible="true" runat="server" />
        <td id="tdExec_Date" visible="false" style="text-align:left;width:500px" >
          <asp:Label ID="lblExec_Date" Text='<% #Eval("lastmod").ToString()=="01/01/00" ? " " : Eval("lastmod") %>' Visible="true" runat="server" />
        <td id="tdVal_date" visible="false" style="text-align:left;width:50px" >
          <asp:Label ID="lblVal_Date" Text='<% #Eval("val_date").ToString()=="01/01/00" ? " " : Eval("val_date","{0:d}") %>' Visible="true" runat="server" />


SERVER SIDE ItemDataBound event:

HtmlTableRow tr = (HtmlTableRow)e.Item.FindControl("trTagOrder");

       if (CurTabView == enTabViews.Executed)
                HtmlTableCell tdExec_Rate = (HtmlTableCell)tr.FindControl("tdExec_Rate");
                HtmlTableCell tdExec_Date = (HtmlTableCell)tr.FindControl("tdExec_Date");
                HtmlTableCell tdVal_Date = (HtmlTableCell)tr.FindControl("tdVal_Date");
                HtmlTableCell tdStatus = (HtmlTableCell)tr.FindControl("tdStatus");
                tdExec_Rate.Visible = true;
                tdExec_Date.Visible = true;
                tdVal_Date.Visible = true;
                tdStatus.Visible = false;

Previously, I was going after the Label itself in the FindControl(). Now going after the HtmlTableCell instead seems to be rendering the page MUCH CLEANER !

If all is well then I will go ahead and close this out...

Thank you,
Question has a verified solution.

Are you are experiencing a similar issue? Get a personalized answer when you ask a related question.

Have a better answer? Share it in a comment.

All Courses

From novice to tech pro — start learning today.