import React, { useMemo, useState, useRef, useContext } from 'react';
import { isEmpty } from 'lodash';
import { useTranslation } from 'react-i18next';
import styled from 'styled-components';
import { grid, override } from '@pubsweet/ui-toolkit';
import { v4 as uuidv4 } from 'uuid';
import {
  WaxContext,
  useOnClickOutside,
  MenuButton,
} from 'wax-prosemirror-core';

const Wrapper = styled.div`
  font-size: 0;
  position: relative;
  z-index: 2;
`;

const DropWrapper = styled.div`
  background: white;
  margin-top: ${grid(1)};
  position: absolute;
  top: 32px;
  width: max-content;

  ${override('Wax.HighlightToolWrapper')}
`;
const TextHighlightComponent = styled.div`
  background: white;
  border: 1px solid gray;
  display: flex;
  flex-direction: column;
`;
const Highlighter = styled.div`
  border: 1px solid gray;
  cursor: pointer;
  display: inline-grid;
  height: 25px;
  margin: 5px;
  min-width: 25px;
`;

const TextHighlightingTool = ({ view: { dispatch, state }, item }) => {
  const { icon, title, select } = item;
  const [isOpen, setIsOpen] = useState(false);
  const { t, i18n } = useTranslation();

  const highlightDropDownOptions = [
    { name: 'yellow', value: '#F3E95C' },
    { name: 'blue', value: '#7DE5DB' },
    { name: 'green', value: '#C0EB96' },
    { name: 'pink', value: '#F2C4D1' },
    { name: 'orange', value: '#FFB56B' },
    { name: 'red', value: '#FF8080' },
    { name: 'remove highlight', value: 'transparent' },
  ];

  const ref = useRef();
  const {
    activeViewId,
    activeView,
    pmViews: { main },
  } = useContext(WaxContext);

  const isEditable = main.props.editable(editable => {
    return editable;
  });

  useOnClickOutside(ref, () => setIsOpen(false));

  const renderList = () => {
    const lists = [];

    Object.keys(highlightDropDownOptions).forEach(key => {
      lists.push(
        <Highlighter
          data-style={highlightDropDownOptions[key].value}
          key={uuidv4()}
          onMouseDown={e =>
            handleMouseDown(e, highlightDropDownOptions[key].value)
          }
          style={{ backgroundColor: highlightDropDownOptions[key].value }}
          title={highlightDropDownOptions[key].name}
        />,
      );
    });
    return <div>{lists}</div>;
  };

  const handleMouseDown = (e, color) => {
    e.preventDefault();
    item.run(activeView.state, activeView.dispatch, color);
    if (color !== 'transparent') localStorage.setItem('lastBgColor', color);
    setIsOpen(false);
  };

  const handleDblClk = () => {
    const color = localStorage.getItem('lastBgColor')
      ? localStorage.getItem('lastBgColor')
      : highlightDropDownOptions[0].value;

    item.run(state, dispatch, color);
  };

  let isDisabled = !select(state, activeViewId, activeView);
  if (!isEditable) isDisabled = true;

  const line = document.getElementById('trait');
  if (line)
    line.style.fill =
      localStorage.getItem('lastBgColor') !== null
        ? localStorage.getItem('lastBgColor')
        : highlightDropDownOptions[0].name;

  const MenuButtonComponent = useMemo(
    () => (
      <Wrapper onDoubleClick={handleDblClk} ref={ref}>
        <div disabled={isDisabled}>
          <MenuButton
            active={isOpen}
            disabled={isDisabled}
            iconName={icon}
            onMouseDown={() => {
              setIsOpen(!isOpen);
            }}
            title={
              !isEmpty(i18n) && i18n.exists(`Wax.Various.${title}`)
                ? t(`Wax.Various.${title}`)
                : title
            }
          />
        </div>
        {isOpen && (
          <DropWrapper>
            <TextHighlightComponent
              close={() => {
                setIsOpen(false);
              }}
              item={item}
              key={uuidv4()}
              view={(dispatch, state)}
            >
              {renderList()}
            </TextHighlightComponent>
          </DropWrapper>
        )}
      </Wrapper>
    ),
    [isOpen, isDisabled, t(`Wax.Various.${title}`)],
  );

  return MenuButtonComponent;
};

export default TextHighlightingTool;