Presenting Parent/Child Data in a Data Grid Row

Introduction

The Data Grid provides a richer UI presentation for Web applications. Most of the time, there may be a requirement to show one or more child data items that belong to the parent row in a column within the Data Grid. The following article gives an example of defining a Repeater control inside the Template column. The Repeater binds to the child data of the parent row.

Data Grid HTML Code

<asp:datagrid id="dataGrid1"
              runat="server"
              width="792px"
              autogeneratecolumns="False"
              cellpadding="0"
              pagerstyle-mode="NumericPages"
              pagerstyle-pagebuttoncount="20"
              pagesize="20"
              allowpaging="True"
              allowsorting="True"

<Columns>

<!-- First Column With ID as hidden column -->

<asp:BoundColumn DataField="ID" Visible="False" HeaderText="ID">
   <HeaderStyle Width="190px" HorizontalAlign="Center" >
   </HeaderStyle>
</asp:BoundColumn>

<!-- Second Column defined as Check Box in a Template Column -->

<asp:TemplateColumn HeaderText="Select" HeaderStyle-Width="40px" >
   <ItemStyle Width="40px"></ItemStyle>
   <ItemTemplate>
      <input type="checkbox" runat="server" id="chkSelected"
         checked ='<% # DataBinder.Eval(Container.DataItem,
                                        "Selected") %>' />
   </ItemTemplate>
</asp:TemplateColumn>

<!-- Third Column bound to the Field Description -->

<asp:BoundColumn DataField="Description"
                 SortExpression="Description"
                 HeaderText="Description">
   <HeaderStyle HorizontalAlign="Center"></HeaderStyle>
   <ItemStyle Wrap="True" Width="2000px"></ItemStyle>
</asp:BoundColumn>

<!-- Fourth Column a Numeric column for displaying Currency
     with DataFormat -->

<asp:BoundColumn DataField="Amount" SortExpression="Amount"
                 ReadOnly="True"
                 HeaderText="Amount"
                 DataFormatString="{0:$#,##0.0000;($#,##0.0000)}">
   <HeaderStyle HorizontalAlign="Center"
                Width="70px"></HeaderStyle>
   <ItemStyle HorizontalAlign="Right" Wrap="False"></ItemStyle>
</asp:BoundColumn>

<!-- Fifth Column That displays the child record of the
     row inside a Repeater control -->

<asp:TemplateColumn HeaderText="Child Data"
                    HeaderStyle-HorizontalAlign="Center">
   <ItemStyle HorizontalAlign="Left" Wrap="True"></ItemStyle>
   <ItemTemplate>
      <asp:Repeater ID="rptChild" runat = "server"
           DataSource = '<%# ((System.Data.DataRowView)
                        Container.DataItem).Row.
                        GetChildRows("relationParentChild") %>'>
            <ItemTemplate>
               <asp:LinkButton ID="linkChild" Runat="server"
                    CommandArgument=<%# DataBinder.
                       Eval(Container.DataItem, "["ChildID"]")%>
                    OnClick="linkChild_Click">
               <%# DataBinder.Eval(Container.DataItem,
                                   "["ChildFieldNameToDisplay"]")%>
               </asp:LinkButton>
            </ItemTemplate>
      </asp:Repeater>
   </ItemTemplate>
</asp:TemplateColumn>

</Columns>
<PagerStyle PageButtonCount="20" Mode="NumericPages"></PagerStyle>
</asp:datagrid>

Code Required in the Code Behind Page

private void Page_Load(object sender, System.EventArgs e)
{
   System.Data.DataSet ds = Get Data Set();
      // This Data Set should be populated with two
      // tables one for the Parent Row Data and the
      // second for the child data to be displayed
      // in the repeater control
      ds.Relations.Add("relationParentChild",
                       ds.Tables[0].Columns["ID"],
                       ds.Tables[1].Columns["FKID"]);
   DataView dv = ds.Tables[0].DefaultView;
   dataGrid1.DataSource = dv;
}

Code Explanation

Add the data grid control to the page and set its properties (like width and autogeneratecolumns) as well as its events. Then, define the Bound Column and the DataField Name for those columns. These columns will be displayed as just text. If data needs to be presented in a special control such as a Check Box as shown in the example, you should define this in the Item Template column. The code also shows how you can set the Data Format string for the column.

The Repeater should be declared inside the Item Template column in the grid (inside an Item Template). The data source for the Repeater is set inside the Server Tag as:

((System.Data.DataRowView)Container.DataItem).
   Row.GetChildRows("relationParentChild")

This will get the child rows of the row to which the data is being bound.

In this example, a link button is displayed inside the Repeater. Clicking on the link will take you to the appropriate page as required. This can be changed to fit your needs. To access the child table’s field, this syntax is used:

DataBinder.Eval(Container.DataItem, "["ColumnNameinChildTable"]")%

The CommandArgument attribute is used to get the querystring to open up the page for the selected child link.

Conclusion

The code sample demonstrates how to display the child data inside the column of a Data Grid with minimum amount and efficient way of coding. Also, the zip file attached contains the sample project showing a working version of the above code.

More by Author

Get the Free Newsletter!

Subscribe to Developer Insider for top news, trends & analysis

Must Read