import { useState } from 'react';
import dynamic from 'next/dynamic';

import type { MenuDialogSection } from '~/src/components/MenuDialog/types';
import type { MappedUserPage } from '~/src/lib/songwhipApi/users/types';

import { ItemTypes } from '~/lib/types';
import Box from '~/src/components/Box';
import { Clickable } from '~/src/components/Clickable';
import ChartIcon from '~/src/components/Icon/ChartIcon';
import CopyIcon from '~/src/components/Icon/CopyIcon';
import EditIcon from '~/src/components/Icon/EditIcon';
import MoreIcon from '~/src/components/Icon/MoreIcon';
import Link from '~/src/components/Link2';
import useIsLargeScreen from '~/src/hooks/useIsLargeScreen';
import { useI18n } from '~/src/lib/i18n';
import { useAppRouter } from '~/src/lib/router2';
import { useCatalogFilters } from '../hooks';
import { ArchivedPageItem } from './ArchivedPageItem';
import { PageItem } from './PageItem';

const MenuDialogLazy = dynamic({
  ssr: false,
  loader: () => import('~/src/components/MenuDialog'),
});

export const PagesItems = ({
  itemsToRender,
  itemsCount,
}: {
  itemsToRender: MappedUserPage[];
  itemsCount: number;
}) => {
  const [menuActions, setMenuActions] = useState<MenuDialogSection[]>();
  const isLargeScreen = useIsLargeScreen();
  const [filters] = useCatalogFilters();
  const appRouter = useAppRouter();
  const { t } = useI18n('catalog');

  const renderPageItemActions = (
    item: MappedUserPage,
    { copy }: { copy(): Promise<void> }
  ) => {
    const ICON_COLOR = '#ccc';
    const ICON_SIZE = '2.3rem';
    const ICON_OPACITY = 0.65;

    return (
      <Box flexRow alignCenter gap="1.4rem" style={{ marginLeft: '1.5rem' }}>
        {isLargeScreen ? (
          <>
            <Clickable
              testId="catalogItemDashboard"
              isInline
              title={t('actions.viewInDashboard')}
              withHoverOpacityFrom={ICON_OPACITY}
              href={getDashboardPath(item)}
            >
              <ChartIcon color={ICON_COLOR} size={ICON_SIZE} />
            </Clickable>
            <Clickable
              testId="catalogItemEdit"
              isInline
              title={t('actions.editPage')}
              withHoverOpacityFrom={ICON_OPACITY}
              href={`/${item.path}/edit`}
            >
              <EditIcon color={ICON_COLOR} size={ICON_SIZE} />
            </Clickable>
            <Clickable
              testId="catalogItemCopy"
              isInline
              title={t('actions.copyLink')}
              withHoverOpacityFrom={ICON_OPACITY}
              onClick={copy}
            >
              <CopyIcon color={ICON_COLOR} size={ICON_SIZE} />
            </Clickable>
          </>
        ) : (
          <Clickable
            testId="catalogItemMenu"
            isInline
            title="menu"
            withHoverOpacityFrom={ICON_OPACITY}
            onClick={() => {
              setMenuActions([
                [
                  {
                    testId: 'catalogItemDashboard',
                    Icon: ChartIcon,
                    content: t('actions.viewInDashboard'),
                    onClick: () => {
                      appRouter.push(getDashboardPath(item));
                    },
                  },
                  {
                    testId: 'catalogItemEdit',
                    Icon: EditIcon,
                    content: t('actions.editPage'),
                    onClick: () => {
                      appRouter.push(`/${item.path}/edit`);
                    },
                  },
                  {
                    testId: 'catalogItemCopy',
                    Icon: CopyIcon,
                    content: t('actions.copyLink'),
                    onClick: copy,
                  },
                ],
              ]);
            }}
          >
            <MoreIcon color={ICON_COLOR} size="3rem" direction="right" />
          </Clickable>
        )}
      </Box>
    );
  };

  return itemsToRender.length ? (
    <>
      <Box flexColumn gap="2.4rem">
        {itemsToRender.map((item) =>
          item.archivedAtTimestamp ? (
            <ArchivedPageItem
              key={`${item.type}-${item.id}`}
              testId="catalogItem"
              item={item}
            />
          ) : (
            <PageItem
              key={`${item.type}-${item.id}`}
              testId="catalogItem"
              item={item}
              renderActions={renderPageItemActions}
            />
          )
        )}
      </Box>
      {menuActions && (
        <MenuDialogLazy
          onClose={() => setMenuActions(undefined)}
          sections={menuActions}
        />
      )}
    </>
  ) : (
    <Box
      testId="catalogEmpty"
      centerContent
      flexColumn
      style={{ textAlign: 'center' }}
    >
      {itemsCount ? (
        <div>
          {filters.search
            ? t('notFound', { searchValue: filters.search })
            : t('notFoundByFilter')}
        </div>
      ) : (
        <>
          <div style={{ marginBottom: '0.5rem' }}>{t('noItems')}</div>
          <Link href="/create" style={{ fontWeight: 'bold' }}>
            {t('createPage')}
          </Link>
        </>
      )}
    </Box>
  );
};

const getDashboardPath = (item: MappedUserPage): string => {
  switch (item.type) {
    case ItemTypes.ALBUM:
      return `/dashboard/album/${item.id}`;
    case ItemTypes.ARTIST:
      return `/dashboard/artist/${item.id}`;
    case ItemTypes.TRACK:
      return `/dashboard/song/${item.id}`;
    case ItemTypes.CUSTOM_PAGE:
      return `/dashboard/custom/${item.id}`;
    case ItemTypes.PRERELEASE:
      return `/dashboard/prerelease/${item.id}`;
    default:
      return '/dashboard';
  }
};
