我的 Controller 代码
public ActionResult Create(string id)
{
ViewBag.ALLO_ID = new SelectList(_unitOfWork.AllocationMRepository.Get(), "ALLO_ID", "ALLO_ID", id);
ViewBag.TERR_ID = new SelectList(_unitOfWork.TerrListRepository.Get().OrderBy(m => m.TERR_ID), "TERR_ID", "TERR_ID");
ViewBag.ITEM_ID = new SelectList(_unitOfWork.SampleInfo.Get(), "ITEM_ID", "ITEM_ID");
return View();
}
在我看来
<div class="editor-field">
@Html.DropDownList("ALLO_ID", String.Empty)
@Html.ValidationMessageFor(model => model.ALLO_ID)
</div>
<div class="editor-label">
@Html.LabelFor(model => model.TERR_ID, "Territory Name")
</div>
<div class="editor-field">
@Html.DropDownList("TERR_ID", String.Empty)
@Html.ValidationMessageFor(model => model.TERR_ID)
</div>
<div class="editor-label">
@Html.LabelFor(model => model.ITEM_ID, "Item Name")
</div>
<div class="editor-field">
@Html.DropDownList("ITEM_ID", String.Empty)
@Html.ValidationMessageFor(model => model.ITEM_ID)
</div>
这些下拉列表是如何创建的?我不太清楚。我想知道它是如何工作的。
最佳答案
Grab the source并在您的机器上构建它。严重地。我经常引用我的副本。
回答您的具体问题,即“框架如何创建下拉列表?”它迭代可枚举集合并创建一个字符串。
MVC 库为 HtmlHelper
类定义了许多扩展方法。您可以轻松定义自己的。当然,您可以构建其他帮助器类,但是 HtmlHelper
可以随时用于此目的。
通过几层重载,我们发现:
private IHtmlString BuildDropDownList(string name, string defaultOption, IEnumerable<SelectListItem> selectList,
object selectedValue, IDictionary<string, object> htmlAttributes) {
var modelState = ModelState[name];
if (modelState != null) {
selectedValue = selectedValue ?? ModelState[name].Value;
}
selectedValue = ConvertTo(selectedValue, typeof(string));
if (selectedValue != null) {
var newSelectList = new List<SelectListItem>(from item in selectList select new SelectListItem(item));
var comparer = StringComparer.InvariantCultureIgnoreCase;
var selectedItem = newSelectList.FirstOrDefault(item => item.Selected || comparer.Equals(item.Value ?? item.Text, selectedValue));
if (selectedItem != default(SelectListItem)) {
selectedItem.Selected = true;
selectList = newSelectList;
}
}
TagBuilder tagBuilder = new TagBuilder("select") {
InnerHtml = BuildListOptions(selectList, defaultOption)
};
tagBuilder.MergeAttributes(htmlAttributes);
tagBuilder.MergeAttribute("name", name, replaceExisting: true);
tagBuilder.GenerateId(name);
// If there are any errors for a named field, we add the css attribute.
AddErrorClass(tagBuilder, name);
return tagBuilder.ToHtmlString(TagRenderMode.Normal);
}
其实没那么复杂。使用“For”后缀的扩展方法稍微复杂一些。
@Html.LabelFor(model => model.TERR_ID, "Territory Name")
注意到 lambda 表达式了吗?框架实际上并不执行它;而是执行它。相反,它将其解析为元数据并使用它来获取项目的完全限定名称。然后,可以使用它从原始属性中检索各种信息,例如与验证相关的DataAnnotations
。
实现的关键在于 private static MvcHtmlString SelectInternal(...)
,包含在 System.Web.Mvc.Html.SelectExtensions
中。与模型状态和验证的集成值得注意。
关于asp.net - 下面的代码在mvc3中如何工作?,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/16931736/