import { useEffect, useState } from 'react';
import {
  Button,
  Checkbox,
  Divider,
  Drawer,
  Group,
  NumberInput,
  Select,
  Stack,
  Text,
  TextInput,
} from '@mantine/core';
import { IconPlus, IconTrash } from '@tabler/icons-react';
import { useTranslation } from 'react-i18next';
import { BilingualInput, ModalFooter } from '@ema-platform/ui';
import type { FormFieldConfig, FormSchemaPalette } from '@ema-platform/api';
import { ConditionBuilder, type ConditionValue } from './ConditionBuilder';
import type { ConditionTarget } from '../config/schema-paths';

const KEY_PATTERN = /^[A-Za-z][A-Za-z0-9_]*$/;

function emptyField(): FormFieldConfig {
  return { key: '', label: { en: '', am: '' }, type: 'TEXT' };
}

/** Adds/edits one field within a section. Options only show for SELECT. */
export function FieldEditorDrawer({
  opened,
  onClose,
  field,
  onSave,
  palette,
  conditionTargets,
}: {
  opened: boolean;
  onClose: () => void;
  /** Null = adding a new field. */
  field: FormFieldConfig | null;
  onSave: (field: FormFieldConfig) => void;
  palette: FormSchemaPalette | undefined;
  conditionTargets: ConditionTarget[];
}) {
  const { t } = useTranslation();
  const [draft, setDraft] = useState<FormFieldConfig>(emptyField());
  const [keyError, setKeyError] = useState<string | null>(null);

  useEffect(() => {
    if (opened) {
      setDraft(field ? { ...field, label: { ...field.label } } : emptyField());
      setKeyError(null);
    }
  }, [opened, field]);

  const typeInfo = palette?.fieldTypes.find((f) => f.type === draft.type);
  const isNew = !field;

  function save() {
    if (!draft.key.trim() || !KEY_PATTERN.test(draft.key.trim())) {
      setKeyError(t('certReq.field.keyInvalid', 'Key must start with a letter and contain only letters, numbers, underscores'));
      return;
    }
    if (!draft.label.en?.trim()) {
      setKeyError(null);
      return;
    }
    onSave({
      ...draft,
      key: draft.key.trim(),
      options: typeInfo?.supportsOptions ? draft.options : undefined,
      min: typeInfo?.supportsRange ? draft.min : undefined,
      max: typeInfo?.supportsRange ? draft.max : undefined,
      maxLength: typeInfo?.supportsMaxLength ? draft.maxLength : undefined,
    });
  }

  function addOption() {
    setDraft((d) => ({
      ...d,
      options: [...(d.options ?? []), { value: '', label: { en: '', am: '' } }],
    }));
  }

  function updateOption(index: number, patch: Partial<{ value: string; label: { en: string; am: string } }>) {
    setDraft((d) => ({
      ...d,
      options: (d.options ?? []).map((o, i) => (i === index ? { ...o, ...patch } : o)),
    }));
  }

  function removeOption(index: number) {
    setDraft((d) => ({ ...d, options: (d.options ?? []).filter((_, i) => i !== index) }));
  }

  return (
    <Drawer
      opened={opened}
      onClose={onClose}
      position="right"
      size="md"
      title={<Text fw={700}>{isNew ? t('certReq.field.add', 'Add field') : t('certReq.field.edit', 'Edit field')}</Text>}
    >
      <Stack gap="md">
        <TextInput
          label={t('certReq.field.key', 'Field key')}
          placeholder="rank"
          required
          value={draft.key}
          error={keyError}
          disabled={!isNew}
          description={
            isNew
              ? t('certReq.field.keyHelp', 'Letters, numbers and underscores only — becomes the form data key')
              : t('certReq.field.keyLocked', 'Key cannot change once created')
          }
          onChange={(e) => {
            const { value } = e.currentTarget;
            setDraft((d) => ({ ...d, key: value }));
          }}
        />

        <BilingualInput
          label={t('certReq.field.label', 'Label')}
          required
          value={{ en: draft.label.en ?? '', am: draft.label.am ?? '' }}
          onChange={(v) => setDraft((d) => ({ ...d, label: v }))}
        />

        <Select
          label={t('certReq.field.type', 'Field type')}
          data={(palette?.fieldTypes ?? []).map((f) => ({ value: f.type, label: f.type }))}
          value={draft.type}
          onChange={(v) => v && setDraft((d) => ({ ...d, type: v as FormFieldConfig['type'] }))}
          allowDeselect={false}
        />

        <Checkbox
          label={t('certReq.field.required', 'Required')}
          checked={Boolean(draft.required)}
          onChange={(e) => {
            const { checked } = e.currentTarget;
            setDraft((d) => ({ ...d, required: checked }));
          }}
        />

        <BilingualInput
          label={t('certReq.field.placeholder', 'Placeholder')}
          value={{ en: draft.placeholder?.en ?? '', am: draft.placeholder?.am ?? '' }}
          onChange={(v) => setDraft((d) => ({ ...d, placeholder: v }))}
        />

        <BilingualInput
          label={t('certReq.field.helpText', 'Help text')}
          value={{ en: draft.helpText?.en ?? '', am: draft.helpText?.am ?? '' }}
          onChange={(v) => setDraft((d) => ({ ...d, helpText: v }))}
        />

        {typeInfo?.supportsRange && (
          <Group grow>
            <NumberInput
              label={t('certReq.field.min', 'Minimum')}
              value={draft.min ?? ''}
              onChange={(v) => setDraft((d) => ({ ...d, min: typeof v === 'number' ? v : undefined }))}
            />
            <NumberInput
              label={t('certReq.field.max', 'Maximum')}
              value={draft.max ?? ''}
              onChange={(v) => setDraft((d) => ({ ...d, max: typeof v === 'number' ? v : undefined }))}
            />
          </Group>
        )}

        {typeInfo?.supportsMaxLength && (
          <NumberInput
            label={t('certReq.field.maxLength', 'Max length')}
            value={draft.maxLength ?? ''}
            onChange={(v) => setDraft((d) => ({ ...d, maxLength: typeof v === 'number' ? v : undefined }))}
          />
        )}

        {typeInfo?.supportsOptions && (
          <Stack gap="xs">
            <Group justify="space-between">
              <Text fz="sm" fw={600}>{t('certReq.field.options', 'Options')}</Text>
              <Button size="xs" variant="light" leftSection={<IconPlus size={13} />} onClick={addOption}>
                {t('certReq.field.addOption', 'Add option')}
              </Button>
            </Group>
            {(draft.options ?? []).map((o, i) => (
              <Group key={i} gap="xs" wrap="nowrap" align="flex-end">
                <TextInput
                  size="xs"
                  label={i === 0 ? t('certReq.field.optionValue', 'Value') : undefined}
                  value={o.value}
                  onChange={(e) => updateOption(i, { value: e.currentTarget.value })}
                  style={{ flex: 1 }}
                />
                <BilingualInput
                  size="xs"
                  label={i === 0 ? t('certReq.field.optionLabel', 'Label') : undefined}
                  value={{ en: o.label.en ?? '', am: o.label.am ?? '' }}
                  onChange={(v) => updateOption(i, { label: v })}
                  style={{ flex: 2 }}
                />
                <Button size="xs" color="red" variant="subtle" px={6} onClick={() => removeOption(i)}>
                  <IconTrash size={14} />
                </Button>
              </Group>
            ))}
          </Stack>
        )}

        <Divider label={t('certReq.condition.title', 'Visibility condition')} labelPosition="left" />
        <ConditionBuilder
          value={(draft.showWhen ?? null) as ConditionValue | null}
          onChange={(v) => setDraft((d) => ({ ...d, showWhen: v ?? undefined }))}
          targets={conditionTargets}
          palette={palette}
        />

        <ModalFooter>
          <Button variant="default" onClick={onClose}>{t('certReq.cancel', 'Cancel')}</Button>
          <Button color="teal" onClick={save}>
            {isNew ? t('certReq.field.add', 'Add field') : t('certReq.saveChanges', 'Save changes')}
          </Button>
        </ModalFooter>
      </Stack>
    </Drawer>
  );
}
