import _InputAdornment from "@mui/material/InputAdornment";
/*!
 * Copyright (c) 2022-present, Okta, Inc. and/or its affiliates. All rights reserved.
 * The Okta software accompanied by this notice is provided pursuant to the Apache License, Version 2.0 (the "License.")
 *
 * You may obtain a copy of the License at http://www.apache.org/licenses/LICENSE-2.0.
 * Unless required by applicable law or agreed to in writing, software
 * distributed under the License is distributed on an "AS IS" BASIS, WITHOUT
 * WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
 *
 * See the License for the specific language governing permissions and limitations under the License.
 */
import { DateTimeField as MuiDateTimeField } from "@mui/x-date-pickers";
import { memo, useCallback, useEffect, useImperativeHandle, useRef, useState } from "react";
import { Field } from "../../Field.js";
import { useTranslation } from "../../i18n.generated/i18n.js";
import { jsx as _jsx, Fragment as _Fragment } from "react/jsx-runtime";
const useOdysseyDateError = () => {
  const {
    t
  } = useTranslation();
  return new Map([["invalidDate", t("picker.error.invalid")], ["maxDate", t("picker.error.maxdate")], ["minDate", t("picker.error.mindate")]]);
};
const formatDateTimeToUtcIsoDateString = value => value.toUTC().toISO();
const DateTimeField = ({
  defaultValue,
  endAdornment,
  errorMessage,
  hasInitialFocus,
  hint,
  HintLinkComponent,
  id: idOverride,
  inputRef,
  isDisabled = false,
  isOptional = false,
  isReadOnly,
  label,
  minDate,
  maxDate,
  onBlur,
  onChange,
  onFocus,
  timezone,
  value
}) => {
  const errorMap = useOdysseyDateError();
  const [displayedErrorMessage, setDisplayedErrorMessage] = useState(errorMessage);
  const internalValidationError = useRef();
  const localInputRef = useRef(null);
  useImperativeHandle(inputRef, () => {
    return {
      focus: () => {
        localInputRef.current?.focus();
      }
    };
  }, []);
  const checkMinMaxValidity = useCallback(value => {
    const hasMinError = minDate && value.toUTC() < minDate.toUTC();
    const hasMaxError = maxDate && value.toUTC() > maxDate.toUTC();
    if (hasMinError || hasMaxError) {
      if (hasMinError) {
        setDisplayedErrorMessage(errorMap.get("minDate"));
      }
      if (hasMaxError) {
        setDisplayedErrorMessage(errorMap.get("maxDate"));
      }
      return false;
    }
    return true;
  }, [errorMap, minDate, maxDate]);
  useEffect(() => {
    if (value) {
      checkMinMaxValidity(value);
    }
    if (defaultValue) {
      checkMinMaxValidity(defaultValue);
    }
  }, [checkMinMaxValidity, defaultValue, minDate, maxDate, value]);
  const clearErrorMessages = useCallback(() => {
    setDisplayedErrorMessage(undefined);
    internalValidationError.current = undefined;
  }, [internalValidationError, setDisplayedErrorMessage]);
  const validateAndCallOnChange = useCallback((value, validationContext) => {
    clearErrorMessages();
    const {
      validationError
    } = validationContext;
    const hasEnteredFullYear = value?.year.toString().length === 4;
    if (validationError) {
      const odysseyValidationError = errorMap.get(validationError);
      if (odysseyValidationError) {
        internalValidationError.current = odysseyValidationError;
        if (value?.isValid && hasEnteredFullYear) {
          setDisplayedErrorMessage(odysseyValidationError);
        }
      }
    }
    if (value?.isValid && !validationError) {
      const dateStringFromDateTime = formatDateTimeToUtcIsoDateString(value);
      if (dateStringFromDateTime && checkMinMaxValidity(value)) {
        onChange?.(dateStringFromDateTime);
      }
    }
  }, [checkMinMaxValidity, clearErrorMessages, errorMap, onChange]);
  const checkFieldValidityAndSetError = useCallback(event => {
    if (internalValidationError?.current && !displayedErrorMessage) {
      setDisplayedErrorMessage(internalValidationError.current);
    }
    onBlur?.(event);
  }, [displayedErrorMessage, internalValidationError, onBlur]);
  const hasVisibleAdornment = !isReadOnly && !isDisabled;
  const renderFieldComponent = useCallback(({
    ariaDescribedBy,
    errorMessageElementId,
    id,
    labelElementId
  }) => _jsx(MuiDateTimeField, {
    autoFocus: hasInitialFocus,
    defaultValue: defaultValue,
    disabled: isDisabled,
    id: id,
    inputProps: {
      "aria-describedby": ariaDescribedBy,
      "aria-errormessage": errorMessageElementId,
      "aria-labelledby": labelElementId
    },
    InputProps: {
      error: Boolean(displayedErrorMessage || errorMessage),
      endAdornment: _jsx(_Fragment, {
        children: hasVisibleAdornment && _jsx(_InputAdornment, {
          position: "end",
          children: endAdornment
        })
      })
    },
    inputRef: localInputRef,
    maxDate: maxDate,
    minDate: minDate,
    name: id,
    onBlur: checkFieldValidityAndSetError,
    onChange: validateAndCallOnChange,
    onFocus: onFocus,
    readOnly: isReadOnly,
    timezone: timezone,
    value: value,
    variant: "standard"
  }), [checkFieldValidityAndSetError, defaultValue, displayedErrorMessage, endAdornment, errorMessage, hasInitialFocus, hasVisibleAdornment, isDisabled, localInputRef, minDate, maxDate, onFocus, isReadOnly, timezone, validateAndCallOnChange, value]);
  return _jsx(Field, {
    errorMessage: displayedErrorMessage || errorMessage,
    fieldType: "single",
    hasVisibleLabel: true,
    hint: hint,
    HintLinkComponent: HintLinkComponent,
    id: idOverride,
    isDisabled: isDisabled,
    isOptional: isOptional,
    label: label,
    renderFieldComponent: renderFieldComponent
  });
};
const MemoizedDateTimeField = memo(DateTimeField);
MemoizedDateTimeField.displayName = "DateTimeField";
export { MemoizedDateTimeField as DateTimeField };
//# sourceMappingURL=DateTimeField.js.map