Skip to content

HTTPS clone URL

Subversion checkout URL

You can clone with HTTPS or Subversion.

Download ZIP
Browse files

fixing repositioning of open menu (formerly an accidental re-open)

  • Loading branch information...
commit 19f8a9a518a9373a358f42d0d26382fee52933c8 1 parent b8bb0a5
@rodneyrehm rodneyrehm authored
Showing with 40 additions and 12 deletions.
  1. +1 −1  docs.html
  2. +39 −11 src/jquery.contextMenu.js
View
2  docs.html
@@ -93,7 +93,7 @@ <h3 id="options">options (at registration)</h3>
<dd>
<p>default: <em>"right"</em></p>
<p>Specifies the event to show the contextMenu</p>
- <p>Possible values: "right", "left", "hover"</p>
+ <p>Possible values: "right", "left", "hover", "none"</p>
</dd>
<dt id="options-ignoreRightClick"><em>(boolean)</em> ignoreRightClick</dt>
View
50 src/jquery.contextMenu.js
@@ -183,6 +183,7 @@ var // currently active contextMenu trigger
// contextmenu show dispatcher
contextmenu: function(e) {
var $this = $(this);
+
// disable actual context-menu
e.preventDefault();
e.stopImmediatePropagation();
@@ -208,7 +209,7 @@ var // currently active contextMenu trigger
}
// dynamically build menu on invocation
- $.extend(true, e.data, defaults, built || {});
+ e.data = $.extend(true, defaults, e.data, built || {});
// abort if there are no items to display
if (!e.data.items || $.isEmptyObject(e.data.items)) {
@@ -324,13 +325,35 @@ var // currently active contextMenu trigger
e.preventDefault();
e.stopImmediatePropagation();
- $this.remove();
- root.$menu.trigger('contextmenu:hide');
- // ignore right click for left click trigger menu
- if (root.ignoreRightClick && e.button == 2) {
- ignoreThisClick = true;
- }
+ if ((root.trigger == 'left' && e.button == 0) || (root.trigger == 'right' && e.button == 2)) {
+ var offset = root.$trigger.offset();
+
+ // while this looks kinda awful, it's the best way to avoid
+ // unnecessarily calculating any positions
+ offset.top += $(window).scrollTop();
+ if (offset.top <= e.pageY) {
+ offset.left += $(window).scrollLeft();
+ if (offset.left <= e.pageX) {
+ offset.bottom = offset.top + root.$trigger.outerHeight();
+ if (offset.bottom >= e.pageY) {
+ offset.right = offset.left + root.$trigger.outerWidth();
+ if (offset.right >= e.pageX) {
+ // reposition
+ root.position.call(root.$trigger, root, e.pageX, e.pageY);
+ return;
+ }
+ }
+ }
+ }
+ }
+
+ // remove only after mouseup has completed
+ $this.on('mouseup', function(e) {
+ e.preventDefault();
+ e.stopImmediatePropagation();
+ root.$menu.trigger('contextmenu:hide');
+ });
},
// key handled :hover
keyStop: function(e, opt) {
@@ -590,7 +613,6 @@ var // currently active contextMenu trigger
}
},
-
// :hover done manually so key handling is possible
itemMouseenter: function(e) {
var $this = $(this),
@@ -722,7 +744,7 @@ var // currently active contextMenu trigger
// backreference for callbacks
opt.$trigger = $this;
-
+
// show event
if (opt.events.show.call($this, opt) === false) {
$currentTrigger = null;
@@ -779,8 +801,13 @@ var // currently active contextMenu trigger
}
if (opt.$layer) {
+ // keep layer for a bit so the contextmenu event can be aborted properly by opera
+ setTimeout((function($layer){ return function(){
+ $layer.remove();
+ };
+ })(opt.$layer), 10);
+
try {
- opt.$layer.remove();
delete opt.$layer;
} catch(e) {
opt.$layer = null;
@@ -1049,6 +1076,7 @@ var // currently active contextMenu trigger
.css({height: $win.height(), width: $win.width(), display: 'block'})
.data('contextMenuRoot', opt)
.insertBefore(this)
+ .on('contextmenu', handle.abortevent)
.on('mousedown', handle.layerClick);
}
};
@@ -1169,7 +1197,7 @@ $.contextMenu = function(operation, options) {
*/
}
- if (o.trigger != 'hover' && o.ignoreRightClick) {
+ if (o.trigger == 'none' || o.trigger != 'hover' && o.ignoreRightClick) {
$body.on('mousedown' + o.ns, o.selector, handle.ignoreRightClick);
}
Please sign in to comment.
Something went wrong with that request. Please try again.