MVC 3动态地将viewModel添加到View

时间:2011-12-13 15:19:24

标签: c# asp.net-mvc-3 editorfor

我有一些与这些相似的viewModels:

public class ResturantViewModel
{
   public ResturantViewModel()
   {
       Clients.Add(new ClientViewModel());
   }
   public string MyProperty {get;set;}
   public IList<ClientViewModel> Clients = new List<ClientViewModel>();
}

public class ClientViewModel
{
   public string FirstName {get;set;}
   public string LastName {get;set;}
}

在我的视图中,我有类似的内容:

@foreach(var client in Model.Clients)
{
   <tr>
      <td>First Name: @Html.EditorFor(item => client.FirstName)</td>
      <td>Last  Name: @Html.EditorFor(item => client.LastName)</td>
   </tr>
}

我想要一个按钮,可以将一些新的空白ClientViewModel添加到ResturantViewModel.Clients列表中,以便它可以在视图中呈现并发布到Resturant / Create操作。

提前致谢

3 个答案:

答案 0 :(得分:1)

您可以查看following blog post。它使用WebForms视图引擎,但它很容易适应Razor。

答案 1 :(得分:1)

您需要在视图中实现对象列表

  <input type="text" name='Clients[@index].FirstName' value='@c.FirstName' />
  <input type="text" name='Clients[@index].LastName'  value='@c.LastName' /> 

@index++;

之后你必须用下一个索引值克隆这些字段,所以你必须得到这样的输入:

 <input type="text" name='Clients[0].FirstName' value='@c.FirstName' />
 <input type="text" name='Clients[0].LastName'  value='@c.LastName' /> 

 <input type="text" name='Clients[1].FirstName' value='@c.FirstName' />
 <input type="text" name='Clients[1].LastName'  value='@c.LastName' /> 
 <input type="text" name='Clients[2].FirstName' value='@c.FirstName' />
 <input type="text" name='Clients[2].LastName'  value='@c.LastName' /> 

在控制器中,您将接受这些对象的列表:

List<Client> Clients

答案 2 :(得分:0)

好的,谢谢你,这就是我要解决的问题。

首先我创建了一个新的部分View _ClientRow.cshtml:

@using Extensions.CollectionItemsHtmlExtension
@using ClientViewModel
@model ClientViewModel
<div class = "clientEditRow">
   @using(Html.BeginCollectionItem("Clients"))
   {
      @First Name: @Html.TextBoxFor(c=>c.FirstName)
      @Last Name: @Html.TextBoxFor(c=>c.LastName)
   }
</div>

此部分视图为客户端呈现新行。 BeginCollectionItem是在Darin提到的博客文章后下载的Html扩展。

然后在我看来我设置了:

<legend>Clients</legend>
<fieldset>
    <div id="clientEditorRows">
        @foreach(var client in Model.Clients)
        {
           Html.RenderPartial("_ClientRow", client);
        }
    </div>
    @Html.ActionLink("New Client", "NewClientRow", null, new {id = "addItem"})
</fieldset>
...
<script type="text/javascript" scr="../Scripts/listEditor.js"></script>

foreach遍历所有客户端并为每个客户端呈现部分视图。 然后在我的Controller中我写了这个方法:

public PartialViewResult NewClientRow()
{
   return PartialView("_ClientRow", new ClientViewModel())
}

此方法由ActionLink调用,并返回一个新行的html,并将其附加到前一行。 最后我从博客文章中添加了这个javascript文件代码并将其修改为我的案例:

listEditor.js

$("#addItem").click(function () {
    $.ajax({
        url: this.href,
        cache: false,
        success: function (html) { $("#clientEditorRows").append(html); }
    });
    return false;
});

此js代码将新行的html附加到页面。 希望这能有所帮助,再次感谢大家。

亚历

P.S。:接收值的HttpPost方法尚未修改并具有此签名

[HttpPost]
public ActionResult Create(ResturantViewModel resturantVM)
{
   ...
}

注意resturantVM.Clients接收所有值,不需要添加IList Clients参数