【问题标题】:Twitter bootstrap remote modal shows same content every timeTwitter 引导远程模式每次都显示相同的内容
【发布时间】:2012-08-30 11:05:01
【问题描述】:

我正在使用 Twitter 引导程序,我指定了一个模式

<div class="modal hide" id="modal-item">

    <div class="modal-header">
        <button type="button" class="close" data-dismiss="modal">x</button>
        <h3>Update Item</h3>
    </div>

    <form action="http://www.website.com/update" method="POST" class="form-horizontal">

    <div class="modal-body">
        Loading content...
    </div>

    <div class="modal-footer">
        <a href="#" class="btn" data-dismiss="modal">Close</a>
        <button class="btn btn-primary" type="submit">Update Item</button>
    </div>

    </form>

</div>

还有链接

<a href="http://www.website.com/item/1" data-target="#modal-item" data-toggle="modal">Edit 1</a>
<a href="http://www.website.com/item/2" data-target="#modal-item" data-toggle="modal">Edit 2</a>
<a href="http://www.website.com/item/3" data-target="#modal-item" data-toggle="modal">Edit 2</a>

当我第一次单击这些链接中的任何一个时,我看到了正确的内容,但是当我单击其他链接时,它显示了第一次加载的相同内容,它不会更新内容。

我希望它在每次点击时更新。

P.S:我可以通过自定义 jQuery 函数轻松地使其工作,但我想知道它是否可以使用本机 Bootstrap 模态远程函数,因为它应该很简单,我想我只是让事情复杂化。

【问题讨论】:

标签: jquery jquery-plugins twitter-bootstrap modal-dialog


【解决方案1】:

问题有两个方面。

首先,一旦一个 Modal 对象被实例化,它就会持久地附加到 data-target 指定的元素上,随后的调用表明 modal 只会在其上调用 toggle(),但不会更新options 中的值。因此,即使 href 属性在您的不同链接上不同,但当切换模式时,remote 的值不会更新。对于大多数选项,可以通过直接编辑对象来解决这个问题。例如:

$('#myModal').data('bs.modal').options.remote = "http://website.com/item/7";

但是,这在这种情况下不起作用,因为...

第二,Modal插件被设计为在Modal对象的构造函数中加载远程资源,这很不幸的意思是即使修改了@ 987654328@,永远不会重新加载

一个简单的补救措施是在后续切换之前销毁 Modal 对象。一种选择是在它完成隐藏后将其销毁:

$('body').on('hidden.bs.modal', '.modal', function () {
  $(this).removeData('bs.modal');
});

注意:根据需要调整选择器。这是最通用的。

Plunker

或者您可以尝试提出一个更复杂的方案来执行某些操作,例如检查启动模式的链接是否与前一个不同。如果是,则销毁;如果不是,则无需重新加载。

【讨论】:

  • @VladimirStarkov 对此感到抱歉 - 似乎我忘记了模态框上的 hide 类,所以如果您的窗口太小,模态框可能会阻止按钮上的鼠标事件。出于某种原因,JSFiddle.net 今天早上真的很糟糕(尝试更新 504),所以我只是在 plnkr.co 上重做了示例,无论如何这对 AJAX 来说更好。
  • 还有一个问题:.modal-body 中仍然会有文本,所以我添加了: $('#myModal .modal-body').text("Loading. ..") 在隐藏的事件监听器中
  • bs.modal in $(this).removeData('bs.modal') 为我使用 Bootstrap 3
  • Boostrap 3 的完整工作代码是$('body').on('hidden.bs.modal', '.modal', function () { $(this).removeData('bs.modal'); });
  • 我还会检查被隐藏的模态是否从远程源加载,以免破坏具有静态内容的模态:var modalData = $(this).data('bs.modal'); if (modalData &amp;&amp; modalData.options.remote)...
【解决方案2】:

对于引导程序 3,您应该使用:

$('body').on('hidden.bs.modal', '.modal', function () {
    $(this).removeData('bs.modal');
});

【讨论】:

  • 我的英雄。喜欢这些未记录的更改。
  • 这很有帮助。 Bootstrap 3 不向后兼容,并且 SO(或其他论坛)上的大部分内容都是关于 BS
  • 不完美:它在新内容之前简要显示旧内容。
  • 如果你想使用上面的例子清空模式,你应该能够在remoteData行之前或之后添加以下内容:$(this).empty()
  • 你不应该使用$(this).empty()remote 选项将远程数据加载到嵌套的 &lt;div class="modal-content"&gt; 元素中。请改用$('.modal-content', this).empty();
【解决方案3】:

对于 Bootstrap 3.1,您需要删除数据并清空 modal-content 而不是整个对话框 (3.0),以避免在等待远程内容加载时出现闪烁。

$(document).on("hidden.bs.modal", function (e) {
    $(e.target).removeData("bs.modal").find(".modal-content").empty();
});

如果您使用的是非远程模式,那么上面的代码当然会在关闭后删除它们的内容(不好)。您可能需要在这些模式中添加一些东西(例如 .local-modal 类),这样它们就不会受到影响。然后将上面的代码修改为:

$(document).on("hidden.bs.modal", ".modal:not(.local-modal)", function (e) {
    $(e.target).removeData("bs.modal").find(".modal-content").empty();
});

【讨论】:

  • 在远程页面上确保您没有加载引导程序或 jquery 库。它会杀死任何引用,并让您空出一个空的模态。
  • 这对我不起作用。这是我的工作代码: $(document).on("hidden.bs.modal", ".modal", function (e) { if (!$(e.target).is(".local-modal ")) { $(e.target).removeData("bs.modal").find(".modal-content").empty(); } });
  • 当我使用 $(e.target).removeData("bs.modal").find(".modal-content").empty(); 时,就像我的模态以某种方式被隐藏了,只出现了灰色的覆盖层。
【解决方案4】:

谢谢你。我开始对 boostrap.js 进行修补,但您的回答是一个快速而干净的解决方法。这是我最终在代码中使用的内容。

$('#modal-item').on('hidden', function() {
    $(this).removeData('modal');
});

【讨论】:

    【解决方案5】:

    接受的答案对我不起作用,所以我用 JavaScript 来做。

    <a href="/foo" class="modal-link">
    <a href="/bar" class="modal-link">
    
    <script>
    $(function() {
        $(".modal-link").click(function(event) {
            event.preventDefault()
            $('#myModal').removeData("modal")
            $('#myModal').modal({remote: $(this).attr("href")})
        })
    })
    

    【讨论】:

      【解决方案6】:

      这适用于 Bootstrap 3 仅供参考

      $('#myModal').on('hidden.bs.modal', function () {
        $(this).removeData('bs.modal');
      });
      

      【讨论】:

        【解决方案7】:

        我的项目是在 Yii 中构建的并且使用 Bootstrap-Yii 插件,所以这个答案只有在你使用 Yii 时才有意义。

        上述修复确实有效,但仅在第一次显示模式之后。第一次出来是空的。我认为这是因为在我启动代码之后 Yii 调用了模式的隐藏函数,从而清除了我的启动变量。

        我发现将 removeData 调用放在启动模态的代码之前就可以了。所以我的代码结构是这样的......

        $ ("#myModal").removeData ('modal');
        $ ('#myModal').modal ({remote : 'path_to_remote'});
        

        【讨论】:

          【解决方案8】:

          在 Bootstrap 3.2.0 中,“on”事件必须在文档上,并且您必须清空模式:

          $(document).on("hidden.bs.modal", function (e) {
              $(e.target).removeData("bs.modal").find(".modal-content").empty();
          });
          

          在 Bootstrap 3.1.0 中,“on”事件可以在 body 上:

          $('body').on('hidden.bs.modal', '.modal', function () {
              $(this).removeData('bs.modal');
          });
          

          【讨论】:

          • 3.2 解决方案是 Bootstrap 3.1 中唯一适合我的解决方案 - 使用 body 方法,我在 modal 上的一些事件变得不挂钩。
          【解决方案9】:

          为什么不用 BS 3 让它更通用?只需使用“[something]modal”作为模态 DIV 的 ID。

          $("div[id$='modal']").on('hidden.bs.modal',
              function () {
                  $(this).removeData('bs.modal');
              }
          );
          

          【讨论】:

            【解决方案10】:

            对我来说唯一的工作选择是:

            $('body').on('hidden.bs.modal', '#modalBox', function () {
                $(this).remove();
            });
            

            我使用 Bootstrap 3,我有一个名为 popup('popup content') 它附加了模态框html。

            【讨论】:

            • 这是唯一对我有用的 BS 3.3.6。也使用车把模板。但是,我建议使用文档而不是正文。
            【解决方案11】:

            添加 $(this).html('');也可以清除可见数据,并且效果很好

            【讨论】:

              【解决方案12】:

              如果提供了远程 URL,内容将通过 jQuery 的 load 方法加载一次,并注入 .modal-content div。如果您使用的是 data-api,您也可以使用 href 属性来指定远程源。一个例子如下所示

              $.ajaxSetup ({
                  // Disable caching of AJAX responses
                  cache: false
              });
              

              【讨论】:

                【解决方案13】:

                我添加了类似的内容,因为旧内容会一直显示,直到新内容出现,.modal-content 中的 .html('') 会清除里面的 HTML,希望对您有所帮助

                $('#myModal').on('hidden.bs.modal', function () {
                   $('#myModal').removeData('bs.modal');
                   $('#myModal').find('.modal-content').html('');
                });
                

                【讨论】:

                • 这是迄今为止我找到的最简单的工作答案。答案并不复杂,代码几行且易于解释。第一次搞砸它就完美地工作了。
                【解决方案14】:

                我写了一个简单的 sn-p 处理模态的刷新。 基本上它将被点击的链接存储在模态数据中,并检查它是否与被点击的链接相同,删除或不是模态数据。

                var handleModal = function()
                {
                    $('.triggeringLink').click(function(event) {
                        var $logsModal = $('#logsModal');
                        var $triggeringLink = $logsModal.data('triggeringLink');
                
                        event.preventDefault();
                
                        if ($logsModal.data('modal') != undefined
                            && $triggeringLink != undefined
                            && !$triggeringLink.is($(this))
                        ) {
                            $logsModal.removeData('modal');
                        }
                
                        $logsModal.data('triggeringLink', $(this));
                
                        $logsModal.modal({ remote: $(this).attr('href') });
                        $logsModal.modal('show');
                    });
                };
                

                【讨论】:

                  【解决方案15】:

                  对于 Bootstrap 3,我在 modal.js 中进行了更改:

                  $(document)
                    .on('show.bs.modal',  '.modal', function () { $(document.body).addClass('modal-open') })
                    .on('hidden.bs.modal', '.modal', function () { $(document.body).removeClass('modal-open'); })
                  

                  $(document)
                    .on('show.bs.modal',  '.modal', function () { $(document.body).addClass('modal-open') })
                    .on('hidden.bs.modal', '.modal', function () { 
                      $(this).removeData('bs.modal').empty()
                      $(document.body).removeClass('modal-open')
                    })
                  

                  (为清楚起见添加了额外的间距)

                  这通过在模态容器上调用 empty() 以及删除数据来防止任何不需要的旧模态内容闪现。

                  【讨论】:

                    【解决方案16】:
                            $('#myModal').on('hidden.bs.modal', function () {
                                $(this).removeData('modal');
                            });
                    

                    这个对我有用。

                    【讨论】:

                      【解决方案17】:

                      这另一种方法对我很有效:

                      $("#myModal").on("show.bs.modal", function(e) {
                          var link = $(e.relatedTarget);
                          $(this).find(".modal-body").load(link.attr("href"));
                      });
                      

                      【讨论】:

                        【解决方案18】:
                        $('body').on('hidden.bs.modal', '.modal', function () {
                               $("#mention Id here what you showed inside modal body").empty()
                        });
                        

                        你想清空哪个 html 元素(div,span 不管)。

                        【讨论】:

                          【解决方案19】:

                          这个对我有用:

                          模态

                          <div class="modal fade" id="searchKaryawan" tabindex="-1" role="dialog" aria-labelledby="SearchKaryawanLabel" aria-hidden="true"> <div class="modal-dialog">
                          <div class="modal-content">
                            <div class="modal-header">
                              <button type="button" class="close" data-dismiss="modal" aria-label="Close"><span aria-hidden="true">&times;</span></button>
                              <h4 class="modal-title" id="SearchKaryawanLabel">Cari Karyawan</h4>
                            </div>
                            <div class="modal-body">
                              <input type="hidden" name="location">
                              <input name="cariNama" type="text" class="form-control" onkeyup="if (this.value.length > 3) cariNikNama();" />
                              <div class="links-area" id="links-area"></div>
                            </div>
                            <div class="modal-footer">
                            </div>
                          </div> </div></div>
                          

                          脚本

                          <script type="text/javascript">$('body').on('hidden.bs.modal', '.modal', function () {  $(".links-area").empty() }); </script>
                          

                          links-area 是我放置数据并需要清除的区域

                          【讨论】:

                            【解决方案20】:

                            @merv 接受答案的扩展版本。它还会检查被隐藏的模态是否从远程源加载并清除旧内容以防止其闪烁。

                            $(document).on('hidden.bs.modal', '.modal', function () {
                              var modalData = $(this).data('bs.modal');
                            
                              // Destroy modal if has remote source – don't want to destroy modals with static content.
                              if (modalData && modalData.options.remote) {
                                // Destroy component. Next time new component is created and loads fresh content
                                $(this).removeData('bs.modal');
                                // Also clear loaded content, otherwise it would flash before new one is loaded.
                                $(this).find(".modal-content").empty();
                              }
                            });
                            

                            https://gist.github.com/WojtekKruszewski/ae86d7fb59879715ae1e6dd623f743c5

                            【讨论】:

                              【解决方案21】:

                              在 Bootstrap 版本 3.3.2 上测试

                                $('#myModal').on('hide.bs.modal', function() {
                                  $(this).removeData();
                                });
                              

                              【讨论】:

                              • 这是一个糟糕的解决方案。不带参数调用.removeData() 将告诉jquery 删除附加到该元素的所有数据。就 OP 的问题而言,.removeData('bs.modal').removeData('modal') 就足够了,而且非常安全。
                              【解决方案22】:

                              祝你好运:

                              $('#myModal').on('hidden.bs.modal', function () {
                                  location.reload();
                              });
                              

                              【讨论】:

                              • 这是没用的。重新加载页面不是解决方案。
                              猜你喜欢
                              • 1970-01-01
                              • 1970-01-01
                              • 1970-01-01
                              • 1970-01-01
                              • 1970-01-01
                              • 1970-01-01
                              • 2015-06-10
                              • 2012-09-23
                              • 1970-01-01
                              相关资源
                              最近更新 更多