Grid Virtual Scrolling with Dynamic Zoom
Environment
| Product | Progress® Kendo UI® for Angular Grid |
Description
How can I implement zoom functionality in a Grid with virtual scrolling enabled? When applying CSS transformations to scale a Grid wrapper element, the virtual scrolling mechanism becomes misaligned with the Grid layout, causing scrolling to extend beyond the actual content and creating empty space.
This Knowledge Base article also answers the following questions:
- How to implement zoom functionality without using CSS transformations on a Grid?
- Why do CSS scaling transformations cause issues with Grid virtual scrolling?
- How to dynamically scale Grid dimensions while keeping virtual scrolling functional?
- What is the recommended alternative to CSS transformations for Grid zoom functionality?
Solution
Zoom and scale transformations using CSS are not officially supported by the Kendo UI for Angular components. When you apply CSS transformations to an element that wraps the Grid component, this creates visual scaling but does not update the internal calculations that the virtual scrolling mechanism relies on.
Instead of using CSS transformations, dynamically adjust the built-in Grid properties to achieve zoom-like functionality. This approach updates the actual measurements that the virtual scrolling mechanism uses for calculations, which prevents alignment issues and maintains proper scrolling behavior at all zoom levels.
To implement zoom functionality in a Grid with virtual scrolling:
-
Define base values for the Grid dimensions and a
scaleFactorproperty to control the zoom level.typescriptpublic scaleFactor: number = 1; private baseRowHeight: number = 36; private baseFontSize: number = 14; private baseGridHeight: number = 450; private baseGridWidth: number = 680; -
Create computed properties for the Grid dimensions that multiply the defined base values by the scale factor. Use
Math.round()to ensure whole pixel values.typescriptpublic get scaledRowHeight(): number { return Math.round(this.baseRowHeight * this.scaleFactor); } public get scaledGridHeight(): number { return Math.round(this.baseGridHeight * this.scaleFactor); } public get scaledGridWidth(): number { return Math.round(this.baseGridWidth * this.scaleFactor); } public scaledColumnWidth(baseWidth: number): number { return Math.round(baseWidth * this.scaleFactor); } -
Create style objects for the Grid headers and cells that scale the font size and padding accordingly. This ensures that the cell content dimensions adjust proportionally.
typescriptpublic get headerCellStyle(): any { return { 'font-size': `${Math.round(this.baseFontSize * this.scaleFactor)}px`, 'padding-block': `${Math.round(8 * this.scaleFactor)}px`, 'padding-inline': `${Math.round(12 * this.scaleFactor)}px` }; } public get cellStyle(): any { return { 'font-size': `${Math.round(this.baseFontSize * this.scaleFactor)}px`, 'padding-block': `${Math.round(8 * this.scaleFactor)}px`, 'padding-inline': `${Math.round(12 * this.scaleFactor)}px` }; } -
Bind the computed properties to the Grid configuration. Use the corresponding scaled dimensions for the Grid height and width,
rowHeight, and column widths. Apply the header and cell style objects to each Grid column using theheaderStyleandstyleproperties.html<kendo-grid [kendoGridBinding]="gridData" [rowHeight]="scaledRowHeight" [height]="scaledGridHeight" [style.width.px]="scaledGridWidth" scrollable="virtual" > <kendo-grid-column [width]="scaledColumnWidth(80)" [headerStyle]="headerCellStyle" [style]="cellStyle" ></kendo-grid-column> </kendo-grid>
When the scale factor changes, all computed properties recalculate, updating the actual measurements that virtual scrolling uses for calculations rather than just the visual appearance.
The following example demonstrates the complete implementation of the suggested approach.