/* eslint-disable jsdoc/require-jsdoc */

import type * as React from 'react';
import { classNames } from '@vkontakte/vkjs';
import type { Placement } from '../../lib/floating';
import type { HasDataAttribute, HTMLAttributesWithRootRef } from '../../types';
import { CustomScrollView, type CustomScrollViewProps } from '../CustomScrollView/CustomScrollView';
import { Popper } from '../Popper/Popper';
import { Spinner } from '../Spinner/Spinner';
import styles from './CustomSelectDropdown.module.css';

export interface CustomSelectDropdownProps
  extends HTMLAttributesWithRootRef<HTMLDivElement>,
    Pick<CustomScrollViewProps, 'overscrollBehavior'>,
    HasDataAttribute {
  targetRef: React.RefObject<HTMLElement | null>;
  placement?: Placement | undefined;
  scrollBoxRef?: React.Ref<HTMLDivElement> | undefined;
  fetching?: boolean | undefined;
  offsetDistance?: number | undefined;
  /**
   * Ширина раскрывающегося списка зависит от контента.
   */
  autoWidth?: boolean | undefined;
  forcePortal?: boolean | undefined;
  onPlacementChange?: ((placement: Placement) => void) | undefined;
  /**
   * Отключает максимальную высоту по умолчанию.
   */
  noMaxHeight?: boolean | undefined;
}

export const CustomSelectDropdown = ({
  children,
  targetRef,
  scrollBoxRef,
  placement = 'bottom',
  fetching,
  offsetDistance = 0,
  autoWidth = false,
  forcePortal = true,
  className,
  noMaxHeight = false,
  // CustomScrollView
  overscrollBehavior,
  ...restProps
}: CustomSelectDropdownProps): React.ReactNode => {
  return (
    <Popper
      targetRef={targetRef}
      offsetByMainAxis={offsetDistance}
      sameWidth={!autoWidth}
      placement={placement}
      className={classNames(
        styles.host,
        'vkuiInternalCustomSelectDropdown',
        offsetDistance === 0 && (placement.includes('top') ? styles.top : styles.bottom),
        autoWidth && classNames(styles.wide, 'vkuiInternalCustomSelectDropdown--wide'),
        className,
      )}
      usePortal={forcePortal}
      autoUpdateOnTargetResize
      flipMiddlewareFallbackAxisSideDirection="none"
      {...restProps}
    >
      <CustomScrollView
        getRootRef={scrollBoxRef}
        className={noMaxHeight ? undefined : styles.inWithMaxHeight}
        overscrollBehavior={overscrollBehavior}
        tabIndex={-1}
        aria-busy={fetching}
      >
        {fetching ? (
          <div className={styles.fetching}>
            <Spinner size="s" />
          </div>
        ) : (
          children
        )}
      </CustomScrollView>
    </Popper>
  );
};
