/* global React, Icon */
// ============================================================================
// DÉFINITIONS DE BASE · Référentiel géographique
// ----------------------------------------------------------------------------
// Module d'administration des subdivisions administratives utilisées par
// la plateforme. Hiérarchie :
//   Pays (countries) → Région → Département → Arrondissement → Commune → Quartier
//
// Au seed initial, le Sénégal est entièrement peuplé (14 régions, 46
// départements, 168 arrondissements, 536 communes). Les autres pays sont
// dans le catalogue ISO 3166-1 ; chaque org peut compléter sa propre
// liste de quartiers (RLS admin).
//
// Écran à 6 onglets, chacun = un niveau. Filtrage en cascade par le
// parent + recherche texte + CRUD inline.
// ============================================================================

const { useState: useStatePL, useMemo: useMemoPL, useEffect: useEffectPL } = React;

function ProjectPlanning({ t, lang, isSuperAdmin }) {
  const [tab, setTab] = useStatePL("countries");

  // ──────────────────────────────────────────────────────────────────────
  return (
    <div className="screen" data-screen-label="Definitions de base">
      <div className="row" style={{ alignItems: "center", marginBottom: 12 }}>
        <div>
          <div className="screen-title">{window.L("Définitions de base", "Base definitions", "Definiciones de base")}</div>
          <div className="text-faint" style={{ fontSize: 12, marginTop: 2 }}>
            {window.L("Référentiel géographique partagé : pays, régions, départements, arrondissements, communes, quartiers.", "Shared geographic catalog: countries, regions, departments, arrondissements, communes, neighborhoods.", "Catálogo geográfico compartido: países, regiones, departamentos, distritos, municipios, barrios.")}
          </div>
        </div>
      </div>

      {/* Onglets · 6 niveaux */}
      <div className="seg" style={{ marginBottom: 16 }}>
        <button className={"seg-btn" + (tab === "countries"        ? " active" : "")} onClick={() => setTab("countries")}>
          <Icon.globe /> {window.L("Pays", "Countries", "Países")}
        </button>
        <button className={"seg-btn" + (tab === "regions"          ? " active" : "")} onClick={() => setTab("regions")}>
          {window.L("Régions", "Regions", "Regiones")}
        </button>
        <button className={"seg-btn" + (tab === "departments"      ? " active" : "")} onClick={() => setTab("departments")}>
          {window.L("Départements", "Departments", "Departamentos")}
        </button>
        <button className={"seg-btn" + (tab === "arrondissements"  ? " active" : "")} onClick={() => setTab("arrondissements")}>
          {window.L("Arrondissements", "Arrondissements", "Distritos")}
        </button>
        <button className={"seg-btn" + (tab === "communes"         ? " active" : "")} onClick={() => setTab("communes")}>
          {window.L("Communes", "Communes", "Municipios")}
        </button>
        <button className={"seg-btn" + (tab === "quartiers"        ? " active" : "")} onClick={() => setTab("quartiers")}>
          {window.L("Quartiers", "Neighborhoods", "Barrios")}
        </button>
      </div>

      {tab === "countries"       && <CountriesTab       lang={lang} isSuperAdmin={isSuperAdmin} />}
      {tab === "regions"         && <RegionsTab         lang={lang} isSuperAdmin={isSuperAdmin} />}
      {tab === "departments"     && <DepartmentsTab     lang={lang} isSuperAdmin={isSuperAdmin} />}
      {tab === "arrondissements" && <ArrondissementsTab lang={lang} isSuperAdmin={isSuperAdmin} />}
      {tab === "communes"        && <CommunesTab        lang={lang} isSuperAdmin={isSuperAdmin} />}
      {tab === "quartiers"       && <QuartiersTab       lang={lang} isSuperAdmin={isSuperAdmin} />}
    </div>
  );
}

// ── Helpers communs ─────────────────────────────────────────────────────
function _searchMatch(needle, ...haystacks) {
  if (!needle) return true;
  const n = needle.toLowerCase();
  return haystacks.some((h) => h && String(h).toLowerCase().includes(n));
}

const _inp = {
  padding: "7px 9px", borderRadius: 6, border: "1px solid var(--line)",
  fontSize: 12.5, background: "var(--bg, white)", color: "var(--text)",
};
const _btnRow = { display: "flex", gap: 6, marginLeft: "auto" };

function _toolbar({ search, setSearch, count, addLabel, onAdd, canAdd, extras }) {
  return (
    <div className="card-head" style={{ flexWrap: "wrap", gap: 10 }}>
      <input style={{ ..._inp, minWidth: 260, flex: 1 }} placeholder="🔎 Filtrer…"
        value={search} onChange={(e) => setSearch(e.target.value)} />
      <span className="text-faint" style={{ fontSize: 12 }}>{count} résultats</span>
      {extras}
      {canAdd && (
        <button className="btn xs primary" onClick={onAdd} style={{ marginLeft: "auto" }}>
          <Icon.plus /> {addLabel}
        </button>
      )}
    </div>
  );
}

// ============================================================================
// Onglet · Pays
// ============================================================================
function CountriesTab({ lang, isSuperAdmin }) {
  const { data, loading, refresh } = window.melr.useCountries();
  const [search, setSearch] = useStatePL("");
  const [editing, setEditing] = useStatePL(null);
  const [creating, setCreating] = useStatePL(false);

  const rows = useMemoPL(() => {
    return (data || []).filter((r) => _searchMatch(search, r.iso2, r.name_fr, r.name_en, r.region));
  }, [data, search]);

  return (
    <div className="card">
      {_toolbar({
        search, setSearch, count: rows.length,
        addLabel: window.L("Nouveau pays", "New country", "Nuevo país"),
        onAdd: () => setCreating(true),
        canAdd: isSuperAdmin,
      })}
      <div className="card-body flush" style={{ maxHeight: "70vh", overflow: "auto" }}>
        {loading
          ? <div className="text-faint" style={{ padding: 22, textAlign: "center" }}>{window.L("Chargement…", "Loading…", "Cargando…")}</div>
          : (
            <table className="tbl">
              <thead><tr>
                <th>ISO2</th>
                <th>{window.L("Nom (fr)", "Name (fr)", "Nombre (fr)")}</th>
                <th>{window.L("Nom (en)", "Name (en)", "Nombre (en)")}</th>
                <th>{window.L("Région ONU", "UN region", "Región ONU")}</th>
                {isSuperAdmin && <th style={{ width: 60 }}></th>}
              </tr></thead>
              <tbody>
                {rows.map((r) => (
                  <tr key={r.iso2}>
                    <td className="mono strong">{r.iso2}</td>
                    <td>{r.name_fr}</td>
                    <td className="muted">{r.name_en}</td>
                    <td className="muted">{r.region || "—"}</td>
                    {isSuperAdmin && (
                      <td className="num">
                        <button className="iconbtn" title={window.L("Modifier", "Edit", "Editar")} onClick={() => setEditing(r)}>
                          <Icon.edit />
                        </button>
                      </td>
                    )}
                  </tr>
                ))}
              </tbody>
            </table>
          )}
      </div>
      {(creating || editing) && <CountryModal lang={lang} row={editing} onClose={() => { setEditing(null); setCreating(false); }} onSaved={async () => { setEditing(null); setCreating(false); await refresh(); }} />}
    </div>
  );
}

// ============================================================================
// Onglet · Régions
// ============================================================================
function RegionsTab({ lang, isSuperAdmin }) {
  const [country, setCountry] = useStatePL("SN");
  const { data: countries } = window.melr.useCountries();
  const { data, loading, refresh } = window.melr.useGeoRegions(country);
  const [search, setSearch] = useStatePL("");
  const [editing, setEditing] = useStatePL(null);
  const [creating, setCreating] = useStatePL(false);

  const rows = useMemoPL(() => {
    return (data || []).filter((r) => _searchMatch(search, r.code, r.name_fr, r.name_en));
  }, [data, search]);

  return (
    <div className="card">
      <div className="card-head" style={{ flexWrap: "wrap", gap: 10 }}>
        <label style={{ display: "flex", alignItems: "center", gap: 6 }}>
          <span style={{ fontSize: 11, color: "var(--text-faint)", textTransform: "uppercase" }}>{window.L("Pays", "Country", "País")} :</span>
          <select style={_inp} value={country || ""} onChange={(e) => setCountry(e.target.value || null)}>
            <option value="">— Tous —</option>
            {(countries || []).map((c) => <option key={c.iso2} value={c.iso2}>{c.name_fr}</option>)}
          </select>
        </label>
        <input style={{ ..._inp, minWidth: 240, flex: 1 }} placeholder="🔎 Filtrer…" value={search} onChange={(e) => setSearch(e.target.value)} />
        <span className="text-faint" style={{ fontSize: 12 }}>{rows.length} résultats</span>
        {isSuperAdmin && (
          <button className="btn xs primary" onClick={() => setCreating(true)} disabled={!country}>
            <Icon.plus /> {window.L("Nouvelle région", "New region", "Nueva región")}
          </button>
        )}
      </div>
      <div className="card-body flush" style={{ maxHeight: "70vh", overflow: "auto" }}>
        {!country ? (
          <div className="text-faint" style={{ padding: 22, textAlign: "center" }}>
            {window.L("Choisir un pays pour afficher ses régions.", "Pick a country to list its regions.", "Elija un país para mostrar sus regiones.")}
          </div>
        ) : loading ? (
          <div className="text-faint" style={{ padding: 22, textAlign: "center" }}>{window.L("Chargement…", "Loading…", "Cargando…")}</div>
        ) : (
          <table className="tbl">
            <thead><tr>
              <th>{window.L("Code", "Code", "Código")}</th>
              <th>{window.L("Nom (fr)", "Name (fr)", "Nombre (fr)")}</th>
              <th>{window.L("Nom (en)", "Name (en)", "Nombre (en)")}</th>
              {isSuperAdmin && <th style={{ width: 60 }}></th>}
            </tr></thead>
            <tbody>
              {rows.map((r) => (
                <tr key={r.id}>
                  <td className="mono">{r.code || "—"}</td>
                  <td className="strong">{r.name_fr}</td>
                  <td className="muted">{r.name_en || "—"}</td>
                  {isSuperAdmin && (
                    <td className="num">
                      <button className="iconbtn" onClick={() => setEditing(r)}><Icon.edit /></button>
                    </td>
                  )}
                </tr>
              ))}
            </tbody>
          </table>
        )}
      </div>
      {(creating || editing) && <RegionModal lang={lang} row={editing} country={country} onClose={() => { setEditing(null); setCreating(false); }} onSaved={async () => { setEditing(null); setCreating(false); await refresh(); }} />}
    </div>
  );
}

// ============================================================================
// Onglet · Départements (filtre par région)
// ============================================================================
function DepartmentsTab({ lang, isSuperAdmin }) {
  const [country, setCountry] = useStatePL("SN");
  const [regionId, setRegionId] = useStatePL(null);
  const { data: countries } = window.melr.useCountries();
  const { data: regions } = window.melr.useGeoRegions(country);
  const { data, loading, refresh } = window.melr.useGeoDepartments(regionId);
  const [search, setSearch] = useStatePL("");
  const [editing, setEditing] = useStatePL(null);
  const [creating, setCreating] = useStatePL(false);

  const rows = useMemoPL(() => (data || []).filter((r) => _searchMatch(search, r.code, r.name_fr, r.name_en)), [data, search]);

  return (
    <div className="card">
      <div className="card-head" style={{ flexWrap: "wrap", gap: 10 }}>
        <label style={{ display: "flex", alignItems: "center", gap: 6 }}>
          <span style={{ fontSize: 11, color: "var(--text-faint)" }}>{window.L("Pays", "Country", "País")} :</span>
          <select style={_inp} value={country || ""} onChange={(e) => { setCountry(e.target.value || null); setRegionId(null); }}>
            {(countries || []).map((c) => <option key={c.iso2} value={c.iso2}>{c.name_fr}</option>)}
          </select>
        </label>
        <label style={{ display: "flex", alignItems: "center", gap: 6 }}>
          <span style={{ fontSize: 11, color: "var(--text-faint)" }}>{window.L("Région", "Region", "Región")} :</span>
          <select style={_inp} value={regionId || ""} onChange={(e) => setRegionId(e.target.value || null)}>
            <option value="">— {window.L("Choisir", "Pick", "Elegir")} —</option>
            {(regions || []).map((r) => <option key={r.id} value={r.id}>{r.name_fr}</option>)}
          </select>
        </label>
        <input style={{ ..._inp, minWidth: 200, flex: 1 }} placeholder="🔎 Filtrer…" value={search} onChange={(e) => setSearch(e.target.value)} />
        <span className="text-faint" style={{ fontSize: 12 }}>{rows.length} résultats</span>
        {isSuperAdmin && regionId && (
          <button className="btn xs primary" onClick={() => setCreating(true)}>
            <Icon.plus /> {window.L("Nouveau département", "New department", "Nuevo departamento")}
          </button>
        )}
      </div>
      <div className="card-body flush" style={{ maxHeight: "70vh", overflow: "auto" }}>
        {!regionId ? (
          <div className="text-faint" style={{ padding: 22, textAlign: "center" }}>{window.L("Choisir une région.", "Pick a region.", "Elija una región.")}</div>
        ) : loading ? (
          <div className="text-faint" style={{ padding: 22, textAlign: "center" }}>{window.L("Chargement…", "Loading…", "Cargando…")}</div>
        ) : (
          <table className="tbl">
            <thead><tr>
              <th>{window.L("Code", "Code", "Código")}</th>
              <th>{window.L("Nom (fr)", "Name (fr)", "Nombre (fr)")}</th>
              <th>{window.L("Nom (en)", "Name (en)", "Nombre (en)")}</th>
              {isSuperAdmin && <th style={{ width: 60 }}></th>}
            </tr></thead>
            <tbody>
              {rows.map((r) => (
                <tr key={r.id}>
                  <td className="mono">{r.code || "—"}</td>
                  <td className="strong">{r.name_fr}</td>
                  <td className="muted">{r.name_en || "—"}</td>
                  {isSuperAdmin && <td className="num"><button className="iconbtn" onClick={() => setEditing(r)}><Icon.edit /></button></td>}
                </tr>
              ))}
            </tbody>
          </table>
        )}
      </div>
      {(creating || editing) && <DepartmentModal lang={lang} row={editing} regionId={regionId} onClose={() => { setEditing(null); setCreating(false); }} onSaved={async () => { setEditing(null); setCreating(false); await refresh(); }} />}
    </div>
  );
}

// ============================================================================
// Onglet · Arrondissements (filtre par département)
// ============================================================================
function ArrondissementsTab({ lang, isSuperAdmin }) {
  const [country, setCountry] = useStatePL("SN");
  const [regionId, setRegionId] = useStatePL(null);
  const [deptId, setDeptId] = useStatePL(null);
  const { data: countries } = window.melr.useCountries();
  const { data: regions } = window.melr.useGeoRegions(country);
  const { data: departments } = window.melr.useGeoDepartments(regionId);
  const { data, loading, refresh } = window.melr.useGeoArrondissements(deptId);
  const [search, setSearch] = useStatePL("");
  const [editing, setEditing] = useStatePL(null);
  const [creating, setCreating] = useStatePL(false);

  const rows = useMemoPL(() => (data || []).filter((r) => _searchMatch(search, r.name_fr, r.name_en)), [data, search]);

  return (
    <div className="card">
      <div className="card-head" style={{ flexWrap: "wrap", gap: 10 }}>
        <select style={_inp} value={country || ""} onChange={(e) => { setCountry(e.target.value || null); setRegionId(null); setDeptId(null); }}>
          {(countries || []).map((c) => <option key={c.iso2} value={c.iso2}>{c.name_fr}</option>)}
        </select>
        <select style={_inp} value={regionId || ""} onChange={(e) => { setRegionId(e.target.value || null); setDeptId(null); }}>
          <option value="">— {window.L("Région", "Region", "Región")} —</option>
          {(regions || []).map((r) => <option key={r.id} value={r.id}>{r.name_fr}</option>)}
        </select>
        <select style={_inp} value={deptId || ""} onChange={(e) => setDeptId(e.target.value || null)} disabled={!regionId}>
          <option value="">— {window.L("Département", "Department", "Departamento")} —</option>
          {(departments || []).map((d) => <option key={d.id} value={d.id}>{d.name_fr}</option>)}
        </select>
        <input style={{ ..._inp, minWidth: 180, flex: 1 }} placeholder="🔎 Filtrer…" value={search} onChange={(e) => setSearch(e.target.value)} />
        <span className="text-faint" style={{ fontSize: 12 }}>{rows.length} résultats</span>
        {isSuperAdmin && deptId && (
          <button className="btn xs primary" onClick={() => setCreating(true)}>
            <Icon.plus /> {window.L("Nouvel arr.", "New arr.", "Nuevo dist.")}
          </button>
        )}
      </div>
      <div className="card-body flush" style={{ maxHeight: "70vh", overflow: "auto" }}>
        {!deptId ? (
          <div className="text-faint" style={{ padding: 22, textAlign: "center" }}>{window.L("Choisir un département.", "Pick a department.", "Elija un departamento.")}</div>
        ) : loading ? (
          <div className="text-faint" style={{ padding: 22, textAlign: "center" }}>{window.L("Chargement…", "Loading…", "Cargando…")}</div>
        ) : (
          <table className="tbl">
            <thead><tr>
              <th>{window.L("Nom (fr)", "Name (fr)", "Nombre (fr)")}</th>
              <th>{window.L("Nom (en)", "Name (en)", "Nombre (en)")}</th>
              {isSuperAdmin && <th style={{ width: 60 }}></th>}
            </tr></thead>
            <tbody>
              {rows.map((r) => (
                <tr key={r.id}>
                  <td className="strong">{r.name_fr}</td>
                  <td className="muted">{r.name_en || "—"}</td>
                  {isSuperAdmin && <td className="num"><button className="iconbtn" onClick={() => setEditing(r)}><Icon.edit /></button></td>}
                </tr>
              ))}
            </tbody>
          </table>
        )}
      </div>
      {(creating || editing) && <ArrondissementModal lang={lang} row={editing} deptId={deptId} onClose={() => { setEditing(null); setCreating(false); }} onSaved={async () => { setEditing(null); setCreating(false); await refresh(); }} />}
    </div>
  );
}

// ============================================================================
// Onglet · Communes (filtre par arrondissement)
// ============================================================================
function CommunesTab({ lang, isSuperAdmin }) {
  const [country, setCountry] = useStatePL("SN");
  const [regionId, setRegionId] = useStatePL(null);
  const [deptId, setDeptId] = useStatePL(null);
  const [arrId, setArrId] = useStatePL(null);
  const { data: countries } = window.melr.useCountries();
  const { data: regions } = window.melr.useGeoRegions(country);
  const { data: departments } = window.melr.useGeoDepartments(regionId);
  const { data: arrondissements } = window.melr.useGeoArrondissements(deptId);
  const { data, loading, refresh } = window.melr.useGeoCommunes(arrId);
  const [search, setSearch] = useStatePL("");
  const [editing, setEditing] = useStatePL(null);
  const [creating, setCreating] = useStatePL(false);

  const rows = useMemoPL(() => (data || []).filter((r) => _searchMatch(search, r.name_fr, r.name_en, r.type, r.ville_parent)), [data, search]);

  return (
    <div className="card">
      <div className="card-head" style={{ flexWrap: "wrap", gap: 8 }}>
        <select style={_inp} value={country || ""} onChange={(e) => { setCountry(e.target.value || null); setRegionId(null); setDeptId(null); setArrId(null); }}>
          {(countries || []).map((c) => <option key={c.iso2} value={c.iso2}>{c.name_fr}</option>)}
        </select>
        <select style={_inp} value={regionId || ""} onChange={(e) => { setRegionId(e.target.value || null); setDeptId(null); setArrId(null); }}>
          <option value="">— Région —</option>
          {(regions || []).map((r) => <option key={r.id} value={r.id}>{r.name_fr}</option>)}
        </select>
        <select style={_inp} value={deptId || ""} onChange={(e) => { setDeptId(e.target.value || null); setArrId(null); }} disabled={!regionId}>
          <option value="">— Département —</option>
          {(departments || []).map((d) => <option key={d.id} value={d.id}>{d.name_fr}</option>)}
        </select>
        <select style={_inp} value={arrId || ""} onChange={(e) => setArrId(e.target.value || null)} disabled={!deptId}>
          <option value="">— Arrondissement —</option>
          {(arrondissements || []).map((a) => <option key={a.id} value={a.id}>{a.name_fr}</option>)}
        </select>
        <input style={{ ..._inp, minWidth: 160, flex: 1 }} placeholder="🔎 Filtrer…" value={search} onChange={(e) => setSearch(e.target.value)} />
        <span className="text-faint" style={{ fontSize: 12 }}>{rows.length} résultats</span>
        {isSuperAdmin && arrId && (
          <button className="btn xs primary" onClick={() => setCreating(true)}>
            <Icon.plus /> {window.L("Nouvelle commune", "New commune", "Nuevo municipio")}
          </button>
        )}
      </div>
      <div className="card-body flush" style={{ maxHeight: "70vh", overflow: "auto" }}>
        {!arrId ? (
          <div className="text-faint" style={{ padding: 22, textAlign: "center" }}>{window.L("Choisir un arrondissement.", "Pick an arrondissement.", "Elija un distrito.")}</div>
        ) : loading ? (
          <div className="text-faint" style={{ padding: 22, textAlign: "center" }}>{window.L("Chargement…", "Loading…", "Cargando…")}</div>
        ) : (
          <table className="tbl">
            <thead><tr>
              <th>{window.L("Nom", "Name", "Nombre")}</th>
              <th>{window.L("Type", "Type", "Tipo")}</th>
              <th>{window.L("Ville parent", "Parent city", "Ciudad principal")}</th>
              {isSuperAdmin && <th style={{ width: 60 }}></th>}
            </tr></thead>
            <tbody>
              {rows.map((r) => (
                <tr key={r.id}>
                  <td className="strong">{r.name_fr}</td>
                  <td className="muted">{r.type || "—"}</td>
                  <td className="muted">{r.ville_parent || "—"}</td>
                  {isSuperAdmin && <td className="num"><button className="iconbtn" onClick={() => setEditing(r)}><Icon.edit /></button></td>}
                </tr>
              ))}
            </tbody>
          </table>
        )}
      </div>
      {(creating || editing) && <CommuneModal lang={lang} row={editing} arrId={arrId} onClose={() => { setEditing(null); setCreating(false); }} onSaved={async () => { setEditing(null); setCreating(false); await refresh(); }} />}
    </div>
  );
}

// ============================================================================
// Onglet · Quartiers (filtre par commune)
// ============================================================================
function QuartiersTab({ lang, isSuperAdmin }) {
  const [country, setCountry] = useStatePL("SN");
  const [regionId, setRegionId] = useStatePL(null);
  const [deptId, setDeptId] = useStatePL(null);
  const [arrId, setArrId] = useStatePL(null);
  const [commId, setCommId] = useStatePL(null);
  const { data: countries } = window.melr.useCountries();
  const { data: regions } = window.melr.useGeoRegions(country);
  const { data: departments } = window.melr.useGeoDepartments(regionId);
  const { data: arrondissements } = window.melr.useGeoArrondissements(deptId);
  const { data: communes } = window.melr.useGeoCommunes(arrId);
  const { data, loading, refresh } = window.melr.useGeoQuartiers(commId);
  const [search, setSearch] = useStatePL("");
  const [editing, setEditing] = useStatePL(null);
  const [creating, setCreating] = useStatePL(false);

  const rows = useMemoPL(() => (data || []).filter((r) => _searchMatch(search, r.name_fr, r.name_en)), [data, search]);

  return (
    <div className="card">
      <div className="card-head" style={{ flexWrap: "wrap", gap: 8 }}>
        <select style={_inp} value={country || ""} onChange={(e) => { setCountry(e.target.value || null); setRegionId(null); setDeptId(null); setArrId(null); setCommId(null); }}>
          {(countries || []).map((c) => <option key={c.iso2} value={c.iso2}>{c.name_fr}</option>)}
        </select>
        <select style={_inp} value={regionId || ""} onChange={(e) => { setRegionId(e.target.value || null); setDeptId(null); setArrId(null); setCommId(null); }}>
          <option value="">— Région —</option>
          {(regions || []).map((r) => <option key={r.id} value={r.id}>{r.name_fr}</option>)}
        </select>
        <select style={_inp} value={deptId || ""} onChange={(e) => { setDeptId(e.target.value || null); setArrId(null); setCommId(null); }} disabled={!regionId}>
          <option value="">— Département —</option>
          {(departments || []).map((d) => <option key={d.id} value={d.id}>{d.name_fr}</option>)}
        </select>
        <select style={_inp} value={arrId || ""} onChange={(e) => { setArrId(e.target.value || null); setCommId(null); }} disabled={!deptId}>
          <option value="">— Arrondissement —</option>
          {(arrondissements || []).map((a) => <option key={a.id} value={a.id}>{a.name_fr}</option>)}
        </select>
        <select style={_inp} value={commId || ""} onChange={(e) => setCommId(e.target.value || null)} disabled={!arrId}>
          <option value="">— Commune —</option>
          {(communes || []).map((c) => <option key={c.id} value={c.id}>{c.name_fr}</option>)}
        </select>
        <input style={{ ..._inp, minWidth: 140, flex: 1 }} placeholder="🔎 Filtrer…" value={search} onChange={(e) => setSearch(e.target.value)} />
        <span className="text-faint" style={{ fontSize: 12 }}>{rows.length} résultats</span>
        {commId && (
          <button className="btn xs primary" onClick={() => setCreating(true)}>
            <Icon.plus /> {window.L("Nouveau quartier", "New neighborhood", "Nuevo barrio")}
          </button>
        )}
      </div>
      <div className="card-body flush" style={{ maxHeight: "70vh", overflow: "auto" }}>
        {!commId ? (
          <div className="text-faint" style={{ padding: 22, textAlign: "center" }}>{window.L("Choisir une commune.", "Pick a commune.", "Elija un municipio.")}</div>
        ) : loading ? (
          <div className="text-faint" style={{ padding: 22, textAlign: "center" }}>{window.L("Chargement…", "Loading…", "Cargando…")}</div>
        ) : rows.length === 0 ? (
          <div className="text-faint" style={{ padding: 22, textAlign: "center" }}>
            {window.L("Aucun quartier enregistré. Cliquez « Nouveau quartier » pour démarrer.", "No neighborhood. Click 'New neighborhood' to start.", "Ningún barrio registrado. Haga clic en «Nuevo barrio» para empezar.")}
          </div>
        ) : (
          <table className="tbl">
            <thead><tr>
              <th>{window.L("Nom", "Name", "Nombre")}</th>
              <th style={{ width: 60 }}></th>
            </tr></thead>
            <tbody>
              {rows.map((r) => (
                <tr key={r.id}>
                  <td className="strong">{r.name_fr}</td>
                  <td className="num"><button className="iconbtn" onClick={() => setEditing(r)}><Icon.edit /></button></td>
                </tr>
              ))}
            </tbody>
          </table>
        )}
      </div>
      {(creating || editing) && <QuartierModal lang={lang} row={editing} commId={commId} onClose={() => { setEditing(null); setCreating(false); }} onSaved={async () => { setEditing(null); setCreating(false); await refresh(); }} />}
    </div>
  );
}

// ============================================================================
// Modales · création / édition pour chaque niveau
// ============================================================================
function _genericModal(title, fields, onSave, onClose, row) {
  const Modal = window.Modal;
  const [state, setState] = React.useState(() => {
    const init = {};
    fields.forEach((f) => { init[f.key] = (row && row[f.key]) || ""; });
    return init;
  });
  const [busy, setBusy] = React.useState(false);
  const [err, setErr] = React.useState(null);
  const submit = async () => {
    setErr(null); setBusy(true);
    try { await onSave(state); }
    catch (e) { setErr(e.message); setBusy(false); }
  };
  return (
    <Modal title={title} onClose={busy ? null : onClose} size="sm"
      footer={<>
        <button className="btn sm" onClick={onClose} disabled={busy}>Annuler</button>
        <button className="btn sm primary" onClick={submit} disabled={busy}>{busy ? "…" : (row ? "Enregistrer" : "Créer")}</button>
      </>}>
      <div style={{ display: "grid", gap: 10 }}>
        {fields.map((f) => (
          <label key={f.key} style={{ display: "grid", gap: 4 }}>
            <span style={{ fontSize: 11, color: "var(--text-faint)", textTransform: "uppercase", letterSpacing: "0.04em" }}>{f.label}</span>
            <input style={_inp} value={state[f.key] || ""} onChange={(e) => setState((s) => ({ ...s, [f.key]: e.target.value }))} maxLength={f.maxLength || undefined} />
          </label>
        ))}
        {err && <div style={{ color: "#b91c1c", fontSize: 12 }}>{err}</div>}
      </div>
    </Modal>
  );
}

function CountryModal({ lang, row, onClose, onSaved }) {
  return _genericModal(
    lang === "fr" ? (row ? "Modifier le pays" : "Nouveau pays") : (row ? "Edit country" : "New country"),
    [
      { key: "iso2",    label: "ISO2",            maxLength: 2 },
      { key: "name_fr", label: window.L("Nom français", "French name", "Nombre francés") },
      { key: "name_en", label: window.L("Nom anglais", "English name", "Nombre inglés") },
      { key: "region",  label: window.L("Région ONU", "UN region", "Región ONU") },
    ],
    async (state) => {
      if (row) await window.melr.countriesCrud.update(row.iso2, state);
      else     await window.melr.countriesCrud.create({ ...state, iso2: (state.iso2 || "").toUpperCase() });
      await onSaved();
    },
    onClose, row
  );
}
function RegionModal({ lang, row, country, onClose, onSaved }) {
  return _genericModal(
    lang === "fr" ? (row ? "Modifier la région" : "Nouvelle région") : (row ? "Edit region" : "New region"),
    [
      { key: "code",    label: "Code" },
      { key: "name_fr", label: window.L("Nom (français)", "Name (French)", "Nombre (francés)") },
      { key: "name_en", label: window.L("Nom (anglais)", "Name (English)", "Nombre (inglés)") },
    ],
    async (state) => {
      if (row) await window.melr.geoRegionsCrud.update(row.id, state);
      else     await window.melr.geoRegionsCrud.create({ ...state, country_iso2: country });
      await onSaved();
    },
    onClose, row
  );
}
function DepartmentModal({ lang, row, regionId, onClose, onSaved }) {
  return _genericModal(
    lang === "fr" ? (row ? "Modifier le département" : "Nouveau département") : (row ? "Edit department" : "New department"),
    [
      { key: "code",    label: "Code" },
      { key: "name_fr", label: window.L("Nom (français)", "Name (French)", "Nombre (francés)") },
      { key: "name_en", label: window.L("Nom (anglais)", "Name (English)", "Nombre (inglés)") },
    ],
    async (state) => {
      if (row) await window.melr.geoDepartmentsCrud.update(row.id, state);
      else     await window.melr.geoDepartmentsCrud.create({ ...state, region_id: regionId });
      await onSaved();
    },
    onClose, row
  );
}
function ArrondissementModal({ lang, row, deptId, onClose, onSaved }) {
  return _genericModal(
    lang === "fr" ? (row ? "Modifier l'arrondissement" : "Nouvel arrondissement") : (row ? "Edit arrondissement" : "New arrondissement"),
    [
      { key: "name_fr", label: window.L("Nom (français)", "Name (French)", "Nombre (francés)") },
      { key: "name_en", label: window.L("Nom (anglais)", "Name (English)", "Nombre (inglés)") },
    ],
    async (state) => {
      if (row) await window.melr.geoArrondissementsCrud.update(row.id, state);
      else     await window.melr.geoArrondissementsCrud.create({ ...state, department_id: deptId });
      await onSaved();
    },
    onClose, row
  );
}
function CommuneModal({ lang, row, arrId, onClose, onSaved }) {
  return _genericModal(
    lang === "fr" ? (row ? "Modifier la commune" : "Nouvelle commune") : (row ? "Edit commune" : "New commune"),
    [
      { key: "name_fr",      label: window.L("Nom (français)", "Name (French)", "Nombre (francés)") },
      { key: "name_en",      label: window.L("Nom (anglais)", "Name (English)", "Nombre (inglés)") },
      { key: "type",         label: window.L("Type", "Type", "Tipo") },
      { key: "ville_parent", label: window.L("Ville parent (si commune d'arr.)", "Parent city (if commune d'arr.)", "Ciudad principal (si es municipio de distrito)") },
    ],
    async (state) => {
      if (row) await window.melr.geoCommunesCrud.update(row.id, state);
      else     await window.melr.geoCommunesCrud.create({ ...state, arrondissement_id: arrId });
      await onSaved();
    },
    onClose, row
  );
}
function QuartierModal({ lang, row, commId, onClose, onSaved }) {
  return _genericModal(
    lang === "fr" ? (row ? "Modifier le quartier" : "Nouveau quartier") : (row ? "Edit neighborhood" : "New neighborhood"),
    [
      { key: "name_fr", label: window.L("Nom (français)", "Name (French)", "Nombre (francés)") },
      { key: "name_en", label: window.L("Nom (anglais)", "Name (English)", "Nombre (inglés)") },
    ],
    async (state) => {
      if (row) await window.melr.geoQuartiersCrud.update(row.id, state);
      else     await window.melr.geoQuartiersCrud.create({ ...state, commune_id: commId });
      await onSaved();
    },
    onClose, row
  );
}

window.ProjectPlanning = ProjectPlanning;
