使用复合模型从CheckBoxes获取值

时间:2014-01-27 15:55:13

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

我正在尝试获取用户选中复选框的Id值列表。这是模型:

using System.Collections.Generic;

namespace TestWebApplication3.Models
{
    public class TestViewModel
    {
        public IEnumerable<InnerViewModel> ModelData { get; set; }

        public class InnerViewModel
        {
            public int Id { get; set; }

            public bool Checked { get; set; }
        }
    }
}

控制器:

using System.Web.Mvc;
using TestWebApplication3.Models;

namespace TestWebApplication3.Controllers
{
    public class HomeController : Controller
    {
        public ActionResult Index()
        {
            var test = new TestViewModel();

            test.ModelData = new[]
            {
                new TestViewModel.InnerViewModel {Id = 10},
                new TestViewModel.InnerViewModel {Id = 20},
                new TestViewModel.InnerViewModel {Id = 30},
                new TestViewModel.InnerViewModel {Id = 40}
            };

            return View(test);
        }

        [HttpPost]
        public string TestAction(TestViewModel model)
        {
            string s = "";
            foreach (TestViewModel.InnerViewModel innerViewModel in model.ModelData)
            {
                if (innerViewModel.Checked)
                    s += innerViewModel.Id + " ";
            }
            return s;
        }
    }
}

观点:

@model TestWebApplication3.Models.TestViewModel

@using (Html.BeginForm("TestAction", "Home"))
{
    <ol>
        @foreach (var testData in Model.ModelData)
        {
            <li>
                @Html.HiddenFor(m => testData.Id)
                @Html.CheckBoxFor(m => testData.Checked)
            </li>
        }
    </ol>

    <input type="submit"/>
}

所以我正在显示一个InnerViewModel对象列表(在Index action中创建)作为复选框。当用户提交表单时,我想以某种方式获取在TestAction方法中“检查”的Id值列表。但是返回的模型总是为空。

在我正在创建的应用程序中,模型还有更多属性,因此将InnerViewModel对象列表嵌套在TestViewModel中非常重要。我也不想使用像MvcCheckBoxList这样的第三方解决方案,因为在我看来这对于这样一个简单的任务来说太过分了。

任何人都可以向我解释这项工作缺少什么吗?

4 个答案:

答案 0 :(得分:1)

我稍微更改了您的代码以使其正常工作 -

ViewModel -

public class TestViewModel
{
    public List<InnerViewModel> ModelData { get; set; }
    public class InnerViewModel
    {
        public int Id { get; set; }
        public bool Checked { get; set; }
    }
}

控制器 -

    public ActionResult Index()
    {
        var test = new TestViewModel();

        test.ModelData = new List<TestViewModel.InnerViewModel>()
        {
            new TestViewModel.InnerViewModel {Id = 10},
            new TestViewModel.InnerViewModel {Id = 20},
            new TestViewModel.InnerViewModel {Id = 30},
            new TestViewModel.InnerViewModel {Id = 40}
        };

        return View(test);
    }

    public string TestAction(TestViewModel model)
    {
        string s = "";
        foreach (TestViewModel.InnerViewModel innerViewModel in model.ModelData)
        {
            if (innerViewModel.Checked)
                s += innerViewModel.Id + " ";
        }
        return s;
    }

查看 -

@model MVC.Controllers.TestViewModel

@using (Html.BeginForm("TestAction", "Home"))
{
    <ol>
        @for (int i = 0; i < Model.ModelData.Count() ; i++ )
        {
            <li>
                @Html.HiddenFor(m => m.ModelData[i].Id)
                @Html.CheckBoxFor(m => m.ModelData[i].Checked)
            </li>
        }
    </ol>

    <input type="submit" />
}

答案 1 :(得分:0)

您需要了解模型绑定器的工作原理。一旦你理解了,就很简单。

MVC Binding to checkbox

答案 2 :(得分:0)

复杂对象需要建立索引才能让模型绑定器选择它们。

将其更改为此,以便模型装订器将其拾取:

    @for (int i = 0; i < Model.ModelData.Count; i++)
    {
        <li>
            @Html.HiddenFor(m => Model.ModelData[i].Id)
            @Html.CheckBoxFor(m => Model.ModelData[i].Checked)
        </li>
    }

这是一篇很好的文章,解释了模型绑定中的一些问题。

http://msdn.microsoft.com/en-us/magazine/hh781022.aspx

答案 3 :(得分:0)

一种想法是使用CheckBoxFor控件。最终找到检查的内容和不检查的内容,可以为您节省很多麻烦。我之前构建了一个RadioButtonListFor,并不是很困难。实际上,这里有一个可以使用的链接。

Create MVC3 CheckBoxFor from List and getting the list back (With updated values) on Post