SimpleModal 破坏了 ASP.Net 回发

发布于 2024-07-04 14:10:31 字数 586 浏览 12 评论 0原文

我正在使用 jQuerySimpleModal 在 ASP.Net 项目中为 Web 应用程序制作一些漂亮的对话框。 不幸的是,模式对话框中的任何按钮都无法再执行其回发,这是不可接受的。

我发现了一个 解决方法,但在我的一生中,我无法让它发挥作用,主要是因为我没有完全理解所有必要的步骤。

我还有一个解决方法,那就是替换回发,但它很丑陋,而且可能不是最可靠的。 我真的很想让回发再次正常工作。 有任何想法吗?

更新:我应该澄清一下,回发不起作用,因为用于执行回发的 JavaScript 已以某种方式损坏,因此单击按钮时什么也不会发生。

I'm using jQuery and SimpleModal in an ASP.Net project to make some nice dialogs for a web app. Unfortunately, any buttons in a modal dialog can no longer execute their postbacks, which is not really acceptable.

There is one source I've found with a workaround, but for the life of me I can't get it to work, mostly because I am not fully understanding all of the necessary steps.

I also have a workaround, which is to replace the postbacks, but it's ugly and probably not the most reliable. I would really like to make the postbacks work again. Any ideas?

UPDATE: I should clarify, the postbacks are not working because the Javascript used to execute the post backs has broken in some way, so nothing happens at all when the button is clicked.

如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。

扫码二维码加入Web技术交流群

发布评论

需要 登录 才能够评论, 你可以免费 注册 一个本站的账号。

评论(10

眼眸印温柔 2024-07-11 14:10:31

你们俩都走在正确的轨道上。 我意识到 SimpleModal 将对话框附加到正文,该正文位于 ASP.Net 的

之外,这会破坏功能,因为它找不到元素。

为了解决这个问题,我只是修改了 SimpleModal 源代码,将所有内容附加到 'form' 而不是 'body'。 创建对话框时,我还使用 persist: true 选项,以确保按钮在打开和关闭时保持不变。

谢谢大家的建议!

更新:版本 1.3 在配置中添加了一个 appendTo 选项,用于指定模式对话框应附加到哪个元素。 这里是文档

Both of you were on the right track. What I realized is that SimpleModal appends the dialog to the body, which is outside ASP.Net's <form>, which breaks the functionality, since it can't find the elements.

To fix it, I just modified the SimpleModal source to append eveything to 'form' instead of 'body'. When I create the dialog, I also use the persist: true option, to make sure the buttons stay through opening and closing.

Thanks everyone for the suggestions!

UPDATE: Version 1.3 adds an appendTo option in the configuration for specifying which element the modal dialog should be appended to. Here are the docs.

余厌 2024-07-11 14:10:31

所有标准 ASP.NET 回发都是通过调用页面上的 __doPostBack javascript 方法来工作的。 该函数提交表单(ASP.NET 实际上只喜欢每页一个表单),其中包含一些隐藏的输入字段,其中包含所有视图状态和其他优点。

从表面上看,我在 SimpalModal 中看不到任何会破坏页面表单或任何标准隐藏输入的内容,除非该模式的内容恰好来自 HTTP GET 到 ASP.NET 页面。 这将导致两个 ASP.NET 表单被呈现到一个 DOM 中,并且几乎肯定会搞砸 __doPostBack 函数。

您是否考虑过使用 ASP.NET AJAX ModalPopup 控件

All standard ASP.NET postbacks work by calling a __doPostBack javascript method on the page. That function submits the form (ASP.NET only really likes one form per page) which includes some hidden input field in which all the viewstate and other goodness lives.

On the face of it I can't see anything in SimpalModal that would screw up your page's form or any of the standard hidden inputs, unless the contents of that modal happened to come from a HTTP GET to an ASP.NET page. That would result in two ASP.NET forms being rendered into one DOM and would would almost certainly screw up the __doPostBack function.

Have you considered using the ASP.NET AJAX ModalPopup control?

溺深海 2024-07-11 14:10:31

我发现以下工作无需修改 simplemodal.js:

function modalShow(dialog) {

    // if the user clicks "Save" in dialog
    dialog.data.find('#ButtonSave').click(function(ev) {
        ev.preventDefault();

        //Perfom validation                

        // close the dialog
        $.modal.close();

        //Fire the click event of the hidden button to cause a postback
        dialog.data.find('#ButtonSaveTask').click();
    });

    dialog.data.find("#ButtonCancel").click(function(ev) {
        ev.preventDefault();
        $.modal.close();
    });
}          

因此,不要使用对话框中的按钮来导致回发,而是阻止它们的提交,然后在表单中找到一个隐藏的按钮并调用其单击事件。

I have found the following works without modifying simplemodal.js:

function modalShow(dialog) {

    // if the user clicks "Save" in dialog
    dialog.data.find('#ButtonSave').click(function(ev) {
        ev.preventDefault();

        //Perfom validation                

        // close the dialog
        $.modal.close();

        //Fire the click event of the hidden button to cause a postback
        dialog.data.find('#ButtonSaveTask').click();
    });

    dialog.data.find("#ButtonCancel").click(function(ev) {
        ev.preventDefault();
        $.modal.close();
    });
}          

So instead of using the buttons in the dialog to cause the postback you prevent their submit and then find a hidden button in the form and call its click event.

十年九夏 2024-07-11 14:10:31

被这个问题抓住了 - 非常感谢 tghw 和附录表单上的所有其他贡献者,而不是正文修复。 (通过 1.3 版本上的属性解决)

顺便说一句:如果有人需要从 .net 以编程方式关闭对话框 - 您可以使用这种类型的语法,

private void CloseDialog()
{
    string script = string.Format(@"closeDialog()");
    ScriptManager.RegisterClientScriptBlock(this, typeof(Page), UniqueID, script, true);
}

其中 closedialog 的 javascript 是这样的......

    function closeDialog() {
        $.modal.close();
    }

got caught out by this one - many thanks to tghw and all the other contributors on the appendto form instead of body fix. (resolved by attributes on the 1.3 version)

btw: If anyone needs to close the dialog programmatically from .net - you can use this type of syntax

private void CloseDialog()
{
    string script = string.Format(@"closeDialog()");
    ScriptManager.RegisterClientScriptBlock(this, typeof(Page), UniqueID, script, true);
}

where the javascript of closedialog is like this....

    function closeDialog() {
        $.modal.close();
    }
放赐 2024-07-11 14:10:31

Web 浏览器不会发布任何禁用或隐藏的表单元素。

所以发生的事情是:

  1. 用户单击对话框中的按钮。
  2. 按钮调用 SimpleModal 的 close() 方法,隐藏对话框和按钮
  3. 客户端 POST 表单(没有按钮的 ID)
  4. ASP.NET 框架无法确定单击了哪个按钮
  5. 您的服务器端代码不会被执行。

解决方案是在客户端执行您需要执行的操作(在本例中关闭对话框),然后自己调用 __doPostback()。

例如(其中“dlg”是客户端 SimpleModal 对话框引用):

btn.OnClientClick = string.Format("{0}; dlg.close();",
                        ClientScript.GetPostBackEventReference(btn, null));

这应该隐藏对话框,提交表单,并调用该按钮的任何服务器端事件。

@担

<块引用>

所有标准 ASP.NET 回发都是通过调用页面上的 __doPostBack javascript 方法来工作的。

asp:Buttons 不会调用 __doPostback(),因为 HTML 输入控件已提交表单。

Web browsers will not POST any disabled or hidden form elements.

So what's happening is:

  1. The user clicks on a button in your dialog.
  2. The button calls SimpleModal's close() method, hiding the dialog and the button
  3. The client POSTs the form (without the button's ID)
  4. The ASP.NET framework can't figure out which button was clicked
  5. Your server-side code doesn't get executed.

The solution is to do whatever you need to do on the client (closing the dialog in this case) and then call __doPostback() yourself.

For example (where "dlg" is the client-side SimpleModal dialog reference):

btn.OnClientClick = string.Format("{0}; dlg.close();",
                        ClientScript.GetPostBackEventReference(btn, null));

That should hide the dialog, submit the form, and call whatever server-side event you have for that button.

@Dan

All standard ASP.NET postbacks work by calling a __doPostBack javascript method on the page.

asp:Buttons do not call __doPostback() because HTML input controls already submit the form.

银河中√捞星星 2024-07-11 14:10:31

FWIW,我已经更新了 您指向的博客文章 带有澄清,重新发布到此处 - 推理和解释 其他详细信息位于博客文章中:

解决方案(截至午餐前最后一次签入):

  1. 覆盖对话框的 onClose 事件,然后执行以下操作:
    1. 调用对话框的默认关闭函数
    2. 将对话框 div 的 innerHTML 设置为单个  
    3. 劫持 __doPostBack,将其指向一个新函数 newDoPostBack

从我在网上看到的一些评论来看,第 1 点需要一些澄清。 不幸的是,我不再为同一个雇主工作,也无法访问我使用的代码,但我会尽力而为。 首先,您需要通过定义一个新函数并将对话框指向它来覆盖对话框的 onClose 函数,如下所示:

$('#myJQselector').modal({onClose: mynewClose});
  • 调用对话框的默认关闭函数。 在您定义的函数中,您应该首先调用默认功能(这是您通常覆盖的任何内容的最佳实践):
  • 将对话框 div 的 innerHTML 设置为单个   – 这不是必需的步骤,因此如果您不明白这一点,请跳过它。
  • 劫持 __doPostBack,将其指向一个新函数 newDoPostBack
函数 myNewClose(对话框)

<前><代码>{

dialog.close();
  __doPostBack = newDoPostBack;

<前><代码><代码>}

  1. 编写newDoPostBack函数:
函数 newDoPostBack(eventTarget, eventArgument) 
  { 
    
 var theForm = document.forms[0];
 if (!theForm)

<前> {

 theForm = document.aspnetForm;

<前> }
<前> 

 if (!theForm.onsubmit || (theForm.onsubmit() != false))

<前> {

 document.getElementById("__EVENTTARGET").value = eventTarget;
 document.getElementById("__EVENTARGUMENT").value = eventArgument;
 theForm.submit();

<前>}
}

FWIW, I've updated the blog post you pointed to with come clarification, reposted here - the reasoning & other details are in the blog post:

The solution (as of my last checkin before lunch):

  1. Override the dialog's onClose event, and do the following:
    1. Call the dialog's default Close function
    2. Set the dialog div's innerHTML to a single  
    3. Hijack __doPostBack, pointing it to a new function, newDoPostBack

From some comments I’ve seen on the web, point 1 needs some clarification.  Unfortunately, I’m no longer with the same employer, and don’t have access to the code I used, but I’ll do what I can.  First off, you need to override the dialog’s onClose function by defining a new function, and pointing your dialog to it, like this:

$('#myJQselector').modal({onClose: mynewClose});
  • Call the dialog's default Close function.  In the function you define, you should first call the default functionality (a best practice for just about anything you override usually):
  • Set the dialog div's innerHTML to a single   – This is not a required step, so skip it if you don’t understand this.
  • Hijack __doPostBack, pointing it to a new function, newDoPostBack
function myNewClose (dialog)
{
    dialog.close();
    __doPostBack = newDoPostBack;
}
  1. Write the newDoPostBack function:
function newDoPostBack(eventTarget, eventArgument)
{
    var theForm = document.forms[0];
    if (!theForm)
    {
        theForm = document.aspnetForm;
    }
 
    if (!theForm.onsubmit || (theForm.onsubmit() != false))
    {
        document.getElementById("__EVENTTARGET").value = eventTarget;
        document.getElementById("__EVENTARGUMENT").value = eventArgument;
        theForm.submit();
    }
}
    
深者入戏 2024-07-11 14:10:31

如果您不想修改 SimpleModal 源。
尝试这个..

调用 modal() 方法后添加此内容:

$("#simplemodal-overlay").appendTo('form');
$("#simplemodal-container").appendTo('form');

SimpleModal 插件将两个此内容添加到您的标记中。

  1. 背景的“simplemodal-overlay”
  2. “simplemodal-container”包含您想要作为弹出模式的 div。

if you don want modify the SimpleModal source.
try this..

After you call the modal() method add this:

$("#simplemodal-overlay").appendTo('form');
$("#simplemodal-container").appendTo('form');

the SimpleModal plugin add two this to your markup.

  1. 'simplemodal-overlay' for the background
  2. 'simplemodal-container' containig the div that you whant as pop up modal.
丶视觉 2024-07-11 14:10:31

除了 tghw 的回答之外,这篇优秀的博客文章还帮助了我: jQuery:修复模态表单中的回发 - 特别是 BtnMike 的评论:“您也不能在您的 asp:button 上设置 CssClass=”simplemodal-close”。 对我来说,将其从课堂上取消并不是一个显而易见的解决方案。

-约翰

In addition to tghw's answer, this excellent blog post helped me: jQuery: Fix your postbacks in Modal forms -- specifically BtnMike's comment: "You also must not have CssClass=”simplemodal-close” set on your asp:button." Taking that off the class was the not-obvious-to-me solution.

-John

零時差 2024-07-11 14:10:31

有同样的问题,但是 {appendTo:'form'} 导致模式弹出窗口呈现完全错误(好像我遇到了 CSS 问题)。

事实证明,我正在构建的模板包含将其他表单放在页面上的内容。 一旦我设置了 {appendTo:'#aspnetForm'} (默认的 Asp.net 表单 ID),一切都运行良好(包括回发)。

Had the same problem, but {appendTo:'form'} caused the modal popup to be rendered completely wrong (as though I had a CSS issue).

Turns out the template I'm building on top of has includes that put other forms on the page. Once I set {appendTo:'#aspnetForm'} (the default Asp.net form ID), everything worked great (including the postback).

往日 2024-07-11 14:10:31

新的 Jquery.simplemodal-1.3.js 有一个名为appendTo 的选项。 因此添加一个名为appendTo:'form'的选项,因为默认值是appendTo:'body',它在asp.net中不起作用。

The new Jquery.simplemodal-1.3.js has an option called appendTo. So add an option called appendTo:'form' because the default is appendTo:'body' which doesn't work in asp.net.

~没有更多了~
我们使用 Cookies 和其他技术来定制您的体验包括您的登录状态等。通过阅读我们的 隐私政策 了解更多相关信息。 单击 接受 或继续使用网站,即表示您同意使用 Cookies 和您的相关数据。
原文