import React, { MouseEventHandler, useState } from 'react';
import { Box, Button, config, Icon, Icons, Menu, MenuItem, PopOut, RectCords, Text } from 'folds';
import FocusTrap from 'focus-trap-react';
import { stopPropagation } from '../../utils/keyboard';

export type SettingsSelectOption<T extends string> = {
  value: T;
  label: string;
  disabled?: boolean;
};

/**
 * A folds-native dropdown (Button + PopOut + Menu) matching Cinny's select
 * pattern — used instead of a raw `<select>`, which renders OS-styled and
 * breaks under non-default themes.
 */
export function SettingsSelect<T extends string>({
  value,
  options,
  onChange,
  disabled,
  'aria-label': ariaLabel,
}: {
  value: T;
  options: SettingsSelectOption<T>[];
  onChange: (v: T) => void;
  disabled?: boolean;
  'aria-label'?: string;
}) {
  const [menuCords, setMenuCords] = useState<RectCords>();
  const selectedLabel = options.find((o) => o.value === value)?.label ?? value;

  const handleMenu: MouseEventHandler<HTMLButtonElement> = (evt) => {
    setMenuCords(evt.currentTarget.getBoundingClientRect());
  };

  const handleSelect = (v: T) => {
    onChange(v);
    setMenuCords(undefined);
  };

  return (
    <>
      <Button
        size="300"
        variant="Secondary"
        outlined
        fill="Soft"
        radii="300"
        after={<Icon size="300" src={Icons.ChevronBottom} />}
        onClick={handleMenu}
        disabled={disabled}
        aria-label={ariaLabel}
        aria-haspopup="menu"
        aria-expanded={!!menuCords}
      >
        <Text size="T300">{selectedLabel}</Text>
      </Button>
      <PopOut
        anchor={menuCords}
        offset={5}
        position="Bottom"
        align="End"
        content={
          <FocusTrap
            focusTrapOptions={{
              initialFocus: false,
              onDeactivate: () => setMenuCords(undefined),
              clickOutsideDeactivates: true,
              isKeyForward: (evt: KeyboardEvent) =>
                evt.key === 'ArrowDown' || evt.key === 'ArrowRight',
              isKeyBackward: (evt: KeyboardEvent) =>
                evt.key === 'ArrowUp' || evt.key === 'ArrowLeft',
              escapeDeactivates: stopPropagation,
            }}
          >
            <Menu>
              <Box direction="Column" gap="100" style={{ padding: config.space.S100 }}>
                {options.map((opt) => (
                  <MenuItem
                    key={opt.value}
                    size="300"
                    variant={opt.value === value ? 'Primary' : 'Surface'}
                    radii="300"
                    disabled={opt.disabled}
                    onClick={() => !opt.disabled && handleSelect(opt.value)}
                  >
                    <Text size="T300">{opt.label}</Text>
                  </MenuItem>
                ))}
              </Box>
            </Menu>
          </FocusTrap>
        }
      />
    </>
  );
}
