将KeyValuePair绑定到复选框列表

时间:2011-04-15 11:56:54

标签: asp.net-mvc-2 binding

我在C#中使用ASP.Net MVC。我有一个模型,其中包含筛选条件的成员。该成员是IList>。该键包含要显示的值,该值表示是否选择了此过滤器。我想将它绑定到我的视图上的一堆复选框。这就是我做到的。

<% for(int i=0;i<Model.customers.filterCriteria.Count;i++) { %>
<%=Html.CheckBoxFor(Model.customers.filterCriteria[i].value)%>&nbsp;
<%=Model.customers.filterCriteria[i].key%>
<% } %>

这会正确显示所有复选框。但是当我在控制器中提交我的表单时,无论我在视图中选择什么,我都会为filtercriteria获取null。

this帖子我得到了一个创建单独属性的提示。但这对IList如何有效?有什么建议吗?

1 个答案:

答案 0 :(得分:6)

KeyValuePair<TKey, TValue>结构的问题在于它具有私有设置器,这意味着默认模型绑定器无法在POST操作中设置其值。它有一个特殊的构造函数,需要使用它来传递键和值,但当然默认的模型绑定器不知道这个构造函数,它使用默认的一个,所以除非你为这种类型编写自定义模型绑定器将无法使用它。

我建议您使用自定义类型而不是KeyValuePair<TKey, TValue>

因此,我们始终以视图模型开始:

public class Item
{
    public string Name { get; set; }
    public bool Value { get; set; }
}

public class MyViewModel
{
    public IList<Item> FilterCriteria { get; set; }
}

然后是控制器:

public class HomeController : Controller
{
    public ActionResult Index()
    {
        return View(new MyViewModel
        {
            FilterCriteria = new[] 
            {
                new Item { Name = "Criteria 1", Value = true },
                new Item { Name = "Criteria 2", Value = false },
                new Item { Name = "Criteria 3", Value = true },
            }
        });
    }

    [HttpPost]
    public ActionResult Index(MyViewModel model)
    {
        // The model will be correctly bound here
        return View(model);
    }
}

和相应的~/Views/Home/Index.aspx视图:

<% using (Html.BeginForm()) { %>
    <%= Html.EditorFor(x => x.FilterCriteria) %>
    <input type="submit" value="OK" />
<% } %>

最后我们为~/Views/Shared/EditorTemplates/Item.ascx~/Views/Home/EditorTemplates/Item.ascx中的Item类型编写了一个自定义编辑器模板(如果此模板仅适用于Home控制器而未重复使用):

<%@ Control 
    Language="C#" 
    Inherits="System.Web.Mvc.ViewUserControl<AppName.Models.Item>" 
%>
<%= Html.CheckBoxFor(x => x.Value) %>
<%= Html.HiddenFor(x => x.Name) %>
<%= Html.Encode(Model.Name) %>

我们已经实现了两件事:从丑陋的for循环中清除视图,并使模型绑定器成功绑定POST操作中的复选框值。