【问题标题】:How to update view model in a partial view in MVC5?如何在 MVC5 的局部视图中更新视图模型?
【发布时间】:2016-08-19 07:56:04
【问题描述】:

我有一个视图,在该视图中我有一个包含部分视图的 div。

我的问题是这个。用户从下拉列表中选择一个项目,然后我用模型加载部分视图。用户更改更改了一些文本框并单击按钮提交部分视图(在 Html.BeginForm 中)。

当我去检查控制器中的模型时,模型不包含用户所做的更改。

为什么模型没有反映用户所做的更改?

在主视图中:

<div id="personInfo" style="display:none;"></div>

我的部分观点:

    @model MyProject.MyModel

    @(Html.Kendo().DropDownList().Name("ddlFilters")
                                .AutoBind(true)
                                .OptionLabel("--- Select Filter ---")
                                .DataValueField("ID")
                                .DataTextField("MYFILTER")
                                .DataSource(ds =>
                                    ds.Read(r => r.Action("GetPersonFilters", "Home"))
                                )
                                .Events(x => x.Select("ddlFilters_onSelect"))
                        )

    @using (Html.BeginForm("PersonAction", "Home", FormMethod.Post, new { @class = "form-horizontal", id = "personForm" }))
            {
                 // Strongly typed Kendo fields. Several DropDownListFor and TextBoxFor
                 @Html.Kendo().TextBoxFor(x => x.FirstName).HtmlAttributes(new { @class = "form-control kendoTextBox required " })
                // Button to post the form data to the controller.
            }

我的 Javascript:

function ddlFilters_onSelect(e) {
    var itm = this.dataItem(e.item);

    clearForm();

    if (itm.ID > 0) {
        // Ajax call to get data....
        $.ajax({
            url: "/Home/GetPerson",
            type: "GET",
            data: { "myID": itm.ID }
        })
        .done(function (result) {
            //var aaa = data;      
            $("#personInfo").html(result);
        })
        .fail(function (xhr, status, err) {
            alert(xhr.responseText);
        });
    }
};

型号:

 public partial class MyModel
    {
        public decimal ID { get; set; }
        public string FirstName{ get; set; }
        public string LastName{ get; set; }
        public string MiddleName{ get; set; }
    }

编辑: 控制器代码:

 // Initial call to main view
    public ActionResult CreateNewPerson()
    {
        return View();
    }

    // Call to load Partial View initially
    public PartialViewResult GetPersonInfo()
    {
        return PartialView("_PersonForm", new MyModel());
    }

    // Call to load partial view with data
    public PartialViewResult GetPerson(int myID)
    {
        myData = GetFromDB(myID);
        return PartialView("_PersonForm", myData);
    }

    // Method to save partial form
    [HttpPost]
    public ActionResult PersonAction(MyModel filter)
    {           

        if (ModelState.IsValid)
        {
            // Go update DB
        }

        return View("CreateNewPerson");
    }

【问题讨论】:

  • 你能发布控制器代码吗?

标签: asp.net-mvc asp.net-mvc-5


【解决方案1】:

这与您描述的场景不完全一样,但这是我的团队使用部分的方式:

1) 在主视图的 ViewModel 中,为局部视图的模型添加一个属性(例如 MyModel)。

2) 在cshtml中调用partial View时,一定要告诉MVC在哪里绑定partial View的内容:

  @Html.Partial("_PersonAction", Model.MyModel, new ViewDataDictionary(Html.ViewData) {
      TemplateInfo = new TemplateInfo { HtmlFieldPrefix = Html.NameFor(m => m.MyModel).ToString() }
  })

请注意我们如何使用TemplateInfo 为部分设置正确的上下文,因此部分中呈现的输入以正确的名称作为前缀,以使模型绑定工作。例如。 &lt;input name="MyModel.FirstName"&gt; 你可能可以用 javascript 伪造这个,但不要问我是怎么做的。

3) 我们的控制器动作接受主页的 ViewModel。 &lt;form&gt; 在主页上并围绕部分调用。

【讨论】:

  • 第一次模型为空时怎么办?我尝试了您所说的并创建了一个具有 MyModel 属性的 MainModel。在初始视图中,我创建了 MainModel 的一个新实例并初始化了 MyModel 属性。 (即 new MyModel())现在,当我发布数据时,它无法识别任何更改的值。
  • 我仍然怀疑问题在于部分渲染的输入的名称和 ID 前缀不正确(您可以通过检查生成的 HTML 来确认这一点)。您可以尝试从GetPerson 返回正常视图吗?希望这可以解决前缀问题,并且您可以保留原始代码和模型结构。
  • 我对 MVC 还是很陌生,但我不确定应该使用什么前缀?当我检查视图时,我看到了表单及其 ID,并且所有字段都将输入元素的名称和 id 设置为模型中的字段。
  • 我创建了一个按照建议返回视图的方法。我仍然看到相同的行为,因此这与我绑定该模型的方式有关。
  • 感谢您的帮助。我有一个 JS 方法在发布之前清除表单。
猜你喜欢
  • 1970-01-01
  • 1970-01-01
  • 2017-09-02
  • 1970-01-01
  • 1970-01-01
  • 2021-07-16
  • 1970-01-01
  • 1970-01-01
  • 2011-07-26
相关资源
最近更新 更多