Oct 06 2006

Coding the grouping repeater

Posted by admin under Controls

This is part 5 of this tutorial on how to create a expandable/collapsible grouping repeater control with ASP.NET. So, please start by reading part 1. 

Now lets move on to the ASP.NET code. The repeater control ASPX tags looks like this:



<asp:Repeater ID="rptOrder" runat="server" OnItemDataBound="rptOrder_ItemDataBound" EnableViewState="false">
    <HeaderTemplate>
        <table id="table2" class="treetable">
            <tr>
              <th>Group</th>
              <th>Orderid</th>
              <th>Orderdate</th>
              <th>RequiredDate</th>
            </tr>
            
    </HeaderTemplate>
    <ItemTemplate>
        <tr runat="server" id="rowGroupHeader">
            <td colspan="4"><span runat="server" id="idClickable"><asp:Image ID="idImage" runat="server" ImageUrl="images/minus.gif" CssClass="button" Width="16" Height="16" /><asp:Label ID="lblGroupName" runat="server" Font-Bold="true"></asp:Label></span></td>
        </tr>
    <tr runat="server" id="rowItem">
      <td>&nbsp;&nbsp;<%# DataBinder.Eval(Container.DataItem, "CustomerId") %></td>
      <td class="number"><%# DataBinder.Eval(Container.DataItem, "OrderId") %></td>
      <td class="number"><%# DataBinder.Eval(Container.DataItem, "OrderDate") %></td>
      <td class="number"><%# DataBinder.Eval(Container.DataItem, "RequiredDate") %></td>
    </tr>
    </ItemTemplate>
    <FooterTemplate>
        </table>
    </FooterTemplate>
</asp:Repeater>


Although we are creating a sort of nested control (grouping can be seen as  a kind of nesting ) - I have decided to not use nested repeaters. I believe it will be somewhat faster, not having to do multiple databinds. Just one pass and we are done.

The HeaderTemplate contains the table starting tag and defines the columns - and the footer defines the end tags for the table. However, the whole secret lies within the ItemTemplate:

As you can see we have two tr. One called rowGroupHeader and the other rowItem. I will modify the datasource to include extra (special marked) rows for each group header (same technique as in the article Insert user control every N records in gridview).

In ItemDataBound - if the item is a group header we will show the rowGroupHeader and hide the rowItem - and vice versa.

The code looks like this:



    protected void rptOrder_ItemDataBound(object sender, RepeaterItemEventArgs e)
    {
        if (e.Item.ItemType == ListItemType.Item || e.Item.ItemType == ListItemType.AlternatingItem)
        {
            HtmlTableRow rowHeader = e.Item.FindControl("rowGroupHeader") as HtmlTableRow;
            HtmlTableRow rowItem = e.Item.FindControl("rowItem") as HtmlTableRow;

            //Check if it is groupheader
            DataRowView oRow = e.Item.DataItem as DataRowView;
            if (oRow["poorman_type"].ToString() == "groupheader")
            {
                Image oImage = e.Item.FindControl("idImage") as Image;
                m_oGroupingHelper.AddGroup(rowHeader.ClientID, oImage.ClientID);
                HtmlGenericControl oCtrl = e.Item.FindControl("idClickable") as HtmlGenericControl;
                oCtrl.Attributes["onclick"] = "javascript:" + m_oGroupingHelper.CurrentGroupItem.FunctionName + "();";


                string sThisGroupValue = oRow[DropDownList1.SelectedValue].ToString();

                rowHeader.Visible = true;
                rowItem.Visible = false;
                //Bind group stuff
                Label lblGroupname = e.Item.FindControl("lblGroupname") as Label;
                lblGroupname.Text = sThisGroupValue;
            }
            else
            {
                if (DropDownList1.SelectedValue != "None")
                    m_oGroupingHelper.CurrentGroupItem.AddClientRow(rowItem.ClientID);
                rowHeader.Visible = false;
                rowItem.Visible = true;
            }
        }

    }

The secret in how to see if it's a header item lies in

if (oRow["poorman_type"].ToString() == "groupheader")

However, more about that - lets start from the beginning - what happens page is loaded first time or the button Run is clicked.

READ PART 6