【问题标题】:MVC - Passing ViewModel between partial views with JqueryMVC - 使用 Jquery 在部分视图之间传递 ViewModel
【发布时间】:2015-06-09 21:42:25
【问题描述】:

我在部分视图和控制器之间传递 ViewModel 时遇到问题。

我基本上想要的是有一个 ViewModel,它使用 Jquery 通过不同的视图传递并动态更新。

我有一个使用Fuel UX Wizard 的模式对话框。 模式的代码在一个名为“Container”的文件中,部分视图正在加载到容器中。

当模态被点击时,changed.fu.wizard 函数被调用。

$('#uiWizard').on('changed.fu.wizard', function () {
        switch ($('#uiWizard').wizard('selectedItem').step) {
            case 1:
                console.log("step 1");

                $.ajax({
                    url: '@Url.Action("Step1", "Alert")',
                    datatype: "json",
                    type: "POST",
                    contentType: 'application/json; charset=utf-8',
                    beforeSend: function () {
                        $('#container1').html(loadingData());
                    },
                    success: function (data) {
                        $('#container1').html(data);
                    },
                    error: function (data) {
                        $('#container1').html(errorMessage(data));
                    },
                    complete: function () {

                    }
                });
                break;
        }
    });

控制器方法看起来像这样简化:

[HttpPost]
public PartialViewResult Step1()
{
   TestView model = new TestView();
   return PartialView("Step1", model);
}

所以这基本上只是将 Step1 视图加载到容器视图中。

所以这是问题开始的时候。 假设我在Step.cshtml 上面使用@model Application.ViewModels.TestView 导入模型,并在Step1 页面上使用Html 助手,例如复选框和Textareas。

当再次调用向导上的“下一步”按钮时,更改的方法会再次被调用。 (在 Container.cshtml 文件中) 我想通过 Jquery 将第 1 步中的模型传递给采用 ViewModel 的控制器。

我希望控制器看起来像这样。从 View 中获取模型并传递它。

很容易将模型字符串化。这似乎在某些情况下有效,但我遇到的问题是模型没有更新。

$.ajax({
    url: '@Url.Action("Step2", "Alert")',
    datatype: "json",
    data: JSON.stringify('@Model'),
    type: "POST",
    contentType: 'application/json; charset=utf-8'
});

[HttpPost]
public PartialViewResult Step2(TestView model)
{
    return PartialView("Step2", model);
}

这有点混乱,但希望它是可以理解的;)

编辑:

部分视图: 我对部分视图的考虑是我只想从控制器中检索 ViewModel。一些局部视图可能会改变一些变量,而另一些可能只是传递它。

所以在所有部分视图中,我在顶部都有 @model Application.ViewModels.TestView。我在容器页面上没有这个。 (因为这里没有用到)

然后我可以 f.ex 有一个这样的 TextArea:

<section>
    <div class="textarea textarea-resizable">
        @Html.TextAreaFor(m => m.Text, new { @class = "form-control", rows = 15 })
    </div>
</section>

这里基本上没有更多代码,因为表单标签和其他所有内容都在容器视图中。

来自 container.cshtml

        <div class="step-content">
            <form class="form-inline" id="fuelux-wizard" method="post">
                <div class="step-pane text-center active" id="step1">
                    <div id="container1"></div>
                </div>
                <div class="step-pane" id="step2">
                    <div id="container2"></div>
                </div>
                <div class="step-pane" id="step3">
                    <div id="container3"></div>
                </div>
                <div class="step-pane" id="step4">
                    <div id="container4"></div>
                </div>
            </form>
        </div>

并且 div 正在加载前面在成功方法中发布的更改方法。

            success: function (data) {
                $('#container1').html(data);
            },

【问题讨论】:

  • data: JSON.stringify('@Model'), 永远不会传回您的模型。必须是data: $('form').serialize(),
  • 这也是数据类型json吗?它似乎不明白。获取无效的 JSON 原语:文本。而Text是第一个变量。
  • datatype: "json", 是您在成功回调中收到的内容 - 如果您没有,则可以将其删除。使用serialize()功能时还需要删除contentType: 'application/json; charset=utf-8',。但是您需要显示部分视图才能确保我的评论是正确的
  • 现在更新了帖子。见编辑:
  • data: $('#fuelux-wizard').serialize(), 应该可以工作(在ajax(... 之前添加一个console.log($('#fuelux-wizard').serialize()); 以检查其正确序列化表单控件)

标签: javascript jquery asp.net-mvc


【解决方案1】:

data: JSON.stringify('@Model') 只会发回你的类的完全限定名称,而不是模型的任何值(即使它确实有效,它也只会发布模型的原始值,因为剃刀代码是在服务器上解析的在发送给客户之前)。你需要序列化你的表单,所以ajax调用应该是

$.ajax({
    url: '@Url.Action("Step2", "Alert")',
    // datatype: "json",
    data: $('form').serialize(), // update this
    type: "POST",
    // contentType: 'application/json; charset=utf-8'
});

请注意,contentType: 'application/json; charset=utf-8' 需要删除,datatype 指定控制器方法返回的数据 - 您似乎没有访问这些数据,因此没有必要

请注意,您还可以使用手动构建表单数据

data: { Text: $('#Text').val(), AnotherProperty: $('#AnotherProperty').val(), etc },

【讨论】:

  • 这很好用!非常感谢你的帮助。注意到一件事确实很奇怪。如果我在第 2 步(在控制器中)创建一个新的 ViewModel,并且该方法也可以接收相同的 ViewModel。如果我通过一个 ViewModel,它在返回语句(在控制器中)中创建的模型不会被设置。这是我希望它表现出来的,但我发现模型看起来像是从控制器设置的蜜蜂,但实际上并没有在视图中设置,这很奇怪。明天可以展示一个例子。但想知道这是否是有意的行为。
  • 如果我正确理解您的评论,那是因为 ModelState 的值已经设置(作为绑定过程的一部分)并且您的 html 助手使用 ModelState 值(不是模型值)。 This answer 可能有助于解释它。 (如果我误解了,那么最好问一个新问题)
猜你喜欢
  • 2013-07-14
  • 1970-01-01
  • 2017-09-02
  • 1970-01-01
  • 1970-01-01
  • 2015-02-05
  • 1970-01-01
  • 1970-01-01
  • 2019-06-23
相关资源
最近更新 更多