Skip to content

Commit

Permalink
[GEN-1580]: useKeyDown hook fixed (#1648)
Browse files Browse the repository at this point in the history
  • Loading branch information
BenElferink authored Oct 28, 2024
1 parent f3c1a26 commit 3bb2338
Show file tree
Hide file tree
Showing 3 changed files with 119 additions and 67 deletions.
112 changes: 101 additions & 11 deletions frontend/webapp/hooks/useKeyDown.ts
Original file line number Diff line number Diff line change
@@ -1,19 +1,109 @@
import { useEffect } from "react";

export function useKeyDown(key, callback) {
const handleKeyDown = (event) => {
if (key === event.key) {
callback(event);
}
};
import { useEffect } from 'react';

export function useKeyDown(key: Key | null, callback: (e: KeyboardEvent) => void) {
useEffect(() => {
window.addEventListener("keydown", handleKeyDown);
const handleKeyDown = (e: KeyboardEvent) => {
if (key && key === e.key) {
e.preventDefault();
e.stopPropagation();

callback(e);
}
};

window.addEventListener('keydown', handleKeyDown);

return () => {
window.removeEventListener("keydown", handleKeyDown);
window.removeEventListener('keydown', handleKeyDown);
};
}, [key, callback]);

return handleKeyDown;
return null;
}

// Chat GPT scraped from: https://developer.mozilla.org/en-US/docs/Web/API/UI_Events/Keyboard_event_key_values
type Key =
| 'Backspace'
| 'Tab'
| 'Enter'
| 'Shift'
| 'Control'
| 'Alt'
| 'Pause'
| 'CapsLock'
| 'Escape'
| 'Space'
| 'PageUp'
| 'PageDown'
| 'End'
| 'Home'
| 'ArrowLeft'
| 'ArrowUp'
| 'ArrowRight'
| 'ArrowDown'
| 'PrintScreen'
| 'Insert'
| 'Delete'
| '0'
| '1'
| '2'
| '3'
| '4'
| '5'
| '6'
| '7'
| '8'
| '9'
| 'a'
| 'b'
| 'c'
| 'd'
| 'e'
| 'f'
| 'g'
| 'h'
| 'i'
| 'j'
| 'k'
| 'l'
| 'm'
| 'n'
| 'o'
| 'p'
| 'q'
| 'r'
| 's'
| 't'
| 'u'
| 'v'
| 'w'
| 'x'
| 'y'
| 'z'
| 'Meta'
| 'ContextMenu'
| 'F1'
| 'F2'
| 'F3'
| 'F4'
| 'F5'
| 'F6'
| 'F7'
| 'F8'
| 'F9'
| 'F10'
| 'F11'
| 'F12'
| 'NumLock'
| 'ScrollLock'
| 'AudioVolumeMute'
| 'AudioVolumeDown'
| 'AudioVolumeUp'
| 'MediaTrackNext'
| 'MediaTrackPrevious'
| 'MediaStop'
| 'MediaPlayPause'
| 'LaunchMail'
| 'LaunchApp1'
| 'LaunchApp2'
| 'Unidentified';
35 changes: 8 additions & 27 deletions frontend/webapp/reuseable-components/drawer/index.tsx
Original file line number Diff line number Diff line change
@@ -1,4 +1,5 @@
import React, { useEffect } from 'react';
import React from 'react';
import { useKeyDown } from '@/hooks';
import styled from 'styled-components';

interface DrawerProps {
Expand Down Expand Up @@ -33,41 +34,21 @@ const DrawerContainer = styled.div<{
position: fixed;
top: 0;
bottom: 0;
${({ position, width }) => position}: 0;
${({ position }) => position}: 0;
width: ${({ width }) => width};
background-color: ${({ theme }) => theme.colors.translucent_bg};
box-shadow: 0 2px 10px rgba(0, 0, 0, 0.3);
transform: translateX(
${({ isOpen, position }) =>
isOpen ? '0' : position === 'left' ? '-100%' : '100%'}
);
transform: translateX(${({ isOpen, position }) => (isOpen ? '0' : position === 'left' ? '-100%' : '100%')});
transition: transform 0.3s ease;
z-index: 1000;
overflow-y: auto;
`;

export const Drawer: React.FC<DrawerProps> = ({
isOpen,
onClose,
position = 'right',
width = '300px',
children,
closeOnEscape = true,
}) => {
// Handle closing the drawer when escape key is pressed
useEffect(() => {
export const Drawer: React.FC<DrawerProps> = ({ isOpen, onClose, position = 'right', width = '300px', children, closeOnEscape = true }) => {
useKeyDown(isOpen ? 'Escape' : null, () => {
if (!closeOnEscape) return;
const handleEscape = (event: KeyboardEvent) => {
if (event.key === 'Escape' && isOpen) {
event.stopPropagation();
onClose();
}
};
document.addEventListener('keydown', handleEscape);
return () => {
document.removeEventListener('keydown', handleEscape);
};
}, [isOpen, onClose, closeOnEscape]);
onClose();
});

return (
<>
Expand Down
39 changes: 10 additions & 29 deletions frontend/webapp/reuseable-components/modal/index.tsx
Original file line number Diff line number Diff line change
@@ -1,7 +1,8 @@
import React, { useEffect } from 'react';
import React from 'react';
import Image from 'next/image';
import { Text } from '../text';
import ReactDOM from 'react-dom';
import { useKeyDown } from '@/hooks';
import styled from 'styled-components';

interface ModalProps {
Expand Down Expand Up @@ -33,10 +34,8 @@ const ModalWrapper = styled.div`
border-radius: 40px;
max-height: 84vh;
border: ${({ theme }) => `1px solid ${theme.colors.border}`};
box-shadow: 0px 1px 1px 0px rgba(17, 17, 17, 0.8),
0px 2px 2px 0px rgba(17, 17, 17, 0.8), 0px 5px 5px 0px rgba(17, 17, 17, 0.8),
0px 10px 10px 0px rgba(17, 17, 17, 0.8),
0px 0px 8px 0px rgba(17, 17, 17, 0.8);
box-shadow: 0px 1px 1px 0px rgba(17, 17, 17, 0.8), 0px 2px 2px 0px rgba(17, 17, 17, 0.8), 0px 5px 5px 0px rgba(17, 17, 17, 0.8),
0px 10px 10px 0px rgba(17, 17, 17, 0.8), 0px 0px 8px 0px rgba(17, 17, 17, 0.8);
`;

const ModalHeader = styled.div`
Expand Down Expand Up @@ -89,24 +88,11 @@ const CancelText = styled(Text)`
cursor: pointer;
`;

const Modal: React.FC<ModalProps> = ({
isOpen,
header,
onClose,
children,
actionComponent,
}) => {
useEffect(() => {
const handleEscape = (event: KeyboardEvent) => {
if (event.key === 'Escape') {
onClose();
}
};
document.addEventListener('keydown', handleEscape);
return () => {
document.removeEventListener('keydown', handleEscape);
};
}, [isOpen, onClose]);
const Modal: React.FC<ModalProps> = ({ isOpen, header, onClose, children, actionComponent }) => {
useKeyDown(isOpen ? 'Escape' : null, () => {
onClose();
});

if (!isOpen) return null;

return ReactDOM.createPortal(
Expand All @@ -115,12 +101,7 @@ const Modal: React.FC<ModalProps> = ({
{header && (
<ModalHeader>
<ModalCloseButton onClick={onClose}>
<Image
src="/icons/common/x.svg"
alt="close"
width={15}
height={12}
/>
<Image src='/icons/common/x.svg' alt='close' width={15} height={12} />
<CancelText>{'Cancel'}</CancelText>
</ModalCloseButton>
<ModalTitleContainer>
Expand Down

0 comments on commit 3bb2338

Please sign in to comment.