【问题标题】:how to populate text boxes based on dropdownlist selection mvc如何根据下拉列表选择 mvc 填充文本框
【发布时间】:2017-02-19 00:42:32
【问题描述】:

我是 MVC 新手,也是 JQuery 新手。我正在尝试根据下拉列表选择填充文本框。我的产品模型包含字段 ProductId、Name 和 Price。我想根据选择的产品名称在我的 QuoteDetails 中填充 ProductId 和 Price 字段。我的控制器动作如下:

public ActionResult AddProduct(int quoteId, int quoteDetailId)
        {
            var items = db.Products.ToList();
            ViewBag.ProductData = items;


            ViewData["QuoteId"] = quoteId;
            ViewData["QuoteDetailId"] = quoteDetailId;
            return PartialView("EditQuoteDetail", new QuoteDetail { QuoteId = quoteId, QuoteDetailId = quoteDetailId, ProductId = 1, ProductName = " ", Amount = 1, ListPrice = 0, Discount = 0, Price = 0 });
        }

部分视图EditQuoteDetail的相关部分如下:

                @Html.HiddenFor(model => model.QuoteId, new { htmlAttributes = new { @class = "form-control" } })
                @Html.HiddenFor(model => model.QuoteDetailId, new { htmlAttributes = new { @class = "form-control" } })
                @Html.EditorFor(model => model.ProductId, new { htmlAttributes = new { @id="ProductId", @class = "form-control" } })
                @Html.DropDownList("ProductName", new SelectList(ViewBag.ProductData, "Name", "Name"), new { @id = "ProductName" })
                @Html.EditorFor(model => model.Amount, new { htmlAttributes = new { @class = "form-control" } })
                @Html.EditorFor(model => model.ListPrice, new { htmlAttributes = new { @id="Price", @class = "form-control" } })
                @Html.EditorFor(model => model.Discount, new { htmlAttributes = new { @class = "form-control" } })
                @Html.EditorFor(model => model.Price, new { htmlAttributes = new { @class = "form-control" } })

我用来尝试填充 ProductId 和 Price 字段的脚本如下:

<script type="text/javascript">
    $(document).ready(function () {
        $('#ProductName').change(function () {
            $('#ProductId').val($(this).val());
            $('#Price').val($(this).val());
        });
    });
</script> 

但是当我进行下拉列表选择时,什么也没有发生。我究竟做错了什么?任何帮助将不胜感激。

【问题讨论】:

  • 页面上是否存在这些元素 ID? change 处理程序是否已执行?
  • 我添加了 ID(见上文)。不过,当我更改下拉列表选择时,什么也没有发生。

标签: c# jquery asp.net-mvc


【解决方案1】:

这就是我认为正在发生的事情......

(1) @Html.DropDownList("ProductName", new SelectList(ViewBag.ProductData, "Name", "Name"), new { @id = "ProductName" })

此行创建了一个&lt;select&gt; html 元素,其 id 为“ProductName”,正如预期的那样;尽管该列表中optionsvalue 是文本值。因为您对option 的值和文本都使用了“名称”。例如:

<select id="ProductName" name="ProductName">
    <option value="Product 1">Product 1</option>
    <option value="Product 2">Product 2</option>
</select>

(2) @Html.EditorFor(model =&gt; model.ProductId, new { htmlAttributes = new { @id="ProductId", @class = "form-control" } })

由于您使用的是 EditorFor Html 帮助程序,它正在尝试验证 ProductId 的整数(我假设)。您的 javascript 正在尝试插入一个字符串,例如“产品 1”。

(3) @Html.EditorFor(model =&gt; model.ListPrice, new { htmlAttributes = new { @id="Price", @class = "form-control" } })

这有一个稍微不同的问题。 HTML 元素的 ID 将默认为“ListPrice”,并且不会被 htmlAttributes 对象中的 @id 属性覆盖。附带问题,您的意思是将@id = "Price" 放在“ListPrice”元素上吗?即使您修复了这些元素的 ID 属性,您仍然可能会遇到上面 (2) 中的数据类型问题。

尝试将目标元素切换为 TextBoxFor 作为快速测试。

【讨论】:

  • 我将上面示例 2) 和 3) 中的 EditorFor 更改为 TextBoxFor,但仍然没有运气。当我更改下拉列表选择时没有任何反应。
  • 有趣...如果您所做的只是在这两行上将 EditorFor 更改为 TextBoxFor,那么我希望 (2) 可以工作,但 (3) 不会因为 id/naming 问题提及。当我重新创建您的场景时,这就是发生在我身上的事情。
  • javascript 没有触发,我不知道为什么。
  • 在没有看到所有文件的情况下很难弄清楚这一点。我只能说检查文件,开始孤立的事情,删除与问题无关的无关项目,基本上使用消除的过程。
  • 好的,所以 BeginCollectionItem 帮助器的使用完全超越了您的 html 并插入其自己的 ID 和 Class 属性...例如 quoteDetail[2b71523b-3714-4e0d-bb83-e8fbb3b3a7fb].Price 和 quoteDetail_2b71523b -3714-4e0d-bb83-e8fbb3b3a7fb__ProductList。由于这些似乎正在生成随机数,因此您可能无法针对 ID 进行编程。如果要使用 BeginCollectionItem 帮助器,则必须重新考虑整个方法。
【解决方案2】:

问题不在于您正在填充的脚本dropdown ViewBag.ProductData, "Name", "Name" 按名称命名,因此 dropdownid 也将是其 Name 以及 ProductIdPrice 都是 int,因此您无法在 int 字段中设置文本值

所以你应该设置ViewBag.ProductData, "Id", "Name",当你运行脚本时,它会得到intproductId

编辑

如果您想根据您的产品 id 获取数据,您必须在 jquery 中为此进行 ajax 调用,并且您必须在控制器中为此执行操作

 [HttpPost]
        public ActionResult GetProduct(int pId)
        {
            var data = db.Products.Find(id);
            return Json(data);
        }

你的看法是

       @model CMSUsersAndRoles.Models.QuoteDetail

    @{
        ViewBag.Title = "EditQuoteDetail";
        Layout = null;
    }

    @{
        var quoteId = (int)ViewData["QuoteId"];
        var quoteDetailId = (int)ViewData["QuoteDetailId"];
    }

     <!DOCTYPE html>
<html>
<head>
    <script src="https://ajax.googleapis.com/ajax/libs/jquery/3.1.1/jquery.min.js"></script>

</head>
<body>        
    <div id="row">
        <table>

            @using (Html.BeginCollectionItem("quoteDetail"))

            {

                <tr>
                    @Html.HiddenFor(model => model.QuoteId, new { htmlAttributes = new { @class = "form-control" } })
                    @Html.HiddenFor(model => model.QuoteDetailId, new { htmlAttributes = new { @class = "form-control" } })
                    @Html.TextBoxFor(model => model.ProductId, new { htmlAttributes = new { @id="ProductId", @class = "form-control" } })
                    @Html.DropDownList("ProductList", new SelectList(ViewBag.ProductData, "ProductId", "Name"), new { @id = "ProductList" })
                    @Html.EditorFor(model => model.Amount, new { htmlAttributes = new { @class = "form-control" } })
                    @Html.TextBoxFor(model => model.Price, new { htmlAttributes = new { @id="Price", @class = "form-control" } }
                    @Html.EditorFor(model => model.Discount, new { htmlAttributes = new { @class = "form-control" } })
                    @Html.EditorFor(model => model.ListPrice, new { htmlAttributes = new { @class = "form-control" } })
                                @Ajax.ActionLink(" ", "DeleteProduct", "QuoteViewModel", new { quoteId = Model.QuoteId, quoteDetailId = (Model.QuoteDetailId) },
                              new AjaxOptions
                              {
                                  HttpMethod = "POST",
                                  Confirm = "Are you Sure You Want to Delete " + Model.ProductName,
                                  OnSuccess = "RemoveRow"
                              },
                              new { @class = "btn btn-danger glyphicon glyphicon-trash" })
                            </tr>
            }

        </table>
    </div>
<script type="text/javascript">
            $(document).ready(function () {
                $('#ProductList').change(function () {
                    $.post("/QuoteViewModel/GetProduct", { pId: $(this).val() }, function (data) {
                        $('#ProductId').val(data.ProductId);
                        $('#Price').val(data.Price);
                    });
                });
            });
    </script>

</body>
</html>

【讨论】:

【解决方案3】:

终于,我找到了答案。当 travis.js 说 BeginCollectionItem 帮助程序超过了我的 HTML 时,我开始走上正确的道路,所以我必须使用 id contains 语法才能使其工作。工作的 jQuery(在父视图中)如下:

<script type="text/javascript">
            $(document).ready(function () {
                $(document).on("change", '[id*="ProductList"]', function () {
                    $.post("/QuoteViewModel/GetProduct", { pId: $(this).val() }, function (data) {
                        $("[id*='ProductId']").val(data.ProductId);
                        $("[id*='Price']").val(data.Price);
                    });
                });
              });
            </script>

控制器动作(感谢 Usman)如下:

 [HttpPost]
        public ActionResult GetProduct(int pId)
        {
            var data = db.Products.Find(pId);
            return Json(data);
        }

哇!

【讨论】:

    猜你喜欢
    • 2013-05-24
    • 1970-01-01
    • 1970-01-01
    • 2014-05-24
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    相关资源
    最近更新 更多