(function HintNavigation() { var hint_num_str = ''; var hint_elems = []; var hint_tags = []; var hint_enabled = false; var registeredElements = []; var keyId = { "U+0008" : "Backspace", "U+0009" : "Tab", "U+0018" : "Cancel", "U+001B" : "Esc", "U+0020" : "Space", "U+0021" : "!", "U+0023" : "#", "U+0024" : "$", "U+0029" : ")", "U+002A" : "*", "U+002B" : "+", "U+002C" : ",", "U+002E" : ".", "U+002F" : "/", "U+00C0" : "0", "U+0026" : "1", "U+00C9" : "2", "U+0022" : "3", "U+0027" : "4", "U+0028" : "5", "U+002D" : "6", "U+00C8" : "7", "U+005F" : "8", "U+00C7" : "9", "U+003A" : ":", "U+003B" : ";", "U+003C" : "<", "U+003D" : "=", "U+003E" : ">", "U+003F" : "?", "U+0040" : "@", "U+0041" : "a", "U+0042" : "b", "U+0043" : "c", "U+0044" : "d", "U+0045" : "e", "U+0046" : "f", "U+0047" : "g", "U+0048" : "h", "U+0049" : "i", "U+004A" : "j", "U+004B" : "k", "U+004C" : "l", "U+004D" : "m", "U+004E" : "n", "U+004F" : "o", "U+0050" : "p", "U+0051" : "q", "U+0052" : "r", "U+0053" : "s", "U+0054" : "t", "U+0055" : "u", "U+0056" : "v", "U+0057" : "w", "U+0058" : "x", "U+0059" : "y", "U+005A" : "z", "U+00DB" : "[", "U+00DC" : "\\", "U+00DD" : "]", "U+005E" : "^", "U+0060" : "`", "U+007B" : "{", "U+007C" : "|", "U+007D" : "}", "U+007F" : "Delete", "U+00A1" : "¡", "U+0300" : "CombGrave", "U+0301" : "CombAcute", "U+0302" : "CombCircum", "U+0303" : "CombTilde", "U+0304" : "CombMacron", "U+0306" : "CombBreve", "U+0307" : "CombDot", "U+0308" : "CombDiaer", "U+030A" : "CombRing", "U+030B" : "CombDblAcute", "U+030C" : "CombCaron", "U+0327" : "CombCedilla", "U+0328" : "CombOgonek", "U+0345" : "CombYpogeg", "U+20AC" : "€", "U+3099" : "CombVoice", "U+309A" : "CombSVoice", }; function interceptListeners(element) { var addEvent = element.prototype.addEventListener; var removeEvent = element.prototype.removeEventListener; element.prototype.addEventListener = function () { if (arguments[0] === "click" || arguments[0] === "mouseover") { registeredElements.push(this); } addEvent.call(this, arguments[0], arguments[1], arguments[2]); }; element.prototype.removeEventListener = function () { if ((arguments[0] === "click" || arguments[1] === "mouseover") && registeredElements.indexOf(this)>= 0 ) { registeredElements.splice(registeredElements.indexOf(this), 1); } removeEvent.call(this, arguments[0], arguments[1], arguments[2]); }; } function start(){ hint_enabled = true; setHints(); document.removeEventListener('keydown', initKeyBind, false); document.addEventListener('keydown', hintHandler, false); document.addEventListener('scroll', windowChanged, false); document.addEventListener('resize', windowChanged, false); hint_num_str = ''; } function hintHandler(e){ e.preventDefault(); //Stop Default Event var pressedKey = get_key(e); var hint_num; if (pressedKey !== 'U+0000') { if (pressedKey === 'Backspace') { if (hint_num_str.length > 0) { hint_num_str = hint_num_str.substr(0,hint_num_str.length - 1); } } else if (pressedKey === 'Enter') { if (hint_num_str === '') { hint_num_str = '1'; } judgeHintNum(Number(hint_num_str)); return; } else if (/[0-9]/.test(pressedKey) === false) { stop(); } else if (Number(hint_num_str + pressedKey) <= hint_elems.length) { hint_num_str += pressedKey; hint_num = Number(hint_num_str); if (hint_num * 10 > hint_elems.length + 1) { judgeHintNum(hint_num); return; } } for (var i = 1 ; i <= hint_tags.length ; ++i ) { var iStr = i.toString(); if (iStr === hint_num_str) { hint_tags[i - 1].style.display = 'inline'; hint_tags[i - 1].style.border = 'solid 6px blue'; } else if (iStr.length > hint_num_str.length && iStr.substr(0,hint_num_str.length) === hint_num_str) { hint_tags[i - 1].style.display = 'inline'; hint_tags[i - 1].style.border = 'none'; } else { hint_tags[i - 1].style.display = 'none'; hint_tags[i - 1].style.border = 'none'; } } } } function judgeHintNum(hint_num) { var hint_elem = hint_elems[hint_num - 1]; if (hint_elem) { execSelect(hint_elem); } else { stop(); } } function execSelect(elem) { var tag_name = elem.tagName.toLowerCase(); var type = elem.type ? elem.type.toLowerCase() : ''; elem.dispatchEvent(new Event('mouseover')); elem.dispatchEvent(new Event('click', { 'bubbles': true, 'cancelable': true})); if (tag_name === 'input' && (type === "radio" || type === "checkbox")) { elem.checked = !elem.checked; } else if (tag_name === 'input' || tag_name === 'textarea') { elem.focus(); elem.setSelectionRange(0, elem.value.length); } stop(); } function setHints() { var win_top = window.pageYOffset; var win_bottom = win_top + window.innerHeight; var win_left = window.pageXOffset; var elems = document.body.querySelectorAll('a, input:not([type=hidden]), textarea, select, button, [onclick], [onmouseover], [for]'); var elements = []; for (var i = 0 ; i < elems.length ; ++i) { elements.push(elems[i]); } for (i = 0 ; i < registeredElements.length ; ++i) { elements.push(registeredElements[i]); } var div = document.createElement('div'); div.setAttribute('highlight', 'hints'); document.body.appendChild(div); for (i = 0; i < elements.length; i++) { var elem = elements[i]; if (!isHintDisplay(elem)) { continue; } var pos = elem.getBoundingClientRect(); var elem_top = win_top + pos.top; var elem_bottom = win_top + pos.bottom; var elem_left = win_left + pos.left; if ( elem_bottom >= win_top && elem_top <= win_bottom) { hint_elems.push(elem); var span = document.createElement('span'); span.style.cssText = [ 'left: ', elem_left, 'px;', 'top: ', elem_top, 'px;', 'position: absolute;', 'font-size: 13px;', 'background-color: red;', 'color: white;', 'font-weight: bold;', 'padding: 0px 1px;', 'z-index: 10000;' ].join(''); span.innerHTML = hint_elems.length; div.appendChild(span); hint_tags.push(span); } } } function isHintDisplay(elem) { var pos = elem.getBoundingClientRect(); return (pos.height !== 0 && pos.width !== 0); } function stop() { if (!hint_enabled){ return; } hint_enabled = false; hint_elems = []; hint_tags = []; hint_num_str = ''; var div = document.body.querySelector('div[highlight=hints]'); if (div) { document.body.removeChild(div); } document.removeEventListener('keydown', hintHandler, false); document.removeEventListener('scroll', windowChanged, false); document.removeEventListener('resize', windowChanged, false); document.addEventListener('keydown', initKeyBind, false); if (refreshTimeout) { window.clearTimeout(refreshTimeout); } } function initKeyBind(e){ if (e.target.nodeType === 1 && e.ctrlKey){ if (get_key(e) === 'f') { e.preventDefault(); start(); } else if (get_key(e) === 'c') { e.preventDefault(); stop(); } } } var refreshTimeout; function windowChanged(){ if (refreshTimeout) { window.clearTimeout(refreshTimeout); } refreshTimeout = window.setTimeout(refreshHints, 200); } function refreshHints() { stop(); start(); refreshTimeout = undefined; } function get_key(evt){ return keyId[evt.keyIdentifier] || evt.keyIdentifier; } interceptListeners(HTMLElement); document.addEventListener( 'keydown', initKeyBind, false ); })();