Hi,
I'm creating a table completely programtically, creating all columns, rows and textboxes programatically and it works fine. But if I assign styles rules to the textboxes it needs a very long time render the report, depending on the number of objects. It seems that the rendering time increases exponentially.
I'm creating a table completely programtically, creating all columns, rows and textboxes programatically and it works fine. But if I assign styles rules to the textboxes it needs a very long time render the report, depending on the number of objects. It seems that the rendering time increases exponentially.
4 Answers, 1 is accepted
0
Jasper
Top achievements
Rank 1
answered on 04 Oct 2010, 03:27 PM
I found out that the StyleSheet.Add()/StyleSheet.AddRange() method is the problem. If I add one or more styles rules (with style selector) using Add()/AddRange() it takes a long time to render the report, also if the styles rules are not applied to any object of the report.
Strangely it does not have any serious performance impact if I add a descendant selector to the report.
Strangely it does not have any serious performance impact if I add a descendant selector to the report.
0
Jasper
Top achievements
Rank 1
answered on 04 Oct 2010, 08:49 PM
I've created a simplified version to illustrate my approach.
using
System;
using
System.Collections.Generic;
using
System.Data;
using
System.Data.SqlClient;
using
System.Drawing;
using
System.Text;
using
Telerik.Reporting;
using
Telerik.Reporting.Drawing;
namespace
WindowsFormsApplication1
{
/// <summary>
/// Summary description for Report1.
/// </summary>
public
partial
class
Report1 : Telerik.Reporting.Report
{
public
Report1()
{
//
// Required for telerik Reporting designer support
//
InitializeComponent();
}
private
void
Report1_ItemDataBinding(
object
sender, EventArgs e)
{
Unit globalRowHeight =
new
Unit(1d, UnitType.Cm);
DataTable data = GetData();
List<StyleRule> columnStyle =
new
List<StyleRule>();
#region
//Descendant style
StyleRule defaultTextBoxStyle =
new
StyleRule();
DescendantSelector descendantSelector =
new
DescendantSelector();
descendantSelector.Selectors.AddRange(
new
ISelector[]
{
new
TypeSelector(
typeof
(Table)),
new
TypeSelector(
typeof
(TextBox))
});
defaultTextBoxStyle.Selectors.AddRange(
new
ISelector[] { descendantSelector });
defaultTextBoxStyle.Style.BorderStyle.Default = BorderType.Solid;
defaultTextBoxStyle.Style.BorderWidth.Default =
new
Unit(0.15d, UnitType.Mm);
defaultTextBoxStyle.Style.Color = Color.Red;
defaultTextBoxStyle.Style.Font.Bold =
true
;
defaultTextBoxStyle.Style.Font.Name =
"Tahoma"
;
defaultTextBoxStyle.Style.TextAlign = HorizontalAlign.Left;
defaultTextBoxStyle.Style.VerticalAlign = VerticalAlign.Middle;
//Styles per col
for
(
int
i = 0; i < data.Columns.Count; i++)
{
StyleRule sr =
new
StyleRule();
sr.Selectors.Add(
new
StyleSelector(
"columnStyle_"
+ i));
sr.Style.BorderStyle.Default = BorderType.Solid;
sr.Style.BorderWidth.Default =
new
Unit(0.15d, UnitType.Mm);
sr.Style.Font.Name =
"Tahoma"
;
sr.Style.TextAlign = HorizontalAlign.Left;
sr.Style.VerticalAlign = VerticalAlign.Middle;
columnStyle.Add(sr);
}
//Styles for thead
StyleRule headerStyle =
new
StyleRule();
headerStyle.Selectors.Add(
new
StyleSelector(
"headerStyle"
));
headerStyle.Style.BorderStyle.Default = BorderType.Solid;
headerStyle.Style.BorderWidth.Default =
new
Unit(0.15d, UnitType.Mm);
headerStyle.Style.Font.Name =
"Tahoma"
;
headerStyle.Style.TextAlign = HorizontalAlign.Left;
headerStyle.Style.VerticalAlign = VerticalAlign.Middle;
#endregion
//Add styles
//This is slow
StyleSheet.AddRange(columnStyle.ToArray());
//This is slow too
StyleSheet.Add(headerStyle);
//This is fast
//StyleSheet.AddRange(new StyleRule[] { defaultTextBoxStyle });
Telerik.Reporting.Processing.Table processingTable =
(sender
as
Telerik.Reporting.Processing.Table);
if
(processingTable !=
null
)
processingTable.DataSource = data;
//Clear Table
table1.RowGroups.Clear();
table1.ColumnGroups.Clear();
table1.Body.Columns.Clear();
table1.Body.Rows.Clear();
TableGroup detailGroup =
new
TableGroup();
for
(
int
j = 0; j < data.Columns.Count; j++)
{
table1.Body.Columns.Add(
new
TableBodyColumn(
new
Unit(3.0d, UnitType.Cm)));
//Create TextBoxes for table header
Telerik.Reporting.TextBox headerTextBox =
new
Telerik.Reporting.TextBox
{
StyleName =
"headerStyle"
,
Value = data.Columns[j].ColumnName,
Size =
new
SizeU(
new
Unit(3.0d, UnitType.Cm), globalRowHeight)
};
//Add thead
TableGroup tableGroup =
new
TableGroup {ReportItem = headerTextBox};
table1.ColumnGroups.Add(tableGroup);
//Create TextBoxes
for
(
int
i = 0; i < data.Rows.Count; i++)
{
string
styleSheet =
"columnStyle_"
+ j;
Telerik.Reporting.TextBox textBox =
new
Telerik.Reporting.TextBox
{
StyleName = styleSheet,
Value = data.Rows[i][j].ToString(),
Size =
new
SizeU(
new
Unit(3.0d, UnitType.Cm), globalRowHeight)
};
table1.Body.SetCellContent(i, j, textBox);
}
}
// ReSharper disable ForCanBeConvertedToForeach
for
(
int
i = 0; i < data.Rows.Count; i++)
{
table1.Body.Rows.Add(
new
TableBodyRow(globalRowHeight));
detailGroup.ChildGroups.Add(
new
TableGroup());
}
// ReSharper restore ForCanBeConvertedToForeach
table1.RowGroups.Add(detailGroup);
}
//Get data table from northwind db
private
static
DataTable GetData()
{
DataSet ds =
new
DataSet();
StringBuilder sb =
new
StringBuilder();
sb.Append(
"Data Source=SQLSERVER;Initial Catalog=AdventureWorks;"
);
sb.Append(
"Integrated Security = true;"
);
StringBuilder query =
new
StringBuilder();
query.Append(
"SELECT TOP 300 [Name], [ProductNumber], [StandardCost], "
);
query.Append(
"[ListPrice], [SellStartDate] FROM "
);
query.Append(
"[AdventureWorks].[Production].[Product]"
);
using
(SqlConnection con =
new
SqlConnection(sb.ToString()))
{
SqlDataAdapter adapter =
new
SqlDataAdapter();
adapter.SelectCommand =
new
SqlCommand(query.ToString(), con);
adapter.Fill(ds);
}
return
ds.Tables[0];
}
}
}
0
Jasper
Top achievements
Rank 1
answered on 05 Oct 2010, 12:31 PM
Ok, I've written my own method to apply styles to an object. I simply iterate all style properties of a style rule and assign them one by one to the style properties of the respective object. This is incredibly faster than using style rules as recommended in the docs.
Hence it would be great if the setter of the style property could be made public in one of the upcoming releases of Telerik Reporting to combine ease of use and performance.
Kind Regards
Hence it would be great if the setter of the style property could be made public in one of the upcoming releases of Telerik Reporting to combine ease of use and performance.
Kind Regards
0
Hi Jasper,
We have a suspicion that the slowdown comes from the fact that you never invoke BeginInit() and EndInit(). This way all styles are re-added for every item, thus whenever you're making modifications to the definition styles you should invoke BeginInit() and EndInit() just like the Report Designer generates them in the InitializeComponent() method i.e.:
((System.ComponentModel.ISupportInitialize)(this)).BeginInit();
//your stylerules adding code here
((System.ComponentModel.ISupportInitialize)(this)).EndInit();
Greetings,
Steve
the Telerik team
We have a suspicion that the slowdown comes from the fact that you never invoke BeginInit() and EndInit(). This way all styles are re-added for every item, thus whenever you're making modifications to the definition styles you should invoke BeginInit() and EndInit() just like the Report Designer generates them in the InitializeComponent() method i.e.:
((System.ComponentModel.ISupportInitialize)(this)).BeginInit();
//your stylerules adding code here
((System.ComponentModel.ISupportInitialize)(this)).EndInit();
Greetings,
Steve
the Telerik team
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 Public Issue Tracking
system and vote to affect the priority of the items