import type { FormEvent, ReactNode, Ref } from "react";
import Button from "./Button";
import InsetPanel from "./InsetPanel";
import TextInput from "./TextInput";
import { cx } from "./cx";

interface InlineComposerProps {
  label: ReactNode;
  value: string;
  onChange: (value: string) => void;
  onSubmit: () => void;
  placeholder?: string;
  hint?: ReactNode;
  error?: ReactNode;
  submitLabel: ReactNode;
  disabled?: boolean;
  inputId: string;
  inputRef?: Ref<HTMLInputElement>;
  className?: string;
  action?: ReactNode;
}

export default function InlineComposer({
  label,
  value,
  onChange,
  onSubmit,
  placeholder,
  hint,
  error,
  submitLabel,
  disabled = false,
  inputId,
  inputRef,
  className,
  action,
}: InlineComposerProps) {
  return (
    <InsetPanel className={cx("space-y-2.5", className)} padding="sm" as="form" onSubmit={(event: FormEvent) => {
      event.preventDefault();
      onSubmit();
    }}
    >
      <label htmlFor={inputId} className="app-text-soft app-overline mb-1 block">
        {label}
      </label>
      <div className="flex flex-col gap-2 sm:flex-row">
        <TextInput
          ref={inputRef}
          id={inputId}
          value={value}
          onChange={(event) => onChange(event.target.value)}
          placeholder={placeholder}
          disabled={disabled}
          className="flex-1"
        />
        {action ?? (
          <Button type="submit" disabled={disabled || !value.trim()} size="xs" variant="solid" tone="brand">
            {submitLabel}
          </Button>
        )}
      </div>
      {hint ? <div className="app-text-faint app-caption mt-1">{hint}</div> : null}
      {error ? (
        <div role="alert" className="app-text-danger app-caption mt-2">
          {error}
        </div>
      ) : null}
    </InsetPanel>
  );
}
