asp.net - 下面的代码在mvc3中如何工作?

标签 asp.net asp.net-mvc-3 razor

我的 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/

相关文章:

c# - 在将表单发送到后端之前,如何将密码字符串转换为 Base64 字符串?

asp.net - 创建自定义 nuget 包以在项目之间共享通用布局

c# - 使用 Razor 从表中获取行信息

ASP.NET 5 DNX : How to shutdown application properly?

c# - 比较数据表并返回不匹配的行

css - System.Web.Optimization 捆绑 css js 缓存

jquery - 如何禁用只读字段上的 jquery 验证?

javascript - 通过onclick调用asp.net中的onserverclick

ASP.NET MVC 包罗万象的路由

mysql - 如何从连接到 visual studio 的 mysql 数据库中检索数据?