I am trying to create an ecommerce page. I want to make category selections with using checkboxes. It can make the filtering and give me the necessary data; the backend works. But when I change the page (pagination feature), the category selection is getting lost. So the data is not being stable anymore. The list gives me the default SQL query again. How can I make it stable? How do I store my selection?
EDIT (problem occures to this if I use localStorage, based on the answer) If I need to give an example to make sure you understand better. You have 10 item in your data, you display 6 for each, when you change to page two you need to see the rest of 4 data. My problem occures here, I don't see the rest 4 data. I see the first 6 again in everypage. I see the rest 4 data(for a sec) , then I see the first 6 data immidiatly.
If more code blocks are needed I can edit the post
Controller
[Authorize]
public async Task<IActionResult> Index(GetECommerceIndexQuery request, List<int> categoryIds)
{
var result = await MediatrSend(request);
return View(result);
}
[Authorize]
[HttpPost]
public async Task<IActionResult> GetCategories([FromBody] List<int> selectedIds)
{
var result = await MediatrSend(new GetECommerceIndexQuery { CategoryIds = selectedIds});
return Json(result);
}
Query File
public class GetECommerceIndexQuery : MediatR.IRequest<ECommerceListDTO>
{
public ClaimModel ClaimModel { get; set; }
public List<int> CategoryIds { get; set; }
public int Page { get; set; } = 1;
public int PageSize { get; set; } = 6;
}
public class GetECommerceIndexQueryHandler : IRequestHandler<GetECommerceIndexQuery, ECommerceListDTO>
{
private readonly IECommerceProductRepository _eCommerceProductRepository;
public GetECommerceIndexQueryHandler(IECommerceProductRepository eCommerceProductRepository)
{
_eCommerceProductRepository = eCommerceProductRepository;
}
public async Task<ECommerceListDTO> Handle(GetECommerceIndexQuery request, CancellationToken cancellationToken)
{
ECommerceListDTO response = new ECommerceListDTO();
int page = request.Page;
int pageSize = request.PageSize;
var products = await _eCommerceProductRepository.GetECommerceProductList(request.CategoryIds);
var totalProducts = products.Count();
var totalPages = (int)Math.Ceiling((double)totalProducts / pageSize);
var paginatedProducts = products.Skip((page - 1) * pageSize).Take(pageSize);
response.MetaData = new DatatableMetaDTO
{
page = page,
pages = totalPages,
perpage = pageSize,
total = totalProducts,
};
response.ProductData = paginatedProducts;
response.CategoryData = await _eCommerceProductRepository.GetECommerceCategoryList();
return response;
}
}
Pagination
<!-- Pagination Buttons -->
<div class="d-flex justify-content-center">
<ul class="pagination">
@for (int i = 1; i <= Model.MetaData.pages; i++)
{
<li class="page-item @(i == Model.MetaData.page ? "active" : "")">
<a class="page-link" href="@Url.Action("Index", new { page = i })">@i</a>
</li>
}
</ul>
</div>
Script
@section scripts {
<script>
$(document).ready(function () {
$(".checkbox-item").click(function () {
var selectedValues = $(".checkbox-item:checked").map(function () {
return parseInt(this.value, 10);
}).get();
var jsonData = JSON.stringify(selectedValues);
$.ajax({
url: '@Url.Action("GetCategories", "ECommerce")',
type: 'POST',
data: jsonData,
contentType: 'application/json; charset=utf-8',
success: function (data) {
console.log(data);
renderProducts(data.ProductData);
},
error: function (error) {
console.error('Error Occurred:', error);
}
});
});
function renderProducts(products) {
$('#productContainer').empty();
$.each(products, function (index, product) {
var productUrl = '@Url.Action("ProductDetail", new { id = 0 })'.replace("0", product.Id);
var productHtml = `
<div class="col-md-4 col-lg-12 col-xxl-4">
<a href="${productUrl}" class="product-link">
<div class="card card-custom gutter-b card-stretch">
<div class="card-body d-flex flex-column rounded bg-light justify-content-between">
<div class="text-center rounded mb-7">
<img src="assets/media/products/${product.ProductName}" class="mw-100 w-200px" alt="${product.ProductName}">
</div>
<div>
<h4 class="font-size-h5">
<span class="text-dark-75 font-weight-bolder">${product.ProductName}</span>
</h4>
<div class="font-size-h6 text-muted font-weight-bolder">${product.Price}</div>
</div>
</div>
</div>
</a>
</div>`;
$('#productContainer').append(productHtml);
});
}
});
</script>
}
To resolve your issue losing category selections when changing pages and seeing the same data on every page you can follow this below updated code:
@section scripts {
<script>
$(document).ready(function () {
var selectedCategories = JSON.parse(localStorage.getItem('selectedCategories')) || [];
var currentPage = parseInt(localStorage.getItem('currentPage')) || 1;
$(".checkbox-item").each(function() {
var value = parseInt($(this).val(), 10);
if (selectedCategories.includes(value)) {
$(this).prop('checked', true);
}
});
loadProducts();
$(".checkbox-item").click(function () {
updateSelectedCategories();
currentPage = 1;
localStorage.setItem('currentPage', currentPage);
loadProducts();
});
$(".page-link").click(function (e) {
e.preventDefault();
currentPage = parseInt($(this).text(), 10);
localStorage.setItem('currentPage', currentPage);
loadProducts();
});
function updateSelectedCategories() {
selectedCategories = $(".checkbox-item:checked").map(function () {
return parseInt(this.value, 10);
}).get();
localStorage.setItem('selectedCategories', JSON.stringify(selectedCategories));
}
function loadProducts() {
var jsonData = JSON.stringify(selectedCategories);
$.ajax({
url: '@Url.Action("GetCategories", "ECommerce")',
type: 'POST',
data: jsonData,
contentType: 'application/json; charset=utf-8',
success: function (data) {
console.log(data);
renderProducts(data.ProductData);
updatePagination(data.MetaData.page, data.MetaData.pages);
},
error: function (error) {
console.error('Error Occurred:', error);
}
});
}
function renderProducts(products) {
$('#productContainer').empty();
// ... (same as before)
}
function updatePagination(currentPage, totalPages) {
$('.pagination').empty();
for (var i = 1; i <= totalPages; i++) {
var isActive = i === currentPage ? "active" : "";
var pageItem = `<li class="page-item ${isActive}">
<a class="page-link" href="#">${i}</a>
</li>`;
$('.pagination').append(pageItem);
}
}
});
</script>
}