import 'react-intl-tel-input/dist/main.css';
import './index.css';

import classNames from 'classnames';
import React, { FC, useEffect, useState } from 'react';
import IntlTelInput from 'react-intl-tel-input';

import css from './index.module.css';

import { parsePhoneNumberFromString } from 'libphonenumber-js/min';

export interface InputTelProps {
  label?: string;
  placeholder?: string;
  name?: string;
  required?: boolean;
  value?: {
    isValid?: boolean;
    number?: string;
    internationalNumber?: string;
  };
  error?: {
    isValid?: boolean;
    number?: string;
  };
  defaultCountry?: string;
  hideLabel?: boolean;
  onChange?: (e) => void;
  onBlur?: (e) => void;
  variant?: 'normal' | 'booking';
}

export const InputTel: FC<InputTelProps> = ({
  error,
  label,
  onChange,
  onBlur,
  value,
  defaultCountry,
  name,
  hideLabel,
  variant,
}) => {
  const [isActive, setActive] = useState(false);
  const inputTelClassNames = classNames(css.inputTel, {
    [css.inputTelError]: error,
    [css.inputTelBooking]: variant == 'booking',
    [css.inputTelActive]: variant == 'booking' && isActive,
  });

  useEffect(() => {
    setActive(value != null && value.number != '');

    // TODO workaround for bug https://github.com/patw0929/react-intl-tel-input/issues/336
    if (value.number != '' && !value.internationalNumber) {
      const phoneNumber = parsePhoneNumberFromString(value.number);
      if (phoneNumber) {
        const x = phoneNumber.formatNational();

        const event = {
          target: {
            name: name,
            value: {
              number: x,
              internationalNumber: value.number,
              isValid: phoneNumber.isValid(),
            },
          },
        };
        onChange(event);
      }
    }
  }, [value]);

  const disableFocus = (e): void => {
    if (e.target.value.number == '') {
      setActive(false);
    }
  };

  return (
    <div className={inputTelClassNames} data-testid="InputTel">
      <div className={css.inputTel__wrapper}>
        {!hideLabel && (
          <label htmlFor={name} className={css.inputTel__label}>
            {label}
          </label>
        )}

        <IntlTelInput
          value={value.number}
          onPhoneNumberBlur={(_, __, ___, ____, _____, e): void => {
            disableFocus(e);
            onBlur(e);
          }}
          onPhoneNumberChange={(
            isValid,
            number,
            getCountryDetails,
            getCountryCodeWithNumber,
          ): void => {
            const RegExp = '+' + getCountryDetails.dialCode;
            number = number.replace(RegExp, '');
            const event = {
              target: {
                name: name,
                value: {
                  number,
                  internationalNumber: getCountryCodeWithNumber.replace(
                    /\s/g,
                    '',
                  ),
                  isValid,
                },
              },
            };
            onChange(event);
            disableFocus(event);
          }}
          onPhoneNumberFocus={(): void => {
            setActive(true);
          }}
          onSelectFlag={(
            number,
            getCountryDetails,
            getCountryCodeWithNumber,
            isValid,
          ): void => {
            const RegExp = '+' + getCountryDetails.dialCode;
            number = number.replace(RegExp, '');
            const phoneNumber = parsePhoneNumberFromString(
              getCountryCodeWithNumber,
            );
            if (phoneNumber) {
              number = phoneNumber.formatNational();
            }
            const event = {
              target: {
                name: name,
                value: {
                  number,
                  internationalNumber: getCountryCodeWithNumber.replace(
                    /\s/g,
                    '',
                  ),
                  isValid,
                },
              },
            };
            onChange(event);
          }}
          fieldId={name}
          format={true}
          separateDialCode={true}
          autoHideDialCode={true}
          placeholder={''}
          autoComplete="phone"
          preferredCountries={['at', 'ch', 'de', 'fr', 'gb']}
          defaultCountry={defaultCountry}
          containerClassName={classNames([
            'intl-tel-input',
            css.inputTel__container,
            variant == 'booking' ? 'intl-tel-booking-input' : '',
          ])}
          inputClassName={classNames([
            'intl-tel-input-input',
            css.inputTel__input,
          ])}
        />
      </div>
      {error && (
        <div className={css.inputTel__error}>
          {error.number || error.isValid}
        </div>
      )}
    </div>
  );
};

export default InputTel;
