diff options
| author | Oskar Nyberg <oskar@mullvad.net> | 2023-10-04 10:39:53 +0200 |
|---|---|---|
| committer | Oskar Nyberg <oskar@mullvad.net> | 2023-10-09 10:16:53 +0200 |
| commit | 4e26e4c36345afbca25a1a1e760927cd74d2c1a5 (patch) | |
| tree | 07e762d042fdcf2a6e556bb01ff3de0660c98ef2 /gui/src | |
| parent | c1f9e782da8d8cd5731fe43017f056b184f126c9 (diff) | |
| download | mullvadvpn-4e26e4c36345afbca25a1a1e760927cd74d2c1a5.tar.xz mullvadvpn-4e26e4c36345afbca25a1a1e760927cd74d2c1a5.zip | |
Add input component
Diffstat (limited to 'gui/src')
| -rw-r--r-- | gui/src/renderer/components/SimpleInput.tsx | 71 |
1 files changed, 71 insertions, 0 deletions
diff --git a/gui/src/renderer/components/SimpleInput.tsx b/gui/src/renderer/components/SimpleInput.tsx new file mode 100644 index 0000000000..3d2a1a63a7 --- /dev/null +++ b/gui/src/renderer/components/SimpleInput.tsx @@ -0,0 +1,71 @@ +import { useCallback, useState } from 'react'; +import React from 'react'; +import styled from 'styled-components'; + +import { useCombinedRefs } from '../lib/utilityHooks'; +import { normalText } from './common-styles'; + +const StyledInput = styled.input.attrs({ type: 'text' })(normalText, { + padding: '6px 8px', + borderRadius: '4px', + outline: 0, + border: 0, + lineHeight: '21px', +}); + +interface SimpleInputProps extends Omit<React.InputHTMLAttributes<HTMLInputElement>, 'type'> { + onChangeValue?: (value: string) => void; + onSubmitValue?: (value: string) => void; +} + +function SimpleInput(props: SimpleInputProps, ref: React.Ref<HTMLInputElement>) { + const { onChangeValue, onSubmitValue, ...otherProps } = props; + const [value, setValue] = useState((props.value as string) ?? ''); + + const onChange = useCallback( + (event: React.ChangeEvent<HTMLInputElement>) => { + setValue(event.target.value); + otherProps.onChange?.(event); + onChangeValue?.(event.target.value); + }, + [otherProps.onChange, onChangeValue], + ); + + const onSubmit = useCallback( + (event: React.FormEvent<HTMLInputElement>) => { + otherProps.onSubmit?.(event); + onSubmitValue?.(value); + }, + [otherProps.onSubmit, onSubmitValue, value], + ); + + const onKeyPress = useCallback( + (event: React.KeyboardEvent<HTMLInputElement>) => { + props.onKeyPress?.(event); + if (event.key === 'Enter') { + onSubmitValue?.(value); + } + }, + [props.onKeyPress, onSubmitValue, value], + ); + + const refCallback = useCallback((element: HTMLInputElement | null) => { + if (element && otherProps.autoFocus) { + setTimeout(() => element.focus()); + } + }, []); + + const combinedRef = useCombinedRefs(refCallback, ref); + + return ( + <StyledInput + {...otherProps} + ref={combinedRef} + onChange={onChange} + onSubmit={onSubmit} + onKeyPress={onKeyPress} + /> + ); +} + +export default React.forwardRef(SimpleInput); |
