Environment: Visual Studio 2012 using UI for APS.NET AJAX Q2 2016
We are modelling a workflow process using the RadGrid. I have attached a model of what we are trying to represent, along with other screen shots.
Figure 1 contains the workflow model. The model consists of a main task (AEHF 10/20...) that has 3 sub tasks (Terminal 10/20..., Humvee 10/20..., and Shipping). The 2 of the 3 sub tasks have another layer of sub tasks below them. Any task that does not have children is represented as a bubble for each line item. We represent the tasks that do have children in two ways. 1st the task is displayed as a column that is expanded with collapse button along with the task name, each line item then represents the sub tasks of that task (Figure 1 & 4 shows all tasks expanded). 2nd the task is displayed collapsed along with a expand button and the task name, then each line item displays a bubble of the collapsed task, only that task is then displayed, not any of its sub tasks (see Figure 3, the Humvee task is collapsed). Tasks that have grand children are added as a GridGroupColumn, with is sub tasks (column) have a group name of its parent. Tasks that have children and not grand children are added as a TemplateColumn. Being that the workflows are dynamic this is done recursively (see code in AddTaskColumns). The grid is created in OnInit(), after the grid is defined, we then add the task columns 'AddTaskColumns'.
The problem. None of the tasks that have grand children are displayed as they were in the previous release. Figure 4 shows the display as it used to work, Figure 2 shows how it is now displayed. The names of the columns are changed during the OnGridItemCreated event handler (See code below). The issue is that the task that has grand children is not replacing the name, and is not adding the collapse button. Other example documentation I have found is saying that the GridGroupColumn shows up in OnGridItemCreated as a GridGroupHeaderItem, this is not the case, it is showing up as a GridHeaderItem. Any processing of that item (changing the name, and adding the button) is now showing up in the rendered display. As you can see in the OnGridItemCreated code below I added an if statement looking for GridGroupHeaderItem, the code never executes. I am able to change the name of the column by using the RadGridWorkflow.MasterTableView.ColumnGroups finding the correct column then changing it's .HeaderText property, but you can not add additional controls to it since it is not a control.
How can I get the expand/collapse button to be displayed again?
private void AddTaskColumns(WorkflowConfiguration task)
{
// Add group column if the task has grand children, acts as the Expanded column for this task.
if (task.HasGrandChildren())
{
// Make this a Group Column
GridColumnGroup group = new GridColumnGroup();
// Header Text is the only property of a column common between GridColumnGroup and GridColumn that the value can be determined
// in the OnItemCreated to be able to properly add the Expand/Collapse button as needed.
group.HeaderText = "Expanded-" + task.WorkflowID.ToString();
group.HeaderStyle.VerticalAlign = VerticalAlign.Top;
group.HeaderStyle.HorizontalAlign = HorizontalAlign.Center;
group.Name = "Group" + task.WorkflowID.ToString();
RadGridWorkflow.MasterTableView.ColumnGroups.Add(group);
if (task.ParentWorkflowConfiguration != null)
{
group.ParentGroupName =
task.ParentWorkflowConfiguration.WorkflowID.ToString();
}
// Add sub workflow tasks
foreach (WorkflowConfiguration subTask in
task.SubWorkflowConfigurations)
{
AddTaskColumns(subTask);
}
}
// Add expanded column if the task has children.
else if (task.HasSubTasks())
{
AlpsGridTemplateColumn expColumn = new AlpsGridTemplateColumn();
expColumn.ItemTemplate = new TaskButtonsTemplate(_workflowConfig, task, _functions, "Expanded");
expColumn.UniqueName = "Expanded" + task.WorkflowID.ToString();
expColumn.HeaderStyle.VerticalAlign = VerticalAlign.Bottom;
expColumn.HeaderStyle.HorizontalAlign = HorizontalAlign.Center;
// Header Text is the only property of a column common between GridColumnGroup and GridColumn that the value can be determined
// in the OnItemCreated to be able to properly add the Expand/Collapse button as needed.
expColumn.HeaderText = "Expanded-" + task.WorkflowID.ToString();
expColumn.AllowSorting = false;
expColumn.AllowFiltering = false;
expColumn.Groupable = false;
expColumn.Reorderable = false;
// Do some decent sizing for the amount of tasks/bubbles to show.
switch (task.SubWorkflowConfigurations.Count)
{
case 1:
case 2:
case 3:
case 4:
expColumn.HeaderStyle.Width = Unit.Pixel(100);
break;
case 7:
case 8:
case 9:
expColumn.HeaderStyle.Width = Unit.Pixel(100 + (task.SubWorkflowConfigurations.Count - 4) * 20);
break;
default:
expColumn.HeaderStyle.Width = Unit.Pixel(220);
break;
}
if (task.ParentWorkflowConfiguration != null)
{
expColumn.ColumnGroupName = "Group" + task.ParentWorkflowConfiguration.WorkflowID.ToString();
}
RadGridWorkflow.MasterTableView.Columns.Add(expColumn);
}
// Every task will have a Collapsed column, this will add the collapsed column.
AlpsGridTemplateColumn colColumn = new AlpsGridTemplateColumn();
colColumn.ItemTemplate = new TaskButtonsTemplate(_workflowConfig, task, _functions, "Collapsed");
colColumn.UniqueName = "Collapsed" + task.WorkflowID.ToString();
colColumn.HeaderStyle.VerticalAlign = VerticalAlign.Bottom;
colColumn.HeaderStyle.HorizontalAlign = HorizontalAlign.Center;
colColumn.HeaderStyle.Width = Unit.Pixel(100);
colColumn.HeaderText = "Collapsed-" + task.WorkflowID.ToString();
colColumn.AllowSorting = false;
colColumn.AllowFiltering = false;
colColumn.Groupable = false;
colColumn.Reorderable = false;
if (task.ParentWorkflowConfiguration != null)
{
colColumn.ColumnGroupName = "Group" + task.ParentWorkflowConfiguration.WorkflowID.ToString();
}
RadGridWorkflow.MasterTableView.Columns.Add(colColumn);
}
void OnGridItemCreated(object sender, GridItemEventArgs e)
{
if (e.Item is GridGroupHeaderItem)
{
System.Diagnostics.Debug.WriteLine("GridGroupHeaderItem");
}
if (e.Item is GridHeaderItem)
{
GridHeaderItem ghi = e.Item as GridHeaderItem;
foreach (GridTableHeaderCell tc in ghi.Cells)
{
int delimiterIndex = tc.Text.IndexOf('-');
int wfid;
if (delimiterIndex > -1 && int.TryParse(tc.Text.Substring(delimiterIndex + 1, tc.Text.Length - (delimiterIndex + 1)), out wfid))
{
WorkflowConfiguration task = _workflowConfig.FindTaskWithWorkFlowID(wfid);
if (task != null)
{
string state = tc.Text.Substring(0, delimiterIndex);
tc.Text = task.Name;
System.Web.UI.HtmlControls.HtmlGenericControl
createDiv = new System.Web.UI.HtmlControls.
HtmlGenericControl("div");
createDiv.Style.Add(HtmlTextWriterStyle.Width, "100%");
createDiv.Style.Add(HtmlTextWriterStyle.TextAlign,
"center");
createDiv.InnerHtml = task.Name;
if (task.HasSubTasks())
{
createDiv.Controls.Add(CreateHeaderButton(task, state));
}
tc.Controls.Add(createDiv);
}
}
}
}
}
protected virtual void CreateGrid()
{
RadGridWorkflow.ID = "AlpsRadGridWorkflow";
RadGridWorkflow.AllowCustomPaging = true;
RadGridWorkflow.AllowFilteringByColumn = true;
RadGridWorkflow.PageSize = 25;
RadGridWorkflow.ClientSettings.Selecting.AllowRowSelect = true;
RadGridWorkflow.ClientSettings.EnableAlternatingItems = true;
RadGridWorkflow.EnableViewState = true;
RadGridWorkflow.MasterTableView.NoDetailRecordsText = "No Records to Display";
RadGridWorkflow.MasterTableView.DataKeyNames = new string[] { "OperationalWorkflowItemID" };
RadGridWorkflow.MasterTableView.ClientDataKeyNames = new string[] { "OperationalWorkflowItemID" };
}
protected RadButton CreateHeaderButton(WorkflowConfiguration task, string state)
{
RadButton button = new RadButton();
button.AutoPostBack = true;
button.Image.ImageUrl = "~/Images/Menu/Empty.png";
button.Image.IsBackgroundImage = true;
button.CommandArgument = task.WorkflowID.ToString();
button.CausesValidation = false;
button.ButtonType = RadButtonType.StandardButton;
if (state == "Expanded")
{
button.ID = String.Format("RadButton{0}Collapse", task.WorkflowID);
button.CommandName = "Collapse";
button.ToolTip = String.Format("Collapse {0}", task.Name);
button.Icon.PrimaryIconCssClass = "rbPrevious";
}
else
{
button.ID = String.Format("RadButton{0}Expand", task.WorkflowID);
button.CommandName = "Expand";
button.ToolTip = String.Format("Expand {0}", task.Name);
button.Icon.PrimaryIconCssClass = "rbNext";
}
button.Click += RadButtonExpandCollapse_Click;
return button;
}
We have two classes derived from the base page, here is the code that is adding the grid columns that are not part of the hierarchy.
protected override void AddGridColumns()
{
AlpsGridBoundColumn terminalColumn = new AlpsGridBoundColumn();
terminalColumn.DataField = "Name";
terminalColumn.UniqueName = "Name";
terminalColumn.HeaderText = "Serial Number";
terminalColumn.HeaderStyle.VerticalAlign = VerticalAlign.Bottom;
terminalColumn.HeaderStyle.HorizontalAlign = HorizontalAlign.Center;
terminalColumn.HeaderStyle.Width = 150;
AlpsRadGridWorkflow.MasterTableView.Columns.Add(terminalColumn);
AlpsGridBoundColumn subComponentColumn = new AlpsGridBoundColumn();
subComponentColumn.DataField = "SubComponent";
subComponentColumn.UniqueName = "SubComponent";
subComponentColumn.HeaderText = "Sub-Component";
subComponentColumn.HeaderStyle.VerticalAlign = VerticalAlign.Bottom;
subComponentColumn.HeaderStyle.HorizontalAlign = HorizontalAlign.Center;
subComponentColumn.HeaderStyle.Width = 100;
AlpsRadGridWorkflow.MasterTableView.Columns.Add(subComponentColumn);
AlpsGridBoundColumn organizationColumn = new AlpsGridBoundColumn();
organizationColumn.DataField = "Owner";
organizationColumn.UniqueName = "Owner";
organizationColumn.HeaderText = "Owning Organization";
organizationColumn.HeaderStyle.VerticalAlign = VerticalAlign.Bottom;
organizationColumn.HeaderStyle.HorizontalAlign = HorizontalAlign.Center;
organizationColumn.HeaderStyle.Width = 180;
AlpsRadGridWorkflow.MasterTableView.Columns.Add(organizationColumn);
AlpsGridBoundColumn gainingOrganizationColumn = new AlpsGridBoundColumn();
gainingOrganizationColumn.DataField = "GainingOrganization";
gainingOrganizationColumn.UniqueName = "GainingOrganization";
gainingOrganizationColumn.HeaderText = "Gaining Organization";
gainingOrganizationColumn.HeaderStyle.VerticalAlign = VerticalAlign.Bottom;
gainingOrganizationColumn.HeaderStyle.HorizontalAlign = HorizontalAlign.Center;
gainingOrganizationColumn.HeaderStyle.Width = 180;
AlpsRadGridWorkflow.MasterTableView.Columns.Add(gainingOrganizationColumn);
AlpsGridDateTimeColumn startColumn = new AlpsGridDateTimeColumn();
startColumn.DataField = "StartDate";
startColumn.UniqueName = "StartDate";
startColumn.HeaderText = "Capture Date";
startColumn.HeaderStyle.VerticalAlign = VerticalAlign.Bottom;
startColumn.HeaderStyle.HorizontalAlign = HorizontalAlign.Center;
startColumn.DataFormatString = Constants.Format.DATE_FORMAT;
startColumn.Display = false;
AlpsRadGridWorkflow.MasterTableView.Columns.Add(startColumn);
AlpsGridDateTimeColumn endColumn = new AlpsGridDateTimeColumn();
endColumn.DataField = "EndDate";
endColumn.UniqueName = "EndDate";
endColumn.HeaderText = "Completion Date";
endColumn.HeaderStyle.VerticalAlign = VerticalAlign.Bottom;
endColumn.HeaderStyle.HorizontalAlign = HorizontalAlign.Center;
endColumn.CurrentFilterFunction = GridKnownFunction.IsNull;
endColumn.DataFormatString = Constants.Format.DATE_FORMAT;
AlpsRadGridWorkflow.MasterTableView.Columns.Add(endColumn);
AlpsGridCheckBoxColumn activeColumn = new AlpsGridCheckBoxColumn();
activeColumn.AllowFiltering = true;
activeColumn.DataField = "Active";
activeColumn.UniqueName = "Active";
activeColumn.HeaderText = "Active";
activeColumn.HeaderStyle.VerticalAlign = VerticalAlign.Bottom;
activeColumn.HeaderStyle.HorizontalAlign = HorizontalAlign.Center;
activeColumn.HeaderStyle.Width = Unit.Pixel(75);
activeColumn.CurrentFilterFunction = GridKnownFunction.EqualTo;
activeColumn.CurrentFilterValue = "true";
activeColumn.Display = false;
activeColumn.Visible = false;
AlpsRadGridWorkflow.MasterTableView.Columns.Add(activeColumn);
AlpsGridBoundColumn commentColumn = new AlpsGridBoundColumn();
commentColumn.DataField = "Comments";
commentColumn.UniqueName = "Comments";
commentColumn.HeaderText = "Comments";
commentColumn.HeaderStyle.VerticalAlign = VerticalAlign.Bottom;
commentColumn.HeaderStyle.HorizontalAlign = HorizontalAlign.Center;
commentColumn.HeaderStyle.Width = 150;
commentColumn.Display = false;
AlpsRadGridWorkflow.MasterTableView.Columns.Add(commentColumn);
}