New to Telerik UI for WinForms? Start a free 30-day trial
How to apply paging with filter and sort functionalities in VirtualGrid
Updated over 1 year ago
Environment
| Product Version | Product | Author |
|---|---|---|
| 2022.2.511 | Scheduler for WinForms | Dinko Krastev |
Description
RadVirtualGrid is a control providing a convenient UI to display only the visible part of a large set of data. By definition, not all of that data needs to be available locally. This article aims to show you how to add paging with filter and sort functionalities in RadVirtualGrid.
Solution
In this example, we will demonstrate how to use the PageChanging, CellValueNeeded, FilterChanged, and SortChanged to populate the VirtualGrid viewport with data on the current page.

C#
public partial class Form1 : Form
{
List<CarPart> repository = new List<CarPart>();
List<CarPart> data = new List<CarPart>();
int count = 0;
bool shouldCancel = false;
private string[] columnNames = new string[] { "Name","Make","PartId"};
public Form1()
{
for (int i = 1; i < 10000; i++)
{
repository.Add(new CarPart()
{
Name = "Name " + i,
Make = "Tesla",
PartId = i
});
}
InitializeComponent();
this.radVirtualGrid1.ColumnCount = columnNames.Length;
this.radVirtualGrid1.PageChanging += RadVirtualGrid1_PageChanging;
this.radVirtualGrid1.CellEditorInitialized += RadVirtualGrid1_CellEditorInitialized;
this.radVirtualGrid1.FilterChanged += radVirtualGrid1_FilterChanged;
this.radVirtualGrid1.SortChanged += radVirtualGrid1_SortChanged;
SelectData();
}
private void RadVirtualGrid1_CellEditorInitialized(object sender, VirtualGridCellEditorInitializedEventArgs e)
{
VirtualGridCellElement currentCell = null;
foreach (VirtualGridCellElement cellElement in this.radVirtualGrid1.VirtualGridElement.GetDescendants(
delegate (RadElement x) { return x is VirtualGridFilterCellElement; },
TreeTraversalMode.BreadthFirst))
{
if (cellElement.RowIndex == e.RowIndex && cellElement.ColumnIndex == e.ColumnIndex && cellElement.ViewInfo == e.ViewInfo)
{
currentCell = cellElement;
}
}
if (e.RowIndex < 0 && currentCell != null)
{
VirtualGridTextBoxEditor textBoxEditor = e.ActiveEditor as VirtualGridTextBoxEditor;
if (textBoxEditor != null)
{
this.count = 0;
this.shouldCancel = false;
RadTextBoxEditorElement el = textBoxEditor.EditorElement as RadTextBoxEditorElement;
el.KeyDown -= el_KeyDown;
el.KeyDown += el_KeyDown;
}
}
}
private void el_KeyDown(object sender, KeyEventArgs e)
{
this.shouldCancel = ++count % 3 != 0;
if (!this.shouldCancel)
{
count = 0;
}
}
private void RadVirtualGrid1_PageChanging(object sender, VirtualGridPageChangingEventArgs e)
{
SelectData(e.NewIndex);
}
private void SelectData(int pageIndex = -1)
{
//Assume IQueryable
var query = from data in repository select data;
string sortProperty = this.radVirtualGrid1.SortDescriptors.FirstOrDefault()?.PropertyName;
if (string.IsNullOrEmpty(sortProperty) || sortProperty == "Name")
{
if (string.IsNullOrEmpty(sortProperty) || this.radVirtualGrid1.SortDescriptors.First().Direction == ListSortDirection.Ascending)
{
query = query.OrderBy(x => x.Name);
}
else
{
query = query.OrderByDescending(x => x.Name);
}
}
else if (sortProperty == "Make")
{
if (this.radVirtualGrid1.SortDescriptors.First().Direction == ListSortDirection.Ascending)
{
query = query.OrderBy(x => x.Make);
}
else
{
query = query.OrderByDescending(x => x.Make);
}
}
else if (sortProperty == "PartId")
{
if (this.radVirtualGrid1.SortDescriptors.First().Direction == ListSortDirection.Ascending)
{
query = query.OrderBy(x => x.PartId);
}
else
{
query = query.OrderByDescending(x => x.PartId);
}
}
//Contains only
foreach (var filters in radVirtualGrid1.FilterDescriptors)
{
if(filters.Value == null)
{
continue;
}
if (filters.PropertyName == "Name")
{
query = query.Where(x => x.Name.Contains(filters.Value.ToString()));
}
if (filters.PropertyName == "Make")
{
query = query.Where(x => x.Make.Contains(filters.Value.ToString()));
}
if (filters.PropertyName == "PartId")
{
query = query.Where(x => x.PartId.ToString().Contains(filters.Value.ToString()));
}
}
//Retrieve only needed page
if (pageIndex == -1)
{
pageIndex = radVirtualGrid1.PageIndex;
}
data = query.Skip(pageIndex * radVirtualGrid1.PageSize).Take(radVirtualGrid1.PageSize).ToList();
radVirtualGrid1.RowCount = query.Count();
}
private void radVirtualGrid1_SortChanged(object sender, VirtualGridEventArgs e)
{
SelectData();
}
private void radVirtualGrid1_FilterChanged(object sender, VirtualGridEventArgs e)
{
SelectData();
}
private void radVirtualGrid1_CellValueNeeded(object sender, Telerik.WinControls.UI.VirtualGridCellValueNeededEventArgs e)
{
if (e.ColumnIndex < 0)
return;
if (e.RowIndex == RadVirtualGrid.HeaderRowIndex)
{
e.Value = columnNames[e.ColumnIndex];
}
if (e.RowIndex < 0)
{
e.FieldName = columnNames[e.ColumnIndex];
}
if (e.RowIndex >= 0 && e.RowIndex < data.Count * (this.radVirtualGrid1.PageIndex + 1))
{
int index = e.RowIndex - this.radVirtualGrid1.PageSize * this.radVirtualGrid1.PageIndex;
e.Value = data[index][e.ColumnIndex];
}
}
}
Data Model
C#
public class CarPart
{
public string Name { get; set; }
public string Make { get; set; }
public int PartId { get; set; }
public string this[int i]
{
get
{
switch (i)
{
case 0:
return Name;
case 1:
return Make;
case 2:
return PartId.ToString();
default:
return string.Empty;
}
}
}
}