PageSourceSearch

https://academyofcheese.org/wp-content/plugins/powerpack-elements/assets/js/smartmenus-keyboard.js?ver=1.0.0

js academyofcheese.org collected 2026-09-24 21:28:12 UTC 8,060 bytes, 205 lines download raw bytes

1(function(factory) {
2	if (typeof define === 'function' && define.amd) {
3		// AMD
4		define(['jquery', 'smartmenus'], factory);
5	} else if (typeof module === 'object' && typeof module.exports === 'object') {
6		// CommonJS
7		module.exports = factory(require('jquery'));
8	} else {
9		// Global jQuery
10		factory(jQuery);
11	}
12} (function($) {
13
14	function getFirstItemLink($ul) {
15		// make sure we also allow the link to be nested deeper inside the LI's (e.g. in a heading)
16		return $ul.find('> li > a:not(.disabled), > li > :not(ul) a:not(.disabled)').eq(0);
17	}
18	function getLastItemLink($ul) {
19		return $ul.find('> li > a:not(.disabled), > li > :not(ul) a:not(.disabled)').eq(-1);
20	}
21	function getNextItemLink($li, noLoop) {
22		var $a = $li.nextAll('li').find('> a:not(.disabled), > :not(ul) a:not(.disabled)').eq(0);
23		return noLoop || $a.length ? $a : getFirstItemLink($li.parent());
24	}
25	function getPreviousItemLink($li, noLoop) {
26		// bug workaround: elements are returned in reverse order just in jQuery 1.8.x
27		var $a = $li.prevAll('li').find('> a:not(.disabled), > :not(ul) a:not(.disabled)').eq(/^1\.8\./.test($.fn.jquery) ? 0 : -1);
28		return noLoop || $a.length ? $a : getLastItemLink($li.parent());
29	}
30
31	// jQuery's .focus() is unreliable in some versions, so we're going to call the links' native JS focus method
32	$.fn.focusSM = function() {
33		if (this.length && this[0].focus) {
34			this[0].focus();
35		}
36		return this;
37	};
38
39	$.extend($.SmartMenus.Keyboard = {}, {
40		docKeydown: function(e) {
41			var keyCode = e.keyCode;
42			if (!/^(37|38|39|40)$/.test(keyCode)) {
43				return;
44			}
45			var $root = $(this),
46				obj = $root.data('smartmenus'),
47				$target = $(e.target);
48			// exit if this is an A inside a mega drop-down
49			if (!obj || !$target.is('a') || !obj.handleItemEvents($target)) {
50				return;
51			}
52			var $li = $target.closest('li'),
53				$ul = $li.parent(),
54				level = $ul.dataSM('level');
55			// swap left & right keys
56			if ($root.hasClass('sm-rtl')) {
57				if (keyCode == 37) {
58					keyCode = 39;
59				} else if (keyCode == 39) {
60					keyCode = 37;
61				}
62			}
63			switch (keyCode) {
64				case 37: // Left
65					if (obj.isCollapsible()) {
66						break;
67					}
68					if (level > 2 || level == 2 && $root.hasClass('sm-vertical')) {
69						obj.activatedItems[level - 2].focusSM();
70					// move to previous non-disabled parent item (make sure we cycle so it might be the last item)
71					} else if (!$root.hasClass('sm-vertical')) {
72						getPreviousItemLink((obj.activatedItems[0] || $target).closest('li')).focusSM();
73					}
74					break;
75				case 38: // Up
76					if (obj.isCollapsible()) {
77						var $firstItem;
78						// if this is the first item of a sub menu, move to the parent item
79						if (level > 1 && ($firstItem = getFirstItemLink($ul)).length && $target[0] == $firstItem[0]) {
80							obj.activatedItems[level - 2].focusSM();
81						} else {
82							getPreviousItemLink($li).focusSM();
83						}
84					} else {
85						if (level == 1 && !$root.hasClass('sm-vertical') && obj.opts.bottomToTopSubMenus) {
86							if (!obj.activatedItems[0] && $target.dataSM('sub')) {
87								if (obj.opts.showOnClick) {
88									obj.clickActivated = true;
89								}
90								obj.itemActivate($target);
91								if ($target.dataSM('sub').is(':visible')) {
92									obj.focusActivated = true;
93								}
94							}
95							if (obj.activatedItems[0] && obj.activatedItems[0].dataSM('sub') && obj.activatedItems[0].dataSM('sub').is(':visible') && !obj.activatedItems[0].dataSM('sub').hasClass('mega-menu')) {
96								getLastItemLink(obj.activatedItems[0].dataSM('sub')).focusSM();
97							}
98						} else if (level > 1 || $root.hasClass('sm-vertical')) {
99							getPreviousItemLink($li).focusSM();
100						}
101					}
102					break;
103				case 39: // Right
104					if (obj.isCollapsible()) {
105						break;
106					}
107					if (level == 1 && $root.hasClass('sm-vertical')) {
108						if (!obj.activatedItems[0] && $target.dataSM('sub')) {
109							if (obj.opts.showOnClick) {
110								obj.clickActivated = true;
111							}
112							obj.itemActivate($target);
113							if ($target.dataSM('sub').is(':visible')) {
114								obj.focusActivated = true;
115							}
116						}
117						if (obj.activatedItems[0] && obj.activatedItems[0].dataSM('sub') && obj.activatedItems[0].dataSM('sub').is(':visible') && !obj.activatedItems[0].dataSM('sub').hasClass('mega-menu')) {
118							getFirstItemLink(obj.activatedItems[0].dataSM('sub')).focusSM();
119						}
120					// move to next non-disabled parent item (make sure we cycle so it might be the last item)
121					} else if ((level == 1 || obj.activatedItems[level - 1] && (!obj.activatedItems[level - 1].dataSM('sub') || !obj.activatedItems[level - 1].dataSM('sub').is(':visible') || obj.activatedItems[level - 1].dataSM('sub').hasClass('mega-menu'))) && !$root.hasClass('sm-vertical')) {
122						getNextItemLink((obj.activatedItems[0] || $target).closest('li')).focusSM();
123					} else if (obj.activatedItems[level - 1] && obj.activatedItems[level - 1].dataSM('sub') && obj.activatedItems[level - 1].dataSM('sub').is(':visible') && !obj.activatedItems[level - 1].dataSM('sub').hasClass('mega-menu')) {
124						getFirstItemLink(obj.activatedItems[level - 1].dataSM('sub')).focusSM();
125					}
126					break;
127				case 40: // Down
128					if (obj.isCollapsible()) {
129						var $firstSubItem,
130							$lastItem;
131						// move to sub menu if appropriate
132						if (obj.activatedItems[level - 1] && obj.activatedItems[level - 1].dataSM('sub') && obj.activatedItems[level - 1].dataSM('sub').is(':visible') && !obj.activatedItems[level - 1].dataSM('sub').hasClass('mega-menu') && ($firstSubItem = getFirstItemLink(obj.activatedItems[level - 1].dataSM('sub'))).length) {
133							$firstSubItem.focusSM();
134						// if this is the last item of a sub menu, move to the next parent item
135						} else if (level > 1 && ($lastItem = getLastItemLink($ul)).length && $target[0] == $lastItem[0]) {
136							var $parentItem = obj.activatedItems[level - 2].closest('li'),
137								$nextParentItem = null;
138							while ($parentItem.is('li') && !($nextParentItem = getNextItemLink($parentItem, true)).length) {
139								$parentItem = $parentItem.parent().parent();
140							}
141							if ($nextParentItem.length) {
142								$nextParentItem.focusSM();
143							} else {
144								getFirstItemLink($root).focusSM();
145							}
146						} else {
147							getNextItemLink($li).focusSM();
148						}
149					} else {
150						if (level == 1 && !$root.hasClass('sm-vertical') && !obj.opts.bottomToTopSubMenus) {
151							if (!obj.activatedItems[0] && $target.dataSM('sub')) {
152								if (obj.opts.showOnClick) {
153									obj.clickActivated = true;
154								}
155								obj.itemActivate($target);
156								if ($target.dataSM('sub').is(':visible')) {
157									obj.focusActivated = true;
158								}
159							}
160							if (obj.activatedItems[0] && obj.activatedItems[0].dataSM('sub') && obj.activatedItems[0].dataSM('sub').is(':visible') && !obj.activatedItems[0].dataSM('sub').hasClass('mega-menu')) {
161								getFirstItemLink(obj.activatedItems[0].dataSM('sub')).focusSM();
162							}
163						} else if (level > 1 || $root.hasClass('sm-vertical')) {
164							getNextItemLink($li).focusSM();
165						}
166					}
167					break;
168			}
169			e.stopPropagation();
170			e.preventDefault();
171		}
172	});
173
174	// hook it
175	$(document).on('keydown.smartmenus', 'ul.pp-advanced-menu, ul.pp-advanced-menu:not([data-sm-skip])', $.SmartMenus.Keyboard.docKeydown);
176
177	$.extend($.SmartMenus.prototype, {
178		keyboardSetHotkey: function(keyCode, modifiers) {
179			var self = this;
180			$(document).on('keydown.smartmenus' + this.rootId, function(e) {
181				if (keyCode == e.keyCode) {
182					var procede = true;
183					if (modifiers) {
184						if (typeof modifiers == 'string') {
185							modifiers = [modifiers];
186						}
187						$.each(['ctrlKey', 'shiftKey', 'altKey', 'metaKey'], function(index, value) {
188							if ($.inArray(value, modifiers) >= 0 && !e[value] || $.inArray(value, modifiers) < 0 && e[value]) {
189								procede = false;
190								return false;
191							}
192						});
193					}
194					if (procede) {
195						getFirstItemLink(self.$root).focusSM();
196						e.stopPropagation();
197						e.preventDefault();
198					}
199				}
200			});
201		}
202	});
203
204	return $;
205}));

Line numbers count LF bytes from the start of the resource, as the search results do. Vendor segments are library code the classifier recognised; they are stored but not indexed. Bytes are shown as Latin1 characters, one per byte.