(^260) ❘ CHAPTER 9 PLUGINS
{
x = document.body.clientWidth;
y = document.body.clientHeight;
}return {
x : x,
y : y
};
}The dimensions of the viewport are needed to reposition the context menu depending on where the
user clicks inside the viewport. If the user clicks on the left side of the viewport, the context menu
is positioned from the left. If the user clicks near the top of the view port, the context menu is posi-
tioned from the top, and if the user clicks near the bottom, the context menu is positioned from
the bottom. Using a little math, you attempt to avoid a situation in which the element used for the
context menu might appear offscreen. Instead, by analyzing where a user clicks and the proximity to
the edges of the viewport, you can reposition based on that data.if (contextMenuIsEnabled)
{The preceding block of code detects if contextMenu() is called with no arguments, or in other words,
when the context menu is enabled.First, you set up some mouseover and mouseout events for the <li> elements, but only elements that
aren’t disabled or separators.this.find('li')
.not('li.contextMenuDisabled, li.contextMenuSeparator')
.bind(
'mouseover.contextMenu',
function()
{
$(this).addClass('contextMenuHover');
}
)
.bind(
'mouseout.contextMenu',
function()
{
$(this).removeClass('contextMenuHover');
}
);The call to find('li') fi nds the <li> elements inside the element acting as the context menu. These
receive mouseover and mouseout events that are namespaced for our contextMenu plugin. The entire
event is mouseover.contextMenu. The mouseover part is the standard event you are attaching, and the
contextMenu part is the name of this application of the mouseover event. As you’ve learned in all the
chapters preceding this one, naming your events is good practice because it isolates the events that
you apply into namespaces and makes it much easier to selectively enable and disable events, just as
you see here where you bind and unbind events based on the event and the event name. So each <li>