Self-referencing hierarchy that is n-levels deep

9 posts, 0 answers
  1. Mike Gombar
    Mike Gombar avatar
    4 posts
    Member since:
    Dec 2009

    Posted 08 Dec 2009 Link to this post

    Is it possible to create a self-referencing hierarchical Silverlight GridView that is more than 1 level deep?  For example, I want to show the following hierarchy using a single list with the parentID pointing to the id for the parent node:

    Parent1
        Child1.1
        Child1.2
            Child1.2.1
            Child1.2.2
    Parent2
        Child2.1
        Child2.2
    etc.....
  2. Milan
    Admin
    Milan avatar
    1989 posts

    Posted 10 Dec 2009 Link to this post

    Hi Mike Gombar,

     There is no problem to do that. You just have to add another ChildTableDefinition. You can use our Self Reference sample as a reference. The sample only shows one level of hierarchy. To support more levels you should simply add another level of child TableDefinitions:

    <telerik:RadGridView.ChildTableDefinitions>
        <telerik:GridViewTableDefinition>
            <telerik:GridViewTableDefinition.Relation>
                <data:TableRelation IsSelfReference="True">
                    <data:TableRelation.FieldNames>
                        <data:FieldDescriptorNamePair 
                            ParentFieldDescriptorName="Name" 
                            ChildFieldDescriptorName="FriendName"/>
                    </data:TableRelation.FieldNames>
                </data:TableRelation>
            </telerik:GridViewTableDefinition.Relation>
            <telerik:GridViewTableDefinition.ChildTableDefinitions>
                <telerik:GridViewTableDefinition>
                    <telerik:GridViewTableDefinition.Relation>
                        <data:TableRelation IsSelfReference="True">
                            <data:TableRelation.FieldNames>
                                <data:FieldDescriptorNamePair 
                            ParentFieldDescriptorName="Name" 
                            ChildFieldDescriptorName="CoachName"/>
                            </data:TableRelation.FieldNames>
                        </data:TableRelation>
                    </telerik:GridViewTableDefinition.Relation>
                </telerik:GridViewTableDefinition>
            </telerik:GridViewTableDefinition.ChildTableDefinitions>
        </telerik:GridViewTableDefinition>
    </telerik:RadGridView.ChildTableDefinitions>

    One you create such structure you should also handle the DataLoading event to be able to turn off the hierarchy after the 2nd level:

    void clubsGrid_DataLoading(object sender, GridViewDataLoadingEventArgs e)
    {
        GridViewDataControl dataControl = (GridViewDataControl)sender;
      
        if (dataControl.ParentRow != null)
        {
            // configure child grid
            dataControl.ShowGroupPanel = false;
            dataControl.AutoGenerateColumns = false;
            dataControl.CanUserFreezeColumns = false;
              
            // stop hierarchy after level 2
            if (dataControl.ParentRow.GridViewDataControl != this.clubsGrid)
            {
                dataControl.ChildTableDefinitions.Clear();
            }
              
            GridViewDataColumn column = new GridViewDataColumn();
            column.DataMemberBinding = new Binding("Name");
            dataControl.Columns.Add(column);
        }
    }

    Hope this helps.

    Best wishes,
    Milan
    the Telerik team

    Instantly find answers to your questions on the new Telerik Support Portal.
    Watch a video on how to optimize your support resource searches and check out more tips on the blogs.
  3. DevCraft banner
  4. Mike Gombar
    Mike Gombar avatar
    4 posts
    Member since:
    Dec 2009

    Posted 14 Dec 2009 Link to this post

    I must be missing something.  Attached is my sample project.  I expect the following hierarcy:

    John Smith
        - Sally Smith
            - Emma Smith
                - Lisa Smith
        - Fred Smith
            - Fred Smith Jr.

    Instead, what I am getting is:

    John Smith
        - Sally Smith
        - Fred Smith
    Sally Smith
        - Emma Smith
    Fred Smith
        - Fred Smith Jr.
    Emma Smith
        - Lisa Smith
    Fred Smith Jr.
    Lisa Smith

    It appears I am getting all the items in the list, plus all their children (only 1 level deep).  I was hoping to see all children appear only under their parent, and I would see 3 levels deep.

    I am using a single list, with an EmployeeName (displayed), EmployeeID, and ReportsTo (that references the EmployeeID).

    Here is my .xaml code:
    <UserControl x:Class="RadGridViewTemplateBug.MainPage" 
        xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"   
        xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml" 
        xmlns:d="http://schemas.microsoft.com/expression/blend/2008"   
         xmlns:mc="http://schemas.openxmlformats.org/markup-compatibility/2006"   
         xmlns:Controls="clr-namespace:Telerik.Windows.Controls;assembly=Telerik.Windows.Controls.GridView"   
         xmlns:telerikData="clr-namespace:Telerik.Windows.Data;assembly=Telerik.Windows.Data"   
         xmlns:telerik="clr-namespace:Telerik.Windows.Controls.GridView;assembly=Telerik.Windows.Controls.GridView"   
         xmlns:Controls1="clr-namespace:Telerik.Windows.Controls;assembly=Telerik.Windows.Controls"   
        mc:Ignorable="d" d:DesignWidth="640" d:DesignHeight="480">  
     
        <Grid x:Name="LayoutRoot">  
            <!-- ********** ROOT RADGRIDVIEW CONTROL ********** --> 
            <Controls:RadGridView x:Name="radGridViewHierarchy"   
                                  AutoGenerateColumns="False" 
                                  ShowGroupPanel="False" DataLoading="radGridViewHierarchy_DataLoading">  
                  
                <Controls:RadGridView.ChildTableDefinitions> 
                    <Controls:GridViewTableDefinition> 
                        <Controls:GridViewTableDefinition.Relation> 
                            <telerikData:TableRelation IsSelfReference="True" > 
                                <telerikData:TableRelation.FieldNames> 
                                    <telerikData:FieldDescriptorNamePair ParentFieldDescriptorName="EmployeeID" ChildFieldDescriptorName="ReportsTo" /> 
                                </telerikData:TableRelation.FieldNames> 
                            </telerikData:TableRelation> 
                        </Controls:GridViewTableDefinition.Relation> 
                        <Controls:GridViewTableDefinition.ChildTableDefinitions> 
                            <Controls:GridViewTableDefinition> 
                                <Controls:GridViewTableDefinition.Relation> 
                                    <telerikData:TableRelation IsSelfReference="True" > 
                                        <telerikData:TableRelation.FieldNames> 
                                            <telerikData:FieldDescriptorNamePair ParentFieldDescriptorName="EmployeeID" ChildFieldDescriptorName="ReportsTo" /> 
                                        </telerikData:TableRelation.FieldNames> 
                                    </telerikData:TableRelation> 
                                </Controls:GridViewTableDefinition.Relation> 
                            </Controls:GridViewTableDefinition> 
                        </Controls:GridViewTableDefinition.ChildTableDefinitions> 
                    </Controls:GridViewTableDefinition> 
                </Controls:RadGridView.ChildTableDefinitions> 
                  
                 <Controls:RadGridView.Columns> 
                    <Controls:GridViewDataColumn Width="Auto" Header="Employee Name">  
                        <Controls:GridViewColumn.CellTemplate> 
                            <DataTemplate> 
                                <TextBlock Text="{Binding EmployeeName}" /> 
                            </DataTemplate> 
                        </Controls:GridViewColumn.CellTemplate> 
                    </Controls:GridViewDataColumn> 
                </Controls:RadGridView.Columns> 
            </Controls:RadGridView> 
        </Grid> 
    </UserControl> 
     

    And the associated .cs code:
    using System.IO;  
    using System.Net;  
    using System.Windows.Data;  
    using System.Windows.Controls;  
    using System.Collections.Generic;  
    using Telerik.Windows.Controls;  
    using Telerik.Windows.Controls.GridView;  
    using Telerik.Windows.Data;  
    using Telerik.Windows;  
     
    namespace RadGridViewTemplateBug {  
        public partial class MainPage : UserControl {  
            public MainPage() {  
                InitializeComponent();  
     
                var employeeList = new List<Employee>();  
     
                var emp = new Employee();  
                emp.EmployeeName = "John Smith";  
                emp.EmployeeID = "js";  
                emp.ReportsTo = "";  
                employeeList.Add(emp);  
     
                emp = new Employee();  
                emp.EmployeeName = "Sally Smith";  
                emp.EmployeeID = "ss";  
                emp.ReportsTo = "js";  
                employeeList.Add(emp);  
     
                emp = new Employee();  
                emp.EmployeeName = "Fred Smith";  
                emp.EmployeeID = "fs";  
                emp.ReportsTo = "js";  
                employeeList.Add(emp);  
     
                emp = new Employee();  
                emp.EmployeeName = "Emma Smith";  
                emp.EmployeeID = "es";  
                emp.ReportsTo = "ss";  
                employeeList.Add(emp);  
     
                emp = new Employee();  
                emp.EmployeeName = "Fred Smith Jr";  
                emp.EmployeeID = "fsj";  
                emp.ReportsTo = "fs";  
                employeeList.Add(emp);  
     
                emp = new Employee();  
                emp.EmployeeName = "Lisa Smith";  
                emp.EmployeeID = "ls";  
                emp.ReportsTo = "es";  
                employeeList.Add(emp);  
     
              radGridViewHierarchy.ItemsSource = employeeList;  
            }  
     
            private void radGridViewHierarchy_DataLoading(object sender, Telerik.Windows.Controls.GridView.GridViewDataLoadingEventArgs e)  
            {  
                GridViewDataControl dataControl = (GridViewDataControl)sender;  
     
                if (radGridViewHierarchy.ParentRow != null)  
                {  
                    // configure child grid   
                    radGridViewHierarchy.ShowGroupPanel = false;  
                    radGridViewHierarchy.AutoGenerateColumns = false;  
                    radGridViewHierarchy.CanUserFreezeColumns = false;  
     
                    // stop hierarchy after level 2   
                    if (radGridViewHierarchy.ParentRow.GridViewDataControl != this.radGridViewHierarchy )  
                    {  
                        radGridViewHierarchy.ChildTableDefinitions.Clear();  
                    }  
     
                    GridViewDataColumn column = new GridViewDataColumn();  
                    column.DataMemberBinding = new Binding("EmployeeName");  
                    //radGridViewHierarchy.Columns.Add(column);  
                }   
            }  
        }  
     
        public class Employee {  
            public string EmployeeName { get; set; }  
            public string EmployeeID { get; set; }  
            public string ReportsTo { get; set; }  
        }  
     
    }  
     

  5. Milan
    Admin
    Milan avatar
    1989 posts

    Posted 15 Dec 2009 Link to this post

    Hi Mike Gombar,

     

    Well, seeing all data items is actually the expected behavior since you are passing all items to the grid.

    If you would like to have this structure:

    John Smith
    - Sally Smith
    - Emma Smith
    - Lisa Smith
    - Fred Smith
    - Fred Smith Jr.

    you should restructure your data in such a way that only John Smith is the only item in the data source.


    Sincerely yours,
    Milan
    the Telerik team

    Instantly find answers to your questions on the new Telerik Support Portal.
    Watch a video on how to optimize your support resource searches and check out more tips on the blogs.
  6. Michael Gombar
    Michael Gombar avatar
    2 posts
    Member since:
    Nov 2009

    Posted 05 Jan 2010 Link to this post

    I have restructured my data, and included the XAML code  for the ChildTableDefinitions as follows:

                        <telerikGridView:RadGridView.ChildTableDefinitions> 
                            <telerikGridView:GridViewTableDefinition> 
                                <telerikGridView:GridViewTableDefinition.Relation> 
                                    <telerikData:PropertyRelation IsSelfReference="True" ParentPropertyName="children"/> 
                                </telerikGridView:GridViewTableDefinition.Relation> 
                             
                                <telerikGridView:GridViewTableDefinition.ChildTableDefinitions> 
                                    <telerikGridView:GridViewTableDefinition> 
                                        <telerikGridView:GridViewTableDefinition.Relation> 
                                            <telerikData:PropertyRelation IsSelfReference="True" ParentPropertyName="children"/> 
                                        </telerikGridView:GridViewTableDefinition.Relation> 
                                    </telerikGridView:GridViewTableDefinition> 
                                </telerikGridView:GridViewTableDefinition.ChildTableDefinitions> 
                            </telerikGridView:GridViewTableDefinition> 
                        </telerikGridView:RadGridView.ChildTableDefinitions> 

    I am also setting row.IsExpandable = false if there are no children.  This is done using the RowLoaded event on the RadGridView.  But, this event is not firing for the new child rows.

    How do I register the RowLoaded event handler for the Child Grid elements?

    Thanks.
  7. Michael Gombar
    Michael Gombar avatar
    2 posts
    Member since:
    Nov 2009

    Posted 08 Jan 2010 Link to this post

    Has anyone been able to implement the expand/collapse feature of RadGridView on child GridViews?

    Thanks in advance.
  8. Milan
    Admin
    Milan avatar
    1989 posts

    Posted 11 Jan 2010 Link to this post

    Hi Michael Gombar,

    You can use the DataLoading event to access each child grid and subscribe to its RowLoaded event:

    public MainPage()
    {
        InitializeComponent();
          
        this.clubsGrid.ItemsSource = Club.GetPlayers();
        this.clubsGrid.DataLoading += new System.EventHandler<GridViewDataLoadingEventArgs>(clubsGrid_DataLoading);
    }
      
    void clubsGrid_DataLoading(object sender, GridViewDataLoadingEventArgs e)
    {
        var dataControl = sender as GridViewDataControl;
      
        dataControl.RowLoaded += new System.EventHandler<RowLoadedEventArgs>(dataControl_RowLoaded);
    }
      
    void dataControl_RowLoaded(object sender, RowLoadedEventArgs e)
    {
          
    }

    Hope this helps.


    Kind regards,
    Milan
    the Telerik team

    Instantly find answers to your questions on the new Telerik Support Portal.
    Watch a video on how to optimize your support resource searches and check out more tips on the blogs.
  9. Siqi
    Siqi avatar
    3 posts
    Member since:
    Jun 2015

    Posted 22 Jun 2015 in reply to Milan Link to this post

    Hi Milan,

      I want to do the same thing as Mike Gombar, and I use the same method as Mike, but I get the same issue(

    John Smith
        - Sally Smith
        - Fred Smith
    Sally Smith
        - Emma Smith
    Fred Smith
        - Fred Smith Jr.
    Emma Smith
        - Lisa Smith
    Fred Smith Jr.
    Lisa Smith

     you said "we could justrestructure the data in such a way that only John Smith is the only item in the data source". But I don't understand how to do this. If I keep only John Smith in the list, it doesn't show the other "Employee".

     

     

  10. Dimitrina
    Admin
    Dimitrina avatar
    3769 posts

    Posted 25 Jun 2015 Link to this post

    Hello Siqi,

    Thank you so much for sharing the solution with the community in the other forum thread you opened.

    Regards,
    Dimitrina
    Telerik
    Do you want to have your say when we set our development plans? Do you want to know when a feature you care about is added or when a bug fixed? Explore the Telerik Feedback Portal and vote to affect the priority of the items
Back to Top
DevCraft banner