// // "menu.js" // A Menu Enhancement Library // (function(){ var items = {}; var domImpl = document.implementation; var hasMouseEnter = domImpl.hasFeature("Events.mouseenter", "3.0"); var hasMouseLeave = domImpl.hasFeature("Events.mouseleave", "3.0"); var started = false; // Abstraction layer for event registration differences function addListener(obj, event, handler) { if (obj.addEventListener) { // Code for IE9, Firefox, Chrome, Safari, etc. obj.addEventListener(event, handler, false); } else { // Code for IE8 and lower obj.attachEvent("on" + event, function(){handler.call(obj, arguments)}); } } // Initialize menu summaries function init() { if(started) return; started = true; var summaries = document.querySelectorAll(".menu .summary"); for(var i = 0; i < summaries.length; i++) { initSummary(summaries[i]); } addListener(window, "keydown", seek); } // Retrieve the character associated with an event function getChar(e) { if(e.key) { if(e.key.length == 1) return e.key.toLowerCase(); } else if (e.keyCode && e.keyCode >= 65 && e.keyCode <= 90) { return String.fromCharCode(e.keyCode).toLowerCase(); } } // // Menu Event Handlers // // Seek out typing of menu item names var name = "", timeout; function seek(e) { clearTimeout(timeout); name += getChar(e) || ""; if(items[name]) items[name].focus(); timeout = setTimeout(function(){name=""}, 750); } // Display a single summary function showSummary(e) { var elm = this; elm.summary.style.display = "block"; } // Hide a single summary function hideSummary(e) { var elm = this; elm.summary.style.display = "none"; } // // Initialization Methods // // Add listeners to show/hide summaries when needed function initSummary(summary) { // Link menu item with summary var menuitem = summary.parentNode; var name = menuitem.querySelector(".name").firstChild.nodeValue.toLowerCase(); menuitem.summary = summary; items[name] = menuitem; // Hide summary summary.style.display = "none"; // Hook show/hide focus listeners addListener(menuitem, "focus", showSummary); addListener(menuitem, "blur", hideSummary); // Hook show/hide mouse listeners if(hasMouseEnter && hasMouseLeave) { addListener(menuitem, "mouseenter", showSummary); addListener(menuitem, "mouseleave", hideSummary); } else { addListener(menuitem, "mouseover", showSummary); addListener(menuitem, "mouseout", hideSummary); } } // DON'T USE THIS: // Simulate known compatibility patterns. // In the real-world, this typically happens after an "if IE" check. var write = document.write; write("Menu framework loaded."); addListener(window, "load", init); addListener(document, "DOMContentLoaded", init); })()