Adds keyboard support to the media quality selector
This commit is contained in:
parent
3827f05db9
commit
a73d7b42cf
3 changed files with 57 additions and 3 deletions
|
@ -23,6 +23,11 @@
|
||||||
opacity: 0.5;
|
opacity: 0.5;
|
||||||
width: 32px;
|
width: 32px;
|
||||||
|
|
||||||
|
&:focus,
|
||||||
|
&:hover {
|
||||||
|
opacity: 1;
|
||||||
|
}
|
||||||
|
|
||||||
&::after {
|
&::after {
|
||||||
content: '';
|
content: '';
|
||||||
display: block;
|
display: block;
|
||||||
|
@ -106,6 +111,7 @@
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
&--focused,
|
||||||
&:focus,
|
&:focus,
|
||||||
&:active {
|
&:active {
|
||||||
border-radius: 6px;
|
border-radius: 6px;
|
||||||
|
|
|
@ -7,6 +7,7 @@ import { storiesOf } from '@storybook/react';
|
||||||
import { action } from '@storybook/addon-actions';
|
import { action } from '@storybook/addon-actions';
|
||||||
import { boolean } from '@storybook/addon-knobs';
|
import { boolean } from '@storybook/addon-knobs';
|
||||||
|
|
||||||
|
import { IMAGE_JPEG } from '../types/MIME';
|
||||||
import { CompositionArea, Props } from './CompositionArea';
|
import { CompositionArea, Props } from './CompositionArea';
|
||||||
import { setup as setupI18n } from '../../js/modules/i18n';
|
import { setup as setupI18n } from '../../js/modules/i18n';
|
||||||
import enMessages from '../../_locales/en/messages.json';
|
import enMessages from '../../_locales/en/messages.json';
|
||||||
|
@ -33,7 +34,7 @@ const createProps = (overrideProps: Partial<Props> = {}): Props => ({
|
||||||
micCellEl,
|
micCellEl,
|
||||||
onChooseAttachment: action('onChooseAttachment'),
|
onChooseAttachment: action('onChooseAttachment'),
|
||||||
// AttachmentList
|
// AttachmentList
|
||||||
draftAttachments: [],
|
draftAttachments: overrideProps.draftAttachments || [],
|
||||||
onAddAttachment: action('onAddAttachment'),
|
onAddAttachment: action('onAddAttachment'),
|
||||||
onClearAttachments: action('onClearAttachments'),
|
onClearAttachments: action('onClearAttachments'),
|
||||||
onClickAttachment: action('onClickAttachment'),
|
onClickAttachment: action('onClickAttachment'),
|
||||||
|
@ -144,3 +145,15 @@ story.add('SMS-only', () => {
|
||||||
|
|
||||||
return <CompositionArea {...props} />;
|
return <CompositionArea {...props} />;
|
||||||
});
|
});
|
||||||
|
|
||||||
|
story.add('Attachments', () => {
|
||||||
|
const props = createProps({
|
||||||
|
draftAttachments: [
|
||||||
|
{
|
||||||
|
contentType: IMAGE_JPEG,
|
||||||
|
},
|
||||||
|
],
|
||||||
|
});
|
||||||
|
|
||||||
|
return <CompositionArea {...props} />;
|
||||||
|
});
|
||||||
|
|
|
@ -21,6 +21,9 @@ export const MediaQualitySelector = ({
|
||||||
}: PropsType): JSX.Element => {
|
}: PropsType): JSX.Element => {
|
||||||
const [menuShowing, setMenuShowing] = useState(false);
|
const [menuShowing, setMenuShowing] = useState(false);
|
||||||
const [popperRoot, setPopperRoot] = useState<HTMLElement | null>(null);
|
const [popperRoot, setPopperRoot] = useState<HTMLElement | null>(null);
|
||||||
|
const [focusedOption, setFocusedOption] = useState<0 | 1 | undefined>(
|
||||||
|
undefined
|
||||||
|
);
|
||||||
|
|
||||||
// We use regular MouseEvent below, and this one uses React.MouseEvent
|
// We use regular MouseEvent below, and this one uses React.MouseEvent
|
||||||
const handleClick = (ev: KeyboardEvent | React.MouseEvent) => {
|
const handleClick = (ev: KeyboardEvent | React.MouseEvent) => {
|
||||||
|
@ -29,8 +32,31 @@ export const MediaQualitySelector = ({
|
||||||
ev.preventDefault();
|
ev.preventDefault();
|
||||||
};
|
};
|
||||||
|
|
||||||
|
const handleKeyDown = (ev: KeyboardEvent) => {
|
||||||
|
if (!popperRoot) {
|
||||||
|
if (ev.key === 'Enter') {
|
||||||
|
setFocusedOption(isHighQuality ? 1 : 0);
|
||||||
|
}
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
|
if (ev.key === 'ArrowDown' || ev.key === 'ArrowUp') {
|
||||||
|
setFocusedOption(oldFocusedOption => (oldFocusedOption === 1 ? 0 : 1));
|
||||||
|
ev.stopPropagation();
|
||||||
|
ev.preventDefault();
|
||||||
|
}
|
||||||
|
|
||||||
|
if (ev.key === 'Enter') {
|
||||||
|
onSelectQuality(Boolean(focusedOption));
|
||||||
|
setMenuShowing(false);
|
||||||
|
ev.stopPropagation();
|
||||||
|
ev.preventDefault();
|
||||||
|
}
|
||||||
|
};
|
||||||
|
|
||||||
const handleClose = useCallback(() => {
|
const handleClose = useCallback(() => {
|
||||||
setMenuShowing(false);
|
setMenuShowing(false);
|
||||||
|
setFocusedOption(undefined);
|
||||||
}, [setMenuShowing]);
|
}, [setMenuShowing]);
|
||||||
|
|
||||||
useEffect(() => {
|
useEffect(() => {
|
||||||
|
@ -69,6 +95,7 @@ export const MediaQualitySelector = ({
|
||||||
'MediaQualitySelector__button--active': menuShowing,
|
'MediaQualitySelector__button--active': menuShowing,
|
||||||
})}
|
})}
|
||||||
onClick={handleClick}
|
onClick={handleClick}
|
||||||
|
onKeyDown={handleKeyDown}
|
||||||
ref={ref}
|
ref={ref}
|
||||||
type="button"
|
type="button"
|
||||||
/>
|
/>
|
||||||
|
@ -91,7 +118,11 @@ export const MediaQualitySelector = ({
|
||||||
aria-label={i18n(
|
aria-label={i18n(
|
||||||
'MediaQualitySelector--standard-quality-title'
|
'MediaQualitySelector--standard-quality-title'
|
||||||
)}
|
)}
|
||||||
className="MediaQualitySelector__option"
|
className={classNames({
|
||||||
|
MediaQualitySelector__option: true,
|
||||||
|
'MediaQualitySelector__option--focused':
|
||||||
|
focusedOption === 0,
|
||||||
|
})}
|
||||||
type="button"
|
type="button"
|
||||||
onClick={() => {
|
onClick={() => {
|
||||||
onSelectQuality(false);
|
onSelectQuality(false);
|
||||||
|
@ -119,7 +150,11 @@ export const MediaQualitySelector = ({
|
||||||
aria-label={i18n(
|
aria-label={i18n(
|
||||||
'MediaQualitySelector--high-quality-title'
|
'MediaQualitySelector--high-quality-title'
|
||||||
)}
|
)}
|
||||||
className="MediaQualitySelector__option"
|
className={classNames({
|
||||||
|
MediaQualitySelector__option: true,
|
||||||
|
'MediaQualitySelector__option--focused':
|
||||||
|
focusedOption === 1,
|
||||||
|
})}
|
||||||
type="button"
|
type="button"
|
||||||
onClick={() => {
|
onClick={() => {
|
||||||
onSelectQuality(true);
|
onSelectQuality(true);
|
||||||
|
|
Loading…
Add table
Add a link
Reference in a new issue