DropDownListFor SelectedItem的问题

时间:2011-05-05 03:41:43

标签: asp.net-mvc asp.net-mvc-3 drop-down-menu razor html.dropdownlistfor

这让我很困惑。

这是我的观点:

@Html.DropDownListFor(model => model.ScoreDescription, 
                               Model.RatingOptions, 
                               "--", 
                               new { @id = clientId })

模特:

public decimal? Score { get; set; }
public SelectList RatingOptions
{ 
    get
    {
        var options = new List<SelectListItem>();

        for (var i = 1; i <= 5; i++)
        {
            options.Add(new SelectListItem
            {
                Selected = Score.HasValue && Score.Value == Convert.ToDecimal(i),
                Text = ((decimal)i).ToRatingDescription(ScoreFactorType),
                Value = i.ToString()
            });
        }

        var selectList = new SelectList(options, "Value", "Text");
            // At this point, "options" has an item with "Selected" to true.
            // Also, the underlying "MultiSelectList" also has it.
            // Yet selectList.SelectedValue is null. WTF?
        return selectList;
    }
}

正如评论所示,我无法让所选值发生。

这与我使用可空decimal的事实有关吗?在那个循环之后,options是正确的,因为它只有1个项目,其中select为true,所以看起来我做的是正确的。

现在,如果我使用不同的 SelectList重载:

var selectedValue = Score.HasValue ? Score.Value.ToString("0") : string.Empty;
var selectList = new SelectList(options, "Value", "Text", selectedValue);

有效。为什么?起初我认为它可能是一个LINQ技巧(例如延迟执行),但我尝试强制.ToList()并没有区别。

就像设置Selected属性一样,SelectListItem无效,您可以使用SelectList ctor参数在最后设置它。

任何人都可以对此有所了解吗?

1 个答案:

答案 0 :(得分:4)

如果你看一下SelectList类的实现,它实际上并没有使用你传递SelectListItem的事实。它适用于IEnumerable。因此,不使用Selected的{​​{1}}属性。我个人更喜欢通过设置绑定ddl的相应属性的值来设置下拉列表的选择值。

示例:

SelectListItem

然后在控制器操作中只需将public int? Score { get; set; } public SelectList RatingOptions { get { var options = Enumerable.Range(1, 5).Select(i => new SelectListItem { Text = ((decimal)i).ToRatingDescription(ScoreFactorType), Value = ((decimal)i).ToString() }); return new SelectList(options, "Value", "Text"); } } 属性设置为必要值,并在视图中使用此Score属性绑定到:

Score