import React, { FunctionComponent, memo, MouseEventHandler, ReactNode, useCallback, useContext, useState } from 'react';
import classNames from 'classnames';
import DropDown, { DropDownProps } from '../dropdown';
import { Placements } from '../dropdown/enum';
import Icon from '../icon';
import List, { ListProps } from '../list';
import buildPlacements from './placements';
import ConfigContext from '../config-provider/ConfigContext';

export interface menuListItemProps {
  href?: string;
  listItemName?: string;
  listChildren?: ({ listItemName, href }: { listItemName: string; href: string }) => ReactNode;
  onClick?: MouseEventHandler<HTMLAnchorElement | HTMLSpanElement>;
}

export interface BreadcrumbItemProps {
  prefixCls?: string;
  separator?: ReactNode;
  href?: string;
  overlay?: DropDownProps['overlay'];
  dropdownProps?: Partial<DropDownProps>;
  listProps?: Partial<ListProps>;
  menuList?: menuListItemProps[];
  onClick?: MouseEventHandler<HTMLAnchorElement | HTMLSpanElement>;
  children?: ReactNode;
}

interface BreadcrumbItemInterface extends FunctionComponent<BreadcrumbItemProps> {
  __C7N_BREADCRUMB_ITEM?: boolean;
}

const BreadcrumbItem: BreadcrumbItemInterface = function BreadcrumbItem({
  prefixCls: customizePrefixCls,
  separator = '/',
  menuList = [],
  children,
  overlay,
  listProps,
  dropdownProps,
  ...restProps
}) {
  const { getPrefixCls } = useContext(ConfigContext);
  const prefixCls = getPrefixCls('breadcrumb', customizePrefixCls);
  const [active, setActive] = useState(false);
  const isMenuListOn = menuList ? menuList.length > 0 : false;
  const onVisibleChange = useCallback(async (visible: boolean) => {
    if (isMenuListOn) {
      setActive(visible);
    }
  }, [isMenuListOn]);
  /**
   * 渲染Link
   * @param childrenLink
   * @param restPropsLink
   */
  const renderLink = (childrenLink, restPropsLink, classNameLink, key): ReactNode => {
    if (key in restPropsLink) {
      return (
        <a className={`${prefixCls}-${classNameLink}`} {...restPropsLink}>
          {childrenLink}
        </a>
      );
    }
    return (
      <span className={`${prefixCls}-${classNameLink}`} {...restPropsLink}>
        {childrenLink}
      </span>
    );
  };

  /**
   * 渲染List列表
   */
  const renderList = (
    <List
      className={`${prefixCls}-overlay-menu-list`}
      grid={{ gutter: 0, column: 3 }}
      {...listProps}
      dataSource={menuList}
      renderItem={item => {
        const { href } = item;
        const { listChildren, listItemName, ...listRestProps } = item;
        let titleItem = listItemName || href;
        titleItem = listChildren ? listChildren({ href, listItemName }) : listItemName;
        return (
          <List.Item>
            {renderLink(titleItem, listRestProps, 'overlay-menu-list-item', 'href')}
          </List.Item>
        );
      }}
    />
  );

  const overlayMenu = overlay || (isMenuListOn && renderList);

  const onOverlayClick = useCallback(() => {
    setTimeout(() => {
      setActive(false);
    }, 300);
  }, []);

  if (children) {

    const renderBreadcrumbMenu = (linkItem: ReactNode) => {
      if (overlayMenu) {
        const buildASPlacements = buildPlacements;
        const dropDownProps = {
          overlayClassName: isMenuListOn ? `${prefixCls}-overlay-popup` : undefined,
          onOverlayClick,
          overlay: overlayMenu,
          placement: isMenuListOn ? Placements.bottomLeft : Placements.bottomCenter,
          onVisibleChange,
          overlayPlacements: buildASPlacements,
          ...dropdownProps,
        };
        return (
          <DropDown {...dropDownProps}>
            <span className={classNames(`${prefixCls}-overlay-link`, {
              [`${prefixCls}-overlay-border`]: active,
              [`${prefixCls}-overlay-menu`]: isMenuListOn,
            })}>
              {linkItem}
              {isMenuListOn || <Icon type="arrow_drop_down" />}
              <i className={classNames(`${prefixCls}-overlay-cover`, {
                [`${prefixCls}-overlay-cover-active`]: active,
              })} />
            </span>
          </DropDown>
        );
      }
      return linkItem;
    };

    let link: ReactNode = renderLink(children, restProps, `link`, 'href');

    // wrap to dropDown
    link = renderBreadcrumbMenu(link);
    return (
      <span>
        {link}
        {separator && separator !== '' && (
          <span className={`${prefixCls}-separator`}>{separator}</span>
        )}
      </span>
    );
  }
  return null;
};

BreadcrumbItem.displayName = 'BreadcrumbItem';

BreadcrumbItem.__C7N_BREADCRUMB_ITEM = true;

export default memo(BreadcrumbItem);