This is a migrated thread and some comments may be shown as answers.

Reordering self-referencing hierarchical grid only reorders top level column

6 Answers 74 Views
Grid
This is a migrated thread and some comments may be shown as answers.
Matt
Top achievements
Rank 1
Matt asked on 27 Dec 2013, 03:38 PM
I have a self-referencing hierarchical grid defined as follows:

<telerik:RadGrid
    ID="grdNotes"
    runat="server"
    OnColumnCreated="grdNotes_ColumnCreated"
    OnItemCreated="grdNotes_ItemCreated"
    OnItemDataBound="grdNotes_ItemDataBound"
    OnNeedDataSource="grdNotes_NeedDataSource"
    OnPreRender="grdNotes_PreRender"
    AutoGenerateColumns="False"
    SkinID="HierarchicalGrid"
    GridLines="None"
    AllowCustomPaging="True"
    ShowStatusBar="True"
    PageSize="20"
    EnableLinqExpressions="False"
    Width="99%" CellSpacing="0">
    <MasterTableView
        HierarchyDefaultExpanded="true"
        HierarchyLoadMode="Client"
        AllowSorting="true"
        DataKeyNames="Id,ParentId,Token,IsRoot,Replies,NoteCreator"
        ClientDataKeyNames="Id,ParentId,Token,IsRoot,Replies,NoteCreator"
        NoDetailRecordsText=""
        EnableNoRecordsTemplate="False"
        TableLayout="Auto"
        Width="100%"
        HorizontalAlign="Right"
        EnableHeaderContextMenu="True">
        <SelfHierarchySettings ParentKeyName="ParentId" KeyName="Id" MaximumDepth="20" />
        <RowIndicatorColumn Visible="False" FilterControlAltText="Filter RowIndicator column"></RowIndicatorColumn>
        <ExpandCollapseColumn Visible="True" FilterControlAltText="Filter ExpandColumn column"></ExpandCollapseColumn>
        <Columns>
            <telerik:GridClientSelectColumn DataTextField="Id" HeaderAbbr="Select" HeaderButtonType="TextButton"
                HeaderText="Select" HeaderTooltip="Select/Deselect" Text="Select" Visible="false"
                UniqueName="asgSelect">
            </telerik:GridClientSelectColumn>
            <telerik:GridBoundColumn DataField="Id" SortExpression="Id" UniqueName="Id">
                <HeaderStyle Width="50px" />
            </telerik:GridBoundColumn>
            <telerik:GridBoundColumn DataField="Title" SortExpression="Title" UniqueName="Title"
                HtmlEncode="true">
                <HeaderStyle Width="150px" />
            </telerik:GridBoundColumn>
            <telerik:GridBoundColumn DataField="Body" SortExpression="Body" UniqueName="Body" HtmlEncode="False">
                <HeaderStyle Width="350px" />
            </telerik:GridBoundColumn>
            <telerik:GridBoundColumn DataField="CreatedBy" SortExpression="CreatedBy" UniqueName="CreatedBy">
                <HeaderStyle Width="150px" />
            </telerik:GridBoundColumn>
            <telerik:GridBoundColumn DataField="CreatedDate" SortExpression="CreatedDate" UniqueName="CreatedOn">
                <HeaderStyle Width="150px" />
            </telerik:GridBoundColumn>
            <telerik:GridBoundColumn DataField="ParentId" HeaderText="Parent Id" SortExpression="ParentId"
                UniqueName="ParentId" Visible="false" />
            <telerik:GridBoundColumn DataField="Token" HeaderText="Token" SortExpression="Token"
                UniqueName="Token" Visible="false" />
            <telerik:GridBoundColumn DataField="IsRoot" HeaderText="Is Root" SortExpression="IsRoot"
                UniqueName="IsRoot" Visible="false" />
            <telerik:GridBoundColumn DataField="Replies" HeaderText="Replies" SortExpression="Replies"
                UniqueName="Replies" Visible="false" />
            <telerik:GridBoundColumn DataField="NoteCreator" HeaderText="NoteCreator" SortExpression="NoteCreator"
                UniqueName="NoteCreator" Visible="false" />
            <telerik:GridTemplateColumn UniqueName="Actions" Visible="false">
                <ItemTemplate>
                    <telerik:RadToolBar ID="rtbNoteActions" runat="server" SkinID="ActionToolbar" OnButtonClick="NotesGridToolbarButtonClicked"
                        OnClientButtonClicking="NoteActionToolbarClicking">
                        <Items>
                            <telerik:RadToolBarButton Text="Properties" CommandName="Properties" ImageUrl="~/Images/page_view.gif" />
                            <telerik:RadToolBarButton Text="Reply" CommandName="Reply" ImageUrl="~/Images/page_edit.gif" />
                            <telerik:RadToolBarButton Text="Security" CommandName="Security" ImageUrl="~/Images/shield16.gif" />
                            <telerik:RadToolBarButton Text="Delete" CommandName="Delete" ImageUrl="~/Images/delete16.gif" />
                        </Items>
                    </telerik:RadToolBar>
                </ItemTemplate>
                <HeaderStyle Width="15%"></HeaderStyle>
            </telerik:GridTemplateColumn>
        </Columns>
        <EditFormSettings>
            <EditColumn FilterControlAltText="Filter EditCommandColumn column"></EditColumn>
        </EditFormSettings>
        <PagerStyle AlwaysVisible="True"></PagerStyle>
    </MasterTableView>
    <HeaderContextMenu EnableTheming="True">
        <CollapseAnimation Type="OutQuint" Duration="200"></CollapseAnimation>
    </HeaderContextMenu>
    <ExportSettings ExportOnlyData="True" IgnorePaging="True">
    </ExportSettings>
    <ClientSettings
        Selecting-AllowRowSelect="true"
        Resizing-AllowColumnResize="true"
        AllowColumnsReorder="true">
        <Selecting AllowRowSelect="True"></Selecting>
        <ClientEvents
            OnRowSelected="NoteRowSelected"
            OnRowContextMenu="NoteContextMenu"
            OnRowDblClick="grdNotes_OnRowDblClick"
            OnGridCreated="NotePageLoad"
            OnTableCreated="ResizeAllNoteColumns"
            OnColumnResized="ResizeAllNoteColumns"
            OnColumnHiding="HideDetailColumn"
            OnColumnShowing="ShowDetailColumn" />
    </ClientSettings>
    <PagerStyle Position="Bottom" AlwaysVisible="True" Mode="NextPrevAndNumeric" Wrap="False"
        BackColor="White" Font-Size="Large" />
</telerik:RadGrid>


Each item can have 0 or more children.  When I reorder the columns, the root level entries (indicated as "Parent Col Val" below) are reordered, but the child column values (e.g., "Child Col Val") remain in the order in the grid defintion.  For example, if I have the initial layout defined as:

Col A        | Col B        | Col C
Parent A Val | Parent B Val | Parent C Val
Child A Val  | Child B Val  | Child C Val
Child A Val  | Child B Val  | Child C Val
Parent A Val | Parent B Val | Parent C Val

I then reorder the columns.  While the parent values reorder properly, the child ones do not.

Col B        | Col A        | Col C
Parent B Val | Parent A Val | Parent C Val
Child A Val  | Child B Val  | Child C Val
Child A Val  | Child B Val  | Child C Val
Parent B Val | Parent A Val | Parent C Val

This also occurs when I the saved grid settings are reloaded during Page_init (e.g., the parent items are ordered in the saved order, but the child columns are ordered as they're defined).  Attached are screenshots showing the grid before and after the columns are reordered to better describe the behavior I'm experiencing.

Is this a bug w/ the grid?  I would expect that self-referencing grids would automatically reorder the child tables as well.  If this isn't a bug, what is required in order for the columns to be ordered properly?

6 Answers, 1 is accepted

Sort by
0
Matt
Top achievements
Rank 1
answered on 27 Dec 2013, 10:19 PM
I've made some progress on manually moving the detail columns when I apply user settings, but have only been successful in getting the first child level formatted; any 3rd level (or greater) tables remain as defined.  The code I'm using is as follows:

private void ApplyUserSettings()
{
    if (!CachedActivatorData.UseAssistiveTechnology)
    {
        TelerikGridHelper helper = new TelerikGridHelper();
        helper.LoadSettings(grdNotes, string.Format("GridState_Activator_Notes_{0}", AuthenticationTicket.UserId));
    }
 
    //call this here for when loading the grid on tab click
    //traverse through the master grid and hide any child columns that need hiding
    for (int i = 0; i < grdNotes.MasterTableView.DetailTables.Count; i++)
    {
        FormatDetailTable(grdNotes.MasterTableView, i);
    }
 }
 
public void FormatDetailTable(GridTableView parentTable, int i)
{
 
    for (int x = 0; x < parentTable.DetailTables[i].Columns.Count; x++)
    {
        string columnName = grdNotes.MasterTableView.DetailTables[i].Columns[x].UniqueName;
        parentTable.DetailTables[i].Columns[x].Display = parentTable.Columns.FindByUniqueNameSafe(columnName).Display;
 
        int parentOrderIndex = grdNotes.MasterTableView.Columns.FindByUniqueNameSafe(columnName).OrderIndex;
 
        if (parentOrderIndex != grdNotes.MasterTableView.DetailTables[i].Columns[x].OrderIndex)
        {
            grdNotes.MasterTableView.DetailTables[i].Columns[x].OrderIndex = parentOrderIndex;
        }
 
        if (parentTable.DetailTables[i].DetailTables.Count > 0)
        {
            for (int y = 0; y < parentTable.DetailTables[i].DetailTables.Count; y++)
            {
                // FormatDetailTable(parentTable.DetailTables[i], y);
            }
        }
    }
}

I tried doing a recursive call (shown in the commented out line calling FormatDetailTable), but that just led to an infinite loop as it seems that all tables have a detail table.

What property (or series of properties) can I use to traverse the detail table structures so I can manually reorder the columns based on the master table view?
0
Matt
Top achievements
Rank 1
answered on 31 Dec 2013, 02:52 AM
Based on what I found here, I implemented the following.  However, nothing happens (e.g., the columns remain out of the correct order).

public void FormatDetailTable(GridTableView parentTable)
{
 
    foreach (GridNestedViewItem nestedViewItem in parentTable.GetItems(GridItemType.NestedView))
    {
        // you should skip the items if not expanded, or tables not bound
        if (nestedViewItem.NestedTableViews.Length > 0)
        {
            // now you can access: nestedViewItem.NestedTableViews[0].Items, which will be the DataItems of this nested table
 
            for (int x = 0; x < grdNotes.Columns.Count; x++)
            {
                parentTable.Columns.FindByUniqueNameSafe(grdNotes.Columns[x].UniqueName).Display = grdNotes.Columns[x].Display;
                parentTable.Columns.FindByUniqueNameSafe(grdNotes.Columns[x].UniqueName).OrderIndex = grdNotes.Columns[x].OrderIndex;
            }                   
             
            // then make recursive call
            FormatDetailTable(nestedViewItem.NestedTableViews[0]);
 
            // above [0] stands for the first table in the hierarchy, since Telerik RadGrid supports multiple tables at a level
        }
    }
}

I have had luck in getting the first level of tables' columns to reorder properly (using the previously posted code), but not the second or more.

I ask again:  What properties should I be referencing?  Also, should it be when IsPostPack == true or IsPostBack == false?  (Or should I key it off the grid.Notes.Count value?)

Furthermore, why doesn't this occur automatically for self-referencing hierarchical tables?!?
0
Viktor Tachev
Telerik team
answered on 02 Jan 2014, 01:05 PM
Hi Matt,

Self-referencing hierarchy is not supported in RadGrid. If you need to present such hierarchical relations I would suggest using RadTreeList control as it is designed to handle self-referencing hierarchy.

Online demo illustrating the functionality of the control is available here.

Regards,
Viktor Tachev
Telerik
If you want to get updates on new releases, tips and tricks and sneak peeks at our product labs directly from the developers working on the RadControls for ASP.NET AJAX, subscribe to the blog feed now.
0
Matt
Top achievements
Rank 1
answered on 02 Jan 2014, 02:27 PM
According to your RadGrid documentation, self-referencing hierarchy is supported.

I ask again:  How do I get the columns for *all* child tables (at all levels, not just the first child level) to match up with the master view columns?
0
Viktor Tachev
Telerik team
answered on 07 Jan 2014, 09:11 AM
Hi Matt,

Thank you for writing back.

What I meant in my previous post was that self-referencing hierarchy is a custom scenario. The help article illustrates an approach for implementing such functionality, however it is not available out-of-the-box for RadGrid and needs to be implemented manually.

This said it is highly recommended to use RadTreeList control in cases where you need self-referencing hierarchy.

Regards,
Viktor Tachev
Telerik
If you want to get updates on new releases, tips and tricks and sneak peeks at our product labs directly from the developers working on the RadControls for ASP.NET AJAX, subscribe to the blog feed now.
0
Matt
Top achievements
Rank 1
answered on 08 Jan 2014, 02:56 PM
Ahhh....thanks for the clarification; that's a relief!  We'll take a look at the treelist for our next release since we're too close to finishing our dev cycle for our current one.  Thanks again.
Tags
Grid
Asked by
Matt
Top achievements
Rank 1
Answers by
Matt
Top achievements
Rank 1
Viktor Tachev
Telerik team
Share this question
or