More work into base behaviour
- Selection stage sort-of finished (needs more love) - Labels are only shown for items visible on screen, the rest are ignored. - Current actions include focus for input, submit for forms and click for anchors. - Using numbers for now, will change to text later.
This commit is contained in:
parent
82af7d3812
commit
dbd77765a5
97
keyhinter.js
97
keyhinter.js
|
@ -1,9 +1,27 @@
|
|||
var isVisible = function(node) {
|
||||
// From: http://stackoverflow.com/questions/123999/how-to-tell-if-a-dom-element-is-visible-in-the-current-viewport/7557433#7557433
|
||||
var rect = node.getBoundingClientRect();
|
||||
return (
|
||||
rect.top >= 0 &&
|
||||
rect.left >= 0 &&
|
||||
rect.bottom <= (window.innerHeight || document.documentElement.clientHeight) && /*or $(window).height() */
|
||||
rect.right <= (window.innerWidth || document.documentElement.clientWidth) /*or $(window).width() */
|
||||
);
|
||||
}
|
||||
|
||||
class KeyHinter {
|
||||
constructor() {
|
||||
this.number = 0;
|
||||
this.nodes = {};
|
||||
|
||||
this.currentSelectionNumber = 0;
|
||||
this.currentSelection = [];
|
||||
|
||||
this.mappings = {}
|
||||
|
||||
this.keyCodes = [
|
||||
48, 49, 50, 51, 52, 53, 54, 55, 56, 57
|
||||
]
|
||||
}
|
||||
|
||||
// Highlight
|
||||
|
@ -14,22 +32,18 @@ class KeyHinter {
|
|||
this.listenKeybinds()
|
||||
|
||||
var _this = this;
|
||||
document.querySelectorAll('a, form').forEach(function(nodeEl) {
|
||||
_this.number++;
|
||||
_this.nodes[_this.number] = nodeEl;
|
||||
document.querySelectorAll('a, form, input').forEach(function(nodeEl) {
|
||||
if (isVisible(nodeEl)) {
|
||||
_this.number++;
|
||||
_this.nodes[_this.number] = nodeEl;
|
||||
|
||||
var el = _this.generateLabelFor(nodeEl);
|
||||
var el = _this.generateLabelFor(nodeEl);
|
||||
|
||||
if (nodeEl.nodeName == 'A') {
|
||||
el.classList.add('keyhinter-label-anchor');
|
||||
} else if (nodeEl.nodeName == 'FORM') {
|
||||
el.classList.add('keyhinter-label-form');
|
||||
el.textContent = _this.number;
|
||||
el.setAttribute('data-keyhinter-number', _this.number);
|
||||
|
||||
document.body.appendChild(el);
|
||||
}
|
||||
|
||||
el.textContent = _this.number;
|
||||
el.setAttribute('data-keyhinter-number', _this.number);
|
||||
|
||||
document.body.appendChild(el);
|
||||
})
|
||||
}
|
||||
|
||||
|
@ -38,19 +52,65 @@ class KeyHinter {
|
|||
var el = document.createElement('div');
|
||||
var nodePosition = node.getBoundingClientRect();
|
||||
el.classList.add('keyhinter-label');
|
||||
|
||||
el.style.left = nodePosition.left + 'px';
|
||||
el.style.top = nodePosition.top + 'px';
|
||||
|
||||
if (node.nodeName === 'A') {
|
||||
el.classList.add('keyhinter-label-anchor');
|
||||
} else if (node.nodeName === 'FORM') {
|
||||
el.classList.add('keyhinter-label-form');
|
||||
} else if (node.nodeName === 'INPUT') {
|
||||
el.classList.add('keyhinter-label-input');
|
||||
}
|
||||
|
||||
return el;
|
||||
}
|
||||
|
||||
doClick(obj) {
|
||||
console.log(obj.nodeName)
|
||||
switch(obj.nodeName) {
|
||||
case 'INPUT':
|
||||
obj.focus();
|
||||
break;
|
||||
case 'FORM':
|
||||
obj.submit();
|
||||
break;
|
||||
default:
|
||||
obj.click();
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
// Keybinds
|
||||
listenKeybinds() {
|
||||
var _this = this;
|
||||
document.onkeydown = function(event) {
|
||||
if (event.keyCode == 27) {
|
||||
console.log('Esc')
|
||||
if (event.keyCode === 27) { // ESC
|
||||
event.preventDefault();
|
||||
_this.destroy();
|
||||
} else if (_this.keyCodes.indexOf(event.keyCode) !== -1) {
|
||||
event.preventDefault();
|
||||
var num = event.keyCode - 48;
|
||||
_this.currentSelection.push(num);
|
||||
|
||||
document.querySelectorAll('[data-keyhinter-number]').forEach(function(item){
|
||||
item.style.visibility = 'hidden';
|
||||
})
|
||||
|
||||
var query = document.querySelectorAll('[data-keyhinter-number^="' + _this.currentSelection.join('') + '"]')
|
||||
if (query.length === 1) {
|
||||
var node = _this.nodes[_this.currentSelection.join('')];
|
||||
_this.doClick(node);
|
||||
_this.destroy();
|
||||
} else {
|
||||
query.forEach(function(item){
|
||||
item.style.visibility = 'visible'
|
||||
})
|
||||
_this.currentSelectionNumber++;
|
||||
}
|
||||
} else {
|
||||
console.log("Default:" + event.keyCode)
|
||||
}
|
||||
}
|
||||
}
|
||||
|
@ -65,18 +125,17 @@ class KeyHinter {
|
|||
document.body.removeChild(node);
|
||||
})
|
||||
this.stopListeningKeybinds();
|
||||
stage = new KeyHinter()
|
||||
keyHinter = new KeyHinter()
|
||||
}
|
||||
}
|
||||
|
||||
var stage = new KeyHinter();
|
||||
var keyHinter = new KeyHinter();
|
||||
|
||||
chrome.runtime.onMessage.addListener(function (msg, sender, sendResponse) {
|
||||
// If the received message has the expected format...
|
||||
console.log(msg, sender, sendResponse)
|
||||
if (msg.action === 'start_keyhinter') {
|
||||
// Call the specified callback, passing
|
||||
// the web-page's DOM content as argument
|
||||
stage.highlight();
|
||||
keyHinter.highlight();
|
||||
}
|
||||
});
|
||||
|
|
Loading…
Reference in New Issue