'use strict';

Object.defineProperty(exports, '__esModule', { value: true });

var _rollupPluginBabelHelpers = require('../../../../_virtual/_rollupPluginBabelHelpers.js');
var React = require('react');
var index$1 = require('../../../../utils/index.js');
var constants = require('../../../../utils/constants.js');
var index = require('../../utils/index.js');
var NumberInput_tokens = require('../../NumberInput.tokens.js');
var Input_styles = require('./Input.styles.js');
var useForkRef = require('../../../../hooks/useForkRef.js');
var useDidMountEffect = require('../../../../hooks/useDidMountEffect.js');
var isNumber = require('../../../../utils/isNumber.js');

function _interopDefault (e) { return e && e.__esModule ? e : { default: e }; }

var React__default = /*#__PURE__*/_interopDefault(React);

var _StyledSpinner;
var _excluded = ["value", "precision", "min", "max", "isLoading", "loader", "disabled", "segmentation", "textBefore", "textAfter", "isManualInput", "isInputFocused", "setIsInputFocused", "setIsAnimationRun", "setInnerValue", "onChange", "onBlur", "onKeyDown", "onDecrementKey", "onIncrementKey", "shouldFocusInput", "onFocusHandled"];
var NumberInput = /*#__PURE__*/React.forwardRef(function (_ref, ref) {
  var value = _ref.value,
    precision = _ref.precision,
    min = _ref.min,
    max = _ref.max,
    isLoading = _ref.isLoading,
    loader = _ref.loader,
    disabled = _ref.disabled,
    segmentation = _ref.segmentation,
    textBefore = _ref.textBefore,
    textAfter = _ref.textAfter,
    isManualInput = _ref.isManualInput,
    isInputFocused = _ref.isInputFocused,
    setIsInputFocused = _ref.setIsInputFocused,
    setIsAnimationRun = _ref.setIsAnimationRun,
    setInnerValue = _ref.setInnerValue,
    onChange = _ref.onChange,
    onBlur = _ref.onBlur,
    onKeyDown = _ref.onKeyDown,
    onDecrementKey = _ref.onDecrementKey,
    onIncrementKey = _ref.onIncrementKey,
    shouldFocusInput = _ref.shouldFocusInput,
    onFocusHandled = _ref.onFocusHandled,
    rest = _rollupPluginBabelHelpers.objectWithoutProperties(_ref, _excluded);
  var _useState = React.useState(value ? "".concat(String(value).length, "ch") : index.defaultCharacterWidth),
    _useState2 = _rollupPluginBabelHelpers.slicedToArray(_useState, 2),
    dynamicWidth = _useState2[0],
    setDynamicWidth = _useState2[1];
  var _useState3 = React.useState(value),
    _useState4 = _rollupPluginBabelHelpers.slicedToArray(_useState3, 2),
    lastValidValue = _useState4[0],
    setLastValidValue = _useState4[1];
  var _useState5 = React.useState(undefined),
    _useState6 = _rollupPluginBabelHelpers.slicedToArray(_useState5, 2),
    errorClass = _useState6[0],
    setErrorClass = _useState6[1];
  var _useState7 = React.useState(),
    _useState8 = _rollupPluginBabelHelpers.slicedToArray(_useState7, 2),
    errorValue = _useState8[0],
    setErrorValue = _useState8[1];
  var inputHelperRef = React.useRef(null);
  var wrapperRef = React.useRef(null);
  var textWrapperRef = React.useRef(null);
  var inputRef = React.useRef(null);
  var inputForkRef = useForkRef.useForkRef(inputRef, ref);
  var solidViewClass = segmentation === 'solid' ? NumberInput_tokens.classes.solidView : undefined;
  var manualInputClass = isManualInput ? NumberInput_tokens.classes.manualInput : undefined;
  var getInputWidth = function getInputWidth() {
    var _inputHelperRef$curre;
    var firstRender = arguments.length > 0 && arguments[0] !== undefined ? arguments[0] : true;
    if (!firstRender && (_inputHelperRef$curre = inputHelperRef.current) !== null && _inputHelperRef$curre !== void 0 && _inputHelperRef$curre.clientWidth) {
      var _inputHelperRef$curre2;
      return "".concat((_inputHelperRef$curre2 = inputHelperRef.current) === null || _inputHelperRef$curre2 === void 0 ? void 0 : _inputHelperRef$curre2.clientWidth, "px");
    }
    if (value) {
      return "".concat(String(value).length, "ch");
    }
    return index.defaultCharacterWidth;
  };
  var setValues = function setValues(event, newValue) {
    setLastValidValue(newValue);
    setInnerValue(newValue);
    if (onChange) {
      onChange(event, newValue);
    }
  };
  var validateValue = function validateValue(newValue) {
    if (!(newValue !== null && newValue !== void 0 && newValue.toString()) || !isNumber.isNumber(newValue)) {
      setValues(null, '');
      setIsAnimationRun(false);
      return;
    }
    var resValue = Number(newValue);
    if (max !== undefined && resValue > max) {
      setErrorClass(NumberInput_tokens.classes.errorAnimation);
      setErrorValue(max);
      setIsAnimationRun(true);
      return;
    }
    if (min !== undefined && resValue < min) {
      setErrorClass(NumberInput_tokens.classes.errorAnimation);
      setErrorValue(min);
      setIsAnimationRun(true);
      return;
    }
    if (String(newValue).endsWith('.')) {
      setValues(null, Number(newValue));
      setIsAnimationRun(false);
      return;
    }
    if (precision !== undefined) {
      var preciseNewValue = Number(index.getPreciseValue(newValue, precision));
      setValues(null, preciseNewValue);
    }
    setIsAnimationRun(false);
  };
  var handleManualInputChange = function handleManualInputChange(event) {
    var _textWrapperRef$curre, _wrapperRef$current;
    if (!isManualInput || disabled) {
      return;
    }
    setIsAnimationRun(true);
    var newValue = event.target.value;
    if (!isNumber.isNumber(lastValidValue) && lastValidValue !== '' && !newValue) {
      return;
    }
    if (!newValue) {
      setInnerValue('');
      if (onChange) {
        onChange(event, '');
      }
      return;
    }
    var cleanValue = newValue.replace(index.excludingNumberSchema, '');
    if (cleanValue.endsWith('.') || cleanValue === '-') {
      setInnerValue(cleanValue);
      if (onChange) {
        onChange(event, cleanValue);
      }
      return;
    }
    var isValid = index.numberSchema.test(cleanValue);
    if (!isValid) {
      setValues(event, lastValidValue);
      return;
    }
    if (textWrapperRef !== null && textWrapperRef !== void 0 && textWrapperRef.current && wrapperRef !== null && wrapperRef !== void 0 && wrapperRef.current && (textWrapperRef === null || textWrapperRef === void 0 || (_textWrapperRef$curre = textWrapperRef.current) === null || _textWrapperRef$curre === void 0 ? void 0 : _textWrapperRef$curre.clientWidth) > (wrapperRef === null || wrapperRef === void 0 || (_wrapperRef$current = wrapperRef.current) === null || _wrapperRef$current === void 0 ? void 0 : _wrapperRef$current.clientWidth)) {
      wrapperRef.current.scrollLeft = textWrapperRef.current.offsetWidth - textWrapperRef.current.offsetLeft || 0;
    }
    setValues(event, cleanValue);
  };
  var handleClickInputWrapper = function handleClickInputWrapper() {
    if (!isManualInput || !inputRef.current) {
      return;
    }
    if (!isInputFocused) {
      inputRef.current.focus();
    }
    setIsInputFocused(true);
  };
  var handleBlur = function handleBlur(event) {
    validateValue(value);
    setIsInputFocused(false);
    if (onBlur) {
      onBlur(event);
    }
  };
  var handleFocus = function handleFocus() {
    if (isManualInput && !isInputFocused) {
      var _inputRef$current;
      (_inputRef$current = inputRef.current) === null || _inputRef$current === void 0 || _inputRef$current.select();
    }
    setIsInputFocused(true);
  };
  var handleKeyDown = function handleKeyDown(event) {
    if (disabled) {
      return;
    }
    if (event.keyCode === constants.keyCodes.Up && onIncrementKey) {
      event.preventDefault();
      onIncrementKey();
      return;
    }
    if (event.keyCode === constants.keyCodes.Down && onDecrementKey) {
      event.preventDefault();
      onDecrementKey();
      return;
    }
    if (event.keyCode === constants.keyCodes.Enter) {
      event.preventDefault();
      validateValue(value);
      if (onKeyDown) {
        onKeyDown(event);
      }
    }
  };
  var handleEndErrorAnimation = function handleEndErrorAnimation(correctValue) {
    setIsAnimationRun(false);
    setIsInputFocused(false);
    setErrorClass(undefined);
    setValues(null, correctValue);
  };
  React.useEffect(function () {
    setDynamicWidth(getInputWidth());
  }, []);
  useDidMountEffect.useDidMountEffect(function () {
    setDynamicWidth(getInputWidth(false));
  }, [value]);
  React.useEffect(function () {
    if (shouldFocusInput && inputRef.current) {
      inputRef.current.focus();
      onFocusHandled === null || onFocusHandled === void 0 || onFocusHandled();
    }
  }, [shouldFocusInput]);
  return /*#__PURE__*/React__default.default.createElement(Input_styles.InputWrapper, {
    ref: wrapperRef,
    className: index$1.cx(solidViewClass, errorClass, manualInputClass),
    isManualInput: Boolean(isManualInput),
    onClick: handleClickInputWrapper
  }, /*#__PURE__*/React__default.default.createElement(Input_styles.TextWrapper, {
    ref: textWrapperRef
  }, !isLoading && textBefore && /*#__PURE__*/React__default.default.createElement(Input_styles.AdditionalText, {
    className: NumberInput_tokens.classes.textBefore
  }, textBefore), isLoading ? /*#__PURE__*/React__default.default.createElement(Input_styles.Loader, null, loader || _StyledSpinner || (_StyledSpinner = /*#__PURE__*/React__default.default.createElement(Input_styles.StyledSpinner, null))) : /*#__PURE__*/React__default.default.createElement(Input_styles.DynamicInput, null, /*#__PURE__*/React__default.default.createElement(Input_styles.Input, _rollupPluginBabelHelpers.extends({
    ref: inputForkRef,
    dynamicWidth: dynamicWidth,
    value: value,
    isManualInput: Boolean(isManualInput),
    tabIndex: disabled ? -1 : 0,
    onChange: handleManualInputChange,
    onFocus: handleFocus,
    onBlur: handleBlur,
    onKeyDown: handleKeyDown,
    onAnimationEnd: function onAnimationEnd() {
      return handleEndErrorAnimation(Number(errorValue));
    }
  }, rest)), /*#__PURE__*/React__default.default.createElement(Input_styles.InputWidthHelper, {
    ref: inputHelperRef
  }, value)), !isLoading && textAfter && /*#__PURE__*/React__default.default.createElement(Input_styles.AdditionalText, {
    className: NumberInput_tokens.classes.textAfter
  }, textAfter)));
});

exports.NumberInput = NumberInput;
