aboutsummaryrefslogtreecommitdiffstats
path: root/ui/jquery.ui.menu.js
diff options
context:
space:
mode:
Diffstat (limited to 'ui/jquery.ui.menu.js')
-rw-r--r--ui/jquery.ui.menu.js51
1 files changed, 44 insertions, 7 deletions
diff --git a/ui/jquery.ui.menu.js b/ui/jquery.ui.menu.js
index 6d9db8879..bf36a77fe 100644
--- a/ui/jquery.ui.menu.js
+++ b/ui/jquery.ui.menu.js
@@ -24,10 +24,12 @@ $.widget( "ui.menu", {
position: {
my: "left top",
at: "right top"
- }
+ },
+ trigger: null
},
_create: function() {
this.activeMenu = this.element;
+ this.isScrolling = false;
this.menuId = this.element.attr( "id" ) || "ui-menu-" + idIncrement++;
if ( this.element.find( ".ui-icon" ).length ) {
this.element.addClass( "ui-menu-icons" );
@@ -38,6 +40,16 @@ $.widget( "ui.menu", {
id: this.menuId,
role: "menu"
})
+ // Prevent focus from sticking to links inside menu after clicking
+ // them (focus should always stay on UL during navigation).
+ // If the link is clicked, redirect focus to the menu.
+ // TODO move to _bind below
+ .bind( "mousedown.menu", function( event ) {
+ if ( $( event.target).is( "a" ) ) {
+ event.preventDefault();
+ $( this ).focus( 1 );
+ }
+ })
// need to catch all clicks on disabled menu
// not possible through _bind
.bind( "click.menu", $.proxy( function( event ) {
@@ -57,10 +69,13 @@ $.widget( "ui.menu", {
},
"mouseover .ui-menu-item": function( event ) {
event.stopImmediatePropagation();
- var target = $( event.currentTarget );
- // Remove ui-state-active class from siblings of the newly focused menu item to avoid a jump caused by adjacent elements both having a class with a border
- target.siblings().children( ".ui-state-active" ).removeClass( "ui-state-active" );
- this.focus( event, target );
+ if ( !this.isScrolling ) {
+ var target = $( event.currentTarget );
+ // Remove ui-state-active class from siblings of the newly focused menu item to avoid a jump caused by adjacent elements both having a class with a border
+ target.siblings().children( ".ui-state-active" ).removeClass( "ui-state-active" );
+ this.focus( event, target );
+ }
+ this.isScrolling = false;
},
"mouseleave": "collapseAll",
"mouseleave .ui-menu": "collapseAll",
@@ -70,10 +85,14 @@ $.widget( "ui.menu", {
},
blur: function( event ) {
this._delay( function() {
- if ( ! $.contains( this.element[0], document.activeElement ) ) {
+ if ( ! $.contains( this.element[0], this.document[0].activeElement ) ) {
this.collapseAll( event );
}
}, 0);
+ },
+ scroll: function( event ) {
+ // Keep track of scrolling to prevent mouseover from firing inadvertently when scrolling the menu
+ this.isScrolling = true;
}
});
@@ -188,17 +207,31 @@ $.widget( "ui.menu", {
}
});
- this._bind( document, {
+ this._bind( this.document, {
click: function( event ) {
if ( !$( event.target ).closest( ".ui-menu" ).length ) {
this.collapseAll( event );
}
}
});
+
+ if ( this.options.trigger ) {
+ this.element.popup({
+ trigger: this.options.trigger,
+ managed: true,
+ focusPopup: $.proxy( function( event, ui ) {
+ this.focus( event, this.element.children( ".ui-menu-item" ).first() );
+ this.element.focus( 1 );
+ }, this)
+ });
+ }
},
_destroy: function() {
//destroy (sub)menus
+ if ( this.options.trigger ) {
+ this.element.popup( "destroy" );
+ }
this.element
.removeAttr( "aria-activedescendant" )
.find( ".ui-menu" )
@@ -500,6 +533,10 @@ $.widget( "ui.menu", {
item: this.active
};
this.collapseAll( event, true );
+ if ( this.options.trigger ) {
+ $( this.options.trigger ).focus( 1 );
+ this.element.popup( "close" );
+ }
this._trigger( "select", event, ui );
}
});