import React from 'react';
import Box from '@mui/material/Box';
import InputAdornment from '@mui/material/InputAdornment';
import CircularProgress from '@mui/material/CircularProgress';
import SearchIcon from '@mui/icons-material/Search';
import ClearIcon from '@mui/icons-material/Clear';
import type { SxProps, Theme } from '@mui/material/styles';
import { Input } from '../../atoms/Input';
import { IconButton } from '../../atoms/IconButton';
import { Button } from '../../atoms/Button';

// ─── Types ───────────────────────────────────────────────────────────────────

/** Props for the FA SearchBar molecule */
export interface SearchBarProps {
  /** Current search value (controlled) */
  value: string;
  /** Called when the search value changes */
  onChange: (value: string) => void;
  /** Called when the user submits a search (Enter key or button click) */
  onSearch?: (value: string) => void;
  /** Placeholder text */
  placeholder?: string;
  /** Input size — `medium` (48px) or `small` (40px) */
  size?: 'medium' | 'small';
  /** Whether to show a submit button alongside the input */
  showButton?: boolean;
  /** Label for the submit button (default: "Search") */
  buttonLabel?: string;
  /** Whether the search bar is disabled */
  disabled?: boolean;
  /** Whether a search is in progress (shows loading on button) */
  loading?: boolean;
  /** Whether the input takes full width of its container */
  fullWidth?: boolean;
  /** Accessible label for the search input */
  'aria-label'?: string;
  /** MUI sx prop for the root container */
  sx?: SxProps<Theme>;
}

// ─── Component ───────────────────────────────────────────────────────────────

/**
 * Search bar for the FA design system.
 *
 * Composes Input (with search icon) + optional Button for provider and
 * venue search screens. Supports controlled input, Enter-to-submit,
 * clear button, and a loading state for async searches.
 *
 * Sizes align with Input + Button for visual harmony:
 * - `medium` — Input medium (48px) + Button large (48px)
 * - `small` — Input small (40px) + Button medium (40px)
 *
 * Usage:
 * ```tsx
 * <SearchBar
 *   value={query}
 *   onChange={setQuery}
 *   onSearch={handleSearch}
 *   placeholder="Search funeral directors..."
 * />
 * ```
 */
export const SearchBar = React.forwardRef<HTMLDivElement, SearchBarProps>(
  (
    {
      value,
      onChange,
      onSearch,
      placeholder = 'Search...',
      size = 'medium',
      showButton = false,
      buttonLabel = 'Search',
      disabled = false,
      loading = false,
      fullWidth = true,
      'aria-label': ariaLabel = 'Search',
      sx,
    },
    ref,
  ) => {
    const inputRef = React.useRef<HTMLInputElement>(null);

    const handleKeyDown = (e: React.KeyboardEvent) => {
      if (e.key === 'Enter' && onSearch && value.trim()) {
        onSearch(value.trim());
      }
    };

    const handleClear = () => {
      onChange('');
      // Refocus the input after clearing so the user can resume typing
      inputRef.current?.focus();
    };

    const handleSubmit = () => {
      if (onSearch && value.trim()) {
        onSearch(value.trim());
      }
    };

    // Button size aligns with input: medium input → large button (both 48px)
    const buttonSize = size === 'medium' ? 'large' : 'medium';

    return (
      <Box
        ref={ref}
        role="search"
        sx={[
          {
            display: 'flex',
            alignItems: 'flex-start',
            gap: 2.5,
            ...(fullWidth && { width: '100%' }),
          },
          ...(Array.isArray(sx) ? sx : [sx]),
        ]}
      >
        <Input
          value={value}
          onChange={(e) => onChange(e.target.value)}
          onKeyDown={handleKeyDown}
          placeholder={placeholder}
          size={size}
          disabled={disabled}
          fullWidth
          startIcon={<SearchIcon />}
          inputRef={inputRef}
          endAdornment={
            loading && !showButton ? (
              <InputAdornment position="end">
                <CircularProgress size={18} color="inherit" aria-label="Searching" />
              </InputAdornment>
            ) : value ? (
              <InputAdornment position="end">
                <IconButton
                  aria-label="Clear search"
                  onClick={handleClear}
                  size="small"
                  disabled={disabled}
                  edge="end"
                  sx={{ mr: -0.5 }}
                >
                  <ClearIcon />
                </IconButton>
              </InputAdornment>
            ) : undefined
          }
          inputProps={{
            'aria-label': ariaLabel,
          }}
          sx={{
            // Tighten the gap between search icon and text
            '& .MuiInputAdornment-positionStart': { mr: 0.5 },
          }}
        />

        {showButton && (
          <Button
            variant="contained"
            size={buttonSize}
            onClick={handleSubmit}
            disabled={disabled || !value.trim()}
            loading={loading}
            sx={{
              flexShrink: 0,
              // Explicit height to match input — FormControl wrapper can offset alignment
              height: size === 'medium' ? 'var(--fa-input-height-md)' : 'var(--fa-input-height-sm)',
            }}
          >
            {buttonLabel}
          </Button>
        )}
      </Box>
    );
  },
);

SearchBar.displayName = 'SearchBar';
export default SearchBar;
