我有一个页面,其中包含类'对话'的链接,单击时会在JQueryUI dialog中生成。这些对话框是从页面上的其他元素创建的,并且可以包含类“add_tab”的链接,这些链接应该在单击时创建新的JQueryUI [tab](http://jqueryui.com/demos/dialog/)。这些选项卡通过Ajax加载其内容并包含相同的结构。这意味着对话框中的“add_tab”链接会创建一个新选项卡,其中包含“对话框”链接,这些链接生成包含更多“add_tab”链接的对话框,依此类推。
这是基本的HTML结构:
<div id="tabs">
<ul>
<li><a href="#tabs-1">tab 1</a></li>
</ul>
<div id="tabs-1">
<p>This tab contains a <a href="#popup1" class="dialog" target="_new">popup</a> and a direct link to a <a href="tabs2.htm" class="add_tab">new tab</a>.</p>
<div id="popup1" style="display:nonee;">This popup contains a link to a <a href="tabs2.htm" class="add_tab" target="_new">new tab</a>.</div>
</div>
使用JQuery 1.7的.on() method,我在为添加的标签上的对话框中出现的'add_tab'链接正确注册点击处理程序时遇到了麻烦。我设法在新生成的选项卡中为“对话框”链接注册单击处理程序(以便它们生成对话框),但无法为在那些对话框中出现的“add_tab”链接注册单击处理程序。我在http://www.kantl.be/ctb/temp/jquerytest/tabs1.htm在线提供了一个简化的测试版本。例如,遵循以下场景:
,单击“新选项卡”:这不会生成新的JQueryUI选项卡,而是在新窗口中打开目标
==&GT;这说明了此事件处理程序显然 NOT 正确注册了在新添加的选项卡中生成的对话框中出现的“add_tab”链接
在标签为'tabs2.htm'的标签中,点击'新标签':这将生成一个新的JQueryUI标签
==&GT;这说明了如何为直接在新添加的选项卡中出现的“add_tab”链接正确注册此事件处理程序
这是我的javascript代码:
// these event registrations register clicks on $('a.dialog') and $('a.add_tab') to open new JQueryUI dialogs / tabs
// note: this event registration works for all such links on the original page
$('a.dialog').on('click', function(){
$($(this).attr('href')).dialog();
return false;
});
$('a.add_tab').on('click', function(){
$tabs.tabs( "add", $(this).attr('href'), 'added tab');
$('.ui-dialog-content').each(function(){$(this).dialog('close')})
return false;
});
// tabs: upon creation, register clicks on nested $('a.dialog') and $('a.add_tab') to open new JQueryUI dialogs / tabs
var $tabs = $( "#tabs" ).tabs({
add: function(event, ui) {
$tabs.tabs('select', '#' + ui.panel.id);
$tabs.tabs($tabs.tabs('option', 'selected'))
.on('click', 'a.dialog', function(){
$($(this).attr('href')).dialog();
return false;
})
// this registration doesn't seem to work for <a class="add_tab"> links occurring inside generated JQueryUI dialogs inside added JQueryUI tabs
.on('click', 'a.add_tab', function(){
$tabs.tabs( "add", $(this).attr('href'), 'added tab');
return false;
});
}
});
我几乎那里!任何人都可以帮我解决上面代码中的最后一个事件处理程序吗?非常感谢任何帮助!
答案 0 :(得分:1)
事件委托的想法是将事件绑定在页面上固定的父上(不是动态创建的)。使用.on()方法的selector参数可以告诉应该触发事件处理程序的元素。
在您的代码中,您使用事件绑定有两种方式,例如,如果您使用.on():
首先直接绑定现有元素a.dialog和a.add_tab - 这只适用于tab1上的链接,因为它们是代码执行时唯一存在的元素,没有事件代表团在这里。
添加选项卡时,您正在选项卡容器$ tabs:
上执行事件委派用于打开$tabs.on('click', 'a.dialog', function(){ ... })
对话框的链接 - 这可以正常工作,因为链接a.dialog确实位于标签容器中。
对于$tabs.on('click', 'a.add_tab', function(){ ... })
对话框中的链接 - 这不起作用,因为在创建对话框时,插件会移动正文末尾的<div id="popup2">
(</body>
之前1}})。因此,当您单击对话框中的a.add_tab时,它不再是选项卡容器的后代,并且不会发生事件委派。
这就是我要做的事情:
为避免重复相同的代码,请将事件处理程序声明为变量
在选项卡容器上使用事件委托来获取链接a.dialog和a.add_tab
创建新对话框时,在对话框中使用事件委托,其中包含
以下是代码:
var addTabClickHandler = function(e) {
$tabs.tabs("add", $(this).attr('href'), 'added tab');
$('.ui-dialog-content').each(function() {
$(this).dialog('close')
})
return false;
};
var dialogOpenClickHandler = function(e) {
$($(this).attr('href'))
.dialog()
.on('click', 'a.add_tab', addTabClickHandler);
return false;
}
var $tabs = $("#tabs").tabs({
add: function(event, ui) {
$tabs
.tabs('select', '#' + ui.panel.id)
.tabs($tabs.tabs('option', 'selected'));
}
});
$tabs
.on('click', 'a.dialog', dialogOpenClickHandler)
.on('click', 'a.add_tab', addTabClickHandler);
答案 1 :(得分:1)
与此同时,我提出了一种解决方法,只需在“tabs”容器上注册事件处理程序,并在创建时将对话框附加到“tabs”容器。因此,我的初始代码可以缩减为:
// tabs: upon creation, register clicks on nested $('a.dialog') and $('a.add_tab') to open new JQueryUI dialogs / tabs
var $tabs = $( "#tabs" ).tabs({
create: function(event, ui) {
$(this)
.on('click', 'a.dialog', function(){
// dialog: upon creation, move the dialog to the tab to ensure delegated event registration
$($(this).attr('href')).dialog().parent('.ui-dialog').appendTo($tabs);
return false;
})
.on('click', 'a.add_tab', function(){
$tabs.tabs( "add", $(this).attr('href'), $(this).attr('href'));
$('.ui-dialog-content').dialog('close');
return false;
})
}
});