Improve RangeSettings keyboard compatibility

This commit is contained in:
Thomas Nordquist
2019-06-24 15:58:43 +02:00
parent c2a9b7b1c6
commit 759176c4fc

View File

@@ -1,4 +1,4 @@
import React, { useCallback, useState, ChangeEvent, MouseEvent } from 'react' import React, { useCallback, useState, ChangeEvent, MouseEvent, useRef, useEffect, useMemo } from 'react'
import { ChartParameters } from '../../../reducers/Charts' import { ChartParameters } from '../../../reducers/Charts'
import { Menu, TextField, Typography } from '@material-ui/core' import { Menu, TextField, Typography } from '@material-ui/core'
import { connect } from 'react-redux' import { connect } from 'react-redux'
@@ -19,37 +19,71 @@ function RangeSettings(props: Props) {
const [rangeFrom, setRangeFrom] = useState<string | number | undefined>(props.chart.range && props.chart.range.from) const [rangeFrom, setRangeFrom] = useState<string | number | undefined>(props.chart.range && props.chart.range.from)
const [rangeTo, setRangeTo] = useState<string | number | undefined>(props.chart.range && props.chart.range.to) const [rangeTo, setRangeTo] = useState<string | number | undefined>(props.chart.range && props.chart.range.to)
useRangeStateToFireUpdateAction(rangeFrom, rangeTo, props) useRangeStateToFireUpdateAction(rangeFrom, rangeTo, props)
const dismissTabKey = (e: React.KeyboardEvent<any>) => { const rangeFromRef = useRef<HTMLInputElement>()
const rangeToRef = useRef<HTMLInputElement>()
useEffect(() => {
rangeFromRef.current && rangeFromRef.current.focus()
}, [props.open])
const handleKeyEvents = (e: React.KeyboardEvent<any>) => {
if (e.keyCode === KeyCodes.tab) { if (e.keyCode === KeyCodes.tab) {
// Switch focus between those two
if (document.activeElement === rangeFromRef.current) {
rangeToRef.current && rangeToRef.current.focus()
} else {
rangeFromRef.current && rangeFromRef.current.focus()
}
// Prevent closing the menu
e.stopPropagation() e.stopPropagation()
// Prevent default tab behavior (focus/blur)
e.preventDefault()
} else if (e.keyCode === KeyCodes.enter) {
props.onClose()
} }
} }
const setFromHandler = useCallback((e: ChangeEvent<HTMLInputElement>) => setRangeFrom(e.target.value), []) const setFromHandler = useCallback((e: ChangeEvent<HTMLInputElement>) => setRangeFrom(e.target.value), [])
const setToHandler = useCallback((e: ChangeEvent<HTMLInputElement>) => setRangeTo(e.target.value), []) const setToHandler = useCallback((e: ChangeEvent<HTMLInputElement>) => setRangeTo(e.target.value), [])
return ( return useMemo(
<Menu style={{ textAlign: 'center' }} anchorEl={props.anchorEl} open={props.open} onClose={props.onClose}> () => (
<Typography>Define custom ranges for the Y-Axis</Typography> <Menu
<div style={{ padding: '0 16px' }}> style={{ textAlign: 'center' }}
<TextField keepMounted={true}
onKeyDownCapture={dismissTabKey} anchorEl={props.anchorEl}
style={{ marginTop: '0' }} open={props.open}
onClick={dismissClick} onClose={props.onClose}
label="from" onKeyDownCapture={handleKeyEvents}
value={rangeFrom} >
onChange={setFromHandler} <Typography>Define custom ranges for the Y-Axis</Typography>
margin="normal" <div style={{ padding: '0 16px' }}>
/> <TextField
<TextField inputProps={{
style={{ marginLeft: '8px', marginTop: '0' }} ref: rangeFromRef,
onClick={dismissClick} }}
label="to" autoFocus={true}
value={rangeTo} style={{ marginTop: '0' }}
onChange={setToHandler} label="from"
margin="normal" value={rangeFrom}
/> onChange={setFromHandler}
</div> margin="normal"
</Menu> />
<TextField
inputProps={{
ref: rangeToRef,
}}
style={{ marginLeft: '8px', marginTop: '0' }}
onClick={dismissClick}
label="to"
value={rangeTo}
onChange={setToHandler}
margin="normal"
/>
</div>
</Menu>
),
[rangeFrom, rangeTo, props.open]
) )
} }