// procurement-forms.jsx — «Пакет документів» закупівлі (хаб форм PIN).
// Спільні дані (шапка, позиції, учасники, комітет) живлять усі форми; кожна
// форма експортується в .xlsx (SheetJS). Дані зберігаються у procurement.case
// (+ procurement.prf для FORM 10). Підхід: відтворення форм + експорт Excel.

(function () {
  const rnd = () => Math.random().toString(36).slice(2, 6);

  // канонічна процедура з тексту
  function procLabel(s) {
    s = (s || "").toLowerCase();
    if (s.includes("tender") || s.includes("тендер")) return "Відкритий тендер / Open tender";
    if (s.includes("negoti") || s.includes("перегов")) return "Переговорна / Negotiated";
    if (s.includes("simplif") || s.includes("спрощ")) return "Спрощена / Simplified";
    if (s.includes("simple") || s.includes("прост")) return "Проста / Simple purchase";
    return s || "";
  }
  function procKey(s) {
    s = (s || "").toLowerCase();
    if (s.includes("tender") || s.includes("тендер")) return "tender";
    if (s.includes("negoti") || s.includes("перегов")) return "negotiated";
    if (s.includes("simplif") || s.includes("спрощ")) return "simplified";
    if (s.includes("simple") || s.includes("прост")) return "simple";
    return "";
  }

  const blankCase = () => ({ eloFolder: "", location: "", bidders: [], committee: [] });

  // позиції закупівлі: беремо з PRF, інакше — одна позиція з рядка плану
  function itemsOf(row, project, planIndex) {
    if (row.prf && row.prf.items && row.prf.items.length) return row.prf.items;
    return [{ planLine: String(planIndex != null ? planIndex + 1 : ""), desc: row.title || "", unit: "", qty: "", projectCode: project.code || "", budgetLine: row.budgetLine || "" }];
  }

  // ── експорт через спільний рендерер ExcelJS (блоки) ──
  const X = () => window.ProcXlsx;
  const fileName = (project, code) => `${code}_${(project.code || "DOVIRA").replace(/[^\wА-Яа-яІЇЄґ.-]+/g, "_")}.xlsx`;
  const col = (header, width) => ({ header, width });
  function hdrFields(row, project, cs, n) {
    const X0 = X();
    const f = [
      X0.field("Contract title / Назва закупівлі", row.title || ""),
      X0.field("Project code / Код проєкту", project.code || ""),
      X0.field("Procurement ELO folder no. / № папки ELO", cs.eloFolder || ""),
      X0.field("Procedure / Процедура", procLabel(row.procedure)),
      X0.field("Location / Місцезнаходження", cs.location || ""),
    ];
    return n ? f.slice(0, n) : f;
  }

  // ════════ Білдери форм (блоки) ════════
  const BUILD = {
    f6(ctx) {
      const x = X(), { project, cs, items } = ctx;
      const cols = [col("S.No", 6), col("Description / Опис", 42), col("Unit / Од.", 12), col("Qty / К-сть", 10), col("Currency", 12), col("Unit price / Ціна", 14), col("Total / Сума", 14)];
      const rows = items.map((it, i) => [i + 1, it.desc, it.unit, it.qty, "USD", "", ""]);
      const blocks = [
        x.title("QUOTATION FORM / ФОРМА ЦІНОВОЇ ПРОПОЗИЦІЇ (Форма 6)"), x.gap(),
        x.field("PRF Number / № запиту", items[0] ? items[0].planLine : ""), x.gap(),
        x.section("SUPPLIER DETAILS / РЕКВІЗИТИ ПОСТАЧАЛЬНИКА"),
        x.field("Name / Назва", ""), x.field("Address / Адреса", ""), x.field("Owner / Власник", ""), x.field("Phone / Телефон", ""), x.field("E-mail", ""), x.gap(),
        x.table(cols, rows), x.gap(),
        x.section("SIGNATURE / ПІДПИС"),
        x.field("Place / Місце", ""), x.field("Date / Дата", ""), x.field("Full name & position / ПІБ і посада", ""),
      ];
      return { filename: fileName(project, "FORM6_Quotation"), sheet: "Quotation", blocks };
    },
    f7(ctx) {
      const x = X(), { row, project, cs, prf } = ctx;
      const crit = (prf && prf.criteria && prf.criteria.length) ? prf.criteria : [{ name: "Ціна / Price", weight: "" }, { name: "Якість / Quality", weight: "" }];
      const bidders = cs.bidders.length ? cs.bidders : [{ name: "<Учасник 1>" }, { name: "<Учасник 2>" }, { name: "<Учасник 3>" }];
      const cols = [col("Criteria / Критерій", 42), col("Weight / Вага", 12), ...bidders.map(b => col(b.name || "—", 18))];
      const rows = crit.map(c => [c.name, (c.weight ? c.weight + "%" : ""), ...bidders.map(() => "")]);
      rows.push(["TOTAL / РАЗОМ", "100%", ...bidders.map(() => "")]);
      rows.push(["Rank / Ранг", "", ...bidders.map(() => "")]);
      const blocks = [x.title("QUOTATION EVALUATION PROTOCOL / ПРОТОКОЛ ОЦІНКИ (Форма 7/13)"), x.gap(), ...hdrFields(row, project, cs), x.gap(), x.table(cols, rows)];
      return { filename: fileName(project, "FORM7_Evaluation"), sheet: "Evaluation", blocks };
    },
    f3(ctx) {
      const x = X(), { row, project, cs } = ctx;
      const bidders = cs.bidders.length ? cs.bidders : [{}, {}, {}];
      const cols = [col("No", 6), col("Bidder / Учасник", 36), col("Submission date / Дата", 16), col("Time / Час", 12), col("PIN signature", 20), col("Bidder signature", 20)];
      const rows = bidders.map((b, i) => [i + 1, b.name || "", "", "", "", ""]);
      const blocks = [x.title("TENDER DOCUMENTATION DELIVERY REPORT / ЗВІТ ПРО ПОДАННЯ (Форма 3)"), x.gap(), ...hdrFields(row, project, cs, 3), x.gap(), x.table(cols, rows)];
      return { filename: fileName(project, "FORM3_Delivery"), sheet: "Delivery", blocks };
    },
    f4(ctx) {
      const x = X(), { row, project, cs } = ctx;
      const bidders = cs.bidders.length ? cs.bidders : [{}, {}, {}];
      const cols = [col("No", 6), col("Bidder / Учасник", 36), col("Qualification (Pass/Fail) / Кваліфікація", 40), col("Meets all? / Відповідає всім?", 22)];
      const rows = bidders.map((b, i) => [i + 1, b.name || "", "", ""]);
      const blocks = [x.title("PROTOCOL OF OPENING ENVELOPES / ВІДКРИТТЯ КОНВЕРТІВ (Форма 4)"), x.gap(), ...hdrFields(row, project, cs), x.gap(), x.table(cols, rows)];
      return { filename: fileName(project, "FORM4_Opening"), sheet: "Opening", blocks };
    },
    f8(ctx) {
      const x = X(), { row, project, cs } = ctx;
      const bidders = cs.bidders.length ? cs.bidders : [{}, {}, {}];
      const cols = [col("No", 6), col("Bidder / Учасник", 32), col("E-mail / контакт", 24), col("Request date / Дата запиту", 16), col("Sending date / Дата надсилання", 16), col("PIN sign", 14), col("Bidder sign", 14)];
      const rows = bidders.map((b, i) => [i + 1, b.name || "", b.email || "", "", "", "", ""]);
      const blocks = [x.title("TENDER NOTICE / DOCUMENTATION DISTRIBUTION / РОЗПОВСЮДЖЕННЯ (Форма 8)"), x.gap(), ...hdrFields(row, project, cs, 3), x.gap(), x.table(cols, rows)];
      return { filename: fileName(project, "FORM8_Distribution"), sheet: "Distribution", blocks };
    },
    f12(ctx) {
      const x = X(), { project, cs, items } = ctx;
      const cols = [col("S.No", 6), col("Description / Опис", 40), col("Unit / Од.", 10), col("Qty / К-сть", 9), col("Budget no. / Бюджет", 16), col("Budget line / Лінія", 16), col("Currency", 10), col("Unit price / Ціна", 14)];
      const rows = items.map((it, i) => [i + 1, it.desc, it.unit, it.qty, it.projectCode, it.budgetLine, "USD", ""]);
      const blocks = [
        x.title("PURCHASE ORDER / ЗАМОВЛЕННЯ НА ЗАКУПІВЛЮ (Форма 12)"), x.gap(),
        x.field("Contract ELO number / № контракту ELO", cs.eloFolder || ""),
        x.field("Delivery address / Адреса постачання", cs.location || ""), x.gap(),
        x.section("SUPPLIER DETAILS / РЕКВІЗИТИ ПОСТАЧАЛЬНИКА"),
        x.field("Name / Назва", ""), x.field("Address / Адреса", ""), x.field("Phone / Телефон", ""), x.field("E-mail", ""), x.gap(),
        x.table(cols, rows), x.gap(), x.field("Total / Разом", ""),
      ];
      return { filename: fileName(project, "FORM12_PurchaseOrder"), sheet: "PO", blocks };
    },
    f17(ctx) {
      const x = X();
      const cols = [col("Score / Бал", 12), col("Benchmark / Опис (послуги/роботи)", 70)];
      const rows = [
        [5, "Відмінна відповідь без слабких місць, повне розуміння вимог"],
        [4, "Дуже добра відповідь, реальне розуміння вимог"],
        [3, "Задовільна відповідь, базове розуміння"],
        [2, "Відповідь із застереженнями — бракує повноти"],
        [1, "Серйозні застереження — суттєві прогалини"],
        [0, "Відповідь повністю не відповідає критерію"],
      ];
      const blocks = [x.title("QUALITY EVALUATION — SCORING GRID / СІТКА БАЛІВ (Форма 17)"), x.gap(), x.table(cols, rows)];
      return { filename: fileName(ctx.project, "FORM17_ScoringGrid"), sheet: "Grid", blocks };
    },
  };

  // реєстр форм: code, назва, тип, для яких процедур, білдер
  const FORMS = [
    { code: "10", name: "Запит на закупівлю (PRF)", kind: "editor", procs: ["simplified", "negotiated", "tender"] },
    { code: "6", name: "Форма цінової пропозиції", kind: "xlsx", b: "f6", procs: ["simplified", "negotiated"] },
    { code: "7/13", name: "Протокол оцінки пропозицій", kind: "xlsx", b: "f7", procs: ["simplified", "negotiated", "tender"] },
    { code: "16", name: "Таблиця оцінки з формулами", kind: "xlsx", b: "f7", procs: ["negotiated", "tender"] },
    { code: "17", name: "Сітка балів (критерії якості)", kind: "xlsx", b: "f17", procs: ["simplified", "negotiated", "tender"] },
    { code: "3", name: "Звіт про подання пропозицій", kind: "xlsx", b: "f3", procs: ["negotiated", "tender"] },
    { code: "4", name: "Протокол відкриття конвертів", kind: "xlsx", b: "f4", procs: ["negotiated", "tender"] },
    { code: "8", name: "Розповсюдження тендерної док.", kind: "xlsx", b: "f8", procs: ["tender"] },
    { code: "12", name: "Замовлення на закупівлю (PO)", kind: "xlsx", b: "f12", procs: ["simplified", "negotiated", "tender"] },
    { code: "15", name: "Призначення комітету оцінки", kind: "word", procs: ["negotiated", "tender"], note: "Word · якщо > €10 000" },
    { code: "1/11", name: "Оголошення тендеру", kind: "word", procs: ["negotiated", "tender"] },
    { code: "2", name: "Декларація відповідності", kind: "word", procs: ["negotiated", "tender"] },
    { code: "14", name: "Технічне завдання (ToR)", kind: "word", procs: ["negotiated", "tender"] },
    { code: "5", name: "Звіт про оцінку тендеру", kind: "word", procs: ["negotiated", "tender"] },
    { code: "9", name: "Повідомлення про результат", kind: "word", procs: ["negotiated", "tender"] },
    { code: "18", name: "Сітка зважених критеріїв", kind: "xlsx", b: "f17", procs: ["tender"] },
    { code: "19", name: "Специфікація для IT-закупівель", kind: "word", procs: ["tender"], note: "лише IT" },
  ];

  function FormsHub({ row, planIndex, project, role, onSave, onClose }) {
    const canEdit = role === "director"; // тільки директор (рішення: доступ лише директорці)
    const [cs, setCs] = React.useState(() => Object.assign(blankCase(), row.case || {}));
    const [openPrf, setOpenPrf] = React.useState(false);
    const pk = procKey(row.procedure);

    React.useEffect(() => {
      const onKey = (e) => { if (e.key === "Escape") { if (openPrf) setOpenPrf(false); else onClose(); } };
      window.addEventListener("keydown", onKey);
      return () => window.removeEventListener("keydown", onKey);
    }, [openPrf, onClose]);

    const saveCase = (next) => { setCs(next); onSave({ case: next }); };
    const addBidder = () => saveCase({ ...cs, bidders: [...cs.bidders, { id: "bd-" + rnd(), name: "", email: "" }] });
    const upBidder = (id, patch) => saveCase({ ...cs, bidders: cs.bidders.map(b => b.id === id ? { ...b, ...patch } : b) });
    const rmBidder = (id) => saveCase({ ...cs, bidders: cs.bidders.filter(b => b.id !== id) });
    const addMember = () => saveCase({ ...cs, committee: [...cs.committee, { id: "cm-" + rnd(), name: "", position: "" }] });
    const upMember = (id, patch) => saveCase({ ...cs, committee: cs.committee.map(m => m.id === id ? { ...m, ...patch } : m) });
    const rmMember = (id) => saveCase({ ...cs, committee: cs.committee.filter(m => m.id !== id) });

    const ctx = () => ({ row, project, planIndex, cs, prf: row.prf, items: itemsOf(row, project, planIndex) });
    const exportForm = (f) => { const r = BUILD[f.b](ctx()); window.ProcXlsx.save(r.filename, r.sheet, r.blocks); };

    if (openPrf && window.ProcurementPRF) {
      return <window.ProcurementPRF row={row} planIndex={planIndex} project={project} role={role}
        onSave={(prf) => { onSave({ prf }); setOpenPrf(false); }} onClose={() => setOpenPrf(false)} />;
    }

    const grouped = [
      { key: "simplified", label: "Спрощена процедура" },
      { key: "negotiated", label: "Переговорна процедура" },
      { key: "tender", label: "Відкритий тендер" },
    ];

    return (
      <div className="pc-overlay">
        <div className="pc-panel" style={{ maxWidth: 940 }}>
          <div className="pc-panel-head">
            <div>
              <div className="pc-panel-title">Пакет документів закупівлі</div>
              <div className="pc-panel-sub">{row.title} · {procLabel(row.procedure) || "процедура не задана"}</div>
            </div>
            <button className="drawer-close" onClick={onClose}><window.Icon.X /></button>
          </div>

          <div className="pc-panel-body">
            {/* спільні дані */}
            <div className="prf-grid">
              <label className="pc-lbl">№ папки ELO (Procurement ELO folder)
                <input className="cp-input" value={cs.eloFolder} onChange={e => saveCase({ ...cs, eloFolder: e.target.value })} disabled={!canEdit} />
              </label>
              <label className="pc-lbl">Місцезнаходження / адреса
                <input className="cp-input" value={cs.location} onChange={e => saveCase({ ...cs, location: e.target.value })} disabled={!canEdit} />
              </label>
            </div>

            {/* учасники + комітет */}
            <div className="fm-cols">
              <div>
                <div className="fm-sub">Учасники (бідери)</div>
                {cs.bidders.map(b => (
                  <div key={b.id} className="fm-row">
                    <input className="cp-input" placeholder="Назва / ПІБ" value={b.name} onChange={e => upBidder(b.id, { name: e.target.value })} disabled={!canEdit} />
                    <input className="cp-input" placeholder="e-mail" value={b.email} onChange={e => upBidder(b.id, { email: e.target.value })} disabled={!canEdit} />
                    {canEdit && <button className="prj-row-del" onClick={() => rmBidder(b.id)}><window.Icon.X /></button>}
                  </div>
                ))}
                {canEdit && <button className="btn btn-sm" onClick={addBidder}><window.Icon.Plus /> Учасник</button>}
              </div>
              <div>
                <div className="fm-sub">Комітет з оцінки</div>
                {cs.committee.map(m => (
                  <div key={m.id} className="fm-row">
                    <input className="cp-input" placeholder="ПІБ" value={m.name} onChange={e => upMember(m.id, { name: e.target.value })} disabled={!canEdit} />
                    <input className="cp-input" placeholder="Посада" value={m.position} onChange={e => upMember(m.id, { position: e.target.value })} disabled={!canEdit} />
                    {canEdit && <button className="prj-row-del" onClick={() => rmMember(m.id)}><window.Icon.X /></button>}
                  </div>
                ))}
                {canEdit && <button className="btn btn-sm" onClick={addMember}><window.Icon.Plus /> Член комітету</button>}
              </div>
            </div>

            {/* список форм за процедурою */}
            {grouped.map(g => {
              const list = FORMS.filter(f => f.procs.includes(g.key));
              const isActive = pk === g.key;
              return (
                <div key={g.key} className="fm-group">
                  <div className="fm-group-h">{g.label}{isActive && <span className="status-tag tone-blue" style={{ marginLeft: 8 }}>ваша процедура</span>}</div>
                  <div className="fm-forms">
                    {list.map(f => (
                      <div key={f.code} className="fm-form">
                        <span className="fm-code">FORM {f.code}</span>
                        <span className="fm-name">{f.name}{f.note && <span className="fm-note"> · {f.note}</span>}</span>
                        {f.kind === "editor" && <button className="proc-form-btn" onClick={() => setOpenPrf(true)}>Редагувати{row.prf ? " ✓" : ""}</button>}
                        {f.kind === "xlsx" && <button className="proc-form-btn" onClick={() => exportForm(f)}>Excel ↓</button>}
                        {f.kind === "word" && <span className="fm-soon">Word · готуємо</span>}
                      </div>
                    ))}
                  </div>
                </div>
              );
            })}
          </div>
        </div>
      </div>
    );
  }

  window.ProcurementFormsHub = FormsHub;
})();
