import { useEffect, useMemo } from 'react';
import { useFormContext, useWatch } from 'react-hook-form';

import Stack from '@material-hu/mui/Stack';
import { useTheme } from '@material-hu/mui/styles';
import { getNow } from '@material-hu/utils/time';

import FormTimePicker from '@material-hu/components/composed-components/TimePicker/form';
import FormDatePicker from '@material-hu/components/design-system/Inputs/DatePicker/form';

import useRules from 'src/hooks/useRules';
import { LearningCard } from 'src/pages/dashboard/Learning/common/components/LearningCard';
import { newSessionRules } from 'src/pages/dashboard/Learning/Sessions/New/form';
import { type NewSessionFormValues } from 'src/pages/dashboard/Learning/Sessions/types';
import { useLokaliseTranslation } from 'src/utils/i18n';
import { setDateToTime } from 'src/utils/timeUtils';

import { useSessionStatus } from '../../../hooks/useSessionStatus';
import { isOldSession } from '../../../utils';
import BeforeTodayAlert from '../BeforeTodayAlert';

const SessionDate = () => {
  const { t } = useLokaliseTranslation('learning');
  const { palette } = useTheme();
  const { control, getValues, setValue, trigger } =
    useFormContext<NewSessionFormValues>();
  const { blockSessionEdition } = useSessionStatus();

  const [localDate, startTime, endTime, timeZone] = useWatch({
    control,
    name: [
      'basic_information.localDate',
      'basic_information.startTime',
      'basic_information.endTime',
      'basic_information.timeZone',
    ],
  });

  const now = useMemo(() => getNow(timeZone), [timeZone]);
  const isOld = isOldSession({ localDate, startTime, timeZone });

  const localDateRules = useRules(
    newSessionRules.basic_information.localDate(),
  );
  const startTimeRules = useRules(
    newSessionRules.basic_information.startTime(),
  );
  const endTimeRules = useRules(
    newSessionRules.basic_information.endTime({ startTime, isOld, now }),
  );

  useEffect(() => {
    if (!localDate || blockSessionEdition) return;

    const currentStartTime = getValues('basic_information.startTime');
    const currentEndTime = getValues('basic_information.endTime');

    if (currentStartTime) {
      const syncedStartTime = setDateToTime(currentStartTime, localDate);
      if (syncedStartTime.getTime() !== currentStartTime.getTime()) {
        setValue('basic_information.startTime', syncedStartTime, {
          shouldValidate: false,
        });
      }
    }

    if (currentEndTime) {
      const syncedEndTime = setDateToTime(currentEndTime, localDate);
      if (syncedEndTime.getTime() !== currentEndTime.getTime()) {
        setValue('basic_information.endTime', syncedEndTime, {
          shouldValidate: false,
        });
      }
    }
  }, [localDate, blockSessionEdition, getValues, setValue]);

  useEffect(() => {
    if (blockSessionEdition || !startTime || !endTime) return;
    trigger('basic_information.endTime');
  }, [startTime, blockSessionEdition, endTime, trigger]);

  return (
    <LearningCard id="session-basic-information-date-card">
      <Stack
        sx={{
          flexDirection: 'row',
          gap: 2,
          '& > .MuiFormControl-root': {
            flex: 1,
            '& > .MuiStack-root > .MuiTypography-root::after': {
              content: '"*"',
              color: palette.textColors?.errorText,
            },
          },
        }}
      >
        <FormDatePicker
          name="basic_information.localDate"
          rules={localDateRules}
          inputProps={{
            label: t('general:date_label'),
            timezone: timeZone,
            disabled: blockSessionEdition,
            sx: {
              '& .MuiInputBase-input::placeholder': {
                textTransform: 'lowercase',
              },
            },
          }}
        />
        <FormTimePicker
          name="basic_information.startTime"
          rules={startTimeRules}
          inputProps={{
            label: t('general:hour_start'),
            placeholder: t('general:time_placeholder'),
            timezone: timeZone,
            referenceDate: localDate || undefined,
            minutesStep: 10,
            disabled: blockSessionEdition,
            disableOpenPicker: blockSessionEdition,
          }}
        />
        <FormTimePicker
          name="basic_information.endTime"
          rules={endTimeRules}
          inputProps={{
            label: t('general:hour_end'),
            placeholder: t('general:time_placeholder'),
            timezone: timeZone,
            minTime: startTime || undefined,
            referenceDate: localDate || undefined,
            minutesStep: 10,
            disabled: blockSessionEdition,
            disableOpenPicker: blockSessionEdition,
          }}
        />
      </Stack>
      <BeforeTodayAlert
        localDate={localDate}
        startTime={startTime}
        timeZone={timeZone}
      />
    </LearningCard>
  );
};

export default SessionDate;
