/**
 * @Move (?)
 * Only used by DashboardLayout - move with it
 */
import { useEffect, useMemo, useState } from 'react';

import {
  IconMessage2Question,
  IconMinus,
  IconX,
} from '@material-hu/icons/tabler';
import IconButton from '@material-hu/mui/IconButton';
import Stack from '@material-hu/mui/Stack';
import { useTheme } from '@material-hu/mui/styles';
import Typography from '@material-hu/mui/Typography';

import { colorPalette } from '@material-hu/theme/hugo/colors';

import Badge from '@material-hu/components/design-system/Badge';

import { CUSTOM_ZENDESK_Z_INDEX, useZendesk } from 'src/config/zendesk';
import useHuGoTheme from 'src/hooks/useHuGoTheme';
import { logEvent, LogEvents } from 'src/utils/logging';

//Custom zIndex setted by API to handle and select the zendesk messenger iframe
const ZENDESK_IFRAME_SELECTOR = `iframe[style*="z-index: ${CUSTOM_ZENDESK_Z_INDEX}"]`;

const HEADER_HEIGHT = 64;
const HEADER_WIDTH = 300;

//same styles as in zendesk widget
const TRANSITIONS = {
  open: {
    transform: 'scale(1) translateY(0px)',
    opacity: 1,
    pointerEvents: 'auto',
    transition:
      'transform 410ms cubic-bezier(0.76, 0, 0.16, 1), opacity 360ms cubic-bezier(0.76, 0, 0.16, 1) 20ms, height linear',
  },
  closed: {
    transform: 'scale(1) translateY(640px)',
    opacity: 0,
    pointerEvents: 'none',
    transition:
      'transform 410ms cubic-bezier(0.66, 0, 0.1, 1), opacity 305ms cubic-bezier(0.66, 0, 0.1, 1) 200ms, height linear 400ms',
  },
};
const baseHeaderStyles = {
  position: 'fixed',
  backgroundColor: colorPalette.base.blueBrand[400],
  display: 'flex',
  flexDirection: 'row',
  gap: 1,
  p: 2,
  alignItems: 'center',
  justifyContent: 'space-between',
  zIndex: 10000000,
  borderRadius: '20px',
  borderBottomLeftRadius: 0,
  borderBottomRightRadius: 0,
  transformOrigin: 'center bottom',
  border: 0,
  width: HEADER_WIDTH,
  height: HEADER_HEIGHT,
  filter: 'brightness(100%)',
  pointerEvents: 'auto',
};

const BADGE_STYLES = {
  position: 'fixed',
  bottom: 0,
  mb: 4,
  ml: 1.5,
  cursor: 'pointer',
  borderRadius: '100%',
  backgroundColor: colorPalette.buttons.buttonPrimaryEnabled,
  p: 2,
  zIndex: 9999,
  '& .MuiBadge-badge': {
    mr: 1,
    mt: 0.5,
  },
};

const useZendeskIframeRect = () => {
  const [rect, setRect] = useState<DOMRect | null>(null);
  const { isWidgetOpen } = useZendesk();

  useEffect(() => {
    const iframe = document.querySelector(
      ZENDESK_IFRAME_SELECTOR,
    ) as HTMLIFrameElement | null;

    if (!iframe || !isWidgetOpen) {
      return;
    }

    const updateRect = () => {
      setRect(iframe.getBoundingClientRect());
    };

    const resizeObserver = new ResizeObserver(updateRect);
    resizeObserver.observe(iframe);

    window.addEventListener('resize', updateRect);

    return () => {
      resizeObserver.disconnect();
      window.removeEventListener('resize', updateRect);
    };
  }, [isWidgetOpen]);

  return rect;
};

const calculateHeaderStyles = (
  iframeRect: DOMRect | null,
  isWidgetOpen: boolean,
) => {
  if (!iframeRect) {
    return TRANSITIONS.closed;
  }

  const baseStyles = {
    bottom: iframeRect.height - HEADER_HEIGHT + iframeRect.left,
    left: iframeRect.left + 59,
    width: iframeRect.width - 59,
  };

  if (!isWidgetOpen && iframeRect) {
    return {
      ...TRANSITIONS.closed,
      ...baseStyles,
    };
  }

  return {
    ...TRANSITIONS.open,
    ...baseStyles,
  };
};

const ZendeskWidgetHeader = () => {
  const { isWidgetOpen, onHide, setShowSupportButton } = useZendesk();
  const theme = useTheme();
  const iframeRect = useZendeskIframeRect();

  const handleClose = () => {
    onHide();
    logEvent(LogEvents.SUPPORT_WIDGET_CLOSED);
    setShowSupportButton(false);
  };

  const headerStyles = useMemo(
    () => calculateHeaderStyles(iframeRect, isWidgetOpen),
    [iframeRect, isWidgetOpen],
  );

  return (
    <Stack
      sx={{
        ...baseHeaderStyles,
        ...headerStyles,
      }}
    >
      <Typography
        variant="globalM"
        sx={{
          color: theme.palette.common.white,
          fontWeight: 'fontWeightSemiBold',
        }}
      >
        Humand
      </Typography>
      <Stack sx={{ display: 'flex', flexDirection: 'row', gap: 1 }}>
        <IconButton
          onClick={onHide}
          sx={{ '& > svg': { stroke: theme.palette.common.white } }}
        >
          <IconMinus color={theme.palette.common.white} />
        </IconButton>
        <IconButton
          onClick={handleClose}
          sx={{ '& > svg': { stroke: theme.palette.common.white } }}
        >
          <IconX stroke={theme.palette.common.white} />
        </IconButton>
      </Stack>
    </Stack>
  );
};

const ZendeskContainer = () => {
  const {
    onShow,
    isWidgetOpen,
    onHide,
    totalUnreadMessagesCount,
    showSupportButton,
  } = useZendesk();
  const HuGoThemeProvider = useHuGoTheme();
  const theme = useTheme();

  const handleClick = () => {
    if (isWidgetOpen) {
      onHide();
    } else {
      logEvent(LogEvents.SUPPORT_WIDGET_OPENED, {
        source: 'FLOATING_BUTTON',
      });
      onShow();
    }
  };

  return (
    <HuGoThemeProvider>
      <Stack>
        {showSupportButton && (
          <Stack onClick={handleClick}>
            <Badge
              badgeContent={totalUnreadMessagesCount}
              color="error"
              sx={BADGE_STYLES}
            >
              <IconMessage2Question color={theme.palette.common.white} />
            </Badge>
          </Stack>
        )}
        <ZendeskWidgetHeader />
      </Stack>
    </HuGoThemeProvider>
  );
};

export default ZendeskContainer;
