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

import { IconCheck, IconExclamationCircle } from '@material-hu/icons/tabler';
import Stack from '@material-hu/mui/Stack';
import { useTheme } from '@material-hu/mui/styles';
import Typography from '@material-hu/mui/Typography';

import HuAlert from '@material-hu/components/design-system/Alert';
import HuFormInputClassic from '@material-hu/components/design-system/Inputs/Classic/form';

import useRules from 'src/hooks/useRules';
import { useLokaliseTranslation } from 'src/utils/i18n';

import {
  GOAL_WEIGHTS_DRAWER_SECTION_BORDER_RADIUS,
  GOAL_WEIGHTS_DRAWER_TOTAL_ROW_BORDER_RADIUS,
} from '../../constants';
import { type Goal } from '../../types';
import { getTotal, isGoalDraftStatus } from '../../utils';

export type ContentData = {
  goals: Goal[];
  shouldApplyApprovalFlowOnMyGoals: boolean;
  hasNonDraftGoals: boolean;
  isValid: boolean;
  totalFromLocal: number;
};

type GoalWeightsDrawerContentProps = {
  contentDataRef: React.RefObject<ContentData>;
};

export function GoalWeightsDrawerContent({
  contentDataRef,
}: GoalWeightsDrawerContentProps) {
  const { control } = useFormContext();
  const theme = useTheme();
  const successColor = theme.palette.new?.text.feedback.success;
  const errorColor = theme.palette.new?.text.feedback.error;
  const neutralBorder = `1px solid ${theme.palette.new?.border.neutral.default}`;
  const snap = contentDataRef.current;
  const goals = snap?.goals ?? [];
  const weightFieldNames = goals.map(goal => `weight-${goal.id}`);
  /** Subscribe to weight fields so this tree re-renders when weights change (parent ref alone would stay stale with memoized drawer children). */
  useWatch({ control, name: weightFieldNames });
  const shouldApplyApprovalFlowOnMyGoals =
    snap?.shouldApplyApprovalFlowOnMyGoals ?? false;
  const hasNonDraftGoals = snap?.hasNonDraftGoals ?? false;
  const isValid = snap?.isValid ?? false;
  const totalFromLocal = snap?.totalFromLocal ?? 0;
  const { t } = useLokaliseTranslation('goals');

  const weightRules = useRules(
    {
      required: true,
      decimalFormat: true,
      validateMinValueAllowed: 0,
    },
    {
      maxValue: (value: number) => {
        const numValue = Number(value);
        return numValue <= 100 || t('weights.max_weight_error');
      },
      noNegativeValues: (value: number) => {
        const numValue = Number(value);
        return numValue >= 0 || t('weights.negative_value_error');
      },
    },
  );

  return (
    <Stack sx={{ gap: 2, height: '100%', overflowY: 'auto' }}>
      <Stack
        sx={{
          height: 'auto',
        }}
      >
        <Stack
          sx={{
            p: 2,
            height: 'auto',
            border: neutralBorder,
            borderRadius: GOAL_WEIGHTS_DRAWER_SECTION_BORDER_RADIUS,
          }}
        >
          <Stack sx={{ gap: 2 }}>
            {goals?.map(({ title, id, status }: Goal) => (
              <HuFormInputClassic
                key={`weight-${id}`}
                name={`weight-${id}`}
                rules={weightRules}
                inputProps={{
                  type: 'number',
                  size: 'small',
                  label: title,
                  fullWidth: true,
                  hasCounter: false,
                  showClear: true,
                  disabled: shouldApplyApprovalFlowOnMyGoals
                    ? !isGoalDraftStatus(status)
                    : false,
                  sx: {
                    '& input': {
                      textAlign: 'left',
                    },
                  },
                }}
              />
            ))}
          </Stack>
        </Stack>
      </Stack>
      <Stack
        sx={{
          p: 2,
          border: neutralBorder,
          borderRadius: GOAL_WEIGHTS_DRAWER_SECTION_BORDER_RADIUS,
          gap: 0.5,
        }}
      >
        <Typography
          variant="globalS"
          fontWeight="fontWeightSemiBold"
          sx={{
            color: isValid ? successColor : errorColor,
          }}
        >
          {t('weights.total_weight')}
        </Typography>
        <Stack sx={{ gap: 1 }}>
          <Stack
            sx={{
              flexDirection: 'row',
              width: '100%',
              px: '14px',
              height: '40px',
              border: neutralBorder,
              borderRadius: GOAL_WEIGHTS_DRAWER_TOTAL_ROW_BORDER_RADIUS,
              alignItems: 'center',
              justifyContent: 'space-between',
              borderColor: isValid ? successColor : errorColor,
            }}
          >
            <Stack sx={{ flexDirection: 'row', alignItems: 'center', gap: 1 }}>
              <Typography variant="globalS">
                {getTotal(totalFromLocal)}
              </Typography>
              <Typography variant="globalS">%</Typography>
            </Stack>
            {isValid && <IconCheck color={successColor} />}
            {!isValid && <IconExclamationCircle color={errorColor} />}
          </Stack>
          {!isValid && (
            <Stack sx={{ flexDirection: 'row', alignItems: 'center', gap: 1 }}>
              <IconExclamationCircle
                color={errorColor}
                size={16}
              />
              <Typography
                variant="globalS"
                sx={{ color: errorColor }}
              >
                {t('weights.weights_must_sum_100')}
              </Typography>
            </Stack>
          )}
        </Stack>
      </Stack>
      {shouldApplyApprovalFlowOnMyGoals && hasNonDraftGoals && (
        <HuAlert
          severity="warning"
          title={t('my_team.edit_weight_alert')}
        />
      )}
    </Stack>
  );
}
