通过Ajax Post更新模型更改视图 - MVC3

时间:2023-01-20 20:34:42

I am trying to use an Ajax (I think) call to update my model value and then have that new value reflected in the view. I am just using this for testing purposes for the moment.

我试图使用Ajax(我认为)调用来更新我的模型值,然后将新值反映在视图中。我现在只是将它用于测试目的。

Here's the overview:

这是概述:

MODEL

模型

public class MyModel
{
    public int Integer { get; set; }
    public string Str { get; set; }
}

CONTROLLER

CONTROLLER

    public ActionResult Index()
    {
        var m = new MyModel();
        return View("Test1", m);
    }

    [HttpPost]
    public ActionResult ChangeTheValue(MyModel model)
    {
        var m = new MyModel();
        m.Str = model.Str;
        m.Str = m.Str + " Changed! ";
        m.Integer++;

        return View("Test1", m);

    }

VIEW

视图

  @model Test_Telerik_MVC.Models.MyModel
@using Test_Telerik_MVC.Models
@{
    ViewBag.Title = "Test1";
    Layout = "~/Views/Shared/_Layout.cshtml";
}
<h2>
    Test1</h2>
@if (false)
{
    <script src="~/Scripts/jquery-1.4.4.min.js" type="text/javascript"></script>
    <script src="~/Scripts/jquery-ui.min.js" type="text/javascript"></script>
}
<h2>
    ViewPage1
</h2>

<div>
    <input type="button" onclick="changeButtonClicked()" id="changeButton" value="Click Me!" />
    <input type="text" value="@Model.Str" class="txt" id="str" name="Str"/>
    <div></div>
</div>

<script type="text/javascript">

    function changeButtonClicked() {
        var url = '@Url.Action("ChangeTheValue", "Test1")';
        var data = '@Model';
        $.post(url, data, function (view) {
            $("#Str").value = '@Model.Str';
        });
    }

</script>

Basically the view renders a button with a textbox. My sole aim is to simply display the value of my model (Str property) in the textbox.

基本上,视图呈现带有文本框的按钮。我唯一的目的是在文本框中简单地显示我的模型(Str属性)的值。

I have tried various combinations of the changeButtonClicked() function to no avail. Test1 is the name of my controller. What I don't understand is when I debug it, the controller action fires and sets my values correctly. If I place a breakpoint on the "@Model.Str" section of the input tag, it shows me that my @Model.Str is equal to Changed! which is correct. However, as soon as my success function fires in the javascript, the value reverts back to it's original value.

我尝试过changeButtonClicked()函数的各种组合无济于事。 Test1是我的控制器的名称。我不明白的是,当我调试它时,控制器动作会触发并正确设置我的值。如果我在输入标签的“@ Model.Str”部分放置一个断点,它会告诉我我的@ Model.Str等于Changed!哪个是对的。但是,只要我的成功函数在javascript中触发,该值就会恢复为原始值。

I can make it work by changing the input type to submit and wrapping it in a @Html.BeginForm() section but I am wondering if/how to do it like this? Or is a Submit the only way to accomplish it?

我可以通过更改输入类型来提交它并将其包装在@Html.BeginForm()部分中,但是我想知道是否/如何这样做?或者提交是完成它的唯一方法吗?

Thanks

谢谢

1 个解决方案

#1


27  

First thing in the jQuery the proper way to set a value of an input is to use

jQuery中的第一件事是设置输入值的正确方法是使用

$("#Str").val(@Model.Str);

Next we'll look at the controller, in the Post action result you are returning the entire View in your ajax call. That means all the html, script references, and javascript are being returned in your jquery post request. Since all you are trying to update is the value of the input named str, I would just return that value as json and nothing else.

接下来我们将看一下控制器,在Post动作结果中,您将在ajax调用中返回整个View。这意味着在jquery post请求中返回所有html,脚本引用和javascript。因为您尝试更新的所有内容都是名为str的输入的值,所以我只是将该值作为json返回,而不是其他任何内容。

[HttpPost]
public ActionResult ChangeTheValue(MyModel model)
{
    var m = new MyModel();
    m.Str = model.Str;
    m.Str = m.Str + " Changed! ";
    m.Integer++;

    return Json(m.Str);

}

Next I would place your html inputs in a so you can have jquery serialize your model for you and then you can change your jquery post code to be:

接下来我将你的html输入放在一个,这样你就可以让jquery为你序列化你的模型,然后你可以将你的jquery邮政编码更改为:

function changeButtonClicked() {
    var url = '@Url.Action("ChangeTheValue", "Test1")';
    $.post(url, $('form').serialize(), function (view) {
        $("#Str").val(view);
    });
}

All the serialize is doing is encoding the inputs in your form into a string and if everything is named properly aps.net will bind that back to your model.

所有序列化正在进行的是将表单中的输入编码为字符串,如果所有内容都正确命名,则aps.net会将其绑定回模型。

If you need to have your route handle both ajax calls and full requests you could use asp.net's IsAjaxRequest function to test the request and return different results depending on if the request is ajax or not. You would do something like this in your controller:

如果您需要让路由处理ajax调用和完整请求,您可以使用asp.net的IsAjaxRequest函数来测试请求并返回不同的结果,具体取决于请求是否为ajax。您可以在控制器中执行以下操作:

[HttpPost]
public ActionResult ChangeTheValue(MyModel model)
{
    var m = new MyModel();
    m.Str = model.Str;
    m.Str = m.Str + " Changed! ";
    m.Integer++;

    if (Request.IsAjaxRequest) {
        return Json(m.Str);
    }
    else {
        return View("Test1", m);
    }
}

In the actionresult above you are doing everything you did before, but now are testing the request type and if it's ajax you return a Json result of your string value. If the request was not from an ajax call then the full View (html, scripts, etc) are returned to be displayed in the browser.

在上面的actionresult中,你正在做你以前做过的所有事情,但现在正在测试请求类型,如果它是ajax,则返回字符串值的Json结果。如果请求不是来自ajax调用,则返回完整的View(html,脚本等)以在浏览器中显示。

I hope this is helps you out and is what you were looking for.

我希望这可以帮助你,并且是你正在寻找的。

#1


27  

First thing in the jQuery the proper way to set a value of an input is to use

jQuery中的第一件事是设置输入值的正确方法是使用

$("#Str").val(@Model.Str);

Next we'll look at the controller, in the Post action result you are returning the entire View in your ajax call. That means all the html, script references, and javascript are being returned in your jquery post request. Since all you are trying to update is the value of the input named str, I would just return that value as json and nothing else.

接下来我们将看一下控制器,在Post动作结果中,您将在ajax调用中返回整个View。这意味着在jquery post请求中返回所有html,脚本引用和javascript。因为您尝试更新的所有内容都是名为str的输入的值,所以我只是将该值作为json返回,而不是其他任何内容。

[HttpPost]
public ActionResult ChangeTheValue(MyModel model)
{
    var m = new MyModel();
    m.Str = model.Str;
    m.Str = m.Str + " Changed! ";
    m.Integer++;

    return Json(m.Str);

}

Next I would place your html inputs in a so you can have jquery serialize your model for you and then you can change your jquery post code to be:

接下来我将你的html输入放在一个,这样你就可以让jquery为你序列化你的模型,然后你可以将你的jquery邮政编码更改为:

function changeButtonClicked() {
    var url = '@Url.Action("ChangeTheValue", "Test1")';
    $.post(url, $('form').serialize(), function (view) {
        $("#Str").val(view);
    });
}

All the serialize is doing is encoding the inputs in your form into a string and if everything is named properly aps.net will bind that back to your model.

所有序列化正在进行的是将表单中的输入编码为字符串,如果所有内容都正确命名,则aps.net会将其绑定回模型。

If you need to have your route handle both ajax calls and full requests you could use asp.net's IsAjaxRequest function to test the request and return different results depending on if the request is ajax or not. You would do something like this in your controller:

如果您需要让路由处理ajax调用和完整请求,您可以使用asp.net的IsAjaxRequest函数来测试请求并返回不同的结果,具体取决于请求是否为ajax。您可以在控制器中执行以下操作:

[HttpPost]
public ActionResult ChangeTheValue(MyModel model)
{
    var m = new MyModel();
    m.Str = model.Str;
    m.Str = m.Str + " Changed! ";
    m.Integer++;

    if (Request.IsAjaxRequest) {
        return Json(m.Str);
    }
    else {
        return View("Test1", m);
    }
}

In the actionresult above you are doing everything you did before, but now are testing the request type and if it's ajax you return a Json result of your string value. If the request was not from an ajax call then the full View (html, scripts, etc) are returned to be displayed in the browser.

在上面的actionresult中,你正在做你以前做过的所有事情,但现在正在测试请求类型,如果它是ajax,则返回字符串值的Json结果。如果请求不是来自ajax调用,则返回完整的View(html,脚本等)以在浏览器中显示。

I hope this is helps you out and is what you were looking for.

我希望这可以帮助你,并且是你正在寻找的。