summaryrefslogtreecommitdiffhomepage
path: root/desktop/packages/mullvad-vpn/src/renderer/components/SimpleInput.tsx
blob: 8d4a51d8e9b7d6bd1c5fd0da8a030ed19a88755e (plain)
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
import { useCallback, useState } from 'react';
import React from 'react';
import styled from 'styled-components';

import { useCombinedRefs } from '../lib/utility-hooks';
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,
    onChange: propsOnChange,
    onSubmit: propsOnSubmit,
    onKeyPress: propsOnKeyPress,
    ...otherProps
  } = props;
  const [value, setValue] = useState((props.value as string) ?? '');

  const onChange = useCallback(
    (event: React.ChangeEvent<HTMLInputElement>) => {
      setValue(event.target.value);
      propsOnChange?.(event);
      onChangeValue?.(event.target.value);
    },
    [propsOnChange, onChangeValue],
  );

  const onSubmit = useCallback(
    (event: React.FormEvent<HTMLInputElement>) => {
      propsOnSubmit?.(event);
      onSubmitValue?.(value);
    },
    [propsOnSubmit, onSubmitValue, value],
  );

  const onKeyPress = useCallback(
    (event: React.KeyboardEvent<HTMLInputElement>) => {
      propsOnKeyPress?.(event);
      if (event.key === 'Enter') {
        onSubmitValue?.(value);
      }
    },
    [propsOnKeyPress, onSubmitValue, value],
  );

  const refCallback = useCallback(
    (element: HTMLInputElement | null) => {
      if (element && otherProps.autoFocus) {
        setTimeout(() => element.focus());
      }
    },
    [otherProps.autoFocus],
  );

  const combinedRef = useCombinedRefs(refCallback, ref);

  return (
    <StyledInput
      {...otherProps}
      ref={combinedRef}
      onChange={onChange}
      onSubmit={onSubmit}
      onKeyPress={onKeyPress}
    />
  );
}

export default React.forwardRef(SimpleInput);