Improving Performance by Suspending the Layout
In This Topic
One way to improve the performance of the control, if there are changes to many cells, is to hold the repainting until all the changes are complete. By holding the repainting (suspending the layout) while all the changes and recalculations are done, and then resuming the layout and repainting all the cells, the control can save a lot of time and still deliver a refreshed interface to the user.
The following describes the layout and its suspension.
Layout Objects
A layout is an object that stores calculated values (mostly width and height of cells, spans, and viewports) used for painting the control in its current state. This may include how many viewports there are, what the top left cell in each viewport is, how big each column and row is and how many are currently visible in each viewport, etc. The purpose of the layout object is to optimize painting of the control by storing the calculated layout values used during painting and reusing them each time the control repaints instead of recalculating them each time. When a change is tracked that requires the layout object to be regenerated, the existing objects are discarded and a new one is calculated by the paint code. The layout objects are not part of the public API, but they cache all of the layout information required to paint the sheet, like the column widths, row heights, cell spans, cell overflows and the rectangles of cell notes that are always visible (Cell.NoteStyle = NoteStyle.StickyNote).
Suspending the Layout Logic
To improve performance, you can suspend the layout, which stops the layout object from being updated and thus the component does not spend any time making calculations for repainting until the layout is resumed. Two methods accomplish this, the SuspendLayout and ResumeLayout methods in the FpSpread class. Be sure to use the two methods together within a particular scope of operation, otherwise a problem may occur with the layout being suspended and not able to resume.
The SuspendLayout method prevents the component from recomputing the layout of columns, rows, and cells when changes are made to the sheet. If you are making lots of changes to the sheet in a block of code, using SuspendLayout prevents the component from doing redundant intermediate recalculations of the layout objects as each change is made, and using ResumeLayout (true) recomputes the layout once after all of your changes are made. This approach increases performance greatly, but there are additional approaches you can do depending on what features your sheets require, as described in the section, "Other Performance Improvements."
Suspended Notification
If the layout is suspended without a corresponding resume method in the same scope and an exception occurs, the component displays a notification, as shown in the following figure. If the state of the component changes such that the layout object contains invalid data (usually the incorrect number of items) then an exception can result when the component tries to paint with the invalid layout data. The notification is shown whenever there is an unhandled exception that occurs during the painting of the control, and the layout is suspended when the exception occurred.
This should only happen when the layout is suspended with SuspendLayout, and then changes are made to the component state and the component somehow made to paint again with an invalid layout object. It is possible that there could be an exception that causes this message to be displayed that is not related to the layout being suspended, for example, if an exception is thrown by a custom cell type object during a call to IRenderer.PaintCell.Any changes made to the component state could trigger layout recalculation, but not all changes do so. Changes that rearrange rows or columns, such as sorting and filtering, definitely require it, but when setting text only, the layout is recalculated under certain circumstances, such as when AllowCellOverflow property of the FpSpread class is enabled. If the layout is suspended, but the Spread is able to paint using old layout information without any problems, then the Spread may act in unexpected ways, for example, it will not scroll when you try, but the notification is not displayed.
Using the Methods Together
A rough outline of the code for suspending layout would be:
SuspendLayout
Insert your code here
ResumeLayout
The methods are intended for temporarily ignoring changes to the layout so that many changes can be made without performing the redundant layout recalculations between each change. While layout calculation is suspended, event handlers tracking changes to the component are not able to recalculate the layout and the paint code does not access the new layout. For a nested loop that makes a change to every cell, say changing a value in each cell, this is a case that would definitely benefit from suspending the layout before and resuming the layout afterward.
- Do not use these methods unless the changes are such that the performance can benefit from the layout being suspended temporarily.
- Always use the two methods together in the same scope, otherwise the component might not paint correctly if SuspendLayout is called without a matching call to ResumeLayout in the same scope.
Sample Code
The following sample code is an example of temporarily disabling the painting of the control and setting the background color to the cell.
C# |
Copy Code
|
fpSpread1.SuspendLayout();
fpSpread1.Sheets[0].Cells[0, 0, 499, 499].BackColor = Color.White;
fpSpread1.ResumeLayout(true);
|
Visual Basic |
Copy Code
|
FpSpread1.SuspendLayout()
FpSpread1.Sheets(0).Cells(0, 0, 499, 499).BackColor = Color.White
FpSpread1.ResumeLayout(True)
|
See Also