【问题标题】:ASP.NET MVC Form loaded via .ascx & ajax submits multiple times通过 .ascx 和 ajax 加载的 ASP.NET MVC 表单多次提交
【发布时间】:2011-04-18 21:01:19
【问题描述】:

我有 Resorts.aspx,它通过 Ajax 将来自 ResortProducts.ascx 的内容加载到一个 div 中。

Resorts.aspx

<script type="text/JavaScript" src="http://ajax.microsoft.com/ajax/jquery/jquery-1.4.2.min.js">
</script>

    <script type="text/javascript">

        $(function () {
            // View Resort Rates >>
            $('.ViewResortRatesLink').click(function () {
                var sID = getQueryStringParameterByName("sID", this.href);
                sID = sID.replace("~", "");
                renderCart("div" + sID, "Loading Resort Product Information...");
                $.ajax({
                    url: this.href,
                    success: function (result) {
                        renderCart("div" + sID, result)
                    }
                });
                return false;
            });
        });

        function renderCart(container, data) {
            $("#" + container).html(data);
        }

这是在 jQuery 之上触发的 ActionLink 的代码:

                        <%= Html.ActionLink(
                                    "View Resort Rates >>",
                                    "ResortProducts", 
                                    "Resorts",
                                    new { sID = _supplier.SupplierID },
                                    new { @class = "ViewResortRatesLink" })%> 

这是分区:

<div id="div<% =ResortSupplierID %>"></div>

ResortProducts.ascx 加载度假村产品列表,每个产品都包含自己的表单,使用该表单可以将产品添加到购物车。

ResortProducts.ascx

<%@ Control Language="C#" Inherits="System.Web.Mvc.ViewUserControl<TrlSite.Services.ViewModels.ResortsView>" %>
<script type="text/JavaScript" src="http://ajax.microsoft.com/ajax/jquery/jquery-1.4.2.min.js">
</script>
   <script type="text/javascript">
        $(function () {
            //+ Add to cart
            $(".addProductToCartForm").submit(function (e) {
                e.preventDefault();
                var HiddenCartForm = {
                    SupplierID: $(this.hSupplierID).val(),
                    Code: $(this.hProductCode).val(),
                };
                $.post($(this).attr("action"), HiddenCartForm, function (data) {
                    renderCart("rightColumn", data)
                });
                return false; // form already submitted using ajax, don't submit it again the regular way 
            });
        });

        function renderCart(container, data) {
            $("#" + container).html(data);
        } 
    </script>

<% foreach (var _supplier in Model.resorts) { %>
<table width="100%" cellpadding="2" cellspacing="0" id="tb_PAL">
    <tr>
        <td colspan="2" width="15%">&nbsp;</td>
        <td colspan="2">
            <table width="100%" cellpadding="2" cellspacing="0" border="0" style="table-layout:fixed;">
                <tr>
                    <td colspan="6"><hr /></td>
                </tr>
                <tr style="font-weight:bold;">
                    <td>ROOM TYPE</td>
                    <td>&nbsp;</td>
                    <td>&nbsp;</td>
                    <td align="center">PRICE</td>
                </tr>
                <tr>
                    <td colspan="6"><hr /></td>
                </tr>
                <% 
                    foreach (var _product in products)
                    { %>
                    <tr>
                        <td colspan="2" align="left" valign="top"><% = _product.Description %></td>
                        <td  align="left">
                            <% using (Html.BeginForm("AddToCart", "ShoppingCart", FormMethod.Post, new { @class = "addProductToCartForm" }))
                                { %>
                                <input type="hidden" name="hSupplierID" id="hSupplierID" value="<% = _supplier.SupplierID %>" />
                                <input type="hidden" name="hProductCode" id="hProductCode" value="<% = _product.Code %>" />
                                <input type="submit" value="+ Add to cart" />
                            <% } %>
                        </td>
                        <td valign="top" align="center">
                            <span id="roomprice_" onclick="return false;" style="text-decoration:none;cursor:default;color:#000000">
                                $<% = _product.TotalPrice %>
                            </span>
                        </td>
                    </tr>
                <% } %>    
                <tr >                       
                    <td colspan="4">
                    </td>
                </tr>
            </table>
        </td>
    </tr>
    <tr>
        <td colspan="5"><hr /></td>
    </tr>                   
</table>
<% } %>

Resorts.aspx 中可能有多个“查看度假村价格>>”链接,单击每个链接将加载包含相应产品列表的 ResortProducts.ascx。如果我在 Resorts.aspx 中仅加载一次 ResortProducts.ascx 并单击提交按钮,一切正常。它发布一次表格。但是,如果我多次加载 .ascx ,那么表单会被提交多次 .ascx 被加载。我该如何解决这个问题?当我提交表单时,它应该只发布一次,同时我应该能够发布多个表单。

【问题讨论】:

  • 我看错了,我不相信我的答案是正确的,所以我删除了它。对于那个很抱歉。我会继续关注它,如果我有其他想法,我会发布它。
  • Dusty,您将 javascript 从 .ascx 文件中移出的解决方案是正确的。现在我已经完成了所有工作。我将 javascript 移动到单独的 .js 文件中并将其引用到父 .aspx 文件中,还使用“jquery.live('click', function (e))”函数将 .ascx 文件生成的所有表单绑定到包含的 div 中父 .aspx 文件。我们缺少的最后一块是使用 .live() 函数绑定所有动态生成的表单。它现在可以按需要工作。感谢您的耐心和指引我正确的方向。
  • 好的,如果其他人有类似的问题,我会取消删除我的答案。我很高兴你能成功。

标签: jquery asp.net-mvc-2


【解决方案1】:

我没有测试过这个,我相信如果你多次添加这个控件,那么javascript部分也会被创建几次。检查是否发生这种情况,如果发生这种情况,那么我认为最好的方法是将 javascript 部分放在它自己的 js 文件中,然后在包含控件的页面中引用一次 javascript 文件。我希望这会有所帮助。

【讨论】:

  • Dusty,我尝试了您的建议,但没有帮助。即使将 javascript 移动到它自己的 .js 文件后,我也看到了相同的行为。
  • 您是在局部视图还是在父视图中引用它?如果在局部视图中,那么我相信它与您在局部视图中使用 javascript 时相同,因此请仔细检查以确保它在父视图中并且只呈现一次函数。让我知道。谢谢
  • 参考在局部视图中。我最初试图将其保留在父视图中,但随后来自 .ascx 的函数调用没有被触发。如何在 .aspx 中拥有脚本(或引用)并让 .ascx 触发它?
  • 您应该能够像往常一样使用它。查看正在发生的事情的最佳方法是在浏览器中打开页面的源代码,或者使用 Firebug 等开发人员工具。当您在主视图中有 javascript 时,它应该只显示一次,但如果您在局部视图中有它,它将显示在局部视图的每个实例中。所以如果你调用这个函数,实际上有几个函数被调用。我希望这会有所帮助。
  • 由于某种原因,当我在 .ascx 中引用 .js 文件时,表单提交会触发 .js 文件中定义的 jquery 函数但是如果我在父 .​​aspx 文件中引用 .js 文件,则表单提交通过传递 jquery 逻辑直接进入我的控制器。知道为什么会出现这种行为吗?
【解决方案2】:

更新

我刚刚在初始帖子的 cmets 中看到了相同的答案...


我知道这篇文章已经过时了,但我遇到了类似的问题。首先,我使用的是 .NET 3.5、MVC 2.0、jQuery 1.8、bootstrap 2.0。我引用的局部视图实际上是一个用户控件 (ascx),它表示一个带有几个字段和验证的表单,该表单作为模式对话框打开。

其次,这是我所做的:

  • 我将分部视图(用户控件)的 javascript 文件移至父视图,因为即使在一次调用分部视图时它也被多次调用。
  • 但是,局部视图中的 jQuery 绑定停止工作,因为在加载局部视图的内容之前执行了 javascript。
  • 我找到的解决方案是修改绑定类型以使用 jQuery 实时绑定,并且成功了。

希望对其他人有所帮助!

【讨论】:

    猜你喜欢
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2011-06-16
    • 2011-05-27
    • 1970-01-01
    • 2015-05-17
    • 2016-02-29
    • 2011-07-09
    相关资源
    最近更新 更多