【问题标题】:Html.DropDownListFor confusionHtml.DropDownList 用于混淆
【发布时间】:2014-10-24 21:42:19
【问题描述】:

有人可以帮我理解 Html.DropDownListFor 的工作原理吗? 我有一个模型如下

public class TestModel
{
    public IList<SelectListItem> ProductNames { get; set; }
    public string Product { get; set; }
}

对 DropDownListFor 的调用看起来像

@Html.DropDownListFor(model => model.ProductNames,  Model.ProductNames, "Select a Product", new {@class="selectproductname" })

通过此设置,我发现下拉列表已正确填充,但是在提交表单后,我似乎无法获取所选项目。另外从我读到的对 Html.DropDownListFor 的调用实际上应该看起来像

@Html.DropDownListFor(model => model.Product,  Model.ProductNames, "Select a Product", new {@class="selectproductname" })

事实上,代码的其他部分也是如此,但是当我这样做时,下拉列表不会被填充。我在这里遗漏了什么吗?

一些旁注: 1)这个下拉列表的填充发生在从另一个下拉列表中选择一个值之后,所以我通过调用 getJSON 进行 AJAX 调用以从数据库中获取数据 2) 该应用程序是一个MVC应用程序

非常感谢您提供的任何帮助。如果您需要任何其他信息来帮助回答此问题,请告诉我

编辑: 这里有更多细节

这是控制器中用于检索下拉数据的操作方法

[AcceptVerbs(HttpVerbs.Get)]
    public JsonResult LoadProductsBySupplier(string parentId)
    {
        var ctgy = this._categoryService.GetAllCategoriesByParentCategoryId(Convert.ToInt32(parentId));
        List<int> ctgyIds = new List<int>();

        foreach (Category c in ctgy)
        {
            ctgyIds.Add(c.Id);
        }

        var prods = this._productService.SearchProducts(categoryIds: ctgyIds, storeId: _storeContext.CurrentStore.Id, orderBy: ProductSortingEnum.NameAsc);

        products = prods.Select(m => new SelectListItem()
        {
            Value = m.Id.ToString(),
            Text = m.Name.Substring(m.Name.IndexOf(' ') + 1)
        });

        var p = products.ToList();
        p.Insert(0, new SelectListItem() { Value = "0", Text = "Select A Product" });
        products = p.AsEnumerable();
        //model.ProductNames = products.ToList();


        return Json(products, JsonRequestBehavior.AllowGet);
    }

这是对控制器中操作的 JQuery 调用

$("#Supplier").change(function () {
        var pID = $(this).val();            
        $.getJSON("CoaLookup/LoadProductsBySupplier", { parentId: pID },
                function (data) {
                    var select = $("#ProductNames");
                    select.empty();
                    if (pID != "0") {
                        $.each(data, function (index, itemData) {
                            select.append($('<option/>', {
                                value: itemData.Value,
                                text: itemData.Text
                            }));
                        });
                    }
                });
    });

当我使用 model => model.Product 时,即使在变量 data 中返回了数据,也不会进入这个 $.each 循环

【问题讨论】:

  • 第二种用法正确。 Property 的值将是所选选项的值,但是您没有显示如何在 ajax 调用中填充选项,因此很难知道问题出在哪里。
  • 向我们展示您如何填充IList&lt;SelectListItem&gt; ProductNames 这完全取决于SelectListItemValue 部分。正如@StephenMuecke 所说,如果您将Product 值分配给ValueProductNames ListItem 的一部分,则第二次使用是正确的
  • 当你在 ajax 成功回调中使用model =&gt; model.Product 时,像这样使用var select = $("#Product")var select = $(".selectproductname") 选择器可以是#id.classname
  • 谢谢文卡塔。我知道这一定很愚蠢。感谢您的帮助

标签: c# asp.net-mvc html.dropdownlistfor


【解决方案1】:

第二种用法是正确的,但是当你使用时

@Html.DropDownListFor(model => model.Product, .....

您正在生成一个带有id="Product" 属性的&lt;select&gt;,因此您需要更改脚本以引用具有此ID 的元素

....
$.getJSON("CoaLookup/LoadProductsBySupplier", { parentId: pID }, function (data) {
  var select = $("#Product"); // change this selector
  select.empty();
  ....

编辑

另一方面,您不一定需要在控制器方法中创建SelectList,您的代码可以简化为

[AcceptVerbs(HttpVerbs.Get)]
public JsonResult LoadProductsBySupplier(int parentId)
{
  List<int> ctgyIds = _categoryService.GetAllCategoriesByParentCategoryId(parentId).Select(c => c.ID).ToList();
  var products= _productService.SearchProducts(categoryIds: ctgyIds, storeId: _storeContext.CurrentStore.Id, orderBy: ProductSortingEnum.NameAsc).AsEnumerable().Select(p => new
  {
    ID = p.ID,
    Text = p.Name.Substring(m.Name.IndexOf(' ') + 1)
  });
  return Json(products, JsonRequestBehavior.AllowGet);
}

和脚本

$("#Supplier").change(function () {
  var pID = $(this).val();
  var select = $("#Product").empty().append($('<option/>').text('Select A Product'));
  if (pID == '0') { return; } // this should really be testing for null or undefined but thats an issue with your first select          
  $.getJSON('@Url.Action("LoadProductsBySupplier", "CoaLookup")', { parentId: $(this).val() }, function (data) {
    $.each(data, function (index, item) {
      select.append($('<option/>').val(item.ID).text(item.Text);
    });
  });
});

还要注意脚本中$.getJSON 之前的if 子句 - 调用服务器然后决定忽略返回值没有多大意义

【讨论】:

  • 非常感谢 Stephen,非常感谢您给我一些关于如何改进代码的提示。我总是试图寻找这样的建议
【解决方案2】:

要在编辑页面中获取选定的值,请尝试使用:

@Html.DropDownList("name", new SelectList(ViewBag.Product, "Id","Name", item.Id))

在此 item.Id 是选定的值,而 ViewBag.Product 您必须使用 linq 从您的产品中填充它,例如在控制器中。

【讨论】:

    猜你喜欢
    • 2016-03-28
    • 1970-01-01
    • 2010-12-25
    • 1970-01-01
    • 1970-01-01
    • 2012-12-17
    • 1970-01-01
    • 2021-10-22
    • 2011-06-05
    相关资源
    最近更新 更多