简体   繁体   中英

How to refresh data without page reloading in Asp.net core MVC using Ajax?

I have data filtering using a checkbox. I want that when I click on the "Submit" button, only the products are updated without reloading the page

Here's the filtering:

<form id="my_form" asp-action="Face" method="get">
    <label>Color:</label>
    <input type="checkbox" name="color" value="black" /><span>Black</span>
    <input type="checkbox" name="color" value="white" /><span>White</span>
    <br />
    <p></p>
    <label>Manufacturer:</label>
    <input type="checkbox" name="brand" value="A" /><span>A</span>
    <input type="checkbox" name="brand" value="B" /><span>B</span>
    <input class="btn btn-info float-right" type="submit" value="Search" />
    //Etc
</form>

I need this data to be displayed first. And in the case of passing filters, they were updated depending on what I passed to the controller

 <div class="row pr-3 pl-3">
            @foreach (var c in Model)
            {
                <div class="filter col-md-3 p-0 hover-bc-card" data-category="@c.PurposeFor">
                    <div class="p-3">
                        <a class="text-decoration-none text-dark" asp-action="Product" asp-controller="Cosmetic" asp-route-id="@c.Id">
                            <div>
                                <img class="card-img-top p-4 bg-white" src=@c.Img alt="@c.Name">
                            </div>
                        </a>
                        <div class="card-body">
                            <h5 class="card-title text-center">@c.Name</h5>
                            <p class="card-text text-center f-sz-12 ">@c.PurposeFor</p>
                            <p class="card-text rounded text-center price-for-list">@c.Price ₴</p>
                        </div>
                    </div>
                </div>
            }
        </div>

Just in case my controller:

public IActionResult Face(string[] color, string[] brand, string[] PurposeFor, string sortOrder)
    {

        ViewBag.color = color;
        ViewBag.PurposeFor = PurposeFor;
        ViewBag.brand = brand;
        ViewBag.NameSortParm = string.IsNullOrEmpty(sortOrder) ? "Name_desc" : "";
        ViewBag.PriceSortParm = sortOrder == "Price" ? "Price_desc" : "Price";

        var cosmetics = db.Cosmetics.Where(c => c.PurposeFor.Contains("Face")).ToList();
        var co_cars = new List<Cosmetic>();
        var ma_cars = new List<Cosmetic>();
        var purposeFor = new List<Cosmetic>();


        if (color.Length != 0)
        {
            foreach (string co in color)
            {
                var colorfiltercars = db.Cosmetics.Where(c => c.Color.Contains(co)).ToList();
                co_cars.AddRange(colorfiltercars);
            }
        }
        else
        {
            co_cars = cosmetics;
        }

        if (PurposeFor.Length != 0)
        {
            foreach (string pf in PurposeFor)
            {
                var purposefiltercars = db.Cosmetics.Where(c => c.PurposeFor.Contains(pf)).ToList();
                purposeFor.AddRange(purposefiltercars);
            }
        }
        else
        {
            purposeFor = cosmetics;
        }

        if (brand.Length != 0)
        {
            foreach (string ma in brand)
            {
                var manufacturerfiltercars = db.Cosmetics.Where(c => c.Brand.Contains(ma)).ToList();
                ma_cars.AddRange(manufacturerfiltercars);
            }
        }
        else
        {
            ma_cars = cosmetics;
        }

        var filtercars = co_cars.Intersect(ma_cars);
        filtercars = filtercars.Intersect(purposeFor);

        switch (sortOrder)
        {
            case "Name_desc":
                filtercars = filtercars.OrderByDescending(s => s.Name);
                break;
            case "Price":
                filtercars = filtercars.OrderBy(s => s.Price);
                break;
            case "Price_desc":
                filtercars = filtercars.OrderByDescending(s => s.Price);
                break;
            default:
                filtercars = filtercars.OrderBy(s => s.Name);
                break;
        }
        return View(filtercars.ToList());
    }

I want that when I click on the "Submit" button, only the products are updated without reloading the page

You can refer to the following code snippet to perform AJAX submission using jQuery Unobtrusive AJAX and dynamically update the target container with returned partial view result.

<form id="my_form" asp-action="Face" method="get" data-ajax="true" data-ajax-method="get" data-ajax-update="#panel" data-ajax-mode='replace' data-ajax-url="@Url.Action("GetPartial","Home")">
    <label>Color:</label>
    <input type="checkbox" name="color" value="black" /><span>Black</span>
    <input type="checkbox" name="color" value="white" /><span>White</span>
    <br />
    <p></p>
    <label>Manufacturer:</label>
    <input type="checkbox" name="brand" value="A" /><span>A</span>
    <input type="checkbox" name="brand" value="B" /><span>B</span>
    <input class="btn btn-info float-right" type="submit" value="Search" />
</form>

Add reference to jquery-ajax-unobtrusive

@section scripts{
    <script src="https://cdnjs.cloudflare.com/ajax/libs/jquery-ajax-unobtrusive/3.2.6/jquery.unobtrusive-ajax.min.js"></script>
}

Specify id attribute panel to div container

<div class="row pr-3 pl-3" id="panel">

Action method that returns a partial view

public IActionResult GetPartial(string[] color, string[] brand, string[] PurposeFor, string sortOrder)
{
    //move your query code logic in custom method GetFilterData
    var filtercars = GetFilterData(color, brand, PurposeFor, sortOrder);

    return PartialView("_CarListPartial", filtercars);
}

Partial view _CarListPartial.cshtml

@model IEnumerable<WebNaApp.Models.Cosmetic>

@foreach (var c in Model)
{
    <div class="filter col-md-3 p-0 hover-bc-card" data-category="@c.PurposeFor">
        <div class="p-3">
            <a class="text-decoration-none text-dark" asp-action="Product" asp-controller="Cosmetic" asp-route-id="@c.Id">
                <div>
                    <img class="card-img-top p-4 bg-white" src=@c.Img alt="@c.Name">
                </div>
            </a>
            <div class="card-body">
                <h5 class="card-title text-center">@c.Name</h5>
                <p class="card-text text-center f-sz-12 ">@c.PurposeFor</p>
                <p class="card-text rounded text-center price-for-list">@c.Price ₴</p>
            </div>
        </div>
    </div>
}

Test Result

在此处输入图像描述

I suggest you the following step if you want to avoid page reload:

1- JQuery and Ajax Post to send data to controller

2- Function in your controller to manage the data and send a response with the data you need

3- In the success part of your Ajax.clear or.append the HTML part concerned like a div or select option

here is a little example to guide you, but you have to adapt it corresponding to your need:

In CSHTML: don't forget to add an Id to your checkbox:

<button type="button" onclick="checkMe()">Search</button>
<input type="checkbox" id="Checkbox1" />
<input type="checkbox" id="Checkbox2" />
<script>
  function checkMe() {
  // here get value of your checkbox1 
  var Checkbox1state = $('#Checkbox1').prop('checked');
  var Checkbox2state = $('#Checkbox2').prop('checked');
  // and some logic how you want to filter if there is many parameter
  var id =0
  if (Checkbox2state) { id=1 } else {  id=2 };
  
    $.ajax({
      type: "POST",
      url: "/Home/AjaxMethodeCheckMe",
      data: '{id: "' + id + '" }',
      contentType: "application/json; charset=utf-8",
      dataType: "json",
      success: function (ListOfItems) {
        $("#yourDropDown").empty();
        $.each(ListOfItems, function (i, item) {
        $("#yourDropDown").append('<option value="' + item.Value + '">' + item.Text + '</option>');
        });
      },
      failure: function (response) {
        alert("failure");
      },
      error: function (response) {
        alert("error");
      },
    });
  }
  
</script>

in your controller:

public JsonResult AjaxMethodeCheckMe(int id)
{
    List<SelectListItem> ListOfPort = new List<SelectListItem>();

    ListOfPort.Add(new SelectListItem() { Text = "Text 1", Value = "Value1" });
    ListOfPort.Add(new SelectListItem() { Text = "Text 2", Value = "Value2" });
    ListOfPort.Add(new SelectListItem() { Text = "Text 3", Value = "Value3" });

    return Json(new SelectList(ListOfPort, "Value", "Text"));
}

Here i show how to do with dropdown but you can modify...

The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM