Hotkeys by Label text: No class or id!

Hotkeys are like shortcuts. You press specified key to do some task.
Like, Ctrl+s will save this html page. And when you do Ctrl+c and Ctrl+v to copy-paste.
In background,

  1. Code listens to your click event,
  2. It sees what you have just clicked and
  3. Call the function as per keys.

While few things work, as readily implemented in browser, but you might have to create different features accessible with keys if you need. As per usability case, keys have better speed than using mouse or touch pad. If you are happen to be computer nerd, you better know it :p

Well, so in my project last year, I mostly used id and class to select some dom/tag or node – whatever you call – from html.
For e.x., you might implement Ctrl+3 to open 3rd bog post or something without touching mouse or touch pad.

Idea behind this blog is to make this easier and then you can skip using selectors like id or class. You should be able to implement hotkeys simply giving the button text or label text visible in your page.

I will take a case here, suppose, I want to click ‘ABOUT ME’ when user clicks some specified key, say , Ctrl+a
I will keep the scope limit here, listening click event is easy, please refer  https://www.w3schools.com/jsref/met_element_addeventlistener.asp

To check for key:

if(event.key=='a' && event.ctrlKey==true){
focusOn('some label text');
}

In this code, I am simply checking if fired key event is ‘a’ and ctrl is also triggered, then it will call a function

focusOn('body','ABOUT ME').

This is suppose to find ABOUT ME in the body of my web page, and focus on it. You can click it by passing true as 3rd argument to

focusOn('body','ABOUT ME', true);

You can recursively check for all the text nodes in page and keep counting them. But, here I have found one great piece of code to do the same.
Refer here https://stackoverflow.com/questions/10730309/find-all-text-nodes-in-html-page

function textNodesUnder(el){
  var n, a=[], walk=document.createTreeWalker(el,NodeFilter.SHOW_TEXT,null,false);
  while(n=walk.nextNode()) a.push(n);
  return a;
}

This function simply returns you the array of all text nodes in a given dom, in this case, the all text node from full body.

function bValidate(el){
    return (el && el.length > 2 && !bExcluded(el));
}

This function simply checks if lentgh is greater than 2 and then validate with excluded comments and script tag. This is optional.

function bExcluded(el){
var arrExluded = ["<script", "/*", "//"];
return (arrExluded.indexOf(el) > -1); }

This function excludes comments and script tag read as text node, because I dont think so we will be finding some html comment and js code here. Dont bother.

function focusOn(selector, focusText, click){
selector= selector? selector: 'body';
// choose between jQuery or $
jQuery = jQuery ? jQuery : $;
var arrText = textNodesUnder(jQuery(selector)[0]);
arrText.forEach(function(elt){
var text = elt.wholeText.trim();
var ctr=1;
if(bValidate(text)){
if(text.toLowerCase() == focusText.toLowerCase()){
if(ctr--){setTimeout(function(){
if(click!=null){
jQuery(elt.parentNode).click();
console.log('clicked')
}else{
jQuery(elt.parentNode).focus();
console.log(document.activeElement);
}
},1000)
}
}
}
})
}

This is where it is happening. You are asking the function to click/focus on ‘ABOUT ME’. It reads all text node used in website. Then it validates it to skip tags and extra blanks. I am making case lower, so its fine if you change cases also. It takes care of click or focus as well. To just prove the idea, I am only focusing or clicking on the first result found from page. Suppose, if in my page, there are two or more than ‘ABOUT ME’ is in text, I am doing nothing for them.

The logic can be improved and modified as per need, but this provides the idea to target and node only with its text value. You better want to use this while implementing hotkey in your app next time. Few things remain concerned, that selecting with id and classes will be alwyas faster to find the dom. But rest is same. In this way, you just have to tell what to click, no brainer.

Be First to Comment

Leave a Reply

Your email address will not be published. Required fields are marked *