DropDownListFor - 不选择“Selected”值

时间:2012-03-23 01:13:19

标签: asp.net-mvc-3 html.dropdownlistfor

关于DropDownListFor未选择“已选择”值的其中一个问题。 这是代码:

型号:

public class CreateEditAccountModel
{
    [Required]
    [Display(Name = "Permission")]
    public int PermissionId { get; set; }
    public IEnumerable<SelectListItem> Permissions { get; set; }
}

控制器:

[HttpGet]
[Authorize]
public ActionResult EditAccount(int id)
{
    CreateEditAccountModel model = new CreateEditAccountModel();
    model.Permissions = PermissionsAll();
    return View("CreateEditAccount", model);
}

此时如果我在返回行上设置了一个断点,model.Permissions包含具有多个项目的正确IEnumerable<SelectListItem>个对象,且只包含一个Selected = true

查看:

@using (Html.BeginForm())
{
    @Html.DropDownListFor(m => m.PermissionId, Model.Permissions)
}

渲染:

<select id="PermissionId" name="PermissionId">
    <option value="">-- Select --</option>
    <option value="1">Permission one</option>
    <option value="2">Permission two</option>
</select>

由于某些原因,任何选项都没有选定属性,并且选择了第一个选项。

感谢任何帮助。


更新

它似乎与此article有关。总结本文的解决方案,我需要确保属性名称(@html.DropDownList的第一个参数不匹配模型的任何现有属性。 任何人都可以解释为什么会这样吗?

当我在视图中写下这样的内容时,它会正确呈现下拉:

@Html.DropDownList("PermissionIdNotMatching", Model.Permissions)

但是,这样做没有任何逻辑意义,因为我实际上希望binder能够将select元素的名称与model属性相匹配。否则我必须手动抓取这样的值:Request.Form["PermissionIdNotMatching"];

有人有任何想法吗?


查看已接受的答案及其第一条评论。

2 个答案:

答案 0 :(得分:8)

好的,当PermissionId为int时,让我们讨论一下你的例子。您发布了CreateEditAccountModel类型的模型进行查看。创建此模型时,PermissionId等于0(默认值为int)。并且DropDownListFor在视图中获得此值。因此,您没有选定的值。 当您使用字符串类型时,默认值PermissionId为null,因此`DropDownListFor采用SelectList的默认值。

在这种情况下,最好对int?使用Nullable<int>PermissionId类型。

答案 1 :(得分:4)

当您使用@Html.DropDownListFor(m => m.PermissionId, Model.Permissions)时,请确保您的模型中已设置 PermissionId - 即所选项目/ ID 。此外,该模型还包含“已选择”属性:

var query = DatabaseContexts.Select(
            c => new SelectListItem
            {
                Value = c.Key,
                Text = c.Value,
                Selected = c.Key == currentUsed
            });

 PermissionId = that want to select;
 Permissions = query.AsEnumerable();

<强>更新

这里是HttpGet的完整示例:

在HomeController.cs中:

[HttpGet]
public ActionResult EditAccount(int id)
{
    CreateEditAccountModel model = new CreateEditAccountModel();

    var permissionsAll = new List<SelectListItem>
         {
             new SelectListItem
                 {
                     Value = "",
                     Text = "--please select--",
                     Selected = false
                 },
             new SelectListItem
                 {
                     Value = "1",
                     Text = "Permission one",
                     Selected = true
                 },
             new SelectListItem
                 {
                     Value = "2",
                     Text = "Permission two",
                     Selected = false
                 }
         };
    model.PermissionId = 1; //add this line
    model.Permissions = permissionsAll; // PermissionsAll();// -- get data from services or anywhere....
    return View("EditAccount", model);
}

CreateEditAccountModel.cs:

public class CreateEditAccountModel
{
    [Required]
    [Display(Name = "Permission")]
    public int PermissionId { get; set; }
    public IEnumerable<SelectListItem> Permissions { get; set; }

}

EditAccount.cshtml:

@using MvcApplication1.Models
@model CreateEditAccountModel
@{
   ViewBag.Title = "EditAccount";
 }

<h2>EditAccount</h2>
@using (Html.BeginForm())
{
   @Html.DropDownListFor(m => m.PermissionId, Model.Permissions)
}

运行应用程序并转到/ home / editaccount / 1,默认情况下,下拉列表将选择“Permission one”。

我认为PermissionId必须是'string'类型,System.Web.Mvc.SelectedListItem.Value是'string'

如果您想在下拉列表中的用户选择项目时执行某些操作,则可能需要[HttpPost]。

BTW:this link对你有用吗?