import { createPortal } from 'react-dom';
import { useEffect, useMemo, useRef, useState } from 'react';
import { codeToText } from 'element-china-area-data';
import {
  CHINA_REGION_OPTIONS,
  DEFAULT_REGION_CODES,
  formatRegionLabel,
  parseRegionCodes,
} from '../lib/china-region';

type RegionNode = {
  value: string;
  label: string;
  children?: RegionNode[];
};

type ChinaRegionPickerProps = {
  value?: string[];
  onChange?: (codes: string[]) => void;
  disabled?: boolean;
};

const STEP_LABELS = ['选择省份', '选择城市', '选择区县'] as const;

function lockBodyScroll(lock: boolean) {
  if (typeof document === 'undefined') return;
  const body = document.body;
  if (lock) {
    const scrollY = window.scrollY;
    body.dataset.dukangScrollY = String(scrollY);
    body.style.position = 'fixed';
    body.style.top = `-${scrollY}px`;
    body.style.left = '0';
    body.style.right = '0';
    body.style.overflow = 'hidden';
  } else {
    const scrollY = Number(body.dataset.dukangScrollY ?? '0');
    body.style.position = '';
    body.style.top = '';
    body.style.left = '';
    body.style.right = '';
    body.style.overflow = '';
    delete body.dataset.dukangScrollY;
    window.scrollTo(0, scrollY);
  }
}

function buildInitialDraft(value: string[]): { draft: string[]; step: number } {
  if (value.length === 3) {
    return { draft: [...value], step: 2 };
  }
  if (value.length > 0) {
    const draft = [...value];
    for (let i = value.length; i < DEFAULT_REGION_CODES.length; i += 1) {
      draft.push(DEFAULT_REGION_CODES[i]);
    }
    return { draft, step: Math.min(value.length, 2) };
  }
  return { draft: [...DEFAULT_REGION_CODES], step: 1 };
}

export default function ChinaRegionPicker({ value = [], onChange, disabled }: ChinaRegionPickerProps) {
  const [open, setOpen] = useState(false);
  const [draft, setDraft] = useState<string[]>(value);
  const [step, setStep] = useState(0);
  const listRef = useRef<HTMLDivElement>(null);
  const activeItemRef = useRef<HTMLButtonElement | null>(null);

  const options = CHINA_REGION_OPTIONS as RegionNode[];
  const parsed = parseRegionCodes(value);
  const display = parsed ? formatRegionLabel(parsed) : '请选择省 / 市 / 区县';

  const provinces = options;
  const cities = useMemo(() => {
    const p = provinces.find((item) => item.value === draft[0]);
    return p?.children ?? [];
  }, [draft, provinces]);

  const districts = useMemo(() => {
    const c = cities.find((item) => item.value === draft[1]);
    return c?.children ?? [];
  }, [draft, cities]);

  const listItems = step === 0 ? provinces : step === 1 ? cities : districts;
  const activeCode = draft[step];

  useEffect(() => {
    if (!open) return;
    lockBodyScroll(true);
    return () => lockBodyScroll(false);
  }, [open]);

  useEffect(() => {
    if (!open) return;
    const timer = window.setTimeout(() => {
      const container = listRef.current;
      const activeEl = activeItemRef.current;
      if (!container || !activeEl) return;
      const offset = activeEl.offsetTop - container.clientHeight / 2 + activeEl.clientHeight / 2;
      container.scrollTo({ top: Math.max(0, offset), behavior: 'smooth' });
    }, 0);
    return () => window.clearTimeout(timer);
  }, [open, step, activeCode, listItems]);

  function openPicker() {
    if (disabled) return;
    const { draft: next, step: initialStep } = buildInitialDraft(value);
    setDraft(next);
    setStep(initialStep);
    setOpen(true);
  }

  function closePicker() {
    setOpen(false);
  }

  function selectItem(code: string) {
    const next = [...draft.slice(0, step), code];
    setDraft(next);
    if (step < 2) {
      setStep(step + 1);
      return;
    }
    onChange?.(next);
    closePicker();
  }

  function confirm() {
    if (draft.length < 3) return;
    onChange?.(draft);
    closePicker();
  }

  const modal = open ? (
    <div className="partner-region-overlay" role="presentation" onClick={closePicker}>
      <div
        className="partner-region-sheet"
        role="dialog"
        aria-modal
        onClick={(e) => e.stopPropagation()}
        onTouchMove={(e) => e.stopPropagation()}
      >
        <div className="partner-region-sheet-header">
          <button type="button" className="partner-region-sheet-btn" onClick={closePicker}>取消</button>
          <span className="headline-md">选择地区</span>
          <button
            type="button"
            className="partner-region-sheet-btn partner-region-sheet-btn--primary"
            disabled={draft.length < 3}
            onClick={confirm}
          >
            确定
          </button>
        </div>

        <div className="partner-region-steps">
          {STEP_LABELS.map((label, index) => (
            <button
              key={label}
              type="button"
              className={`partner-region-step${step === index ? ' partner-region-step--active' : ''}${draft[index] ? ' partner-region-step--done' : ''}`}
              disabled={index === 1 && !draft[0] || index === 2 && !draft[1]}
              onClick={() => {
                if (index === 1 && !draft[0]) return;
                if (index === 2 && !draft[1]) return;
                setStep(index);
              }}
            >
              <span className="partner-region-step-index">{index + 1}</span>
              <span>{label}</span>
            </button>
          ))}
        </div>

        {draft[0] && (
          <p className="partner-region-breadcrumb label-md text-muted">
            {codeToText[draft[0]]}
            {draft[1] ? ` / ${codeToText[draft[1]]}` : ''}
            {draft[2] ? ` / ${codeToText[draft[2]]}` : ''}
          </p>
        )}

        <div className="partner-region-list" role="listbox" ref={listRef}>
          {listItems.map((item) => (
            <button
              key={item.value}
              type="button"
              role="option"
              aria-selected={activeCode === item.value}
              ref={activeCode === item.value ? (el) => { activeItemRef.current = el; } : undefined}
              className={`partner-region-item${activeCode === item.value ? ' partner-region-item--active' : ''}`}
              onClick={() => selectItem(item.value)}
            >
              {item.label}
            </button>
          ))}
        </div>
      </div>
    </div>
  ) : null;

  return (
    <>
      <button type="button" className="partner-field-input partner-region-trigger" onClick={openPicker} disabled={disabled}>
        <span className="material-symbols-outlined">location_on</span>
        <span className={parsed ? '' : 'text-muted'}>{display}</span>
        <span className="material-symbols-outlined partner-region-chevron">expand_more</span>
      </button>
      {typeof document !== 'undefined' ? createPortal(modal, document.body) : null}
    </>
  );
}
