/* eslint-disable */
/**
 * Shared door-pickup UI for the landing-page calculators.
 *
 * Mirrors the homepage Vehicle FCL door-picker (components/HeroAnimated.jsx:
 * `ECU_DOOR_COUNTRIES`, `walioSearchDoors`, `countryFlag`, `formatDoorSummary`,
 * `CountryPicker`, plus the door input UI lifted out of `FCLLocationSelector`).
 *
 * Exposes everything via `window.__abgsSharedDoorUi` so both
 * `landing/calculator.jsx` (international moving) and
 * `landing/vehicle-shipping-sections.jsx` (vehicle shipping) can render the
 * same components without duplicating logic.
 *
 * Babel-standalone'd in the browser — no build step. Loaded by both landing
 * HTMLs BEFORE the per-landing calculator JSX.
 */
(function () {
  const React = window.React;
  const ReactDOM = window.ReactDOM;
  if (!React || !ReactDOM) return;

  // Walio public API. `wl_pk_…` is a public key (Stripe-style) — safe to ship
  // in the browser.
  const WALIO_API_KEY = 'wl_pk_VzywFPpAB0xA2TVqtJSOEEmC6WHONtmP';
  const WALIO_AUTH_HEADERS = { Authorization: `Bearer ${WALIO_API_KEY}` };
  const WALIO_LOCATIONS_BASE = 'https://walio.ai/api/v1/locations';

  // Language detection. The international-moving landings set `window.LANG`
  // explicitly; the vehicle landings rely on `<html lang>`. Check both so
  // labels translate correctly on every landing variant.
  function isEs() {
    if (window.LANG === 'es') return true;
    try {
      const docLang = (document.documentElement.lang || '').toLowerCase();
      if (docLang.startsWith('es')) return true;
    } catch (_) {}
    return false;
  }

  // ─── Full ISO 3166-1 alpha-2 list (alphabetical by name) ─────────────────
  // Walio's /doors endpoint accepts any ISO-2; countries with no ECU
  // coverage just return 0 doors and the Google Places fallback kicks in.
  const ECU_DOOR_COUNTRIES = [
    { code: 'AF', name: 'Afghanistan' }, { code: 'AX', name: 'Åland Islands' },
    { code: 'AL', name: 'Albania' }, { code: 'DZ', name: 'Algeria' },
    { code: 'AS', name: 'American Samoa' }, { code: 'AD', name: 'Andorra' },
    { code: 'AO', name: 'Angola' }, { code: 'AI', name: 'Anguilla' },
    { code: 'AQ', name: 'Antarctica' }, { code: 'AG', name: 'Antigua and Barbuda' },
    { code: 'AR', name: 'Argentina' }, { code: 'AM', name: 'Armenia' },
    { code: 'AW', name: 'Aruba' }, { code: 'AU', name: 'Australia' },
    { code: 'AT', name: 'Austria' }, { code: 'AZ', name: 'Azerbaijan' },
    { code: 'BS', name: 'Bahamas' }, { code: 'BH', name: 'Bahrain' },
    { code: 'BD', name: 'Bangladesh' }, { code: 'BB', name: 'Barbados' },
    { code: 'BY', name: 'Belarus' }, { code: 'BE', name: 'Belgium' },
    { code: 'BZ', name: 'Belize' }, { code: 'BJ', name: 'Benin' },
    { code: 'BM', name: 'Bermuda' }, { code: 'BT', name: 'Bhutan' },
    { code: 'BO', name: 'Bolivia' }, { code: 'BQ', name: 'Bonaire, Sint Eustatius and Saba' },
    { code: 'BA', name: 'Bosnia and Herzegovina' }, { code: 'BW', name: 'Botswana' },
    { code: 'BV', name: 'Bouvet Island' }, { code: 'BR', name: 'Brazil' },
    { code: 'IO', name: 'British Indian Ocean Territory' }, { code: 'BN', name: 'Brunei Darussalam' },
    { code: 'BG', name: 'Bulgaria' }, { code: 'BF', name: 'Burkina Faso' },
    { code: 'BI', name: 'Burundi' }, { code: 'CV', name: 'Cabo Verde' },
    { code: 'KH', name: 'Cambodia' }, { code: 'CM', name: 'Cameroon' },
    { code: 'CA', name: 'Canada' }, { code: 'KY', name: 'Cayman Islands' },
    { code: 'CF', name: 'Central African Republic' }, { code: 'TD', name: 'Chad' },
    { code: 'CL', name: 'Chile' }, { code: 'CN', name: 'China' },
    { code: 'CX', name: 'Christmas Island' }, { code: 'CC', name: 'Cocos (Keeling) Islands' },
    { code: 'CO', name: 'Colombia' }, { code: 'KM', name: 'Comoros' },
    { code: 'CG', name: 'Congo' }, { code: 'CD', name: 'Congo, Democratic Republic of the' },
    { code: 'CK', name: 'Cook Islands' }, { code: 'CR', name: 'Costa Rica' },
    { code: 'CI', name: "Côte d'Ivoire" }, { code: 'HR', name: 'Croatia' },
    { code: 'CU', name: 'Cuba' }, { code: 'CW', name: 'Curaçao' },
    { code: 'CY', name: 'Cyprus' }, { code: 'CZ', name: 'Czechia' },
    { code: 'DK', name: 'Denmark' }, { code: 'DJ', name: 'Djibouti' },
    { code: 'DM', name: 'Dominica' }, { code: 'DO', name: 'Dominican Republic' },
    { code: 'EC', name: 'Ecuador' }, { code: 'EG', name: 'Egypt' },
    { code: 'SV', name: 'El Salvador' }, { code: 'GQ', name: 'Equatorial Guinea' },
    { code: 'ER', name: 'Eritrea' }, { code: 'EE', name: 'Estonia' },
    { code: 'SZ', name: 'Eswatini' }, { code: 'ET', name: 'Ethiopia' },
    { code: 'FK', name: 'Falkland Islands' }, { code: 'FO', name: 'Faroe Islands' },
    { code: 'FJ', name: 'Fiji' }, { code: 'FI', name: 'Finland' },
    { code: 'FR', name: 'France' }, { code: 'GF', name: 'French Guiana' },
    { code: 'PF', name: 'French Polynesia' }, { code: 'TF', name: 'French Southern Territories' },
    { code: 'GA', name: 'Gabon' }, { code: 'GM', name: 'Gambia' },
    { code: 'GE', name: 'Georgia' }, { code: 'DE', name: 'Germany' },
    { code: 'GH', name: 'Ghana' }, { code: 'GI', name: 'Gibraltar' },
    { code: 'GR', name: 'Greece' }, { code: 'GL', name: 'Greenland' },
    { code: 'GD', name: 'Grenada' }, { code: 'GP', name: 'Guadeloupe' },
    { code: 'GU', name: 'Guam' }, { code: 'GT', name: 'Guatemala' },
    { code: 'GG', name: 'Guernsey' }, { code: 'GN', name: 'Guinea' },
    { code: 'GW', name: 'Guinea-Bissau' }, { code: 'GY', name: 'Guyana' },
    { code: 'HT', name: 'Haiti' }, { code: 'HM', name: 'Heard Island and McDonald Islands' },
    { code: 'VA', name: 'Holy See' }, { code: 'HN', name: 'Honduras' },
    { code: 'HK', name: 'Hong Kong' }, { code: 'HU', name: 'Hungary' },
    { code: 'IS', name: 'Iceland' }, { code: 'IN', name: 'India' },
    { code: 'ID', name: 'Indonesia' }, { code: 'IR', name: 'Iran' },
    { code: 'IQ', name: 'Iraq' }, { code: 'IE', name: 'Ireland' },
    { code: 'IM', name: 'Isle of Man' }, { code: 'IL', name: 'Israel' },
    { code: 'IT', name: 'Italy' }, { code: 'JM', name: 'Jamaica' },
    { code: 'JP', name: 'Japan' }, { code: 'JE', name: 'Jersey' },
    { code: 'JO', name: 'Jordan' }, { code: 'KZ', name: 'Kazakhstan' },
    { code: 'KE', name: 'Kenya' }, { code: 'KI', name: 'Kiribati' },
    { code: 'KP', name: 'Korea (North)' }, { code: 'KR', name: 'Korea (South)' },
    { code: 'KW', name: 'Kuwait' }, { code: 'KG', name: 'Kyrgyzstan' },
    { code: 'LA', name: "Lao People's Democratic Republic" }, { code: 'LV', name: 'Latvia' },
    { code: 'LB', name: 'Lebanon' }, { code: 'LS', name: 'Lesotho' },
    { code: 'LR', name: 'Liberia' }, { code: 'LY', name: 'Libya' },
    { code: 'LI', name: 'Liechtenstein' }, { code: 'LT', name: 'Lithuania' },
    { code: 'LU', name: 'Luxembourg' }, { code: 'MO', name: 'Macao' },
    { code: 'MG', name: 'Madagascar' }, { code: 'MW', name: 'Malawi' },
    { code: 'MY', name: 'Malaysia' }, { code: 'MV', name: 'Maldives' },
    { code: 'ML', name: 'Mali' }, { code: 'MT', name: 'Malta' },
    { code: 'MH', name: 'Marshall Islands' }, { code: 'MQ', name: 'Martinique' },
    { code: 'MR', name: 'Mauritania' }, { code: 'MU', name: 'Mauritius' },
    { code: 'YT', name: 'Mayotte' }, { code: 'MX', name: 'Mexico' },
    { code: 'FM', name: 'Micronesia' }, { code: 'MD', name: 'Moldova' },
    { code: 'MC', name: 'Monaco' }, { code: 'MN', name: 'Mongolia' },
    { code: 'ME', name: 'Montenegro' }, { code: 'MS', name: 'Montserrat' },
    { code: 'MA', name: 'Morocco' }, { code: 'MZ', name: 'Mozambique' },
    { code: 'MM', name: 'Myanmar' }, { code: 'NA', name: 'Namibia' },
    { code: 'NR', name: 'Nauru' }, { code: 'NP', name: 'Nepal' },
    { code: 'NL', name: 'Netherlands' }, { code: 'NC', name: 'New Caledonia' },
    { code: 'NZ', name: 'New Zealand' }, { code: 'NI', name: 'Nicaragua' },
    { code: 'NE', name: 'Niger' }, { code: 'NG', name: 'Nigeria' },
    { code: 'NU', name: 'Niue' }, { code: 'NF', name: 'Norfolk Island' },
    { code: 'MK', name: 'North Macedonia' }, { code: 'MP', name: 'Northern Mariana Islands' },
    { code: 'NO', name: 'Norway' }, { code: 'OM', name: 'Oman' },
    { code: 'PK', name: 'Pakistan' }, { code: 'PW', name: 'Palau' },
    { code: 'PS', name: 'Palestine' }, { code: 'PA', name: 'Panama' },
    { code: 'PG', name: 'Papua New Guinea' }, { code: 'PY', name: 'Paraguay' },
    { code: 'PE', name: 'Peru' }, { code: 'PH', name: 'Philippines' },
    { code: 'PN', name: 'Pitcairn' }, { code: 'PL', name: 'Poland' },
    { code: 'PT', name: 'Portugal' }, { code: 'PR', name: 'Puerto Rico' },
    { code: 'QA', name: 'Qatar' }, { code: 'RE', name: 'Réunion' },
    { code: 'RO', name: 'Romania' }, { code: 'RU', name: 'Russian Federation' },
    { code: 'RW', name: 'Rwanda' }, { code: 'BL', name: 'Saint Barthélemy' },
    { code: 'SH', name: 'Saint Helena' }, { code: 'KN', name: 'Saint Kitts and Nevis' },
    { code: 'LC', name: 'Saint Lucia' }, { code: 'MF', name: 'Saint Martin (French part)' },
    { code: 'PM', name: 'Saint Pierre and Miquelon' }, { code: 'VC', name: 'Saint Vincent and the Grenadines' },
    { code: 'WS', name: 'Samoa' }, { code: 'SM', name: 'San Marino' },
    { code: 'ST', name: 'Sao Tome and Principe' }, { code: 'SA', name: 'Saudi Arabia' },
    { code: 'SN', name: 'Senegal' }, { code: 'RS', name: 'Serbia' },
    { code: 'SC', name: 'Seychelles' }, { code: 'SL', name: 'Sierra Leone' },
    { code: 'SG', name: 'Singapore' }, { code: 'SX', name: 'Sint Maarten (Dutch part)' },
    { code: 'SK', name: 'Slovakia' }, { code: 'SI', name: 'Slovenia' },
    { code: 'SB', name: 'Solomon Islands' }, { code: 'SO', name: 'Somalia' },
    { code: 'ZA', name: 'South Africa' }, { code: 'GS', name: 'South Georgia and the South Sandwich Islands' },
    { code: 'SS', name: 'South Sudan' }, { code: 'ES', name: 'Spain' },
    { code: 'LK', name: 'Sri Lanka' }, { code: 'SD', name: 'Sudan' },
    { code: 'SR', name: 'Suriname' }, { code: 'SJ', name: 'Svalbard and Jan Mayen' },
    { code: 'SE', name: 'Sweden' }, { code: 'CH', name: 'Switzerland' },
    { code: 'SY', name: 'Syrian Arab Republic' }, { code: 'TW', name: 'Taiwan' },
    { code: 'TJ', name: 'Tajikistan' }, { code: 'TZ', name: 'Tanzania' },
    { code: 'TH', name: 'Thailand' }, { code: 'TL', name: 'Timor-Leste' },
    { code: 'TG', name: 'Togo' }, { code: 'TK', name: 'Tokelau' },
    { code: 'TO', name: 'Tonga' }, { code: 'TT', name: 'Trinidad and Tobago' },
    { code: 'TN', name: 'Tunisia' }, { code: 'TR', name: 'Türkiye' },
    { code: 'TM', name: 'Turkmenistan' }, { code: 'TC', name: 'Turks and Caicos Islands' },
    { code: 'TV', name: 'Tuvalu' }, { code: 'UG', name: 'Uganda' },
    { code: 'UA', name: 'Ukraine' }, { code: 'AE', name: 'United Arab Emirates' },
    { code: 'GB', name: 'United Kingdom' }, { code: 'US', name: 'United States' },
    { code: 'UM', name: 'United States Minor Outlying Islands' }, { code: 'UY', name: 'Uruguay' },
    { code: 'UZ', name: 'Uzbekistan' }, { code: 'VU', name: 'Vanuatu' },
    { code: 'VE', name: 'Venezuela' }, { code: 'VN', name: 'Vietnam' },
    { code: 'VG', name: 'Virgin Islands (British)' }, { code: 'VI', name: 'Virgin Islands (U.S.)' },
    { code: 'WF', name: 'Wallis and Futuna' }, { code: 'EH', name: 'Western Sahara' },
    { code: 'YE', name: 'Yemen' }, { code: 'ZM', name: 'Zambia' },
    { code: 'ZW', name: 'Zimbabwe' },
  ];

  // 'US' → '🇺🇸' via Unicode regional-indicator codepoints.
  function countryFlag(code) {
    if (!code || code.length !== 2) return '';
    try {
      return code.toUpperCase().split('').map(c =>
        String.fromCodePoint(127397 + c.charCodeAt(0))).join('');
    } catch { return ''; }
  }

  // Door → 'Del Valle Finance · 33012 · Miami, FL · US'. Google fallback
  // rows show just displayName because Maps doesn't reliably resolve
  // zip/state at click time.
  function formatDoorSummary(d) {
    if (!d) return '';
    if (d.isGoogleFallback) return d.displayName;
    const parts = [
      d.displayName,
      d.zipCode || null,
      [d.city, d.state].filter(Boolean).join(', ') || null,
      d.countryCode || null,
    ].filter(Boolean);
    return parts.join(' · ');
  }

  // GET /v1/locations/doors — same wrapper the homepage uses.
  async function walioSearchDoors({ country, zipCode, search, direction = 'export' }) {
    if (!country) return [];
    const z = (zipCode || '').trim();
    const s = (search || '').trim();
    if (!z && s.length < 2) return [];
    const params = new URLSearchParams({ country: String(country).toUpperCase(), direction });
    if (z) params.set('zipCode', z);
    else   params.set('search', s);
    try {
      const res = await fetch(`${WALIO_LOCATIONS_BASE}/doors?${params.toString()}`, { headers: WALIO_AUTH_HEADERS });
      if (!res.ok) return [];
      const json = await res.json();
      const arr = (json && json.success && Array.isArray(json.locations)) ? json.locations : [];
      return arr.map(d => ({
        code: d.code,
        displayName: d.displayName || d.code,
        countryCode: d.country || '',
        countryName: d.countryName || '',
        city: d.city || '',
        state: d.state || '',
        zipCode: d.zipCode || '',
      }));
    } catch {
      return [];
    }
  }

  // Google Places fallback for countries with no ECU coverage. Returns
  // synthetic door objects flagged isGoogleFallback so callers know to
  // skip the ECU doorCode in the request body.
  function searchGooglePlacesFallback(term, country) {
    return new Promise((resolve) => {
      if (!term || !country) { resolve([]); return; }
      if (!(window.google && window.google.maps && window.google.maps.places)) {
        resolve([]); return;
      }
      try {
        const svc = new window.google.maps.places.AutocompleteService();
        const isZipLike = /^\d{4,6}$/.test(term);
        svc.getPlacePredictions({
          input: term,
          types: isZipLike ? ['postal_code'] : ['(regions)'],
          componentRestrictions: { country: country.toLowerCase() },
        }, (preds, status) => {
          const ok = status === window.google.maps.places.PlacesServiceStatus.OK;
          if (!ok || !preds) { resolve([]); return; }
          resolve(preds.slice(0, 8).map(p => ({
            code: '__google__:' + p.place_id,
            placeId: p.place_id,
            displayName: p.description,
            countryCode: country,
            countryName: '',
            city: (p.structured_formatting && p.structured_formatting.main_text) || p.description,
            state: '',
            zipCode: isZipLike ? term : '',
            isGoogleFallback: true,
          })));
        });
      } catch { resolve([]); }
    });
  }

  // Resolve a Google place_id → real lat/lng + address components.
  function resolveGooglePlaceId(placeId) {
    return new Promise((resolve) => {
      if (!(window.google && window.google.maps && window.google.maps.places && placeId)) {
        resolve(null); return;
      }
      try {
        const svc = new window.google.maps.places.PlacesService(document.createElement('div'));
        svc.getDetails(
          { placeId, fields: ['geometry', 'address_components', 'name', 'formatted_address'] },
          (place, status) => {
            if (status !== 'OK' || !place) { resolve(null); return; }
            const ac = place.address_components || [];
            const find = (type) => ac.find(c => c.types.includes(type));
            const country = (find('country') || {}).short_name || '';
            const state   = (find('administrative_area_level_1') || {}).short_name || '';
            const city    = (find('locality') || find('postal_town')
                           || find('administrative_area_level_2') || {}).long_name || '';
            const zip     = (find('postal_code') || {}).short_name || '';
            const loc = place.geometry && place.geometry.location;
            resolve({
              country, state, city, zip,
              lat: loc ? loc.lat() : null,
              lng: loc ? loc.lng() : null,
            });
          }
        );
      } catch { resolve(null); }
    });
  }

  // Geocode "60007, US" → { lat, lng, state, city, zip, country }.
  function geocodeZipViaSDK(zip, country) {
    return new Promise((resolve) => {
      if (!zip) { resolve(null); return; }
      const c = country || 'US';
      if (!(window.google && window.google.maps && window.google.maps.Geocoder)) {
        resolve(null); return;
      }
      try {
        const geocoder = new window.google.maps.Geocoder();
        geocoder.geocode({ address: `${zip}, ${c}` }, (results, status) => {
          if (status === 'OK' && results && results[0]) {
            const loc = results[0].geometry && results[0].geometry.location;
            const ac = results[0].address_components || [];
            const find = (type) => ac.find(x => x.types.includes(type));
            const state = (find('administrative_area_level_1') || {}).short_name || '';
            const city  = (find('locality') || find('postal_town')
                         || find('administrative_area_level_2') || {}).long_name || '';
            resolve({
              lat: loc ? loc.lat() : null,
              lng: loc ? loc.lng() : null,
              state, city, zip, country: c,
            });
          } else {
            resolve(null);
          }
        });
      } catch { resolve(null); }
    });
  }

  // ─── <CountryPicker> — searchable 249-country popover ────────────────────
  function CountryPicker({ value, onChange, label }) {
    const [open, setOpen] = React.useState(false);
    const [query, setQuery] = React.useState('');
    const [rect, setRect] = React.useState(null);
    const wrapRef = React.useRef(null);
    const btnRef = React.useRef(null);
    const inputRef = React.useRef(null);

    const refreshRect = React.useCallback(() => {
      if (btnRef.current) {
        const r = btnRef.current.getBoundingClientRect();
        setRect({ top: r.bottom + 4, left: r.left, width: Math.max(r.width, 260) });
      }
    }, []);

    React.useEffect(() => {
      if (!open) return;
      refreshRect();
      setQuery('');
      setTimeout(() => { if (inputRef.current) inputRef.current.focus(); }, 30);
      const onDoc = (e) => {
        if (wrapRef.current && wrapRef.current.contains(e.target)) return;
        const pop = document.querySelector('[data-shared-country-popover]');
        if (pop && pop.contains(e.target)) return;
        setOpen(false);
      };
      const onKey = (e) => { if (e.key === 'Escape') setOpen(false); };
      const onScroll = () => refreshRect();
      document.addEventListener('mousedown', onDoc);
      document.addEventListener('keydown', onKey);
      window.addEventListener('scroll', onScroll, true);
      window.addEventListener('resize', onScroll);
      return () => {
        document.removeEventListener('mousedown', onDoc);
        document.removeEventListener('keydown', onKey);
        window.removeEventListener('scroll', onScroll, true);
        window.removeEventListener('resize', onScroll);
      };
    }, [open, refreshRect]);

    const current = ECU_DOOR_COUNTRIES.find(c => c.code === value) || ECU_DOOR_COUNTRIES.find(c => c.code === 'US');
    const q = query.trim().toLowerCase();
    const filtered = q.length === 0
      ? ECU_DOOR_COUNTRIES
      : ECU_DOOR_COUNTRIES.filter(c =>
          c.name.toLowerCase().includes(q) || c.code.toLowerCase() === q || c.code.toLowerCase().includes(q));

    return (
      <div ref={wrapRef} style={{ marginTop: 6, display: 'flex',
        alignItems: 'center', gap: 6 }}>
        <span style={{ fontSize: 9, fontWeight: 700, color: '#475467',
          letterSpacing: '0.1em', textTransform: 'uppercase', flexShrink: 0 }}>{label}</span>
        <button type="button" ref={btnRef} onClick={() => setOpen(o => !o)}
          aria-haspopup="listbox" aria-expanded={open}
          style={{ flex: 1, minWidth: 0, position: 'relative',
            padding: '5px 26px 5px 8px',
            background: '#FFFFFF',
            border: '1px solid ' + (open ? '#1E57D6' : 'rgba(16,24,40,0.12)'),
            borderRadius: 7,
            fontFamily: 'inherit', fontSize: 11, fontWeight: 600,
            color: '#0B1220', textAlign: 'left',
            boxShadow: open
              ? '0 0 0 3px rgba(30,87,214,0.12), inset 0 1px 0 rgba(255,255,255,0.85)'
              : 'inset 0 1px 0 rgba(255,255,255,0.85)',
            cursor: 'pointer', outline: 'none',
            transition: 'border-color 160ms, box-shadow 160ms' }}>
          <span style={{ marginRight: 6 }}>{countryFlag(current.code)}</span>
          <span style={{ fontFamily: 'JetBrains Mono, ui-monospace, monospace',
            fontWeight: 700, color: '#1846B0', marginRight: 6 }}>{current.code}</span>
          <span style={{ color: '#0B1220' }}>{current.name}</span>
          <span style={{ position: 'absolute', right: 8, top: '50%',
            transform: `translateY(-50%) rotate(${open ? 180 : 0}deg)`,
            color: '#667085', transition: 'transform 160ms',
            fontSize: 10, lineHeight: 1 }}>▾</span>
        </button>
        {open && rect && ReactDOM.createPortal(
          <div data-shared-country-popover
            onMouseDown={(e) => e.stopPropagation()}
            style={{ position: 'fixed', top: rect.top, left: rect.left,
              width: rect.width, zIndex: 1000,
              background: '#fff', border: '1px solid rgba(16,24,40,0.12)',
              borderRadius: 10,
              boxShadow: '0 20px 40px -16px rgba(11,18,32,0.28), 0 0 0 1px rgba(11,18,32,0.04)',
              padding: 6 }}>
            <input
              ref={inputRef}
              type="text"
              value={query}
              onChange={(e) => setQuery(e.target.value)}
              placeholder={isEs() ? 'Buscar país…' : 'Search country…'}
              autoComplete="off"
              style={{ width: '100%', padding: '7px 10px', borderRadius: 7,
                border: '1px solid rgba(16,24,40,0.12)', background: '#F9FAFB',
                fontFamily: 'inherit', fontSize: 12, color: '#0B1220',
                outline: 'none', marginBottom: 4 }}
              onFocus={(e) => { e.currentTarget.style.borderColor = '#1E57D6';
                e.currentTarget.style.background = '#fff';
                e.currentTarget.style.boxShadow = '0 0 0 3px rgba(30,87,214,0.12)'; }}
              onBlur={(e) => { e.currentTarget.style.borderColor = 'rgba(16,24,40,0.12)';
                e.currentTarget.style.background = '#F9FAFB';
                e.currentTarget.style.boxShadow = 'none'; }}
              onKeyDown={(e) => {
                if (e.key === 'Enter' && filtered.length > 0) {
                  onChange(filtered[0].code); setOpen(false);
                }
              }}
            />
            <div style={{ maxHeight: 260, overflowY: 'auto' }}>
              {filtered.length === 0 ? (
                <div style={{ padding: '10px 12px', fontSize: 11.5,
                  color: '#98A2B3' }}>{isEs() ? 'Sin coincidencias' : 'No match'}</div>
              ) : filtered.map(c => {
                const active = c.code === value;
                return (
                  <button type="button" key={c.code}
                    role="option" aria-selected={active}
                    onClick={() => { onChange(c.code); setOpen(false); }}
                    style={{ width: '100%', textAlign: 'left',
                      padding: '7px 10px', borderRadius: 7,
                      background: active ? '#EFF6FF' : 'transparent',
                      border: 0, cursor: 'pointer', fontFamily: 'inherit',
                      display: 'flex', alignItems: 'center', gap: 8,
                      transition: 'background 120ms' }}
                    onMouseEnter={(e) => { if (!active) e.currentTarget.style.background = '#F2F4F7'; }}
                    onMouseLeave={(e) => { if (!active) e.currentTarget.style.background = 'transparent'; }}>
                    <span style={{ fontSize: 14, lineHeight: 1, flexShrink: 0 }}>{countryFlag(c.code)}</span>
                    <span style={{ fontFamily: 'JetBrains Mono, ui-monospace, monospace',
                      fontWeight: 700, color: active ? '#1846B0' : '#475467',
                      fontSize: 10.5, flexShrink: 0 }}>{c.code}</span>
                    <span style={{ fontSize: 12, fontWeight: 600,
                      color: '#0B1220', minWidth: 0, overflow: 'hidden',
                      textOverflow: 'ellipsis', whiteSpace: 'nowrap' }}>{c.name}</span>
                    {active && (
                      <svg width="12" height="12" viewBox="0 0 24 24" fill="none"
                        stroke="#1E57D6" strokeWidth="2.6" strokeLinecap="round" strokeLinejoin="round"
                        style={{ marginLeft: 'auto', flexShrink: 0 }}>
                        <path d="M4 12 L10 18 L20 6"/>
                      </svg>
                    )}
                  </button>
                );
              })}
            </div>
          </div>,
          document.body
        )}
      </div>
    );
  }

  // ─── <DoorPicker> — input + ECU door dropdown + CountryPicker ────────────
  // Drop-in replacement for the landings' Google Places origin/dest input
  // when the user has flipped the CY/SD radio to SD (door pickup).
  //
  // Props:
  //   country       — ISO-2 to search doors in (auto-derived from prior Place pick)
  //   onCountryChange — fires when user manually picks a country
  //   onSelect      — fires with the picked door object (or a Place-shaped
  //                   synthesized object when the user picks a Google fallback)
  //   placeholder   — input placeholder
  //   label         — label above the input
  //   side          — 'origin' | 'destination' (used for default seeds only)
  //   seedSearch    — initial search term (typically fromPlace.zip || fromPlace.city)
  //   selected      — last-selected door, used to show the collapsed summary
  function DoorPicker({ country, onCountryChange, onSelect, placeholder,
                        label, side, seedSearch, selected }) {
    const [search, setSearch] = React.useState(seedSearch || '');
    const [results, setResults] = React.useState([]);
    const [loading, setLoading] = React.useState(false);
    const [error, setError] = React.useState(null);
    const [open, setOpen] = React.useState(false);
    const timerRef = React.useRef(null);
    const wrapRef = React.useRef(null);
    const inputRef = React.useRef(null);

    // When `selected` changes (parent confirmed a pick) reflect the summary
    // back into the input value, mirroring the homepage behaviour.
    React.useEffect(() => {
      if (selected) setSearch(formatDoorSummary(selected));
    }, [selected]);

    // Re-seed search on country change so the user gets fresh results.
    React.useEffect(() => {
      if (!seedSearch) return;
      // Only re-seed if the user hasn't typed yet
      if (!search || search === seedSearch) setSearch(seedSearch);
    }, [country]);

    // Debounced ECU door search + Google Places fallback.
    React.useEffect(() => {
      const typed = (search || '').trim();
      if (timerRef.current) clearTimeout(timerRef.current);
      if (!country || typed.length < 2) {
        setResults([]); setLoading(false); setError(null);
        return;
      }
      const zipParam = /^\d{4,6}$/.test(typed) ? typed : '';
      setLoading(true); setError(null);
      timerRef.current = setTimeout(async () => {
        const doors = await walioSearchDoors({
          country,
          zipCode: zipParam || undefined,
          search:  zipParam ? undefined : typed,
          direction: side === 'origin' ? 'export' : 'import',
        });
        if (doors.length > 0) {
          setResults(doors.slice(0, 10));
          setLoading(false);
          setError(null);
          return;
        }
        const fallback = await searchGooglePlacesFallback(typed, country);
        setResults(fallback.slice(0, 8));
        setLoading(false);
        setError(fallback.length === 0 ? (isEs()
          ? 'No se encontraron ubicaciones de puerta' : 'No door locations found') : null);
      }, 350);
      return () => { if (timerRef.current) clearTimeout(timerRef.current); };
    }, [search, country, side]);

    // Click-outside / Escape close the dropdown.
    React.useEffect(() => {
      if (!open) return;
      const onDoc = (e) => {
        if (wrapRef.current && !wrapRef.current.contains(e.target)) setOpen(false);
      };
      const onKey = (e) => { if (e.key === 'Escape') setOpen(false); };
      document.addEventListener('mousedown', onDoc);
      document.addEventListener('keydown', onKey);
      return () => {
        document.removeEventListener('mousedown', onDoc);
        document.removeEventListener('keydown', onKey);
      };
    }, [open]);

    const handlePick = async (door) => {
      // Google-fallback rows resolve their place_id for real coords.
      if (door.isGoogleFallback) {
        const place = await resolveGooglePlaceId(door.placeId);
        const c = (place && place.country) || (door.countryCode || country || 'US').toUpperCase();
        onSelect && onSelect({
          door, // raw door object — caller decides if .code is sent
          country: c,
          state: (place && place.state) || '',
          city:  (place && place.city)  || door.city || door.displayName || '',
          zip:   (place && place.zip)   || door.zipCode || '',
          lat:   place ? place.lat : null,
          lng:   place ? place.lng : null,
        });
      } else {
        // Regular ECU door: seed with what the API returned, then async
        // geocode the zip to backfill lat/lng/city/state.
        const zip = String(door.zipCode || '').match(/\b(\d{5})\b/);
        const z = zip ? zip[1] : (door.zipCode || '');
        const c = (door.countryCode || country || 'US').toUpperCase();
        const initial = {
          door,
          country: c,
          state: door.state || '',
          city: door.city || door.displayName || '',
          zip: z,
          lat: null,
          lng: null,
        };
        onSelect && onSelect(initial);
        if (z) {
          const geo = await geocodeZipViaSDK(z, c);
          if (geo && geo.lat && geo.lng) {
            onSelect && onSelect({
              ...initial,
              lat: geo.lat,
              lng: geo.lng,
              state: geo.state || initial.state,
              city: geo.city || initial.city,
            });
          }
        }
      }
      setOpen(false);
    };

    // If the user typed a recognisable country name AND we're searching in
    // a different country, offer to swap. Example: country='US', search='dominican'
    // → suggest 'DO'. Detected case-insensitively against ECU_DOOR_COUNTRIES.
    // Returns null if no clean match, or the typed term IS the current country.
    const countrySuggestion = (() => {
      const q = (search || '').trim().toLowerCase();
      if (q.length < 3) return null;
      const cur = (country || '').toUpperCase();
      // Look for partial matches on country name. Prefer longest match.
      const matches = ECU_DOOR_COUNTRIES.filter(c =>
        c.code !== cur && c.name.toLowerCase().includes(q));
      if (matches.length === 0) return null;
      // Prefer a match whose name starts with the query
      const starts = matches.find(c => c.name.toLowerCase().startsWith(q));
      return starts || matches[0];
    })();
    const showCountrySuggestion = !!(countrySuggestion && onCountryChange
      && !loading && results.length === 0);
    // Hint shown to nudge users toward typing a postal code — by-zip queries
    // always return precise door matches whereas city-name queries can miss
    // (e.g. typing "dominican" in a US-defaulted picker returns nothing).
    // Hidden once the user starts typing a likely zip (≥4 digits).
    const looksLikeZip = /^\d{4,}/.test((search || '').trim());

    return (
      <div ref={wrapRef} style={{ position: 'relative', minWidth: 0 }}>
        {label && (
          <div style={{ fontSize: 9, fontWeight: 700, color: '#475467',
            letterSpacing: '0.1em', textTransform: 'uppercase',
            marginBottom: 3, paddingLeft: 2 }}>{label}</div>
        )}
        <input
          ref={inputRef}
          type="text"
          value={search}
          onChange={(e) => { setSearch(e.target.value); setOpen(true); }}
          onFocus={() => setOpen(true)}
          placeholder={placeholder || (isEs()
            ? 'Buscar ubicación de puerta' : 'Search door location')}
          autoComplete="off"
          style={{ width: '100%', padding: '10px 12px',
            background: '#FFFFFF',
            border: '1px solid rgba(16,24,40,0.12)', borderRadius: 8,
            fontFamily: 'inherit', fontSize: 13, color: '#0B1220',
            boxShadow: 'inset 0 1px 0 rgba(255,255,255,0.85)',
            outline: 'none' }}
          onFocusCapture={(e) => { e.currentTarget.style.borderColor = '#1E57D6';
            e.currentTarget.style.boxShadow = '0 0 0 3px rgba(30,87,214,0.12)'; }}
          onBlurCapture={(e) => { e.currentTarget.style.borderColor = 'rgba(16,24,40,0.12)';
            e.currentTarget.style.boxShadow = 'inset 0 1px 0 rgba(255,255,255,0.85)'; }}/>
        {!looksLikeZip && (
          <div style={{ marginTop: 5, display: 'flex', alignItems: 'center',
            gap: 5, fontSize: 10.5, color: '#667085',
            fontFamily: 'inherit', letterSpacing: '0.01em' }}>
            <span style={{ display: 'inline-grid', placeItems: 'center',
              width: 13, height: 13, borderRadius: 999,
              background: 'rgba(30,87,214,0.1)', color: '#1846B0',
              fontSize: 8.5, fontWeight: 800, flexShrink: 0 }}>i</span>
            <span>{isEs()
              ? 'Busca por código postal para mejores resultados'
              : 'Search by zip code for more precise matches'}</span>
          </div>
        )}
        {error && !loading && results.length === 0 && !showCountrySuggestion && (
          <div style={{ marginTop: 4, fontSize: 10, color: '#B54708',
            fontFamily: 'inherit' }}>{error}</div>
        )}
        {open && (loading || results.length > 0 || showCountrySuggestion) && (
          <div style={{ position: 'absolute', top: '100%', left: 0, right: 0,
            marginTop: 4, zIndex: 20,
            background: '#fff', borderRadius: 10,
            border: '1px solid rgba(16,24,40,0.12)',
            boxShadow: '0 12px 28px -8px rgba(16,24,40,0.22)',
            maxHeight: 260, overflowY: 'auto' }}>
            {loading && (
              <div style={{ padding: '10px 12px', fontSize: 11.5,
                color: '#667085' }}>{isEs() ? 'Buscando…' : 'Searching…'}</div>
            )}
            {!loading && showCountrySuggestion && (
              <button type="button"
                onClick={() => {
                  // Swap the picker's country — keeps the typed search so the
                  // user can refine within the new country immediately.
                  onCountryChange(countrySuggestion.code);
                }}
                style={{ width: '100%', textAlign: 'left',
                  padding: '11px 12px',
                  background: 'rgba(30,87,214,0.04)',
                  border: 0,
                  borderBottom: results.length > 0
                    ? '1px solid rgba(16,24,40,0.06)' : 'none',
                  cursor: 'pointer', fontFamily: 'inherit',
                  display: 'flex', alignItems: 'center', gap: 8 }}
                onMouseEnter={(e) => { e.currentTarget.style.background = 'rgba(30,87,214,0.08)'; }}
                onMouseLeave={(e) => { e.currentTarget.style.background = 'rgba(30,87,214,0.04)'; }}>
                <span style={{ fontSize: 16, lineHeight: 1, flexShrink: 0 }}>
                  {countryFlag(countrySuggestion.code)}
                </span>
                <span style={{ flex: 1, minWidth: 0 }}>
                  <span style={{ display: 'block', fontSize: 11.5,
                    fontWeight: 700, color: '#1846B0' }}>
                    {isEs()
                      ? `Buscar en ${countrySuggestion.name}`
                      : `Search in ${countrySuggestion.name}`}
                  </span>
                  <span style={{ display: 'block', marginTop: 2,
                    fontSize: 10, color: '#667085' }}>
                    {isEs()
                      ? 'Cambiar país y reintentar la búsqueda'
                      : 'Switch country and retry the search'}
                  </span>
                </span>
                <svg width="11" height="11" viewBox="0 0 24 24" fill="none"
                  stroke="#1E57D6" strokeWidth="2.4" strokeLinecap="round" strokeLinejoin="round"
                  style={{ flexShrink: 0 }}>
                  <path d="M5 12h14M13 6l6 6-6 6"/>
                </svg>
              </button>
            )}
            {!loading && results.map((opt, i) => (
              <button type="button" key={(opt.code || '') + i}
                onClick={() => handlePick(opt)}
                style={{ width: '100%', textAlign: 'left',
                  padding: '9px 12px',
                  background: 'transparent',
                  border: 0, cursor: 'pointer', fontFamily: 'inherit',
                  borderBottom: i < results.length - 1 ? '1px solid rgba(16,24,40,0.06)' : 'none',
                  display: 'block' }}
                onMouseEnter={(e) => { e.currentTarget.style.background = '#F9FAFB'; }}
                onMouseLeave={(e) => { e.currentTarget.style.background = 'transparent'; }}>
                {opt.isGoogleFallback ? (
                  <span style={{ display: 'inline-block',
                    padding: '1px 6px', borderRadius: 5,
                    background: 'rgba(16,185,129,0.12)',
                    color: '#047857',
                    fontSize: 9.5, fontWeight: 800,
                    fontFamily: 'inherit',
                    letterSpacing: '0.04em', marginRight: 6 }}>MAPS</span>
                ) : (opt.zipCode && (
                  <span style={{ display: 'inline-block',
                    padding: '1px 6px', borderRadius: 5,
                    background: 'rgba(30,87,214,0.1)',
                    color: '#1846B0',
                    fontSize: 10, fontWeight: 800,
                    fontFamily: 'inherit',
                    letterSpacing: '0.04em', marginRight: 6 }}>{opt.zipCode}</span>
                ))}
                <span style={{ fontSize: 11.5, fontWeight: 600,
                  color: '#0B1220' }}>{opt.displayName}</span>
                {!opt.isGoogleFallback && (opt.city || opt.state || opt.countryName || opt.countryCode) && (
                  <span style={{ display: 'block', marginTop: 2,
                    fontSize: 10, color: '#667085',
                    fontFamily: 'inherit' }}>
                    {[
                      [opt.city, opt.state].filter(Boolean).join(', '),
                      opt.countryName || opt.countryCode,
                    ].filter(Boolean).join(' · ')}
                  </span>
                )}
              </button>
            ))}
          </div>
        )}
        {onCountryChange && (
          <CountryPicker
            value={country || 'US'}
            onChange={onCountryChange}
            label={isEs() ? 'País' : 'Country'}
          />
        )}
      </div>
    );
  }

  window.__abgsSharedDoorUi = {
    ECU_DOOR_COUNTRIES,
    countryFlag,
    formatDoorSummary,
    walioSearchDoors,
    searchGooglePlacesFallback,
    resolveGooglePlaceId,
    geocodeZipViaSDK,
    CountryPicker,
    DoorPicker,
  };
})();
