4

我有一个通过 ajax 加载的元素列表(使用 jQuery 的 .load())。每个元素旁边都有一个(编辑)链接,该链接将灯箱(使用颜色框)设置为一个小编辑表单。当灯箱关闭时,我使用 onClosed 回调重新加载要显示的 ajax 列表以及在编辑期间所做的更改。

colorbox 调用如下所示:

$('.colorbox').colorbox({
  'iframe':true,
  'onClosed':function(){
    $("#featureList").load("/template/featureList","id="+$("#model_id").val());
  }
});

我的列表如下所示:

<div id="featureList">
  <ul id="features">
    <li id="item_000000000008+0">Element 1 (<a class="colorbox" href="/template/featureLightbox?template_id=000000000008&amp;delta=0">Edit</a>)</li>
    <li id="item_000000000008+1">Element 2 (<a class="colorbox" href="/template/featureLightbox?template_id=000000000008&amp;delta=1">Edit</a>)</li>
  </ul>
</div>

我查看了彩盒源代码,发现它用于jquery live()绑定。这里是:

$('.' + boxElement).live('click', function (e) {
  if ((e.button !== 0 && typeof e.button !== 'undefined') || e.ctrlKey || e.shiftKey || e.altKey) {
    return true;
  } else {
    launch(this);   
    return false;
  }
});

您可以在上面看到 colorbox 的工作方式是绑定到“boxElement”,这是它创建的一个名为“cboxElement”的类。在 live() 绑定颜色框之前,将此类 (cboxElement) 添加到与选择器匹配的所有元素(在我的示例中为 .colorbox),然后绑定到这个新类。

所以认为如果我将颜色框绑定放在 ajaxed 内容之外,它会在我用 ajax 替换 #featureList div 后绑定到链接,因为 live() 应该“现在或将来”绑定到元素。但这不是因为它绑定到 .cboxElement 而不是 .colorbox 所以当 ajax 重新加载 colorbox 时不会将 .cboxElement 类重新添加到元素中。

我尝试在 ajax 内容中调用 $.fn.colorbox.init() 以让 colorbox 将 .cboxElement 类重新添加到元素中,但这没有效果。(我在处理 shadowbox 时会这样做,但它似乎对 colorbox 不一样。)

因此,我尝试将所有颜色框代码放在 ajax 内容中。当我这样做时,颜色框绑定正在堆叠/链接。所以第二次调用它时,我得到了两个颜色框(并且必须按两次“关闭”按钮才能返回主屏幕)。第三次我得到三个。这是因为当我再次调用 colorbox 时,它添加了 .cboxElement 类,使旧的 live() 绑定再次处于活动状态,并且它还添加了另一个 live() 绑定。我试图通过首先调用 .die() 来清除 .live() 绑定,但由于某种原因它不起作用。

我找到了一些相关的帖子,但没有一个解决了这个问题,因为 colorbox 已经在使用 live():
Problem with jQuery Colorbox
jQuery AJAX table to a page but now the colorbox overlays no longer work

还有其他想法吗?我真的很难过。我觉得我应该切换到不同的灯箱,但总的来说,我喜欢彩色箱,它在网站上的其他任何地方都运行良好,直到出现这个 ajax 问题。

谢谢!!!

编辑:

所以,在这种情况下,我的问题是我的框架(Yii)在每个 AJAX 调用中都包含一个重复的colorbox脚本,这导致了问题。所以要小心!

对于没有遇到重复脚本问题的每个人,我是: @Relic 在下面指出,您可以通过执行自己的jQuery delegate()绑定来“回避”一些问题,该绑定执行颜色框的“直接调用”,而不是依赖于 colorbox 的默认live()绑定。对于我的情况,我会像这样调整它:

$(document).delegate("#features a", "click", function (event) { // $.colorbox() call  }
4

3 回答 3

4

首先,您不应该使用.live()它已弃用。相反,学习如何使用.delegate()你会发现这是一个更强大的监听器,将帮助解决你的问题。

在页面加载最初,DOM 已准备就绪,并为选择器初始化颜色框被javascript读取。

尝试以下操作 - 因为它监视body #main所有现有的和新的a[rel='lightbox']

$("body #main").delegate("a[rel='lightbox']", "click", function (event) {
                    event.preventDefault();
                    $.colorbox({href: $(this).attr("href"),
                            transition: "fade",
                            innerHeight: '515px',
                            innerWidth: '579px',
                            overlayClose: true,
                            iframe: true,
                            opacity: 0.3});});

编辑“.on()”

$("body #main").on("click", "a[rel='lightbox']", function (event) {
                        event.preventDefault();
                        $.colorbox({href: $(this).attr("href"),
                                transition: "fade",
                                innerHeight: '515px',
                                innerWidth: '579px',
                                overlayClose: true,
                                iframe: true,
                                opacity: 0.3
                         });
});

是的,很大的变化,我知道,但关键是 'on' 方法也可以用作 'bind',所以这很酷。

于 2012-01-24T17:50:24.987 回答
1

我以一种非常简单的方式解决了这个问题。

如果您要发回 ajax 响应(通常是 javascript 响应) - 在该响应中附加正常的颜色框绑定代码(就像您在任何地方所做的那样)。

$('.colorbox').colorbox({
  'iframe':true,
  'onClosed':function(){
    $("#featureList").load("/template/featureList","id="+$("#model_id").val());
  }
});

将此附加到服务器的 js 响应中。这对我有用。

于 2010-08-24T11:03:17.103 回答
0

这个问题似乎与我一开始没有注意到的事情有关,因此没有提出我的问题。我已经编辑了这个问题以反映这些新信息。

我的问题是 AJAX 响应是多重绑定的,并且多次包含彩盒脚本。我用来包含脚本的 Yii 框架帮助器小部件也在每次响应中包含 jQuery 和 Colorbox。Yii 无法确定所需的脚本(如 jQuery)是否已包含在主页中(典型的无状态 HTTP 问题),因此它每次都将其包含在 AJAX 部分渲染中。

我通过不使用 Yii Widget 对每个 Ajax 调用的renderPartial视图进行 Colorbox 绑定解决了这个问题。我只是在父页面上包含颜色框绑定,所以 Ajax 内容中没有 JS。

于 2010-08-26T17:11:19.790 回答