Home > Software design >  Intercept keydown event on input element
Intercept keydown event on input element

Time:05-10

I have a multipage form that is composed of <input /> fields. Alongside the form I have a collection of "hotkeys" that are implemented via a custom hook (window.attachEventListener("keydown", handler) that listen for an Alt Key combination. e.g. Alt N will navigate to the next page of the form)

The issue I am having is that if the user has focus on an <input /> and then attempts to fire the hotkey (Alt N), the <input /> is still receiving the ˜ character before triggering the hotkey.

I have tried to use capture mode, event.preventDefault(), event.stopPropagation() and event.stopImmediatePropagation() to no avail. Is there a way I can prevent the <input /> elements in the form from receiving the Alt Key keystroke?

useHotkey hook

export const useHotkey = (key: HotkeyTrigger, onTrigger: () => void) => {
  useEffect(() => {
    const handleTriggerKey = (event: KeyboardEvent) => {
      if (event.altKey && event.code === `Key${key}`) {
        // event.preventDefault();
        // event.stopPropagation();
        // event.stopImmediatePropagation();
        onTrigger();
      }
    };

    window.addEventListener("keydown", handleTriggerKey);

    return () => {
      window.removeEventListener("keydown", handleTriggerKey);
    };
  }, [key, onTrigger]);
};

EDIT: Codesandbox

CodePudding user response:

I have a workaround for you, remove the focus from the input when you use the hotKeys.

export const useHotkey = (
  key: string,
  onTrigger: () => void,
  document: any // Add this parameter 
) => {
  useEffect(() => {
    const handleTriggerKey = (event: KeyboardEvent) => {
      if (event.altKey && event.code === `Key${key}`) {
        document.getElementsByTagName("input")[0].blur();//Add this line
        onTrigger();
      }
    };

    window.addEventListener("keydown", handleTriggerKey);

    return () => {
      window.removeEventListener("keydown", handleTriggerKey);
    };
  }, [key, onTrigger]);
}; 

and the call your function as follows:

useHotkey("N", () => console.log("Triggered"), document);

I hope this should resolve the issue for you.

  • Related