Hello,
A grid was dynamically created with 2 Rad combobox controls and 14 Rad numeric controls as columns. As more rows are added to the grid control and placed in edit mode, the creation of the new rows on the grid become slower. Basically, when the grid gets to about 20 rows the time required to add the new row and place all rows into edit mode becomes unacceptable. Also, since the comboboxes are related, the time it takes to load items within the second combo box gets slower.
I realize that adding RAD controls to the grid and placing them in edit mode adds complexity to the creation of the page, especially when all rows are placed in edit mode. I would really like to get this resolved since our requirement is to be able to have all rows in edit mode and provide the capability to quickly enter data without a performance hit.
Provided is sample code of how the issue is created. Any help in resolving the performance issues would be appreciated. You will notice that when you click on the Add button and continue to add rows to the page, the process gets slower and slower.
A grid was dynamically created with 2 Rad combobox controls and 14 Rad numeric controls as columns. As more rows are added to the grid control and placed in edit mode, the creation of the new rows on the grid become slower. Basically, when the grid gets to about 20 rows the time required to add the new row and place all rows into edit mode becomes unacceptable. Also, since the comboboxes are related, the time it takes to load items within the second combo box gets slower.
I realize that adding RAD controls to the grid and placing them in edit mode adds complexity to the creation of the page, especially when all rows are placed in edit mode. I would really like to get this resolved since our requirement is to be able to have all rows in edit mode and provide the capability to quickly enter data without a performance hit.
Provided is sample code of how the issue is created. Any help in resolving the performance issues would be appreciated. You will notice that when you click on the Add button and continue to add rows to the page, the process gets slower and slower.
<%@ Page Language="C#" AutoEventWireup="true" CodeFile="Default4.aspx.cs" Inherits="Default4" %>
<!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.0 Transitional//EN" "http://www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dtd">
<
html
xmlns
=
"http://www.w3.org/1999/xhtml"
>
<
head
runat
=
"server"
>
<
title
></
title
>
</
head
>
<
body
>
<
form
id
=
"form1"
runat
=
"server"
>
<
div
>
<
asp:Button
ID
=
"ButtonAdd"
runat
=
"server"
Text
=
"Add Row"
OnClick
=
"ButtonAdd_Click"
/>
<
asp:placeholder
ID
=
"Placeholder1"
runat
=
"server"
></
asp:placeholder
>
</
div
>
<
telerik:RadScriptManager
runat
=
"server"
ID
=
"RadScriptManager1"
/>
<
telerik:RadAjaxManager
runat
=
"server"
ID
=
"RadAjaxManager1"
/>
</
form
>
</
body
>
</
html
>
using
System;
using
System.Collections.Generic;
using
System.Linq;
using
System.Web;
using
System.Web.UI;
using
System.Web.UI.WebControls;
using
Telerik.Web.UI;
public
partial
class
Default4 : System.Web.UI.Page
{
private
List<ProjectItem> ProjectItemList
{
get
{
if
(ViewState[
"ProjectItemList"
] ==
null
)
{
ProjectItem projectItem =
new
ProjectItem();
List<ProjectItem> list =
new
List<ProjectItem>();
list.Add(projectItem);
ViewState[
"ProjectItemList"
] = list;
}
return
(List<ProjectItem>)ViewState[
"ProjectItemList"
];
}
set
{ ViewState[
"ProjectItemList"
] = value; }
}
private
List<ProjectCode> ProjectCodeList
{
get
{
if
(ViewState[
"ProjectCodeList"
] ==
null
)
{
List<ProjectCode> list =
new
List<ProjectCode>();
list.Add(
new
ProjectCode(
"P1"
,
"Project 1"
));
list.Add(
new
ProjectCode(
"P2"
,
"Project 2"
));
list.Add(
new
ProjectCode(
"P3"
,
"Project 3"
));
list.Add(
new
ProjectCode(
"P4"
,
"Project 4"
));
list.Add(
new
ProjectCode(
"P5"
,
"Project 5"
));
list.Add(
new
ProjectCode(
"P6"
,
"Project 6"
));
list.Add(
new
ProjectCode(
"P7"
,
"Project 7"
));
ViewState[
"ProjectCodeList"
] = list;
}
return
(List<ProjectCode>)ViewState[
"ProjectCodeList"
];
}
set
{ ViewState[
"ProjectCodeList"
] = value; }
}
private
List<ChargeCode> ChargeCodeList
{
get
{
if
(ViewState[
"ChargeCodeList"
] ==
null
)
{
List<ChargeCode> list =
new
List<ChargeCode>();
list.Add(
new
ChargeCode(
"C1"
,
"Charge Code A"
,
"P1"
));
list.Add(
new
ChargeCode(
"C2"
,
"Charge Code B"
,
"P1"
));
list.Add(
new
ChargeCode(
"C3"
,
"Charge Code C"
,
"P1"
));
list.Add(
new
ChargeCode(
"C4"
,
"Charge Code D"
,
"P2"
));
list.Add(
new
ChargeCode(
"C5"
,
"Charge Code E"
,
"P2"
));
list.Add(
new
ChargeCode(
"C6"
,
"Charge Code F"
,
"P3"
));
list.Add(
new
ChargeCode(
"C7"
,
"Charge Code G"
,
"P3"
));
list.Add(
new
ChargeCode(
"C8"
,
"Charge Code H"
,
"P3"
));
list.Add(
new
ChargeCode(
"C9"
,
"Charge Code I"
,
"P4"
));
list.Add(
new
ChargeCode(
"C10"
,
"Charge Code J"
,
"P4"
));
list.Add(
new
ChargeCode(
"C11"
,
"Charge Code K"
,
"P5"
));
list.Add(
new
ChargeCode(
"C12"
,
"Charge Code L"
,
"P5"
));
list.Add(
new
ChargeCode(
"C13"
,
"Charge Code M"
,
"P6"
));
list.Add(
new
ChargeCode(
"C14"
,
"Charge Code N"
,
"P6"
));
list.Add(
new
ChargeCode(
"C15"
,
"Charge Code O"
,
"P7"
));
list.Add(
new
ChargeCode(
"C16"
,
"Charge Code P"
,
"P7"
));
list.Add(
new
ChargeCode(
"C17"
,
"Charge Code Q"
,
"P7"
));
ViewState[
"ChargeCodeList"
] = list;
}
return
(List<ChargeCode>)ViewState[
"ChargeCodeList"
];
}
set
{ ViewState[
"ChargeCodeList"
] = value; }
}
protected
RadGrid Grid
{
get
;
set
;
}
protected
override
void
OnInit(EventArgs e)
{
base
.OnInit(e);
this
.InitializeGrid();
}
protected
void
Page_Load(
object
sender, EventArgs e)
{
InitializeAjaxManager();
// Set grid items in edit mode.
Grid.EditIndexes.Clear();
for
(
int
i = 0; i < ProjectItemList.Count; i++)
{
Grid.EditIndexes.Add(i);
}
}
private
void
InitializeAjaxManager()
{
RadAjaxManager ajaxManager = RadAjaxManager.GetCurrent(Page);
if
(ajaxManager ==
null
)
return
;
ajaxManager.AjaxSettings.AddAjaxSetting(ButtonAdd, Grid);
ajaxManager.AjaxSettings.AddAjaxSetting(Grid, Grid);
}
private
void
InitializeGrid()
{
GridBoundColumn boundColumn;
GridNumericColumn numericColumn;
GridDropDownColumn dropDownColumn;
Grid =
new
RadGrid();
// Setup required event handlers.
Grid.NeedDataSource +=
new
GridNeedDataSourceEventHandler(Grid_NeedDataSource);
Grid.ItemCreated +=
new
GridItemEventHandler(Grid_ItemCreated);
Grid.ItemDataBound +=
new
GridItemEventHandler(Grid_ItemDataBound);
Grid.ID =
"GridProject"
;
Grid.AllowSorting =
false
;
Grid.AutoGenerateColumns =
false
;
Grid.AllowMultiRowEdit =
true
;
Grid.Width = Unit.Percentage(100);
Grid.ClientSettings.Selecting.AllowRowSelect =
false
;
Grid.MasterTableView.DataKeyNames =
new
string
[] {
"Id"
};
Grid.MasterTableView.Name =
"MasterTableViewProject"
;
Grid.MasterTableView.DataMember =
"ProjectItem"
;
Grid.MasterTableView.EditMode = GridEditMode.InPlace;
// Initialize the grid columns.
boundColumn =
new
GridBoundColumn();
Grid.MasterTableView.Columns.Add(boundColumn);
boundColumn.Visible =
false
;
boundColumn.UniqueName =
"Id"
;
boundColumn.DataField =
"Id"
;
boundColumn.HeaderText =
"Id"
;
dropDownColumn =
new
GridDropDownColumn();
Grid.MasterTableView.Columns.Add(dropDownColumn);
dropDownColumn.Visible =
true
;
dropDownColumn.UniqueName =
"ComboBoxProjectCode"
;
dropDownColumn.DataField =
"ProjectCode"
;
dropDownColumn.HeaderText =
"Project Code"
;
dropDownColumn.HeaderStyle.Width = Unit.Pixel(200);
dropDownColumn.ItemStyle.Width = Unit.Pixel(200);
dropDownColumn.DropDownControlType = GridDropDownColumnControlType.RadComboBox;
dropDownColumn =
new
GridDropDownColumn();
Grid.MasterTableView.Columns.Add(dropDownColumn);
dropDownColumn.Visible =
true
;
dropDownColumn.UniqueName =
"ComboBoxChargeCode"
;
dropDownColumn.DataField =
"ChargeCode"
;
dropDownColumn.HeaderText =
"Charge Code"
;
dropDownColumn.HeaderStyle.Width = Unit.Pixel(200);
dropDownColumn.ItemStyle.Width = Unit.Pixel(200);
dropDownColumn.DropDownControlType = GridDropDownColumnControlType.RadComboBox;
for
(
int
i = 0; i < 14; i++)
{
numericColumn =
new
GridNumericColumn();
Grid.MasterTableView.Columns.Add(numericColumn);
numericColumn.Visible =
true
;
numericColumn.UniqueName =
"D"
+ i.ToString();
numericColumn.DataField =
"D"
+ i.ToString();
numericColumn.HeaderText =
"D"
+ i.ToString();
numericColumn.DecimalDigits = 2;
numericColumn.HeaderStyle.Width = Unit.Pixel(50);
numericColumn.HeaderStyle.HorizontalAlign = HorizontalAlign.Right;
numericColumn.ItemStyle.Width = Unit.Pixel(50);
numericColumn.ItemStyle.HorizontalAlign = HorizontalAlign.Right;
numericColumn.ReadOnly =
false
;
}
Placeholder1.Controls.Add(
this
.Grid);
}
void
Grid_NeedDataSource(
object
sender, GridNeedDataSourceEventArgs e)
{
Grid.DataSource = ProjectItemList;
}
void
Grid_ItemCreated(
object
sender, GridItemEventArgs e)
{
if
((e.Item.IsInEditMode) && (e.Item
is
GridDataItem))
{
GridDataItem gridDataItem = e.Item
as
GridDataItem;
RadComboBox comboBoxProjectCode;
comboBoxProjectCode = ((GridDropDownListColumnEditor)gridDataItem.EditManager.GetColumnEditor(
"ComboBoxProjectCode"
)).ComboBoxControl;
comboBoxProjectCode.EmptyMessage =
"Select Project Code"
;
comboBoxProjectCode.AutoPostBack =
true
;
comboBoxProjectCode.EnableLoadOnDemand =
true
;
comboBoxProjectCode.MarkFirstMatch =
true
;
comboBoxProjectCode.Filter = RadComboBoxFilter.StartsWith;
comboBoxProjectCode.Width = Unit.Pixel(200);
comboBoxProjectCode.DropDownWidth = Unit.Pixel(300);
comboBoxProjectCode.SelectedIndexChanged +=
new
RadComboBoxSelectedIndexChangedEventHandler(comboBoxProjectCode_SelectedIndexChanged);
comboBoxProjectCode.ItemsRequested +=
new
RadComboBoxItemsRequestedEventHandler(comboBoxProjectCode_ItemsRequested);
RadComboBox comboBoxChargeCode;
comboBoxChargeCode = ((GridDropDownListColumnEditor)gridDataItem.EditManager.GetColumnEditor(
"ComboBoxChargeCode"
)).ComboBoxControl;
comboBoxChargeCode.Width = Unit.Pixel(200);
comboBoxChargeCode.EmptyMessage =
"Select Charge Code"
;
comboBoxChargeCode.EnableLoadOnDemand =
true
;
comboBoxChargeCode.ItemsRequested +=
new
RadComboBoxItemsRequestedEventHandler(comboBoxChargeCode_ItemsRequested);
// Set data values for the combo box.
if
(gridDataItem.DataItem !=
null
)
{
if
(!
string
.IsNullOrEmpty(((ProjectItem)gridDataItem.DataItem).ProjectCode))
{
comboBoxProjectCode.Items.Add(
new
RadComboBoxItem(((ProjectItem)gridDataItem.DataItem).ProjectName, ((ProjectItem)gridDataItem.DataItem).ProjectCode));
}
if
(!
string
.IsNullOrEmpty(((ProjectItem)gridDataItem.DataItem).ChargeCodeName))
{
comboBoxChargeCode.Items.Add(
new
RadComboBoxItem(((ProjectItem)gridDataItem.DataItem).ChargeCodeName, ((ProjectItem)gridDataItem.DataItem).ChargeCode));
}
}
}
}
void
Grid_ItemDataBound(
object
sender, GridItemEventArgs e)
{
if
((e.Item.IsInEditMode) && (e.Item
is
GridDataItem))
{
GridDataItem gridDataItem = e.Item
as
GridDataItem;
GridNumericColumnEditor columnEditor;
for
(
int
i = 0; i < 14; i++)
{
columnEditor = (GridNumericColumnEditor)gridDataItem.EditManager.GetColumnEditor(
"D"
+ i.ToString());
columnEditor.NumericTextBox.Width = Unit.Percentage(100);
columnEditor.NumericTextBox.EnabledStyle.HorizontalAlign = HorizontalAlign.Right;
columnEditor.NumericTextBox.MinValue = 0;
columnEditor.NumericTextBox.NumberFormat.DecimalDigits = 2;
columnEditor.NumericTextBox.NumberFormat.KeepTrailingZerosOnFocus =
true
;
columnEditor.NumericTextBox.NumberFormat.AllowRounding =
true
;
}
}
}
void
comboBoxProjectCode_SelectedIndexChanged(
object
sender, RadComboBoxSelectedIndexChangedEventArgs e)
{
GridDataItem gridDataItem = (sender
as
RadComboBox).NamingContainer
as
GridDataItem;
RadComboBox comboBoxChargeCode;
comboBoxChargeCode = ((GridDropDownListColumnEditor)gridDataItem.EditManager.GetColumnEditor(
"ComboBoxChargeCode"
)).ComboBoxControl;
if
(comboBoxChargeCode !=
null
)
{
comboBoxChargeCode.Text =
string
.Empty;
comboBoxChargeCode.SelectedValue =
string
.Empty;
}
}
void
comboBoxProjectCode_ItemsRequested(
object
sender, RadComboBoxItemsRequestedEventArgs e)
{
RadComboBox comboBoxProjectCode = sender
as
RadComboBox;
comboBoxProjectCode.Items.Clear();
foreach
(ProjectCode projectCode
in
ProjectCodeList)
{
comboBoxProjectCode.Items.Add(
new
RadComboBoxItem(projectCode.Name, projectCode.Code));
}
}
void
comboBoxChargeCode_ItemsRequested(
object
sender, RadComboBoxItemsRequestedEventArgs e)
{
RadComboBox comboBoxChargeCode = sender
as
RadComboBox;
GridDataItem gridDataItem = comboBoxChargeCode.NamingContainer
as
GridDataItem;
RadComboBox comboBoxProjectCode;
comboBoxProjectCode = ((GridDropDownListColumnEditor)gridDataItem.EditManager.GetColumnEditor(
"ComboBoxProjectCode"
)).ComboBoxControl;
List<ChargeCode> list = ChargeCodeList.Where(code => code.ProjectCode == comboBoxProjectCode.SelectedValue).ToList();
comboBoxChargeCode.Items.Clear();
foreach
(ChargeCode chargeCode
in
list)
{
comboBoxChargeCode.Items.Add(
new
RadComboBoxItem(chargeCode.Name, chargeCode.Code));
}
}
protected
void
ButtonAdd_Click(
object
sender, EventArgs e)
{
for
(
int
i = 0; i < Grid.MasterTableView.Items.Count; i++)
{
GridDataItem gridDataItem = Grid.MasterTableView.Items[i];
if
(!Grid.MasterTableView.Items[i].IsInEditMode)
continue
;
// Persist existing entered data.
RadComboBox comboBoxProjectCode;
comboBoxProjectCode = ((GridDropDownListColumnEditor)gridDataItem.EditManager.GetColumnEditor(
"ComboBoxProjectCode"
)).ComboBoxControl;
ProjectItemList[i].ProjectCode = comboBoxProjectCode.SelectedValue;
ProjectItemList[i].ProjectName = comboBoxProjectCode.Text;
RadComboBox comboBoxChargeCode;
comboBoxChargeCode = ((GridDropDownListColumnEditor)gridDataItem.EditManager.GetColumnEditor(
"ComboBoxChargeCode"
)).ComboBoxControl;
ProjectItemList[i].ChargeCode = comboBoxChargeCode.SelectedValue;
ProjectItemList[i].ChargeCodeName = comboBoxChargeCode.Text;
GridNumericColumnEditor columnEditor;
for
(
int
j = 0; j < 14; j++)
{
columnEditor = (GridNumericColumnEditor)gridDataItem.EditManager.GetColumnEditor(
"D"
+ j.ToString());
ProjectItemList[i].DataList[j] = (
decimal
)columnEditor.NumericTextBox.Value;
}
}
ProjectItem projectItem =
new
ProjectItem();
ProjectItemList.Add(projectItem);
Grid.EditIndexes.Clear();
for
(
int
i = 0; i < ProjectItemList.Count; i++)
{
Grid.EditIndexes.Add(i);
}
Grid.Rebind();
}
[Serializable]
private
class
ProjectItem
{
public
ProjectItem()
{
DataList =
new
List<
decimal
>();
for
(
int
i = 0; i < 14; i++)
{
DataList.Add(0);
}
}
public
long
Id
{
get
;
set
;
}
public
string
ProjectCode
{
get
;
set
;
}
public
string
ProjectName
{
get
;
set
;
}
public
string
ChargeCode
{
get
;
set
;
}
public
string
ChargeCodeName
{
get
;
set
;
}
public
List<
decimal
> DataList
{
get
;
set
;
}
public
decimal
D0
{
get
{
return
DataList[0]; }
}
public
decimal
D1
{
get
{
return
DataList[1]; }
}
public
decimal
D2
{
get
{
return
DataList[2]; }
}
public
decimal
D3
{
get
{
return
DataList[3]; }
}
public
decimal
D4
{
get
{
return
DataList[4]; }
}
public
decimal
D5
{
get
{
return
DataList[5]; }
}
public
decimal
D6
{
get
{
return
DataList[6]; }
}
public
decimal
D7
{
get
{
return
DataList[7]; }
}
public
decimal
D8
{
get
{
return
DataList[8]; }
}
public
decimal
D9
{
get
{
return
DataList[9]; }
}
public
decimal
D10
{
get
{
return
DataList[10]; }
}
public
decimal
D11
{
get
{
return
DataList[11]; }
}
public
decimal
D12
{
get
{
return
DataList[12]; }
}
public
decimal
D13
{
get
{
return
DataList[13]; }
}
}
[Serializable]
private
class
ProjectCode
{
public
ProjectCode(
string
code,
string
name)
{
Code = code;
Name = name;
}
public
string
Code
{
get
;
set
;
}
public
string
Name
{
get
;
set
;
}
}
[Serializable]
private
class
ChargeCode
{
public
ChargeCode(
string
code,
string
name,
string
projectCode)
{
Code = code;
Name = name;
ProjectCode = projectCode;
}
public
string
Code
{
get
;
set
;
}
public
string
Name
{
get
;
set
;
}
public
string
ProjectCode
{
get
;
set
;
}
}
}