如何在C# / ASP.NET的MVC项目中使用jQuery或Ajax更新Razor部分视图

46
在一个MVC的局部视图文件中,我创建了一个Html.TextBox和两个提交按钮。这两个按钮在点击后会增加/减少Html.TextBox的值。Html.TextBox显示的值将相应地改变。但是,一旦我需要根据点击后的新值更新#refTable div,页面或部分就永远不会更新。下面是代码,其中添加了一些注释以解释。感谢您的帮助。
<body>
</body>

<input type="submit" value="PrevY" name="chgYr2" id="pY" />
@{
    var tempItem3 = Model.First(); // just give the first entry from a database, works.
    if (ViewData["curSel"] == null)
    {
    @Html.TextBox("yearSelect3", Convert.ToDateTime(tempItem3.Holiday_date).Year.ToString());  
    ViewBag.selYear = Convert.ToDateTime(tempItem3.Holiday_date).Year; // just initial value, works
    ViewData["curSel"] = Convert.ToDateTime(tempItem3.Holiday_date).Year;
    }
    else
    {
    @Html.TextBox("yearSelect3", ViewData["curSel"].ToString());
    } 
}
<input type="submit" value="NextY" name="chgYr2" id="nY" />


<script type="text/javascript">
    $(document).ready(function () {
        $(document).on("click", "#nY", function () {
            var val = $('#yearSelect3').val();
            $('#yearSelect3').val((val * 1) + 1);
            var dataToSend = {
                id: ((val * 1) + 1)
            }
            // add some jquery or ajax codes to update the #refTable div
            // also ViewBag.selYear need to be updated as ((val * 1) + 1)
            // like:   ViewBag.selYear = ((val * 1) + 1);
            // any similar temp variable is fine
        });

        });
        $(document).on("click", "#pY", function () {
            var val = $('#yearSelect3').val();
            $('#yearSelect3').val((val * 1) - 1);
            var dataToSend = {
                id: ((val * 1) - 1)
            }

        });
    });
</script>



<span style="float: right"><a href="/">Set Holiday Calender for 2013</a></span>
<span id="btnAddHoliday">@Html.ActionLink("Add Holiday", "Create", null, new { id = "addHilBtn" })</span>

<div id="refTable">
    <table class="tblHoliday" style="width: 100%;">
            <th>
                Holiday
            </th>
            <th>
                Dates
            </th>
            <th>Modify</th>
            <th>Delete</th>
        </tr>

        @foreach (var item in Model)
        {

            if (    Convert.ToDateTime(item.Holiday_date).Year == ViewBag.selYear)
            // if the ViewBag.selYear is hard code, this selection "works"
            {
            <tr>                
                <td>
                    @Html.DisplayFor(modelItem => item.Holiday_Name)
                </td>               
                <td>
                    @item.Holiday_date.Value.ToString("MM/dd/yyyy")
                </td>
                <td>
                    @Html.ActionLink("Edit", "Edit", new {  })
                </td>
                <td>
                    @Html.ActionLink("Delete", "Delete", new {  })
                </td>
            </tr>
            }
        }

    </table>
</div>

你试过的 AJAX 代码在哪里? - Jasen
我把ajax去掉了,因为这些ajax用于调用MVC操作。我试图通过执行MVC操作来刷新网页,但徒劳无功。 - user2029505
3个回答

82
如果您想更新页面的一部分而不重新加载整个页面,则需要使用AJAX。 主cshtml视图
<div id="refTable">
     <!-- partial view content will be inserted here -->
</div>

@Html.TextBox("yearSelect3", Convert.ToDateTime(tempItem3.Holiday_date).Year.ToString());
<button id="pY">PrevY</button>

<script>
    $(document).ready(function() {
        $("#pY").on("click", function() {
            var val = $('#yearSelect3').val();
            $.ajax({
                url: "/Holiday/Calendar",
                type: "GET",
                data: { year: ((val * 1) + 1) }
            })
            .done(function(partialViewResult) {
                $("#refTable").html(partialViewResult);
            });
        });
    });
</script>

您需要添加我省略的字段。我使用了一个<button>而不是提交按钮,因为您没有表单(我在您的标记中没有看到任何表单),而且您只需要它们在客户端上触发javascript。 HolidayPartialView被呈现为HTML,并且jquery done回调将该HTML片段插入到refTable div中。 HolidayController Update action
[HttpGet]
public ActionResult Calendar(int year)
{
    var dates = new List<DateTime>() { /* values based on year */ };
    HolidayViewModel model = new HolidayViewModel {
        Dates = dates
    };
    return PartialView("HolidayPartialView", model);
}

这个控制器操作接受年份参数,并使用强类型视图模型返回日期列表,而不是使用 ViewBag。
视图模型。
public class HolidayViewModel
{
    IEnumerable<DateTime> Dates { get; set; }
}

HolidayPartialView.csthml

@model Your.Namespace.HolidayViewModel;

<table class="tblHoliday">
    @foreach(var date in Model.Dates)
    {
        <tr><td>@date.ToString("MM/dd/yyyy")</td></tr>
    }
</table>

这是要插入到你的 div 中的内容。

好的,我喜欢你的解决方案,但为什么要使用 done?为什么不直接使用ajax的成功回调函数? - Jorge
20
注意:自 jQuery 1.8 版本起,jqXHR.success()、jqXHR.error() 和 jqXHR.complete() 回调已被弃用。为了准备将来的移除,应使用 jqXHR.done()、jqXHR.fail() 和 jqXHR.always() 替代它们。更多信息请查看 jQuery.ajax() - Jasen
你好Jorge,非常感谢你的帮助。非常感激!关于“ajax回调”的使用,抱歉,我还是新手在ajax和MVC方面,需要一些时间来消化它们。 - user2029505
.done(function(partialViewResult) { $("#refTable").html(partialViewResult); });以上代码块是一个jQuery的异步请求回调函数,当异步请求成功时,会将返回的partialViewResult局部视图结果作为参数传递给该函数。然后,该函数使用jQuery选择器找到id为“refTable”的元素,并将partialViewResult插入到该元素中,从而更新页面内容。 - Ram

2
主要概念是局部视图返回HTML代码而不是直接访问局部视图本身。
[HttpGet]
public ActionResult Calendar(int year)
{
    var dates = new List<DateTime>() { /* values based on year */ };
    HolidayViewModel model = new HolidayViewModel {
        Dates = dates
    };
    return PartialView("HolidayPartialView", model);
}

这个操作返回部分视图("HolidayPartialView")的HTML代码。

要刷新部分视图,请使用下面的jQuery将现有项替换为新的过滤项。

$.ajax({
                url: "/Holiday/Calendar",
                type: "GET",
                data: { year: ((val * 1) + 1) }
            })
            .done(function(partialViewResult) {
                $("#refTable").html(partialViewResult);
            });

0
你还可以使用 Url.Action 作为路径,例如:
$.ajax({
        url: "@Url.Action("Holiday", "Calendar", new { area = "", year= (val * 1) + 1 })",                
        type: "GET",           
        success: function (partialViewResult) {            
            $("#refTable").html(partialViewResult);
        }
    });

网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接