import type {FC} from 'react';
import React, {useContext, useEffect, useState} from 'react';
import {context, Link} from 'dumi/theme';
import {history} from 'dumi';
import LocaleSelect from './LocaleSelect';
import SlugList from './SlugList';
import {Menu} from '@gyzn/linglong-ui';
import './SideMenu.less';

const {SubMenu} = Menu;

interface INavbarProps {
  mobileMenuCollapsed: boolean;
  location: any;
  darkPrefix?: React.ReactNode;
}

const SideMenu: FC<INavbarProps> = ({mobileMenuCollapsed, location, darkPrefix}) => {
  const {
    config: {logo, title, description, mode},
    menu,
    nav: navItems,
    base,
    meta
  } = useContext(context);

  const [openKeys, setOpenKeys] = useState<string[]>([]);
  const [selectedKeys, setSelectedKeys] = useState<string[]>([location.pathname]);

  useEffect(() => setSelectedKeys([location.pathname]), [location]);
  useEffect(() => setOpenKeys(() => menu.map(item => item.path).filter(item => item) as string[]), [
    menu
  ]);

  const isHiddenMenus =
    Boolean((meta.hero || meta.features || meta.gapless) && mode === 'site') ||
    meta.sidemenu === false ||
    undefined;

  // 导航目录格式
  const singleLayerMenu = menu.map(item => {
    // 标题
    const title = item.title
      .split('_')
      .map((v, i) => {
        if (v.toLocaleLowerCase() === 'll' && i === 0) {
          return 'LL';
        }
        return v.charAt(0).toLocaleUpperCase() + v.slice(1);
      })
      .join('');

    // children
    const children = item.children?.filter(i => i.title !== title);
    return {...item, title, children};
  });

  const onOpenChange = (keys: React.Key[]) => {
    setOpenKeys(keys as string[]);
  };

  const onClickMenu = (path: string | undefined) => {
    path && history.push(path);
  };

  return (
    <div
      className="__dumi-default-menu"
      data-mode={mode}
      data-hidden={isHiddenMenus}
      data-mobile-show={!mobileMenuCollapsed || undefined}
    >
      <div className="__dumi-default-menu-inner">
        <div className="__dumi-default-menu-header">
          <Link
            to={base}
            className="__dumi-default-menu-logo"
            style={{backgroundImage: logo ? `url('${logo}')` : ''}}
          />
          <h1>{title}</h1>
          <p>{description}</p>
        </div>
        {/* mobile nav list */}
        {navItems.length ? (
          <div className="__dumi-default-menu-mobile-area">
            <ul className="__dumi-default-menu-nav-list">
              {navItems.map(nav => {
                const child = Boolean(nav.children?.length) && (
                  <ul>
                    {nav.children.map(item => (
                      <li key={item.path || item.title}>
                        <span onClick={onClickMenu.bind(null, item.path)}>{item.title}</span>
                      </li>
                    ))}
                  </ul>
                );

                return (
                  <li key={nav.path || nav.title}>
                    {nav.path ? (
                      <span onClick={onClickMenu.bind(null, nav.path)}>{nav.title}</span>
                    ) : (
                      nav.title
                    )}
                    {child}
                  </li>
                );
              })}
            </ul>
            {/* site mode locale select */}
            <LocaleSelect location={location} />
            {darkPrefix}
          </div>
        ) : (
          <div className="__dumi-default-menu-doc-locale">
            {darkPrefix}
            {/* doc mode locale select */}
            <LocaleSelect location={location} />
          </div>
        )}

        {/* menu list */}
        <Menu
          mode="inline"
          selectedKeys={selectedKeys}
          openKeys={openKeys}
          onOpenChange={onOpenChange}
          className="__dumi-custom-menu-list"
        >
          {!isHiddenMenus &&
            singleLayerMenu.map(item => {
              // always use meta from routes to reduce menu data size
              const hasSlugs = Boolean(meta.slugs?.length);
              const hasChildren = item.children && Boolean(item.children.length);
              const show1LevelSlugs =
                meta.toc === 'menu' &&
                !hasChildren &&
                hasSlugs &&
                item.path === location.pathname.replace(/([^^])\/$/, '$1');
              const isLeaf = !Boolean(item.children && item.children.length);

              if (isLeaf) {
                return (
                  <Menu.Item key={item.path} onClick={onClickMenu.bind(null, item.path)}>
                    {item.title}
                  </Menu.Item>
                );
              }
              return (
                <SubMenu title={item.title} key={item.path || item.title}>
                  {item.children &&
                    item.children.map(child => (
                      <Menu.Item key={child.path} onClick={onClickMenu.bind(null, child.path)}>
                        <span>{child.title}</span>

                        {/* group children slugs */}
                        {Boolean(
                          meta.toc === 'menu' &&
                            typeof window !== 'undefined' &&
                            child.path === location.pathname &&
                            hasSlugs
                        ) && <SlugList slugs={meta.slugs} />}
                      </Menu.Item>
                    ))}

                  {/*group slugs*/}
                  {show1LevelSlugs && <SlugList slugs={meta.slugs} />}
                </SubMenu>
              );
            })}
        </Menu>
      </div>
    </div>
  );
};

export default SideMenu;
