Performance Tips and Tricks
RadSpreadProcessing allows you to prepare and modify tabular data. Even though the library was built with performance in mind, working with large amounts of data slows it down. This article will help you get the most from the component in terms of performance.
Reduce Layout Updates Frequency
Calculating the layout is an operation computing the width of each column and the height of each row, the size of the text contained in the cells and many other elements, which are used for positioning the UI. The layout update is triggered each time a property is changed and thus is a fairly heavy operation.
Internally there are many mechanisms used to lower the number of calculations, but sometimes they are not enough. For example, if you want to generate a document and then show it, you do not need to trigger any layout updates other than the one after you finish creating the document. The code snippet in Example 1 shows how the layout updates can be suspended and then resumed after document generation is completed.
Example 1: Suspend layout updates
Workbook workbook = new Workbook();
workbook.SuspendLayoutUpdate();
// The code which generates the document
workbook.ResumeLayoutUpdate();
Note that if an exception is thrown between the two method calls, the resuming of the layout update will not be performed and the UI will stop updating. You could ensure the layout update will be resumed whatever happens using UpdateScope. The code snippet in Example 2 demonstrates how to use it.
Example 2: Suspend layout updates in UndoScope
Workbook workbook = new Workbook();
using (new UpdateScope(workbook.SuspendLayoutUpdate, workbook.ResumeLayoutUpdate))
{
// The code which generates the document
}
Reduce the Number of Undo Steps
Preserving information about the steps in the undo stack is usually not a time consuming operation, but even the lightest operation performed thousands of times may slow down your application. If you do not need to preserve each step in the document generation process as a separate undo step, you can simply combine a series of actions into one undo step. For example, if you want to set background color to the even rows in your table you have to set the fill for each row separately. This way each background setting will be preserved as a separate undo step. To combine them in a single undo step you can use the code in Example 3.
Example 3: Combine steps in undo group
Workbook workbook = new Workbook();
workbook.History.BeginUndoGroup();
// The code which generates the document
workbook.History.EndUndoGroup();
Note that if an exception is thrown between the two method calls, the ending of the undo group will not be performed, all the following actions will not be added to the history either and the UI will stop updating. You could ensure that whatever happens the undo group will be closed using UpdateScope. The code snippet in Example 4 demonstrates how to use it.
Example 4: Combine steps in undo group using UndoScope
Workbook workbook = new Workbook();
using (new UpdateScope(workbook.History.BeginUndoGroup, workbook.History.EndUndoGroup))
{
// The code which generates the document
}
Disabling History
As you already know from the Reduce the Number of Undo Steps section, preserving the history steps can lower the performance of RadSpreadProcessing. If you do not want to preserve History while generating your document, you can simply turn the feature off. It can be easily switched on and off through the IsEnabled Boolean property of the history like shown in Example 5.
Example 5: Disable history
workbook.History.IsEnabled = false;
// The code which generates the document
workbook.History.IsEnabled = true;
If an exception is thrown before enabling the history, it will not be enabled and the subsequent history steps will not be preserved. To ensure that the history will be enabled, you can use the UpdateScope class. Example 6 shows how this can be achieved.
Example 6: Disable and enable history using UndoScope
using (new UpdateScope(
() => { workbook.History.IsEnabled = false; },
() => { workbook.History.IsEnabled = true; }))
{
// The code which generates the document
}
Apply Values or Formatting on Large Range at Once
Setting the same values to thousands of cells one by one takes more time than setting the same values to an entire cell range. A CellRange can be created using the row and column indices of the start and end cells.
public CellRange(int fromRowIndex, int fromColumnIndex, int toRowIndex, int toColumnIndex)
Avoid Using the Additional Calculations Options Provided by the Shapes and Images
When setting the properties of an image you have created, you have to keep in mind that some of the members may cause recalculation of other properties in order to make the images more convenient to use in a UI context. You can read more about what calculation are performed in the Shapes and Images article. If you are generating a document from scratch, the recalculation of other properties will most likely be an unnecessary burden for your application. In this case it is advisable to use the properties of the shape classes:
Width
Height
RotationAngle
You should avoid using the methods for setting the same properties with the adjustCellIndex parameter set to true:
SetWidth()
SetHeight()
SetRotationAngle()
Avoid Cell Value Type Parsing
When setting values to cells, the cell value type is determined by an internal parsing mechanism. If you are sure what cell value type should be produced by the passed value, set it specifically. This will bypass the parsing and increase the performance of the application.
The easiest way to achieve this is by using the SetValue() overload with the respective CLR type (DateTime, Double, etc.) or in the case of formula value type and text value type - the SetValueAsFormula() and SetValueAsText() methods respectively.
More information regarding cell value types is available in the Cell Value Types article.