ASP.. Net MVC复选框值从视图到自定义控制器方法

ASP.Net MVC checkbox values from view to custom controller method

本文关键字:自定义 控制器 方法 视图 Net MVC 复选框 ASP      更新时间:2023-09-26

我有一个显示模型项的表的视图。我已经提取了视图的相关部分:

@model System.Collections.Generic.IEnumerable<Provision>
@using (Html.BeginForm("SaveAndSend", "Provision", FormMethod.Post))
{
    if (Model != null && Model.Any())
    {
        <table class="table table-striped table-hover table-bordered table-condensed">
            <tr>
                ...
                // other column headers
                ...
                <th>
                    @Html.DisplayNameFor(model => model.IncludeProvision)
                </th>
                ...
                // other column headers
                ...
            </tr>
            @foreach (var item in Model)
            {
                <tr>
                    ...
                    // other columns
                    ...
                    <td>
                        @Html.CheckBoxFor(modelItem => item.IncludeProvision)
                    </td>
                    ...
                    // other columns
                    ...
                </tr>
            }
        </table>
        <button id="save" class="btn btn-success" type="submit">Save + Send</button>
    }
    ...
}

这样可以很好地工作,并且根据给定模型项的IncludeProvision字段的布尔值,复选框值在视图中正确显示。

根据Andrew Orlov的回答,我已经修改了视图和控制器,SaveAndSend()控制器方法现在是:

[HttpPost]
public ActionResult SaveAndSend(List<Provision> provisions)
{
    if (ModelState.IsValid)
    {
        // perform all the save and send functions
        _provisionHelper.SaveAndSend(provisions);
    }
    return RedirectToAction("Index");
}

但是,此时传入的模型对象为空。

包括Provision模型对象以保证完整性:

namespace
{
    public partial class Provision
    {
        ...
        // other fields
        ...
        public bool IncludeProvision { get; set; }
    }
}

我的问题是,当单击"SaveAndSend"按钮时,从每个复选框中获取选中/未选中值并更新每个模型项的会话IncludeProvision字段的最佳方法是什么?

不能使用foreach循环为集合中的属性生成表单控件。它创建了重复的name属性(在您的情况下name="item.IncludeProvision"),这与您的模型没有关系,并复制了无效的html的id属性。使用for循环(你的模型需要是IList<Provision>

)
for(int i = 0; i < Model.Count; i++)
{
  <tr>
    <td>....</td>
    <td>@Html.CheckBoxFor(m => m[i].IncludeProvision)<td>
  </tr>
}

或为Provision的类型创建一个EditorTemplate。在/Views/Shared/EditorTemplates/Provision.cshtml中(注意模板的名称必须与类型的名称匹配)

@model Provision
<tr>
  <td>....</td>
  <td>@Html.CheckBoxFor(m => m.IncludeProvision)<td>
</tr>

和在主视图中(模型可以是IEnumerable<Provision>)

<table>
  @Html.EditorFor(m => m)
</table>

正如@mattytommo在评论中所说,您应该将模型发布到控制器。这可以通过将复选框放入表单中来实现。在点击"保存并退出"按钮后,来自此表单内输入的所有数据将被序列化并发送到您的控制器,在那里您可以使用会话变量等执行操作。之后,你可以重定向到任何你喜欢的地方。

public class YourModel
{
    ...
    public bool IncludeProvision { get; set; }
    ...
}
<<p> 视图/strong>
@model YourModel
...
@using (Html.BeginForm("SaveAndSend", "Test", FormMethod.Post))
{
    ...
    @Html.CheckBoxFor(model => model.IncludeProvision)
    ...
    <button type="submit">Save and send</button>
}
...
控制器

public class TestController : Controller
{
    ...
    [HttpPost]
    public ActionResult SaveAndSend(YourModel model)
    {
         if (ModelState.IsValid)
         {
             // Some magic with your data
             return RedirectToAction(...);
         }
         return View(model); // As an example
    }
    ...
}