To reproduce: run the attached project and toggle the checkbox in the header cell of the child template.
Workaround: use a custom GridCheckBoxHeaderCellElement
public partial class RadForm1 : Telerik.WinControls.UI.RadForm
{
public RadForm1()
{
InitializeComponent();
this.radGridView1.CreateCell += radGridView1_CreateCell;
DataTable dt = new DataTable();
dt.Columns.Add("CategoryId", typeof(int));
dt.Columns.Add("CategoryName", typeof(string));
dt.Columns.Add("ParentCategoryId", typeof(int));
dt.Rows.Add(1, "Category1", 0);
dt.Rows.Add(2, "Category2", 0);
dt.Rows.Add(3, "Category3", 0);
Random rand = new Random();
for (int i = 4; i < 20; i++)
{
dt.Rows.Add(i, "Category" + i, rand.Next(1, 4));
}
this.radGridView1.Relations.AddSelfReference(this.radGridView1.MasterTemplate, "CategoryId", "ParentCategoryId");
this.radGridView1.DataSource = dt;
this.radGridView1.AutoSizeColumnsMode = Telerik.WinControls.UI.GridViewAutoSizeColumnsMode.Fill;
GridViewTemplate childTemplate = CreateChildTemplate();
GridViewRelation relation = new GridViewRelation(
this.radGridView1.MasterTemplate,
childTemplate);
relation.ChildColumnNames.Add("CategoryId");
relation.ParentColumnNames.Add("CategoryId");
this.radGridView1.Relations.Add(relation);
}
private void radGridView1_CreateCell(object sender, GridViewCreateCellEventArgs e)
{
if (e.CellType == typeof(GridCheckBoxHeaderCellElement))
{
e.CellElement = new CustomGridCheckBoxHeaderCellElement(e.Column, e.Row);
}
}
private GridViewTemplate CreateChildTemplate()
{
GridViewTemplate childTemplate = new GridViewTemplate();
childTemplate.AutoGenerateColumns = false;
this.radGridView1.Templates.Add(childTemplate);
GridViewDecimalColumn decColumn = new GridViewDecimalColumn
{
Name = "CategoryId",
HeaderText = "CategoryId Id",
FieldName = "CategoryId",
IsVisible = false,
MinWidth = 100
};
childTemplate.Columns.Add(decColumn);
GridViewTextBoxColumn tbxColumn = new GridViewTextBoxColumn
{
Name = "RightName",
HeaderText = "Right Name",
FieldName = "RGT_NAME",
ReadOnly = true,
MinWidth = 100
};
childTemplate.Columns.Add(tbxColumn);
GridViewCheckBoxColumn chkxColumn = new GridViewCheckBoxColumn
{
Name = "Checkbox",
EnableHeaderCheckBox = true,
FieldName = "HasAccess",
};
childTemplate.Columns.Add(chkxColumn);
childTemplate.AutoSizeColumnsMode = GridViewAutoSizeColumnsMode.Fill;
return childTemplate;
}
public class CustomGridCheckBoxHeaderCellElement : GridCheckBoxHeaderCellElement
{
public CustomGridCheckBoxHeaderCellElement(GridViewColumn column, GridRowElement row) : base(column, row)
{
}
public bool SuspendProcessingToggleStateChanged
{
get
{
FieldInfo fi = typeof(GridCheckBoxHeaderCellElement).GetField("suspendProcessingToggleStateChanged", BindingFlags.NonPublic | BindingFlags.Instance);
return (bool)fi.GetValue(this);
}
set
{
FieldInfo fi = typeof(GridCheckBoxHeaderCellElement).GetField("suspendProcessingToggleStateChanged", BindingFlags.NonPublic | BindingFlags.Instance);
fi.SetValue(this, value);
}
}
public bool ShouldCheckDataRows
{
get
{
FieldInfo fi = typeof(GridCheckBoxHeaderCellElement).GetField("shouldCheckDataRows", BindingFlags.NonPublic | BindingFlags.Instance);
return (bool)fi.GetValue(this);
}
set
{
FieldInfo fi = typeof(GridCheckBoxHeaderCellElement).GetField("shouldCheckDataRows", BindingFlags.NonPublic | BindingFlags.Instance);
fi.SetValue(this, value);
}
}
protected override void checkbox_ToggleStateChanged(object sender, StateChangedEventArgs args)
{
if (SuspendProcessingToggleStateChanged)
{
return;
}
if (this.ViewTemplate != null && !this.ViewTemplate.IsSelfReference && !this.MasterTemplate.IsSelfReference)
{
this.MasterTemplate.BeginUpdate();
}
else
{
this.TableElement.BeginUpdate();
}
object valueState = DBNull.Value;
if (args.ToggleState == ToggleState.On)
{
valueState = true;
}
else if (args.ToggleState == ToggleState.Off)
{
valueState = false;
}
else if (args.ToggleState == ToggleState.Indeterminate)
{
valueState = null;
}
RaiseToggleStateEvent();
if (!ShouldCheckDataRows)
{
if (this.ViewTemplate != null && !this.ViewTemplate.IsSelfReference && !this.MasterTemplate.IsSelfReference)
{
this.MasterTemplate.EndUpdate(true, new DataViewChangedEventArgs(ViewChangedAction.DataChanged));
}
return;
}
this.GridViewElement.EditorManager.EndEdit();
this.TableElement.BeginUpdate();
this.MasterTemplate.MasterViewInfo.TableSearchRow.SuspendSearch();
List<GridViewRowInfo> list = GetRowsToIterateOver();
foreach (GridViewRowInfo rowInfo in list)
{
GridViewGroupRowInfo groupRow = rowInfo as GridViewGroupRowInfo;
if (groupRow != null)
{
this.CheckAllCheckBoxInChildRows(groupRow, valueState);
}
else
{
rowInfo.Cells[this.ColumnIndex].Value = valueState;
}
}
this.MasterTemplate.MasterViewInfo.TableSearchRow.ResumeSearch();
this.TableElement.EndUpdate(false);
if (this.ViewTemplate != null && !this.ViewTemplate.IsSelfReference && !this.MasterTemplate.IsSelfReference)
{
this.MasterTemplate.EndUpdate(true, new DataViewChangedEventArgs(ViewChangedAction.DataChanged));
}
else
{
this.TableElement.EndUpdate(false);
}
this.TableElement.Update(GridUINotifyAction.DataChanged);
}
private void CheckAllCheckBoxInChildRows(GridViewGroupRowInfo row, object state)
{
List<GridViewRowInfo> list = new List<GridViewRowInfo>();
foreach (GridViewRowInfo rowInfo in row.ChildRows)
{
list.Add(rowInfo);
}
foreach (GridViewRowInfo rowInfo in list)
{
GridViewGroupRowInfo groupInfo = rowInfo as GridViewGroupRowInfo;
if (groupInfo != null)
{
this.CheckAllCheckBoxInChildRows(groupInfo, state);
}
else
{
rowInfo.Cells[this.ColumnIndex].Value = state;
}
}
}
private List<GridViewRowInfo> GetRowsToIterateOver()
{
if (this.ViewTemplate != null && this.ViewTemplate.IsSelfReference)
{
PrintGridTraverser traverser = new PrintGridTraverser(this.ViewInfo);
List<GridViewRowInfo> result = new List<GridViewRowInfo>();
while (traverser.MoveNext())
{
if (traverser.Current is GridViewDataRowInfo)
{
result.Add(traverser.Current);
}
}
return result;
}
return new List<GridViewRowInfo>(this.ViewInfo.Rows);
}
}
}