import React, { ReactNode, ReactElement, forwardRef } from 'react';

import Button from '../Button';
import { Breakpoint } from '../../utils/responsiveBreakpoints';

import { StyledTH, StyledInnerTH, StyledSortingArrows } from './StyledTable';
import TableFilter from './TableFilter';

interface SortingProps {
  sortable?: boolean;
  sorted?: boolean;
  sortedDesc?: boolean;
  toggleSortBy?: (descending?: boolean, multi?: boolean) => void;
}

interface TableTHProps {
  align?: 'left' | 'right';
  children: ReactNode;
  'data-test-id'?: string;
  displayAtBreakpoint?: Breakpoint;
  filterable: boolean;
  hasFilterInput: boolean;
  renderFilter: (props: { onClose: () => void }) => ReactNode;
  sortingProps: SortingProps;
  sticky: boolean;
  themeHorizontallySticky: boolean;
  themeLeft?: number;
  themeShowDivider: boolean;
  themeWidth?: string;
}

const TableTH = forwardRef<HTMLTableHeaderCellElement, TableTHProps>(
  (
    {
      sortingProps,
      sticky,
      displayAtBreakpoint,
      filterable,
      renderFilter,
      hasFilterInput,
      align = 'left',
      children,
      'data-test-id': dataTestId,
      themeWidth,
      themeHorizontallySticky,
      themeLeft,
      themeShowDivider,
      ...otherTHProps
    }: TableTHProps,
    forwardedRef
  ): ReactElement => {
    return (
      <StyledTH
        {...otherTHProps}
        themeSticky={sticky}
        themeDisplayAtBreakpoint={displayAtBreakpoint}
        data-test-id={dataTestId}
        themeWidth={themeWidth}
        themeHorizontallySticky={themeHorizontallySticky}
        themeLeft={themeLeft}
        themeShowDivider={themeShowDivider}
        ref={forwardedRef}
      >
        <StyledInnerTH themeAlign={align}>
          {children}
          {sortingProps.sortable === true && (
            <StyledSortingArrows>
              <Button.Icon
                data-test-id={`${dataTestId}__up`}
                icon="carat-up"
                intent={
                  sortingProps.sortedDesc === false
                    ? 'primary'
                    : 'disabled-text'
                }
                size="small"
                onClick={(e: React.MouseEvent): void => {
                  e.stopPropagation();
                  sortingProps.toggleSortBy?.(false);
                }}
              />
              <Button.Icon
                data-test-id={`${dataTestId}__down`}
                icon="carat-down"
                intent={
                  sortingProps.sortedDesc === true ? 'primary' : 'disabled-text'
                }
                size="small"
                onClick={(e: React.MouseEvent): void => {
                  e.stopPropagation();
                  sortingProps.toggleSortBy?.(true);
                }}
              />
            </StyledSortingArrows>
          )}
          {filterable === true && (
            <TableFilter
              renderFilter={renderFilter}
              hasFilterInput={hasFilterInput}
              data-test-id={dataTestId}
            />
          )}
        </StyledInnerTH>
      </StyledTH>
    );
  }
);

TableTH.displayName = 'TableTH';

export default TableTH;
