Preserving state of the data grid through navigations

In my UI I have several data grids that contain a lot of data, guaranteeing that a user will use filters, paging and sorting to find their interesting row.
They can then navigate to a detail page, which is a separate Blazor page and URL.
Pressing back on the browser, or a page button which calls history.back(); navigates back to the list/grid page.
However at the moment the state of filtering/sorting/paging is lost, which is quite annoying.
Is there a built in or programmatic way so that when pressing Back the grid state will be as the user left it?

2 Likes

Hi!

I've just figured out how to do it (maybe not the cleanest or most straight-forward implementation, but it works):

@page "/Entity"

@inject DigitalGateway.Services.ICalendarService CalendarService;
@inject DigitalGateway.Services.IAzureService AzureService;
@inject NavigationManager NavigationManager;
@inject ProtectedSessionStorage storage;
@using System.Linq.Dynamic.Core;
@using Serilog;
@using System.Text.Json;

<h1>Entities</h1>

<RadzenDataGrid @ref="gridEntities" AllowFiltering="true" AllowColumnResize="true" FilterMode="FilterMode.Simple" PageSizeOptions="@pageSizeOptions" PagerPosition="PagerPosition.TopAndBottom" AllowPaging="true" AllowSorting="true"
				Data="@_entities" LoadData="@LoadData" Count="@count" TItem="Entities.Entity" LogicalFilterOperator="LogicalFilterOperator.And" EditMode="DataGridEditMode.Single" FilterCaseSensitivity="FilterCaseSensitivity.CaseInsensitive">
	<Columns>
		<RadzenDataGridColumn TItem="Entities.Entity" Property="ExtractConfig.ExtractName" Title="Extract Name" TextAlign="TextAlign.Left" FilterProperty="ExtractConfig.ExtractName" />
		<RadzenDataGridColumn TItem="Entities.Entity" Property="EntityName" Title="Entity Name" />
		<RadzenDataGridColumn TItem="Entities.Entity" Property="DGEntityId" Title="DG Entity ID" />
		<RadzenDataGridColumn TItem="Entities.Entity" Property="ExcludedFromExtract" Title="Excluded from Extract" TextAlign="TextAlign.Center">
			<Template Context="entity">
				<RadzenCheckBox id="ExcludedFromExtract" TValue="bool" Value="@entity.ExcludedFromExtract" Change=@(args => CheckChanged(args,entity.Id)) />
			</Template>
		</RadzenDataGridColumn>
		<RadzenDataGridColumn TItem="Entities.Entity" Property="AssignedToGroup" Title="Assigned To Group" />
		<RadzenDataGridColumn Width="200px" TItem="Entities.Entity" Property="Id">
			<Template Context="entity">
				<RadzenButton ButtonStyle="ButtonStyle.Light" Click=@(() => EditEntity(entity.Id.ToString())) Text="Edit" />
			</Template>
		</RadzenDataGridColumn>
	</Columns>
</RadzenDataGrid>
<br />


@code {
	private IEnumerable<Entities.Entity> _entities;
	IEnumerable<int> pageSizeOptions = new int[] { 10, 20, 50, 100 };
	RadzenDataGrid<Entities.Entity> gridEntities;
	string sessionquery;
	int count = 0;


	protected override async Task OnAfterRenderAsync(bool firstRender)
	{
		if (firstRender)
		{
			await GetSessionValues();
			StateHasChanged();
		}
		await base.OnAfterRenderAsync(firstRender);
	}

	private void EditEntity(string entityId)
	{
		NavigationManager.NavigateTo($"EntityEdit/{entityId}");
	}

	private async Task GetSessionValues()
	{
		var result = await storage.GetAsync<string>("gridEntity");
		sessionquery = result.Success ? result.Value : "";
		if (!string.IsNullOrEmpty(result.Value))
		{

			var elems = JsonSerializer.Deserialize<IEnumerable<Tuple<string, string>>>(result.Value);
			foreach (var elem in elems)
			{
				var column = this.gridEntities.ColumnsCollection.FirstOrDefault(x => x.Property.Equals(elem.Item1));
				if (column != null)
				{
					column.FilterValue = elem.Item2;
				}
			}
			this.gridEntities.Reload();


		}
	}

	async Task LoadData(LoadDataArgs args)
	{

		var query = CalendarService.GetEntitiesAsQueryable();

		if (!string.IsNullOrEmpty(args.Filter))
		{
			query = query.Where(args.Filter);
		}

		var filterValues = args.Filters.Where(x => x.FilterValue != null).Select(x => new { Property = x.Property, FilterValue = x.FilterValue }).AsEnumerable().Select(c => new Tuple<string, string>(c.Property, c.FilterValue.ToString())).ToList();

		if (filterValues.Any())
			await storage.SetAsync("gridEntity", JsonSerializer.Serialize(filterValues));
		count = query.Count();
		_entities = query.Skip(args.Skip.Value).Take(args.Top.Value).ToList();
	}

	private async Task CheckChanged(bool? selected, int id)
	{

		CalendarService.UpdateEntitySetup(id, selected.Value);
		//await gridEntities.Reload();
		_entities = await Task.Run(() => CalendarService.GetEntities()).ConfigureAwait(true);
	}

}


3 Likes

... this is what I need. Thanks :sunflower:.

Now I want to clean the filter.

My Question is in another Post. Sorry...
Please see here:
Clearing Filter Post

And one more Question:
Clearing the filter on INT Columns
I set the filter (1) column.FilterValue = elem.Item2;
My Gird is filtered. Now the User gos into the filtercell and deleted the number and pressed enter or leave the filtercell.

The grid set the number from the codeside setting filter (1) automatically and start a new search.
The user has no chance to reset or clean this filter :frowning:

Hi, I'm interested in the same topic here. I'm using Blazor server (no API). I use RadzenDataGrid to display my data. And use FilterMode.Simple for users to find their interesting rows. After the user enter a value on search box, click on a row to see its details, then click "Back" button to navigate back to the previous page where he/she had the filtered grid before. However, when get back the filter now is lost, but the whole data list is displayed again. My users want to see the list with filtered data as he/she left it. I saw the answer from Robert_Simon, I tried but I couldn't make it works. I'm new to Radzen Blazor so it would be helpful if Radzen team or Jon or Robert or Pinki please give me a complete small working example so I can learn and follow. Thank you so much for your help.