我有一个动态<p:menubar>
如下。
<p:menubar style="position: relative; height: 30px; visibility: visible;">
<p:submenu label="Category" icon="ui-icon-document" styleClass="mainMenu">
<c:forEach var="row" items="#{parentMenuManagedBean.category}">
<p:submenu label="#{row.catName}" icon="ui-icon-contact" styleClass="subMenu">
<c:forEach var="subRow" items="#{row.subCategoryList}">
<p:menuitem value="#{subRow.subCatName}" url="ProductDetails.jsf?subCatId=#{subRow.subCatId}"/>
</c:forEach>
</p:submenu>
</c:forEach>
</p:submenu>
</p:menubar>
</p:menubar>
内部的</p:submenu>
不可点击。
有一些CSS类绑定到JavaScript函数。单击这些<p:submenu>
时,将调用以下函数。
$(function(){
$(".mainMenu").bind("click", function(){ alert("mainMenu was clicked"); });
});
$(function(){
$(".subMenu").bind("click", function(){ alert("subMenu was clicked"); });
});
但是当单击最内部的最<p:submenu>
时,这两个函数都被调用,这不应该发生。
还有如何唯一地标识每个<p:submenu>
,当它们被点击时?
有没有办法传递一些值,以便它们可以像附加到 URL 的查询字符串一样唯一标识?
但是当单击最内部的最
<p:submenu>
时,这两个函数都被调用,这不应该发生。
你是事件冒泡的受害者。在所有浏览器中,当 DOM 元素收到事件时,这是在对传播到其所有父级的当前元素进行处理之后。它们的所有事件侦听器(如果有)也会被调用,除非您从当前侦听器函数return false
,或者通过调用 event.stopPropagation()
并像往常一样从函数返回来显式停止传播。与return false
的区别在于,仍将对当前元素执行单击事件的默认操作(转到给定的URL)。
还有如何唯一地标识每个
<p:submenu>
,当它们被点击时?
负责触发事件的 DOM 元素位于 this
可用的侦听器中。您可以通过简单地使用 $()
构造它来将其进一步包装到 jQuery 对象中。在<p:submenu>
的情况下,这将是一个HTML <li>
元素,而该元素又具有<a>
元素作为子元素。
有没有办法传递一些值,以便它们可以像附加到 URL 的查询字符串一样唯一标识?
通常,您最好探索 DOM 元素本身。例如,通过检查子元素的文本内容<a>
。
总而言之,这是一个重写,请注意,event
对象可用作第一个函数参数:
$(document).on("click", ".mainMenu", function() {
console.log("mainMenu was clicked");
});
$(document).on("click", ".subMenu", function(event) {
event.stopPropagation(); // Stop event bubbling.
var $this = $(this); // That's the <li> element.
var $link = $this.children("a"); // That's the immediate child <a> element.
var label = $link.text(); // You could use it to identify the submenu.
// ...
console.log("subMenu with label " + label + " was clicked");
});
(请注意,我还用 $(document).on()
替换了 $(function(){})
和 $.bind()
,这使得它对 ajax 请求的 DOM 更新是安全的;然后你不需要重新执行整个脚本)
更新:根据评论,具体的功能要求,从最初的问题中根本不清楚(我现在改进了问题标题),是在单击子菜单本身时导航到与菜单第一项相同的 URL。在这种情况下,您最好通过.subMenu>a
选择器直接挂钩子菜单自己的<a>
元素,并对菜单的第一个<a>
元素的 URL 执行window.location
。这是另一个重写:
$(document).on("click", ".subMenu>a", function() {
var $this = $(this); // That's the submenu's <a> element itself.
var $link = $this.next().find("a:first"); // That's menu's first <a> element.
var url = $link.attr("href"); // The URL of that link.
// ...
window.location = url; // It'll change the document immediately. No need to stop propagation.
});
你需要使用 stopPropagation
$( ".subMenu").click(function( event ) {
event.stopPropagation();
// Do something
});
这将停止父级收到事件通知。
检查此 http://api.jquery.com/event.stoppropagation/